Commit f7ce428c authored by Jordan Grossemy's avatar Jordan Grossemy
Browse files

Un double clic sur « Enregistrer » créait deux tiers au dossier

Le pendant du filet d'erreurs : celui-ci rattrape ce qui échoue, ce garde
empêche ce qui réussit deux fois.

Trente-et-un des cinquante-sept fichiers qui écrivent n'avaient aucune
protection contre le double envoi. Sur le réseau d'une crise — celui qu'on a
quand le système d'information est chiffré — un bouton qui ne répond pas se
reclique. Le doublon qui en résulte ne se découvre pas le jour même : il se
découvre six mois plus tard, en appelant un prestataire dont on a deux fiches
qui ne disent pas la même chose.

── La règle

Tant qu'une écriture est en vol, une écriture identique — même méthode, même
chemin, même corps — ne repart pas : elle reçoit la promesse de la première. Un
appel réseau, un événement au journal, et les deux appelants voient le même
résultat.

Dans le client d'API et non dans les trente-et-un écrans, pour la raison qui a
valu pour le filet : trente-et-une retouches, ce sont trente-et-une occasions
d'en oublier une, et une de plus au prochain écran écrit.

── Ce que le garde ne fait pas

Il ne dédoublonne pas deux gestes séparés par une réponse : refaire sciemment la
même chose reste permis, et le serveur garde ses propres verrous là où cela
compte — la fenêtre anti-doublon des alertes et des mobilisations. Il ne touche
pas aux lectures, que react-query regroupe déjà. Il laisse passer les dépôts de
fichier : le corps est binaire, l'empreinte coûterait une relecture de plusieurs
mégaoctets, et un dépôt part d'un sélecteur de fichier, pas d'un bouton qu'on
martèle.

Un mot sur les bascules, parce que c'est là qu'un tel garde se trompe
d'ordinaire. Celles du produit portent l'état voulu dans leur corps
(« ajoutee: true »), non l'ordre de l'inverser : deux clics rapides envoient
deux fois le même corps, et n'en faire qu'un ne change pas le résultat. Un
« /basculer » sans corps serait replié à tort — le commentaire du fichier le dit
à qui en écrirait un.

── Six garanties, de comportement et non de forme

J'ai failli n'écrire qu'un contrôle textuel : « le garde est présent dans le
source ». Il aurait été vert sans jamais dire que le garde est juste — cette
session m'a déjà montré une garantie verte au-dessus d'une fonction cassée.

Le module de l'interface est donc chargé et exercé, avec un « fetch » qui compte
les appels et ne répond que lorsqu'on le lui demande : c'est la seule façon de
tenir deux écritures en vol en même temps, c'est-à-dire de reproduire le double
clic. On vérifie que deux écritures identiques ne partent qu'une fois et
partagent leur réponse, qu'un corps ou un chemin différent n'est pas replié,
qu'une écriture aboutie puis refaite repart, qu'un refus libère la clé — sans
quoi on ne pourrait plus réessayer — et que les lectures ne sont pas touchées.

Le chargement passe par un spécificateur calculé : ce fichier appartient au
projet de l'interface, et le compiler dans celui de l'API le priverait de la
bibliothèque du navigateur.

Éprouvé aussi à l'écran : trois clics sur « Ajouter » dans les étiquettes du
dossier, un seul POST, une seule ligne en base.

Co-Authored-By: Claude (RCA)
parent 623db568
Loading
Loading
Loading
Loading