Flux techniques de la caisse v2

Flux d’initialisation

Démarrage de l’application

sequenceDiagram participant App as Application participant CS as CaisseService participant ES as EnvironmentService participant HW as HwProxyService participant POS as PointOfSaleApiService participant KN as KafkaNotifService App->>CS: start() CS->>ES: getEnvironment() ES-->>CS: FullEnvironment CS->>CS: envChange.emit() CS->>HW: isConnected? alt Hardware connecté CS->>CS: bootHostname() else Hardware non connecté CS->>HW: isConnectedChange.subscribe() HW-->>CS: connected = true CS->>CS: bootHostname() end CS->>HW: health.getHostname() HW-->>CS: hostname CS->>POS: getPosData(hostname, date) POS-->>CS: PosData CS->>POS: getById(sessionId) si session existe POS-->>CS: PosSession CS->>KN: registerNotif(territory) CS->>KN: registerNotif(company) CS->>KN: registerNotif(cinema) CS->>KN: registerNotif(pos) CS->>CS: Déterminer statut

Flux d’ouverture de session

Ouverture d’une nouvelle session

sequenceDiagram participant C as CaisseComponent participant M as PosOpenModalComponent participant CS as CaisseService participant HW as HwProxyService participant API as PointOfSaleApiService participant PS as PosSessionApiService C->>M: show(env, posData) M->>HW: escpos.openCashDrawer() HW-->>M: Résultat M-->>C: OpenSessionResult (cashDrawerAmount) C->>CS: openSession(cashDrawerAmount) CS->>CS: checkStatus(READY_OPEN) CS->>API: open({ posId, cashDrawerAmount }) API->>API: Création session + panier API-->>CS: { isSync: true, basket: PosBasket } CS->>PS: getById(basket.sessionId) PS-->>CS: PosSession CS->>CS: basket = posBasket CS->>CS: session = session CS->>CS: status.set(WORKING)

Reprise d’une session existante

sequenceDiagram participant C as CaisseComponent participant CS as CaisseService participant API as PointOfSaleApiService C->>CS: continueSession() CS->>CS: checkStatus(READY_CONTINUE) CS->>CS: cashDrawerAmount = session.openCash CS->>API: open({ posId, cashDrawerAmount }) API->>API: Récupération panier existant API-->>CS: { isSync: true, basket: PosBasket } CS->>CS: basket = posBasket CS->>CS: status.set(WORKING)

Flux d’ajout au panier

Ajout d’un produit

sequenceDiagram participant C as CaisseComponent participant BC as BasketComposerService participant PM as PosMathService participant API as PosBasketApiService C->>BC: addProduct(button) BC->>BC: Créer ligne produit BC->>PM: compute(basket) PM->>PM: computeBasketReal() PM->>PM: setLineProductAndPriceProduct() PM->>PM: Calculer prix HT PM->>PM: Calculer taxes PM->>PM: Calculer totaux PM-->>BC: Résultat (JSON Patch) BC->>BC: Appliquer patch BC->>BC: rebuild() (formatage affichage) BC->>BC: persist(basket, false) BC->>API: persist(params) API-->>BC: OperationResponseWithBasket BC->>BC: Mettre à jour displayBasket C->>C: Rafraîchir affichage

Ajout d’une séance

sequenceDiagram participant C as CaisseComponent participant BC as BasketComposerService participant PM as PosMathService participant CAS as CardApiService participant PAS as PrepaidApiService participant API as PosBasketApiService C->>BC: addShow(show) BC->>BC: Créer ligne séance BC->>PM: compute(basket) PM->>PM: computeBasketReal() PM->>PM: setLineProductAndPriceShow() PM->>PM: Calculer prix HT initial PM->>PM: Réduire avec prépayés PAS->>PAS: getById() pour chaque prépayé PM->>PM: Réduire avec cartes CAS->>CAS: getById() pour chaque carte PM->>PM: Calculer taxes PM->>PM: Calculer totaux PM-->>BC: Résultat (JSON Patch) BC->>BC: Appliquer patch BC->>BC: rebuild() BC->>BC: persist(basket, false) BC->>API: persist(params) API-->>BC: OperationResponseWithBasket BC->>BC: Mettre à jour displayBasket C->>C: Rafraîchir affichage

Flux de paiement

Paiement en espèce

sequenceDiagram participant C as CaisseComponent participant M as PayCashModalComponent participant HW as HwProxyService participant BC as BasketComposerService participant PM as PosMathService C->>M: show(totalRemaining, posData) M->>M: Calculer arrondi si XPF M->>HW: escpos.openCashDrawer() HW-->>M: Résultat M-->>C: CashPayResult C->>C: Créer PosBasketPaymentEntry C->>C: basket.payment.paymentDetails.push() C->>BC: basketUpdated() BC->>PM: compute(basket) PM->>PM: Recalculer avec paiement PM->>PM: Calculer totalPaid PM->>PM: Calculer changeReturned PM->>PM: Calculer totalRemaining PM-->>BC: Résultat BC->>BC: rebuild() BC->>BC: persist(basket, false) C->>C: Rafraîchir affichage

