Lot T4 : l'ADR 0014, le fichier de relecture textes-amorce.md, les contrôles e2e au document de T4

ADR 0014 « Les informations de fonctionnement ne se votent pas » : ce qui sort
(F1, F1.1, F1.2, F1.3, N1, N1.1, O1 et l'ordre de leurs sections), comment (rien
d'effacé, units.retired_at), la garde et ses refus, aucun vote futur (404 / 400),
ce que dira l'interface (U3), la file de publication, le retour arrière (prouvé
avec l'image de de1b7eb), les limites. textes-amorce.md : chaque texte avant /
après en fr, en, es, E12, ce qui sort, les choix à confirmer par Yvv.

e2e (aucun changement de web/src) : C3, C9 (27 articles, cinq sections, quatre
Propositions seed), C17 (33 modules à voter), C18 et C31 (le texte d'I1 de
T4), C25 (cinq lignes d'ordre, E12 dans l'ordre de « fondamental »), C35 (E12
entre E1 et E2 ; le glisser d'une place), C38 (4 Propositions seed).
CONTROLES.md suit ; CLAUDE.md : article_amend.rs, retire.rs, amorce.rs,
fixtures/seed-m8, le seed de 27 articles, l'invariant.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
Yvv
2026-11-03 21:45:27 +01:00
co-authored by Claude Opus 5.5
parent 093d1ca471
commit 3996f6f99d
11 changed files with 512 additions and 53 deletions
+13 -10
View File
@@ -37,7 +37,7 @@ test('C2 — l’accueil avec session : le choix du groupe, ceux de la même cl
await expect(page).toHaveURL((u) => u.pathname === '/');
});
test('C3 — au départ, aucun texte en vigueur : la raison d’être et les deux engagements, Propositions seed, ouvrent le texte', async ({ page }) => {
test('C3 — au départ, aucun texte en vigueur : la raison d’être et les trois engagements, Propositions seed, ouvrent le texte', async ({ page }) => {
await signIn(page, 'Chiara');
await page.goto(DOC);
await expect(page.getByRole('heading', { level: 1 })).toHaveText("Acte d'engagement Certification");
@@ -45,20 +45,22 @@ test('C3 — au départ, aucun texte en vigueur : la raison d’être et les deu
// read whole at the head of the text (lot U), each marked: never the bare page of a text in force.
await expect(page.getByText("Aucun article n'est encore en vigueur. Commence par les Propositions seed : elles y entrent par le vote, comme toute proposition.")).toBeVisible();
const seeds = page.locator('section.text article.unit');
await expect(seeds.locator('h2')).toHaveText(["Raison d'être", 'Unicité du compte', 'Réciprocité']);
await expect(seeds.locator('.tag', { hasText: 'Proposition seed' })).toHaveCount(3);
await expect(seeds.getByTitle("Texte de départ mis en avant pour lancer le vote. Il n'est pas en vigueur : il y entre par le vote, comme toute proposition.")).toHaveCount(3);
// Lot T4 (Yvv, 2026-11-03): « Responsabilité civique » between the two engagements.
await expect(seeds.locator('h2')).toHaveText(["Raison d'être", 'Unicité du compte', 'Responsabilité civique', 'Réciprocité']);
await expect(seeds.locator('.tag', { hasText: 'Proposition seed' })).toHaveCount(4);
await expect(seeds.getByTitle("Texte de départ mis en avant pour lancer le vote. Il n'est pas en vigueur : il y entre par le vote, comme toute proposition.")).toHaveCount(4);
// At the low level they start at, how far each is from passing.
for (const seed of await seeds.all()) await expect(seed).toContainText('0 pour · 0 contre · 9 oui sur 12');
for (const seed of await seeds.all()) await expect(seed).toContainText('inertie 2 / 5 · basse');
// Below, the open proposals, folded by section; the seed proposals are not said twice.
await expect(page.getByRole('heading', { name: 'Propositions en cours' })).toBeVisible();
await expect(page.locator('ul.deep li.section')).toHaveCount(8);
// Five sections: formule, inertie and ordonnancement are out of the document (ADR 0014).
await expect(page.locator('ul.deep li.section')).toHaveCount(5);
await expect(page.locator('ul.deep button.row')).toHaveCount(0);
await expect(page.locator('ul.deep li.section', { hasText: 'Engagements techniques' })).toContainText('11 articles');
await unfold(page);
// One line per article: the 33 less the 3 at the head, E3 and E7 holding their two variants inside.
await expect(page.locator('ul.deep button.row')).toHaveCount(30);
// One line per article: the 27 less the 4 at the head, E3 and E7 holding their two variants inside.
await expect(page.locator('ul.deep button.row')).toHaveCount(23);
await expect(page.locator('ul.deep .tag', { hasText: 'Proposition seed' })).toHaveCount(0);
});
@@ -172,7 +174,7 @@ test('C9 — les aperçus : bien cotées, et tout', async ({ page }) => {
await page.goto(DOC);
await page.getByRole('radio', { name: 'Si tout passe' }).click();
await expect(page.getByText("Aperçu : le texte tel qu'il serait si toutes les propositions", { exact: false })).toBeVisible();
await expect(page.locator('section.text article.unit')).toHaveCount(33);
await expect(page.locator('section.text article.unit')).toHaveCount(27);
// Nothing in force in Monnaie libre, and nothing well rated yet (no « pour » there so far).
await page.getByRole('radio', { name: 'Si les bien cotées passent' }).click();
await expect(page.locator('section.text article.unit')).toHaveCount(0);
@@ -267,8 +269,9 @@ test('C18 — la Raison d’être ouvre le texte, en trois langues', async ({ pa
// The first sentence in italics, then two paragraphs.
const paragraphs = first.locator('.prose p');
await expect(paragraphs).toHaveCount(3);
await expect(paragraphs.nth(0).locator('em')).toContainText("Derrière une clé il n'y a qu'un seul être humain vivant");
await expect(paragraphs.nth(1)).toContainText("C'est le seul et unique propos de la certification");
// The text of Yvv of 2026-11-03 (lot T4).
await expect(paragraphs.nth(0).locator('em')).toContainText('Derrière une clé il y a un et un seul être humain vivant');
await expect(paragraphs.nth(1)).toContainText("C'est l'unique enjeu de la certification et de votre engagement");
await expect(paragraphs.nth(2)).toContainText('la première monnaie libre');
await page.getByRole('radiogroup', { name: 'Langue du texte' }).getByRole('radio', { name: 'EN' }).click();
await expect(first.locator('h2')).toHaveText('Purpose');