Formulaire public : paiement de la cotisation via l'API SumUp (remplace Yapla)
ci-cd / build-backend (push) Failing after 4m12s
ci-cd / build-frontend (push) Skipped
ci-cd / deploy (push) Skipped

Remplace le simple lien Yapla statique par une vraie intégration API SumUp :
checkout hébergé créé à la soumission du formulaire, statut de paiement
(PENDING/PAID/FAILED/EXPIRED) tenu à jour par un webhook SumUp et visible sur
la fiche du bénévole. La cotisation n'est plus un montant unique : la
coordination configure autant de types de paiement qu'elle veut (libellé +
montant, ex. « Cotisation classique », « Mécénat »), et le bénévole en
choisit un à l'inscription — le libellé et le montant choisis sont figés sur
le bénévole, indépendamment d'une modification ultérieure de la config.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
AdamThomas
2026-09-29 19:56:04 +02:00
co-authored by Claude Sonnet 5
parent 0be5daa89c
commit 0bd38a6465
25 changed files with 1457 additions and 125 deletions
+40
View File
@@ -24,6 +24,8 @@ import type {
DayPartUpdate,
EditionUpdate,
FormFieldsSet,
FormPaymentOptionCreate,
FormPaymentOptionUpdate,
FormTemplateUpdate,
ImportMapping,
PlanningNotificationRequest,
@@ -633,6 +635,44 @@ export function useUploadFormLogo() {
});
}
/** Types de paiement de la cotisation (COORDINATION) — voir `FormPaymentOptionRead`. */
export function useFormPaymentOptions() {
return useQuery({
queryKey: ['formPaymentOptions', edition],
queryFn: () => api.forms.paymentOptions.list(edition),
});
}
function useInvalidateFormPaymentOptions() {
const client = useQueryClient();
return () => client.invalidateQueries({ queryKey: ['formPaymentOptions', edition] });
}
export function useCreateFormPaymentOption() {
const invalidate = useInvalidateFormPaymentOptions();
return useMutation({
mutationFn: (body: FormPaymentOptionCreate) => api.forms.paymentOptions.create(edition, body),
onSuccess: invalidate,
});
}
export function useUpdateFormPaymentOption() {
const invalidate = useInvalidateFormPaymentOptions();
return useMutation({
mutationFn: ({ id, body }: { id: string; body: FormPaymentOptionUpdate }) =>
api.forms.paymentOptions.update(edition, id, body),
onSuccess: invalidate,
});
}
export function useDeleteFormPaymentOption() {
const invalidate = useInvalidateFormPaymentOptions();
return useMutation({
mutationFn: (id: string) => api.forms.paymentOptions.remove(edition, id),
onSuccess: invalidate,
});
}
/** URL objet (aperçu) du logo du formulaire public, ou `null` si absent.
* Utilisable sans compte connecté (`GET .../form/logo` n'est pas protégé —
* affiché sur `/inscription`). `refreshKey` (ex. `dataUpdatedAt` de