Premiere commit - Omika
This commit is contained in:
@@ -0,0 +1,468 @@
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Text.Json;
|
||||
using Omika.App.Local.Abstractions;
|
||||
using Omika.App.Local.Models;
|
||||
using Omika.App.Navigation;
|
||||
using Omika.App.ViewModels;
|
||||
using Omika.Core.Contracts.Documents;
|
||||
using Omika.Core.Contracts.Mobile.Sync;
|
||||
|
||||
namespace Omika.Tests.Mobile.Local;
|
||||
|
||||
/// <summary>
|
||||
/// Tests UX du ViewModel « Nouveau courriel » : MÊME moteur de saisie que le
|
||||
/// Rapport (carrousel d'étapes interactives, UN/TAB en cartes, EXTRA, read-only
|
||||
/// hors parcours) + conservation du corps HTML jusqu'à l'aperçu.
|
||||
/// </summary>
|
||||
public class NouveauEmailViewModelTests
|
||||
{
|
||||
private static readonly JsonSerializerOptions Json = new(JsonSerializerDefaults.Web);
|
||||
|
||||
// =====================================================================
|
||||
// Helpers
|
||||
// =====================================================================
|
||||
|
||||
private static string ContactsJson(params (string Nom, string Role, string TelFixe)[] contacts)
|
||||
{
|
||||
var items = contacts.Select(c => new
|
||||
{
|
||||
id = Guid.NewGuid().ToString(),
|
||||
nom = c.Nom,
|
||||
role = c.Role,
|
||||
telFixe = c.TelFixe,
|
||||
telMobile = "06 00 00 00 00",
|
||||
etage = "1"
|
||||
});
|
||||
return JsonSerializer.Serialize(items, Json);
|
||||
}
|
||||
|
||||
private static string RdvJson(params (string dateDebut, string dateFin, string objet)[] rdvs)
|
||||
{
|
||||
var items = rdvs.Select(r => new
|
||||
{
|
||||
dateDebut = r.dateDebut,
|
||||
dateFin = r.dateFin,
|
||||
objet = r.objet,
|
||||
note = string.Empty,
|
||||
collaborateurs = "Jean Claude ROMERO"
|
||||
});
|
||||
return JsonSerializer.Serialize(items, Json);
|
||||
}
|
||||
|
||||
private static RapportChampDto Champ(
|
||||
string rubrique,
|
||||
string? groupeApp = null,
|
||||
string? membreMob = null,
|
||||
string? type = "ChpSimpleChaine",
|
||||
string? listeDonnesBD = null,
|
||||
string? listeDonnesChoix = null,
|
||||
bool modifiable = false,
|
||||
string? nom = null)
|
||||
=> new()
|
||||
{
|
||||
Id = "1",
|
||||
Nom = nom,
|
||||
Rubrique = rubrique,
|
||||
Type = type,
|
||||
GroupeApp = groupeApp,
|
||||
MembreMob = membreMob,
|
||||
ListeDonnesBD = listeDonnesBD,
|
||||
ListeDonnesChoix = listeDonnesChoix,
|
||||
Modifiable = modifiable
|
||||
};
|
||||
|
||||
private static RapportChampDto TableauChamp(
|
||||
string rubrique,
|
||||
string groupeApp,
|
||||
string listeDonnesBD,
|
||||
params RapportChampSousElementDto[] membres)
|
||||
=> new()
|
||||
{
|
||||
Id = "1",
|
||||
Nom = "Tableau",
|
||||
Rubrique = rubrique,
|
||||
Type = "Tableau",
|
||||
GroupeApp = groupeApp,
|
||||
ListeDonnesBD = listeDonnesBD,
|
||||
ListeMembre = membres
|
||||
};
|
||||
|
||||
private static RapportChampSousElementDto SousElement(string rubrique, string? membreMob)
|
||||
=> new() { Rubrique = rubrique, MembreMob = membreMob };
|
||||
|
||||
private static NouveauEmailViewModel CreerViewModel(
|
||||
FakeInterventionService intervention,
|
||||
FakeContactsService contacts,
|
||||
FakeDocumentService documents)
|
||||
=> new(intervention, contacts, documents, new NavigationService(), new FakeSyncEngine(), Omika.Core.Observability.NullTelemetryService.Instance);
|
||||
|
||||
// =====================================================================
|
||||
// TEST 1-9 : moteur de saisie identique au Rapport
|
||||
// =====================================================================
|
||||
|
||||
[Fact]
|
||||
public void Simple_ReadOnly_PasDansEtapes_ValeurConservee()
|
||||
{
|
||||
var nomClient = new RapportChampEdition(Champ("$NOMCLIENT$", "INTER", "IN_NomClient", listeDonnesBD: "Smartis"));
|
||||
var extra = new RapportChampEdition(Champ("$Saisie_Mob_1$", "EXTRA"));
|
||||
|
||||
var vm = CreerViewModel(new FakeInterventionService(), new FakeContactsService(), new FakeDocumentService());
|
||||
vm.Rubriques = new ObservableCollection<RapportRubriqueResume>(
|
||||
new[] { nomClient, extra }.Select(x => new RapportRubriqueResume(x)));
|
||||
|
||||
// « Nom du client » (Modifiable=0) ne fait PAS partie du parcours.
|
||||
Assert.DoesNotContain(vm.EtapesInteractives, e => e.Champ == nomClient);
|
||||
Assert.Same(extra, Assert.Single(vm.EtapesInteractives).Champ);
|
||||
|
||||
// …mais sa valeur reste disponible pour la génération ($NOMCLIENT$).
|
||||
Assert.Equal("Smartis", nomClient.ToDto().ListeDonnesMob);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void Simple_Modifiable_EstEtape()
|
||||
{
|
||||
var modifiable = new RapportChampEdition(Champ(
|
||||
"$REFINTERNE$", "INTER", "IN_RefInterne", listeDonnesBD: "REF", modifiable: true));
|
||||
|
||||
var vm = CreerViewModel(new FakeInterventionService(), new FakeContactsService(), new FakeDocumentService());
|
||||
vm.Rubriques = new ObservableCollection<RapportRubriqueResume>([new(modifiable)]);
|
||||
|
||||
Assert.Same(modifiable, Assert.Single(vm.EtapesInteractives).Champ);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void Extra_EstEtape()
|
||||
{
|
||||
var extra = new RapportChampEdition(Champ("$Saisie_Mob_1$", "EXTRA"));
|
||||
|
||||
var vm = CreerViewModel(new FakeInterventionService(), new FakeContactsService(), new FakeDocumentService());
|
||||
vm.Rubriques = new ObservableCollection<RapportRubriqueResume>([new(extra)]);
|
||||
|
||||
Assert.Same(extra, Assert.Single(vm.EtapesInteractives).Champ);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void UnRdv_TroisRubriques_UnSeulSelecteur()
|
||||
{
|
||||
string json = RdvJson(
|
||||
("2022-08-31 08:00:00", "2022-08-31 17:00:00", "Maintenance"),
|
||||
("2022-09-01 08:00:00", "2022-09-01 17:00:00", "Contrôle"),
|
||||
("2022-09-15 08:00:00", "2022-09-15 09:00:00", "Visite"));
|
||||
|
||||
IReadOnlyList<RapportChampDto> champs =
|
||||
[
|
||||
Champ("$UNRDV.DATEDEBUT$", "RDV_INTER", "dateDebut", listeDonnesChoix: json),
|
||||
Champ("$UNRDV.DATEDEBUT_D$", "RDV_INTER", "dateDebut_D", listeDonnesChoix: json),
|
||||
Champ("$UNRDV.DATEFIN$", "RDV_INTER", "dateFin", listeDonnesChoix: json)
|
||||
];
|
||||
|
||||
var intervention = new FakeInterventionService { Champs = champs };
|
||||
var vm = CreerViewModel(intervention, new FakeContactsService(), new FakeDocumentService());
|
||||
vm.InterventionGuid = Guid.NewGuid();
|
||||
vm.ModeleSelectionne = new ModeleMailDto { Id = "1", Nom = "Modèle" };
|
||||
|
||||
// Les trois rubriques $UNRDV.* sont regroupées en UNE FAMILLE : un seul
|
||||
// sélecteur (une seule entrée dans Rubriques, une seule étape interactive).
|
||||
RapportRubriqueResume resume = Assert.Single(vm.Rubriques);
|
||||
Assert.Equal(3, resume.Champ.MembresFamille.Count);
|
||||
Assert.Single(vm.EtapesInteractives);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void TabContact_MultiSelection_Cartes()
|
||||
{
|
||||
string json = ContactsJson(
|
||||
("Jean Dupont", "Occupant", "04 11 22 33 44"),
|
||||
("Marie Martin", "Responsable", "04 55 66 77 88"));
|
||||
|
||||
var edition = new RapportChampEdition(TableauChamp(
|
||||
"$TABCONTACTSITE$", "CONTACT_SITE", json,
|
||||
SousElement("$TABCTSITE.NOMPRENOM$", "saNom")));
|
||||
|
||||
Assert.True(edition.EstChoixMultiple);
|
||||
Assert.Equal(2, edition.Options.Count);
|
||||
|
||||
edition.BasculerOptionCommand.Execute(edition.Options[0]);
|
||||
edition.BasculerOptionCommand.Execute(edition.Options[1]);
|
||||
Assert.Equal(2, edition.NombreSelectionnes);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void UnContact_SingleSelection_Cartes()
|
||||
{
|
||||
string json = ContactsJson(
|
||||
("Jean Dupont", "Occupant", "04 11 22 33 44"),
|
||||
("Marie Martin", "Responsable", "04 55 66 77 88"));
|
||||
|
||||
var edition = new RapportChampEdition(Champ(
|
||||
"$UNCTSITE.NOMPRENOM$", "CONTACT_SITE", "saNom",
|
||||
listeDonnesBD: "Jean Dupont", listeDonnesChoix: json));
|
||||
|
||||
Assert.True(edition.EstSelectionUnique);
|
||||
Assert.Equal(1, edition.NombreSelectionnes);
|
||||
|
||||
// Clic sur une autre carte : l'ancienne sélection se replie, une seule cochée.
|
||||
edition.BasculerOptionCommand.Execute(edition.Options[1]);
|
||||
Assert.Equal(1, edition.NombreSelectionnes);
|
||||
Assert.True(edition.Options[1].EstSelectionne);
|
||||
Assert.False(edition.Options[0].EstSelectionne);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void Modele100ReadOnly_ApercuDirect()
|
||||
{
|
||||
var a = new RapportChampEdition(Champ("$NOM$", "INTER", "IN_RefInterne", listeDonnesBD: "Nom"));
|
||||
var b = new RapportChampEdition(Champ("$ADRESSE$", "INTER", "IN_RefInterne", listeDonnesBD: "Adresse"));
|
||||
|
||||
var vm = CreerViewModel(new FakeInterventionService(), new FakeContactsService(), new FakeDocumentService());
|
||||
vm.Rubriques = new ObservableCollection<RapportRubriqueResume>(
|
||||
new[] { a, b }.Select(x => new RapportRubriqueResume(x)));
|
||||
|
||||
Assert.Empty(vm.EtapesInteractives);
|
||||
Assert.True(vm.AucuneEtapeInteractive);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void Navigation_Carrousel_SauteLesReadOnly()
|
||||
{
|
||||
var a = new RapportChampEdition(Champ("$A$", "INTER", "IN_RefInterne", listeDonnesBD: "A"));
|
||||
var b = new RapportChampEdition(Champ("$B$", "EXTRA"));
|
||||
var c = new RapportChampEdition(Champ("$C$", "INTER", "IN_RefInterne", listeDonnesBD: "C"));
|
||||
var d = new RapportChampEdition(Champ("$D$", "EXTRA"));
|
||||
|
||||
var vm = CreerViewModel(new FakeInterventionService(), new FakeContactsService(), new FakeDocumentService());
|
||||
vm.Rubriques = new ObservableCollection<RapportRubriqueResume>(
|
||||
new[] { a, b, c, d }.Select(x => new RapportRubriqueResume(x)));
|
||||
|
||||
// Ouvre la première étape interactive (B, la A read-only est sautée).
|
||||
vm.OuvrirRubriqueCommand.Execute(vm.EtapesInteractives[0]);
|
||||
Assert.Same(b, vm.RubriqueSelectionnee);
|
||||
|
||||
// Suivant → D (saute C read-only).
|
||||
vm.RubriqueSuivanteCommand.Execute(null);
|
||||
Assert.Same(d, vm.RubriqueSelectionnee);
|
||||
|
||||
// Précédent → B.
|
||||
vm.RubriquePrecedenteCommand.Execute(null);
|
||||
Assert.Same(b, vm.RubriqueSelectionnee);
|
||||
|
||||
// Retour à la liste des rubriques.
|
||||
vm.RetourRubriquesCommand.Execute(null);
|
||||
Assert.False(vm.AfficheDetail);
|
||||
Assert.True(vm.AfficheListe);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public async Task Continuer_PayloadContientTousLesChamps()
|
||||
{
|
||||
var nomClient = Champ("$NOMCLIENT$", "INTER", "IN_NomClient", listeDonnesBD: "Smartis");
|
||||
var extra = Champ("$Saisie_Mob_1$", "EXTRA");
|
||||
var intervention = new FakeInterventionService
|
||||
{
|
||||
Champs = [nomClient, extra],
|
||||
Apercu = new EmailModeleApercuDto { Sujet = "Rapport intervention 42", Corps = "<p>Bonjour Smartis</p>" }
|
||||
};
|
||||
|
||||
var vm = CreerViewModel(intervention, new FakeContactsService(), new FakeDocumentService());
|
||||
vm.InterventionGuid = Guid.NewGuid();
|
||||
vm.ModeleSelectionne = new ModeleMailDto { Id = "1", Nom = "Modèle" };
|
||||
|
||||
await vm.ContinuerCommand.ExecuteAsync(null);
|
||||
|
||||
// Le payload envoyé au serveur contient TOUS les champs (read-only inclus).
|
||||
Assert.NotNull(intervention.LastApercuRequest);
|
||||
Assert.Equal(2, intervention.LastApercuRequest!.ListeMob.Count);
|
||||
Assert.Contains(intervention.LastApercuRequest.ListeMob, c => c.Rubrique == "$NOMCLIENT$" && c.ListeDonnesMob == "Smartis");
|
||||
Assert.Equal(2, vm.Etape);
|
||||
}
|
||||
|
||||
// =====================================================================
|
||||
// TEST HTML 1-5 : conservation du corps HTML
|
||||
// =====================================================================
|
||||
|
||||
[Fact]
|
||||
public void Html_CorpsHtml_ConserveIntegralementDansViewModel()
|
||||
{
|
||||
var vm = CreerViewModel(new FakeInterventionService(), new FakeContactsService(), new FakeDocumentService());
|
||||
|
||||
vm.Corps = "<p>Bonjour</p>";
|
||||
|
||||
Assert.Equal("<p>Bonjour</p>", vm.Corps);
|
||||
Assert.True(vm.CorpsContientHtml);
|
||||
Assert.Equal("Bonjour", vm.CorpsApercuTexte);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void Html_Tableau_NonConvertiEnTexteSepareParPipes()
|
||||
{
|
||||
var vm = CreerViewModel(new FakeInterventionService(), new FakeContactsService(), new FakeDocumentService());
|
||||
|
||||
string html = "<table><tr><td>Moreau Valérie</td><td>04 13 95 46 73</td></tr></table>";
|
||||
vm.Corps = html;
|
||||
|
||||
// La SOURCE reste le HTML intégral : jamais « Moreau Valérie | … ».
|
||||
Assert.Equal(html, vm.Corps);
|
||||
// L'aperçu visuel contient bien la valeur, séparée par des espaces (pas des pipes).
|
||||
Assert.Contains("Moreau Valérie", vm.CorpsApercuTexte);
|
||||
Assert.DoesNotContain("<table>", vm.CorpsApercuTexte);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void Html_AucunDecodeSurLaSource()
|
||||
{
|
||||
var vm = CreerViewModel(new FakeInterventionService(), new FakeContactsService(), new FakeDocumentService());
|
||||
|
||||
vm.Corps = "<p>R&D & Cie</p>";
|
||||
|
||||
// La source conserve les entités HTML (aucun HtmlDecode / StripTags).
|
||||
Assert.Equal("<p>R&D & Cie</p>", vm.Corps);
|
||||
// Seul l'aperçu visuel décode.
|
||||
Assert.Equal("R&D & Cie", vm.CorpsApercuTexte);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void Html_SujetResteTexteSimple()
|
||||
{
|
||||
var vm = CreerViewModel(new FakeInterventionService(), new FakeContactsService(), new FakeDocumentService());
|
||||
|
||||
vm.Sujet = "Rapport intervention 391244";
|
||||
|
||||
// Le sujet est un string : aucun contrôle HTML, aucun rendu (seul le Corps l'est).
|
||||
Assert.Equal("Rapport intervention 391244", vm.Sujet);
|
||||
Assert.False(vm.CorpsContientHtml);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public async Task Html_Continuer_ConserveLeHtmlDuServeur()
|
||||
{
|
||||
var intervention = new FakeInterventionService
|
||||
{
|
||||
Champs = [Champ("$NOMCLIENT$", "INTER", "IN_NomClient", listeDonnesBD: "DigiNova")],
|
||||
Apercu = new EmailModeleApercuDto
|
||||
{
|
||||
Sujet = "Rapport intervention 391244",
|
||||
Corps = "<p>Bonjour DigiNova</p><table><tr><td>Moreau Valérie</td></tr></table>"
|
||||
}
|
||||
};
|
||||
|
||||
var vm = CreerViewModel(intervention, new FakeContactsService(), new FakeDocumentService());
|
||||
vm.InterventionGuid = Guid.NewGuid();
|
||||
vm.ModeleSelectionne = new ModeleMailDto { Id = "1", Nom = "Modèle" };
|
||||
|
||||
await vm.ContinuerCommand.ExecuteAsync(null);
|
||||
|
||||
// Sujet = texte ; Corps = HTML intégral (même moteur aperçu/création côté serveur).
|
||||
Assert.Equal("Rapport intervention 391244", vm.Sujet);
|
||||
Assert.Equal("<p>Bonjour DigiNova</p><table><tr><td>Moreau Valérie</td></tr></table>", vm.Corps);
|
||||
Assert.True(vm.CorpsContientHtml);
|
||||
Assert.Contains("Moreau Valérie", vm.CorpsApercuTexte);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public async Task Enregistrer_EnvoieCorpsHtml_PasTexteAplati()
|
||||
{
|
||||
var intervention = new FakeInterventionService();
|
||||
var vm = CreerViewModel(intervention, new FakeContactsService(), new FakeDocumentService());
|
||||
vm.InterventionGuid = Guid.NewGuid();
|
||||
vm.Sujet = "Rapport";
|
||||
vm.Corps = "<p>Bonjour</p><table><tr><td>30/01/2026</td></tr></table>";
|
||||
|
||||
await vm.EnregistrerCommand.ExecuteAsync(null);
|
||||
|
||||
// La source envoyée est le HTML intégral (Corps), jamais l'aperçu texte aplati.
|
||||
Assert.NotNull(intervention.LastEmailRequest);
|
||||
Assert.Equal(vm.Corps, intervention.LastEmailRequest!.Message);
|
||||
Assert.NotEqual(vm.CorpsApercuTexte, intervention.LastEmailRequest!.Message);
|
||||
}
|
||||
|
||||
// =====================================================================
|
||||
// Fakes
|
||||
// =====================================================================
|
||||
|
||||
private sealed class FakeInterventionService : IInterventionLocalService
|
||||
{
|
||||
public IReadOnlyList<RapportChampDto> Champs { get; set; } = [];
|
||||
public EmailModeleApercuDto? Apercu { get; set; }
|
||||
public CreateEmailModeleRequest? LastApercuRequest { get; private set; }
|
||||
|
||||
public Task<IReadOnlyList<RapportChampDto>> GetMailChampsAsync(
|
||||
GetRapportChampsRequest request, CancellationToken ct = default) => Task.FromResult(Champs);
|
||||
|
||||
public Task<EmailModeleApercuDto?> GetEmailModeleApercuAsync(
|
||||
CreateEmailModeleRequest request, CancellationToken ct = default)
|
||||
{
|
||||
LastApercuRequest = request;
|
||||
return Task.FromResult(Apercu);
|
||||
}
|
||||
|
||||
public Task<IReadOnlyList<SmtpConfigurationDto>> GetSmtpConfigurationsAsync(
|
||||
CancellationToken ct = default) => Task.FromResult<IReadOnlyList<SmtpConfigurationDto>>([]);
|
||||
|
||||
public CreateEmailInterventionRequest? LastEmailRequest { get; private set; }
|
||||
|
||||
public Task<EmailInterventionDto> AddEmailAsync(
|
||||
Guid interventionGuid, CreateEmailInterventionRequest request, CancellationToken ct = default)
|
||||
{
|
||||
LastEmailRequest = request;
|
||||
return Task.FromResult(new EmailInterventionDto { Id = Guid.NewGuid().ToString() });
|
||||
}
|
||||
|
||||
// Membres abstraits non utilisés par ces tests.
|
||||
public Task<Guid> CreateAsync(InterventionSyncPayload payload, CancellationToken ct = default)
|
||||
=> throw new NotImplementedException();
|
||||
public Task<Guid> UpdateAsync(Guid interventionGuid, InterventionSyncPayload payload, CancellationToken ct = default)
|
||||
=> throw new NotImplementedException();
|
||||
public Task<Guid> ArchiveAsync(Guid interventionGuid, CancellationToken ct = default)
|
||||
=> throw new NotImplementedException();
|
||||
public Task<InterventionDetail?> GetInterventionByIdAsync(Guid interventionGuid, CancellationToken ct = default)
|
||||
=> Task.FromResult<InterventionDetail?>(null);
|
||||
public Task<IReadOnlyList<InterventionListItem>> GetInterventionsAsync(CancellationToken ct = default)
|
||||
=> Task.FromResult<IReadOnlyList<InterventionListItem>>([]);
|
||||
}
|
||||
|
||||
private sealed class FakeContactsService : IInterventionContactsService
|
||||
{
|
||||
public Task<IReadOnlyList<InterventionContact>> GetContactsForInterventionAsync(
|
||||
Guid interventionGuid, CancellationToken ct = default) => Task.FromResult<IReadOnlyList<InterventionContact>>([]);
|
||||
|
||||
public Task<InterventionContact?> GetContactByIdAsync(
|
||||
Guid contactGuid, CancellationToken ct = default) => Task.FromResult<InterventionContact?>(null);
|
||||
|
||||
public Task<IReadOnlyList<InterventionContact>> GetContactsDisponiblesAsync(
|
||||
Guid interventionGuid, CancellationToken ct = default) => Task.FromResult<IReadOnlyList<InterventionContact>>([]);
|
||||
}
|
||||
|
||||
private sealed class FakeDocumentService : IDocumentLocalService
|
||||
{
|
||||
public Task<IReadOnlyList<InterventionDocumentItem>> GetDocumentsForInterventionAsync(
|
||||
Guid interventionGuid, CancellationToken ct = default) => Task.FromResult<IReadOnlyList<InterventionDocumentItem>>([]);
|
||||
|
||||
public Task<bool> EnsureDownloadedAsync(Guid documentGuid, CancellationToken ct = default) => Task.FromResult(true);
|
||||
public Task<bool> OpenAsync(Guid documentGuid, CancellationToken ct = default) => Task.FromResult(true);
|
||||
public Task<string?> GetCachedFilePathAsync(Guid documentGuid, CancellationToken ct = default) => Task.FromResult<string?>(null);
|
||||
public Task<IReadOnlyList<DocumentNoteItem>> GetNotesForDocumentAsync(Guid documentGuid, CancellationToken ct = default)
|
||||
=> Task.FromResult<IReadOnlyList<DocumentNoteItem>>([]);
|
||||
public Task<DocumentNoteItem> AddNoteAsync(Guid documentGuid, string contenu, CancellationToken ct = default)
|
||||
=> Task.FromResult(new DocumentNoteItem());
|
||||
public Task<InterventionDocumentItem?> AddPhotoAsync(Guid interventionGuid, CancellationToken ct = default)
|
||||
=> Task.FromResult<InterventionDocumentItem?>(null);
|
||||
public Task<AddPhotosResult> AddPhotosAsync(Guid interventionGuid, CancellationToken ct = default)
|
||||
=> Task.FromResult(new AddPhotosResult());
|
||||
public Task<InterventionDocumentItem?> AddPhotoFromCameraAsync(Guid interventionGuid, CancellationToken ct = default)
|
||||
=> Task.FromResult<InterventionDocumentItem?>(null);
|
||||
public Task<InterventionDocumentItem?> AddDocumentAsync(Guid interventionGuid, CancellationToken ct = default)
|
||||
=> Task.FromResult<InterventionDocumentItem?>(null);
|
||||
public Task<InterventionDocumentItem?> AddAnnotatedPhotoAsync(
|
||||
Guid interventionGuid, Guid sourceDocumentGuid, byte[] pngBytes, string fileName, CancellationToken ct = default)
|
||||
=> Task.FromResult<InterventionDocumentItem?>(null);
|
||||
}
|
||||
|
||||
private sealed class FakeSyncEngine : ISyncEngine
|
||||
{
|
||||
public Task<SyncCycleResult> SyncAsync(CancellationToken cancellationToken = default)
|
||||
=> Task.FromResult(new SyncCycleResult());
|
||||
|
||||
public Task<SyncCycleResult> PushAsync(CancellationToken cancellationToken = default)
|
||||
=> Task.FromResult(new SyncCycleResult());
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user