PRE-3552: Add UHF refund - #318
Merged
Merged
Conversation
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Description
Cette PR ajoute le remboursement pour les paiements Hosted Fields (UHF) côté back-office Sylius, avec confirmation asynchrone via webhook, et inclut l'adaptation nécessaire suite à la fusion de
payplug/unified-plugin-core's PRE-3589 surdevelop(qui embarque aussi le refactoring PRE-3590 "HF aliasing").Remboursement (synchrone + partiel/total) :
RefundPaymentProcessorroute les paiements Hosted Fields vers UPC'screateRefund()via un nouvel adaptateurUpc/UnifiedApiRefundCreator(implémentantRefundCreatorInterface), au lieu du SDK legacyorderIddu remboursement (numéro de commande, ou l'id du paiement à défaut) et lesubmerchantExternalId/accountId(compte/sous-marchand) sont résolus depuis la config du payment method spécifique au paiement remboursé (Upc/PaymentReferenceHelper::resolveGatewayCredentials()), avec un garde-fou local (LogicException) si l'un des deux n'est pas configuré — évite un aller-retour réseau pour un 400 dont le message ne remonte pas, et évite qu'un remboursement soit routé vers le mauvais compte si le marchand a plusieurs payment methods Hosted Fields configurésprocessHostedFields()) enregistre désormais aussi l'id d'opération du remboursement dansPayment::details['refunds']— nécessaire pour que le webhook de confirmation puisse retrouver le paiementmontant d'origine - somme des remboursements déjà confirmés), pas le montant total d'origine —UnifiedApiPaymentService::createRefund()rembourse le solde restant quand$amountest omis, pas le totalILock, clé = id du paiement) : les deux méthodes se bloquent mutuellement en cas de déclenchement concurrent, faute d'idempotency key côté API UPC pour ce fluxNotification webhook du remboursement :
HostedFieldsWebhookNotificationHandlerdistingue maintenant une confirmation de remboursement (via les ids qu'on a nous-mêmes enregistrés dansPayment::details['refunds']) d'une notification de paiement classique, et appliquePaymentOutcome::REFUNDEDau lieu dePAID— sans ce fix, une confirmation de remboursement aurait été mal interprétéeexecCodeindique un échec n'est jamais forcée enREFUNDED(l'argent n'a pas bougé) ni transmise telle quelle à la state machine du paiement (FAILEDy signifie "ce paiement a échoué", pas "ce remboursement a échoué") — seuls le log et le suivi d'idempotence sont appliqués ; l'entrée correspondante dansPayment::details['refunds']est marquéefailed => truepour ne plus compter dans un calcul de solde restant ultérieurAdaptation à PRE-3590 (UPC) :
payplug/unified-plugin-corepointe sur^1.1.0(version taguée incluant PRE-3589, publiée depuis) au lieu dedev-developUnifiedApiHostedPaymentServicea été supprimée par PRE-3590 (fusionnée dansUnifiedApiPaymentService::createPayment()) etHostedPaymentOutputrenommée enPaymentOutput—Upc/UnifiedApiHostedPaymentCreator,Upc/HostedPaymentCreatorInterface, etCaptureHostedPaymentRequestHandleradaptés en conséquenceHostedFieldDtoa un nouveau paramètre (recurringMode, pour l'aliasing PRE-3590) inséré avantbrowser/customerdans son constructeur — la construction dansCaptureHostedPaymentRequestHandlerest passée en arguments nommés pour éviter ce type de désalignement silencieux à l'avenirNettoyage : extraction d'un helper partagé
Upc/PaymentReferenceHelper(resolveOrderId(),idToString(),resolveGatewayCredentials()), qui remplace les copies précédemment dupliquées dansRefundPaymentProcessor,HostedFieldsWebhookNotificationHandler,CaptureHostedPaymentRequestHandleretUnifiedApiRefundCreator.Related Issue
Ticket: PRE-3552
Type of Change
✅ Quality Checklist
Local Environment & Hooks
make install).(PRE|SMP)-XXXX: descriptionpattern.(feature|fix|hotfix|refactor)/(PRE|SMP)-XXXX...or(release|patch)/x.y.z.Testing & Code Quality
plugin-dockerized-sylius).src/ortests/— n/a pour ce repo (cible PHP ^8.2), etpayplug/unified-plugin-coreest maintenant consommé via une version taguée stable plutôt qu'une branche de dev.CI/CD Deployment Context
compatibilitymatrix (PHP 7.1 / 7.4 / 8.0 / 8.1 / 8.2) and thequalityjob.Notes for Reviewer
resolveGatewayCredentials/resolveOrderId/idToString) désormais centralisée dansUpc/PaymentReferenceHelper. Le seul point non retenu (dispatchisHostedFields()répété) a été jugé peu pertinent : le traitDelegatesToHostedFieldsCommandProviderTraitexistant est conçu pour un autre usage (délégation entre command providers) et ne s'applique pas tel quel ici.payplug/unified-plugin-corepointe maintenant sur^1.1.0(version stable taguée) — plus besoin de suivredev-develop.plugin-dockerized-sylius:debug:autowiring/debug:container/cache:clearconfirment que le nouveau paramètreILockdeRefundPaymentProcessorse résout sans ambiguïté.CaptureHostedPaymentRequestHandler::buildHostedFieldDto()pour le changement d'arguments nommés — comportement identique, juste plus sûr face à un futur changement de signature deHostedFieldDto.