3.6 KiB
3.6 KiB
Architecture — ARGOS (GMAO)
Nom de marque : ARGOS. "GMAO" reste utilisé comme terme générique (Gestion de Maintenance Assistée par Ordinateur) dans le code/les noms de dossiers existants — pas de renommage du repo.
Projets
- App.Core (
net8.0, zéro dépendance EF/WinUI/ASP.NET) : entités du domaine, interfaces de repository, services métier purs (licence, planification préventive, KPI), DTOs de synchronisation. Dépend uniquement deBouncyCastle.Cryptography(Ed25519, .NET n'a pas de support natif). - App.Infrastructure : EF Core (SQLite), implémentations des repositories, WMI (hardware id), DPAPI (état d'essai), QuestPDF, stockage des pièces jointes.
- App.UI : WinUI 3, MVVM (CommunityToolkit.Mvvm), packaging MSIX.
- App.SyncServer : API HTTP locale (ASP.NET Core Minimal API) + découverte mDNS pour la future app Android.
- LicenseGenerator : console séparée, reste sur le poste de développement, jamais packagée dans le client.
- tests/App.Core.Tests : xUnit, couvre licence / calcul d'échéances / KPI (logique pure, sans I/O).
Décisions structurantes
- Rôles utilisateurs : enum
UserRolesurUser, pas de tableRolesséparée (3 rôles fixes en V1). - Pièces jointes : table unique
Attachmentavec clé polymorphe (EntityType+EntityId), pas de FK SQLite dessus — intégrité gérée parIAttachmentRepository. - Paramètres globaux : table clé-valeur
AppSetting, typée côtéApp.CoreviaISettingsProvider. - Licence & essai : stockés hors SQLite (fichier
.licsigné + état DPAPI séparé) pour qu'un reset de la base ne réinitialise jamais l'essai.LicenseActivationCacheen base n'est qu'un cache d'affichage, jamais une source d'autorité. - Repositories : interface générique
IRepository<TEntity, TKey>(CRUD minimal) + interfaces spécifiques par entité pour les requêtes métier (recherche, filtres, dédoublonnage d'occurrence). - Unité de travail :
IUnitOfWork.SaveChangesAsync()— les repositories modifient le graphe en mémoire, la persistance est commitée explicitement par le service appelant (MaintenanceSchedulingEngine,WorkOrderCompletionService, etc.). - Ed25519 :
BouncyCastle.Cryptography(managé pur), pas NSec/libsodium (dépendance native incompatible avec la contrainte "pas de DLL native à embarquer dans le MSIX"). - Moteur de planification préventive : ne calcule jamais qu'UNE seule prochaine occurrence par gamme (
FrequencyCalculator.ComputeNextDueDate), à partir de la dernière exécution réelle. La génération d'OT est dédupliquée par un index unique(MaintenancePlanId, GeneratedForOccurrenceKey)côté base, pas par une logique applicative fragile.
Points ouverts / à trancher au fil de l'implémentation
- Hébergement d'App.SyncServer : en cours d'exécution intégrée au process App.UI (un
WebApplication/Kestrel démarré en tâche de fond dans l'app WinUI, partageant le mêmeDbContext) plutôt qu'un.exeséparé à lancer/superviser — à confirmer à l'étape 3i. - Clé publique Ed25519 :
Ed25519PublicKeyProvidercontient des fragments placeholder (zéros) qui lèvent une exception explicite tant que la vraie paire de clés n'a pas été générée parLicenseGenerator.
Environnement de build
- SDK .NET 8 + Visual Studio 2022 Community (workloads
.NET Desktop Development+Windows application development) installés via winget sur ce poste. - Aucune build/test n'a encore été exécutée au moment de la rédaction de ce document — à faire dès l'installation terminée, avant d'ajouter du code supplémentaire.