Le plafond, mesuré — la section du README qui disait « à vérifier » ne le dit plus
minio/README.md portait :
ce plafond n'a pas été mesuré ici, il doit l'être avec un vrai téléversement avant d'annoncer une limite aux utilisateurs
Sonde par PUT non signé vers le bucket : rien ne s'écrit, et les deux réponses se distinguent proprement — un 403 vient de MinIO (le corps a donc traversé le tunnel), un 413 vient du tunnel lui-même.
Corps
Réponse
Lecture
50 Mio
403
corps passé, refus de signature
100 Mio
403
corps passé
101 Mio
413
refusé par le tunnel
200 Mio
413
refusé par le tunnel
⚠ Le plafond est exactement 100 Mio, alors que kadans-api annonçait 200 Mio.
⚠ Et la parade retenue n'est PAS celle que le README recommandait. Ramener le gabarit sous le plafond aurait aussi fermé les cours longs (~29 min au palier « travail »). C'est le téléversement en parts qui a été livré — kadans-api #188.
Ce que ça crée comme déchet, et à qui il appartient
Un téléversement en parts jamais refermé laisse ses parts dans le bucket : mc ls n'en dit rien, la console non plus, aucun objet ne les montre. Une fuite qui ne se voit qu'à la facture — ou à la saturation d'un volume de 50 Gi.
L'app abandonne ce qu'elle ouvre quand elle échoue en route. Elle ne peut pas rattraper le navigateur qui ferme l'onglet.
⚠ Le README du module disait « il ne pose ni quota, ni règle de cycle de vie ». Cette règle-ci ne le contredit pas — elle en précise la frontière, et c'est la question « à quoi cette connaissance appartient-elle ? » qui tranche :
une expiration de contenu (« ces vidéos se purgent à 90 jours ») demande de connaître le produit. Elle est chez l'app ;
un téléversement incomplet n'est le contenu de personne. Aucune app ne veut le garder, aucune ne peut le voir depuis son code. C'est un déchet de protocole, produit par le mécanisme même du bucket : il est chez celui qui crée les buckets.
Le test pratique, désormais écrit au README du module : si répondre à « combien de temps ? » exige de connaître le produit, c'est chez l'app. Ici la réponse n'exige que de connaître S3 — passé l'expiration des URL signées (2 h côté kadans-api), un téléversement ne peut plus rien recevoir. D'où 1 jour, douze fois la marge, et pas 7.
⚠ Non paramétrable (YAGNI) : un seul cas. Le déclencheur pour en faire une variable est écrit — une app qui signerait des parts au-delà de 24 h.
⚠ Ce réglage-ci fonctionne, contrairement au CORS par bucket
MinIO communautaire stubbe PutBucketCors en 501 (cmd/dummy-handlers.go), ce qui avait déjà coûté une tentative d'IaC — c'est écrit noir sur blanc dans le iac/main.tf du dépôt kadans. Les handlers de cycle de vie, eux, n'y figurent pas : vérifié à la source avant d'écrire une ligne, pour ne pas répéter exactement cette erreur.
Le plancher de version, et pourquoi il est là
abort_incomplete_multipart_upload est apparu en 3.10.0 — mesuré en interrogeant le schéma du provider version par version (3.9.0 ne l'a pas, 3.10.0 l'a). Le module déclare donc >= 3.10.0lui-même.
⚠ Sans ce plancher, un appelant resté sur 3.3.0 échouerait au plan sur un unsupported block type qui ne dit pas qu'il faut monter de version. Avec, il lit dès tofu init :
no available releases match the given constraints 3.3.0, >= 3.10.0
⚠ ORDRE DE FUSION
Cette PR fait passer tout appelant du module sous le plancher 3.10.0. Le dépôt kadans épingle encore 3.3.0 : son bump doit atterrir AVANT celle-ci, sinon son apply casse entre les deux fusions.
Preuve
tofu validate contre le schéma réel du provider 3.10.0, module instancié depuis un bac à sable (aucun backend, aucun appel à MinIO ni Vault) :
Success! The configuration is valid.
Et le plancher a été éprouvé plutôt que relu : épinglé à 3.3.0, tofu init rend bien le refus cité ci-dessus. tofu fmt -check -recursive propre.
## Le plafond, mesuré — la section du README qui disait « à vérifier » ne le dit plus
`minio/README.md` portait :
> ce plafond n'a **pas** été mesuré ici, il doit l'être avec un vrai téléversement avant d'annoncer une limite aux utilisateurs
Sonde par PUT **non signé** vers le bucket : rien ne s'écrit, et les deux réponses se distinguent proprement — un `403` vient de MinIO (le corps a donc traversé le tunnel), un `413` vient du tunnel lui-même.
| Corps | Réponse | Lecture |
|---:|---|---|
| 50 Mio | `403` | corps passé, refus de signature |
| **100 Mio** | `403` | **corps passé** |
| **101 Mio** | `413` | **refusé par le tunnel** |
| 200 Mio | `413` | refusé par le tunnel |
⚠ **Le plafond est exactement 100 Mio**, alors que `kadans-api` annonçait 200 Mio.
⚠ **Et la parade retenue n'est PAS celle que le README recommandait.** Ramener le gabarit sous le plafond aurait aussi fermé les cours longs (~29 min au palier « travail »). C'est le téléversement **en parts** qui a été livré — kadans-api #188.
## Ce que ça crée comme déchet, et à qui il appartient
Un téléversement en parts jamais refermé laisse ses parts dans le bucket : `mc ls` n'en dit rien, la console non plus, **aucun objet ne les montre**. Une fuite qui ne se voit qu'à la facture — ou à la saturation d'un volume de 50 Gi.
L'app abandonne ce qu'elle ouvre quand elle échoue en route. Elle ne peut **pas** rattraper le navigateur qui ferme l'onglet.
⚠ **Le README du module disait « il ne pose ni quota, ni règle de cycle de vie ».** Cette règle-ci ne le contredit pas — elle en précise la frontière, et c'est la question *« à quoi cette connaissance appartient-elle ? »* qui tranche :
- une **expiration de contenu** (« ces vidéos se purgent à 90 jours ») demande de connaître le **produit**. Elle est chez l'app ;
- un **téléversement incomplet** n'est le contenu de personne. Aucune app ne veut le garder, aucune ne peut le voir depuis son code. C'est un déchet de **protocole**, produit par le mécanisme même du bucket : il est chez celui qui crée les buckets.
Le test pratique, désormais écrit au README du module : *si répondre à « combien de temps ? » exige de connaître le produit, c'est chez l'app.* Ici la réponse n'exige que de connaître S3 — passé l'expiration des URL signées (2 h côté kadans-api), un téléversement ne peut plus **rien** recevoir. D'où **1 jour**, douze fois la marge, et pas 7.
⚠ Non paramétrable (**YAGNI**) : un seul cas. Le déclencheur pour en faire une variable est écrit — une app qui signerait des parts au-delà de 24 h.
## ⚠ Ce réglage-ci fonctionne, contrairement au CORS par bucket
MinIO communautaire stubbe `PutBucketCors` en 501 (`cmd/dummy-handlers.go`), ce qui avait déjà coûté une tentative d'IaC — c'est écrit noir sur blanc dans le `iac/main.tf` du dépôt `kadans`. Les handlers de **cycle de vie**, eux, n'y figurent **pas** : vérifié à la source avant d'écrire une ligne, pour ne pas répéter exactement cette erreur.
## Le plancher de version, et pourquoi il est là
`abort_incomplete_multipart_upload` est apparu en **3.10.0** — mesuré en interrogeant le schéma du provider version par version (3.9.0 ne l'a pas, 3.10.0 l'a). Le module déclare donc `>= 3.10.0` **lui-même**.
⚠ Sans ce plancher, un appelant resté sur 3.3.0 échouerait au plan sur un `unsupported block type` qui ne dit pas qu'il faut monter de version. Avec, il lit dès `tofu init` :
```
no available releases match the given constraints 3.3.0, >= 3.10.0
```
## ⚠ ORDRE DE FUSION
Cette PR fait passer **tout appelant** du module sous le plancher 3.10.0. Le dépôt `kadans` épingle encore 3.3.0 : **son bump doit atterrir AVANT celle-ci**, sinon son `apply` casse entre les deux fusions.
## Preuve
`tofu validate` contre le schéma **réel** du provider 3.10.0, module instancié depuis un bac à sable (aucun backend, aucun appel à MinIO ni Vault) :
```
Success! The configuration is valid.
```
Et le plancher a été **éprouvé plutôt que relu** : épinglé à 3.3.0, `tofu init` rend bien le refus cité ci-dessus. `tofu fmt -check -recursive` propre.
## Le plafond, mesuré — la section du README qui disait « à vérifier » ne le dit plus
`minio/README.md` portait : « ce plafond n'a PAS été mesuré ici, il doit l'être
avec un vrai téléversement avant d'annoncer une limite aux utilisateurs ».
Sonde par PUT NON SIGNÉ vers le bucket : rien ne s'écrit, et les deux réponses se
distinguent proprement — un 403 vient de MinIO (le corps a donc traversé le
tunnel), un 413 vient du tunnel.
100 Mio → 403 corps passé
101 Mio → 413 refusé par le tunnel
⚠ Le plafond est EXACTEMENT 100 Mio, alors que kadans-api annonçait 200 Mio.
⚠ Et la parade retenue n'est PAS celle que le README recommandait. Ramener le
gabarit sous le plafond aurait aussi fermé les cours longs (~29 min au palier
« travail »). C'est le téléversement en PARTS qui a été livré (kadans-api #188).
## Ce que ça crée comme déchet, et à qui il appartient
Un téléversement en parts jamais refermé laisse ses parts dans le bucket :
`mc ls` n'en dit rien, la console non plus, aucun objet ne les montre. Une fuite
qui ne se voit qu'à la facture — ou à la saturation d'un volume de 50 Gi.
L'app abandonne ce qu'elle ouvre quand elle échoue en route. Elle ne peut PAS
rattraper le navigateur qui ferme l'onglet.
⚠ LE README DU MODULE DISAIT « il ne pose ni quota, ni règle de cycle de vie » —
et cette règle-ci ne le contredit pas, elle en précise la frontière. La question
qui tranche est « à QUOI cette connaissance appartient-elle ? » :
- une EXPIRATION DE CONTENU (« ces vidéos se purgent à 90 jours ») demande de
connaître le produit. Elle est chez l'app ;
- un téléversement incomplet n'est le contenu de PERSONNE. Aucune app ne veut
le garder, aucune ne peut le voir depuis son code. C'est un déchet de
PROTOCOLE, produit par le mécanisme même du bucket : il est chez celui qui
crée les buckets.
Test pratique écrit au README : si répondre à « combien de temps ? » exige de
connaître le produit, c'est chez l'app. Ici la réponse n'exige que de connaître
S3 — passé l'expiration des URL signées (2 h côté kadans-api), un téléversement
ne peut plus RIEN recevoir. D'où 1 jour, douze fois la marge, et pas 7.
⚠ Non paramétrable (YAGNI) : un seul cas. Le déclencheur pour en faire une
variable est écrit — une app qui signerait des parts au-delà de 24 h.
## ⚠ Ce réglage-ci fonctionne, contrairement au CORS par bucket
MinIO communautaire stubbe `PutBucketCors` en 501 (`cmd/dummy-handlers.go`), ce
qui avait déjà coûté une tentative d'IaC — c'est écrit dans le `iac/main.tf` du
dépôt front. Les handlers de CYCLE DE VIE, eux, n'y figurent PAS : vérifié à la
source avant d'écrire une ligne, pour ne pas répéter exactement cette erreur.
## Le plancher de version, et pourquoi il est là
`abort_incomplete_multipart_upload` est apparu en **3.10.0** — mesuré en
interrogeant le schéma du provider version par version (3.9.0 ne l'a pas,
3.10.0 l'a). Le module déclare donc `>= 3.10.0` LUI-MÊME.
⚠ Sans ce plancher, un appelant resté sur 3.3.0 échouerait au plan sur un
« unsupported block type » qui ne dit pas qu'il faut monter de version. Avec, il
lit dès `tofu init` : « no available releases match the given constraints 3.3.0,
>= 3.10.0 ».
## ⚠ ORDRE DE FUSION
Cette PR fait passer tout appelant du module sous le plancher 3.10.0. Le dépôt
`kadans` épingle encore 3.3.0 : **son bump doit atterrir AVANT celle-ci**, sinon
son apply casse entre les deux fusions.
## Preuve
`tofu validate` contre le schéma RÉEL du provider 3.10.0, module instancié depuis
un bac à sable (aucun backend, aucun appel à MinIO ni Vault) : « Success! The
configuration is valid. »
Et le plancher a été éprouvé plutôt que relu : épinglé à 3.3.0, `tofu init` rend
bien le refus cité ci-dessus.
Co-Authored-By: Claude Opus 5 <[email protected]>
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
Le plafond, mesuré — la section du README qui disait « à vérifier » ne le dit plus
minio/README.mdportait :Sonde par PUT non signé vers le bucket : rien ne s'écrit, et les deux réponses se distinguent proprement — un
403vient de MinIO (le corps a donc traversé le tunnel), un413vient du tunnel lui-même.403403413413⚠ Le plafond est exactement 100 Mio, alors que
kadans-apiannonçait 200 Mio.⚠ Et la parade retenue n'est PAS celle que le README recommandait. Ramener le gabarit sous le plafond aurait aussi fermé les cours longs (~29 min au palier « travail »). C'est le téléversement en parts qui a été livré — kadans-api #188.
Ce que ça crée comme déchet, et à qui il appartient
Un téléversement en parts jamais refermé laisse ses parts dans le bucket :
mc lsn'en dit rien, la console non plus, aucun objet ne les montre. Une fuite qui ne se voit qu'à la facture — ou à la saturation d'un volume de 50 Gi.L'app abandonne ce qu'elle ouvre quand elle échoue en route. Elle ne peut pas rattraper le navigateur qui ferme l'onglet.
⚠ Le README du module disait « il ne pose ni quota, ni règle de cycle de vie ». Cette règle-ci ne le contredit pas — elle en précise la frontière, et c'est la question « à quoi cette connaissance appartient-elle ? » qui tranche :
Le test pratique, désormais écrit au README du module : si répondre à « combien de temps ? » exige de connaître le produit, c'est chez l'app. Ici la réponse n'exige que de connaître S3 — passé l'expiration des URL signées (2 h côté kadans-api), un téléversement ne peut plus rien recevoir. D'où 1 jour, douze fois la marge, et pas 7.
⚠ Non paramétrable (YAGNI) : un seul cas. Le déclencheur pour en faire une variable est écrit — une app qui signerait des parts au-delà de 24 h.
⚠ Ce réglage-ci fonctionne, contrairement au CORS par bucket
MinIO communautaire stubbe
PutBucketCorsen 501 (cmd/dummy-handlers.go), ce qui avait déjà coûté une tentative d'IaC — c'est écrit noir sur blanc dans leiac/main.tfdu dépôtkadans. Les handlers de cycle de vie, eux, n'y figurent pas : vérifié à la source avant d'écrire une ligne, pour ne pas répéter exactement cette erreur.Le plancher de version, et pourquoi il est là
abort_incomplete_multipart_uploadest apparu en 3.10.0 — mesuré en interrogeant le schéma du provider version par version (3.9.0 ne l'a pas, 3.10.0 l'a). Le module déclare donc>= 3.10.0lui-même.⚠ Sans ce plancher, un appelant resté sur 3.3.0 échouerait au plan sur un
unsupported block typequi ne dit pas qu'il faut monter de version. Avec, il lit dèstofu init:⚠ ORDRE DE FUSION
Cette PR fait passer tout appelant du module sous le plancher 3.10.0. Le dépôt
kadansépingle encore 3.3.0 : son bump doit atterrir AVANT celle-ci, sinon sonapplycasse entre les deux fusions.Preuve
tofu validatecontre le schéma réel du provider 3.10.0, module instancié depuis un bac à sable (aucun backend, aucun appel à MinIO ni Vault) :Et le plancher a été éprouvé plutôt que relu : épinglé à 3.3.0,
tofu initrend bien le refus cité ci-dessus.tofu fmt -check -recursivepropre.## Le plafond, mesuré — la section du README qui disait « à vérifier » ne le dit plus `minio/README.md` portait : « ce plafond n'a PAS été mesuré ici, il doit l'être avec un vrai téléversement avant d'annoncer une limite aux utilisateurs ». Sonde par PUT NON SIGNÉ vers le bucket : rien ne s'écrit, et les deux réponses se distinguent proprement — un 403 vient de MinIO (le corps a donc traversé le tunnel), un 413 vient du tunnel. 100 Mio → 403 corps passé 101 Mio → 413 refusé par le tunnel ⚠ Le plafond est EXACTEMENT 100 Mio, alors que kadans-api annonçait 200 Mio. ⚠ Et la parade retenue n'est PAS celle que le README recommandait. Ramener le gabarit sous le plafond aurait aussi fermé les cours longs (~29 min au palier « travail »). C'est le téléversement en PARTS qui a été livré (kadans-api #188). ## Ce que ça crée comme déchet, et à qui il appartient Un téléversement en parts jamais refermé laisse ses parts dans le bucket : `mc ls` n'en dit rien, la console non plus, aucun objet ne les montre. Une fuite qui ne se voit qu'à la facture — ou à la saturation d'un volume de 50 Gi. L'app abandonne ce qu'elle ouvre quand elle échoue en route. Elle ne peut PAS rattraper le navigateur qui ferme l'onglet. ⚠ LE README DU MODULE DISAIT « il ne pose ni quota, ni règle de cycle de vie » — et cette règle-ci ne le contredit pas, elle en précise la frontière. La question qui tranche est « à QUOI cette connaissance appartient-elle ? » : - une EXPIRATION DE CONTENU (« ces vidéos se purgent à 90 jours ») demande de connaître le produit. Elle est chez l'app ; - un téléversement incomplet n'est le contenu de PERSONNE. Aucune app ne veut le garder, aucune ne peut le voir depuis son code. C'est un déchet de PROTOCOLE, produit par le mécanisme même du bucket : il est chez celui qui crée les buckets. Test pratique écrit au README : si répondre à « combien de temps ? » exige de connaître le produit, c'est chez l'app. Ici la réponse n'exige que de connaître S3 — passé l'expiration des URL signées (2 h côté kadans-api), un téléversement ne peut plus RIEN recevoir. D'où 1 jour, douze fois la marge, et pas 7. ⚠ Non paramétrable (YAGNI) : un seul cas. Le déclencheur pour en faire une variable est écrit — une app qui signerait des parts au-delà de 24 h. ## ⚠ Ce réglage-ci fonctionne, contrairement au CORS par bucket MinIO communautaire stubbe `PutBucketCors` en 501 (`cmd/dummy-handlers.go`), ce qui avait déjà coûté une tentative d'IaC — c'est écrit dans le `iac/main.tf` du dépôt front. Les handlers de CYCLE DE VIE, eux, n'y figurent PAS : vérifié à la source avant d'écrire une ligne, pour ne pas répéter exactement cette erreur. ## Le plancher de version, et pourquoi il est là `abort_incomplete_multipart_upload` est apparu en **3.10.0** — mesuré en interrogeant le schéma du provider version par version (3.9.0 ne l'a pas, 3.10.0 l'a). Le module déclare donc `>= 3.10.0` LUI-MÊME. ⚠ Sans ce plancher, un appelant resté sur 3.3.0 échouerait au plan sur un « unsupported block type » qui ne dit pas qu'il faut monter de version. Avec, il lit dès `tofu init` : « no available releases match the given constraints 3.3.0, >= 3.10.0 ». ## ⚠ ORDRE DE FUSION Cette PR fait passer tout appelant du module sous le plancher 3.10.0. Le dépôt `kadans` épingle encore 3.3.0 : **son bump doit atterrir AVANT celle-ci**, sinon son apply casse entre les deux fusions. ## Preuve `tofu validate` contre le schéma RÉEL du provider 3.10.0, module instancié depuis un bac à sable (aucun backend, aucun appel à MinIO ni Vault) : « Success! The configuration is valid. » Et le plancher a été éprouvé plutôt que relu : épinglé à 3.3.0, `tofu init` rend bien le refus cité ci-dessus. Co-Authored-By: Claude Opus 5 <[email protected]>