Paiement par carte (TPE)

sequenceDiagram participant C as CaisseComponent participant M as PayTpeModalComponent participant HW as HwProxyService participant BC as BasketComposerService C->>M: show(totalRemaining, posData, methods) M->>HW: Initier transaction TPE HW->>HW: Attendre insertion carte HW-->>M: Résultat transaction M-->>C: TpePayResult C->>C: Créer PosBasketPaymentEntry C->>C: basket.payment.paymentDetails.push() C->>BC: basketUpdated() BC->>BC: Recalculer panier C->>C: Rafraîchir affichage

Flux de finalisation

Finalisation du panier

sequenceDiagram participant C as CaisseComponent participant FB as FinalizeBasketService participant BC as BasketComposerService participant PM as PosMathService participant API as PosBasketApiService participant M as FinalizingModalComponent participant HW as HwProxyService C->>C: Vérifier totalPaid >= totalWithTaxReal C->>FB: finalize() FB->>BC: Vérifier beeperNumber si requis FB->>BC: computeBasket() (recalcul final) FB->>M: show() M-->>FB: ModalComponent FB->>API: persist(basket, finalize: true) API->>API: Validation API->>API: Enregistrement ES API->>API: Envoi Kafka (finalize.action) API-->>FB: OperationResponseWithBasket FB->>PM: getPrintables(session, user, basket) PM-->>FB: Printable[] (tickets HTML) FB->>FB: convertPrintablesToImages() FB->>M: print(images) M->>HW: escpos.print() HW-->>M: Résultat FB->>BC: replaceBasket(response.basket) FB->>FB: saleDoneSubject.next() FB-->>C: Résultat finalisation C->>C: Rafraîchir panier (nouveau panier vide)

Flux de fermeture de session

Fermeture de session

sequenceDiagram participant C as CaisseComponent participant M as PosCloseModalComponent participant CS as CaisseService participant API as PointOfSaleApiService participant PS as PosSessionApiService participant BC as BankDepositConfirmModalComponent C->>M: open(territory, company, cinema, posData) M->>PS: getById(sessionId) PS-->>M: PosSessionWithStats M->>M: Initialiser comptage caisse M->>M: Compter billets et pièces M->>M: Vérifier cohérence M->>API: close({ posId, cashCounts }) API->>API: Fermeture session API-->>M: Réponse M->>BC: show() BC-->>M: Confirmation (impression/téléchargement) alt Téléchargement M->>PS: getBankDepositSlip(sessionId) PS-->>M: PDF base64 M->>M: Télécharger PDF else Impression M->>PS: getBankDepositSlip(sessionId) PS-->>M: PDF base64 M->>M: Télécharger PDF M->>PS: printBankDepositSlip(sessionId) PS->>PS: Impression via hardware end M->>CS: quickStart() CS->>CS: Recharger données POS M->>M: Logout et redirection login

Flux de calcul du panier

Calcul complet du panier

sequenceDiagram participant BC as BasketComposerService participant PM as PosMathService participant CAS as CardApiService participant PAS as PrepaidApiService participant SS as SubscriptionApiService BC->>PM: compute(basket) PM->>PM: computeBasketReal(basket) loop Pour chaque ligne PM->>PM: setLineProductAndPrice() PM->>PM: Calculer prix HT initial end PM->>PM: Réduire prix avec prépayés loop Pour chaque prépayé PM->>PAS: getById(prepaidId) PAS-->>PM: Prepaid PM->>PM: Calculer réduction end PM->>PM: Réduire prix avec cartes loop Pour chaque carte PM->>CAS: getById(cardId) CAS-->>PM: Card PM->>SS: getById(subscriptionId) SS-->>PM: Subscription PM->>PM: Calculer réduction end PM->>PM: Réduire prix avec réductions employés PM->>PM: Calculer taxes pour chaque ligne PM->>PM: Calculer totaux HT/TTC PM->>PM: Calculer paiements et reste à payer PM-->>BC: Résultat (JSON Patch) BC->>BC: Appliquer patch BC->>BC: rebuild() (formatage affichage)

Flux de persistance

File d’attente de persistance

sequenceDiagram participant BC as BasketComposerService participant API as PosBasketApiService BC->>BC: persist(basket, finalize) BC->>BC: Vérifier isPreview BC->>BC: Vérifier statut panier BC->>BC: Ajouter à queue (remplacer précédent) alt Pas d'opération en cours BC->>BC: persisting.set(true) BC->>BC: Créer Promise persistProm loop Traitement queue BC->>BC: Prendre entrée de queue BC->>API: persist(params) API-->>BC: OperationResponseWithBasket alt Finalisation BC->>BC: Remplacer basket si ID différent end end BC->>BC: persisting.set(false) BC->>BC: persistProm = undefined else Opération en cours BC->>BC: Remplacer entrée dans queue end