Files
echo-du-huit/statut-mairie.test.ts
Pierre Martin 3248b28e1f feat: read and write the mairie status carried by CATEGORIES
Two pure modules: statut-mairie.js (string[] -> string[] status logic) and
ics-categories.js, which rewrites CATEGORIES in an iCalendar resource behind a
structural guard: nothing is written if anything but CATEGORIES changed.
2026-08-13 16:50:16 +02:00

107 lines
3.5 KiB
TypeScript

import { describe, expect, test } from "bun:test";
import {
jourParis,
lireStatut,
poserIgnore,
poserSoumis,
retirerStatut,
} from "./extension/statut-mairie.js";
describe("lireStatut", () => {
test("aucune catégorie → aucun", () => {
expect(lireStatut([])).toEqual({ type: "aucun" });
});
test("tag ignoré", () => {
expect(lireStatut(["mairie:ignoré"])).toEqual({ type: "ignoré" });
});
test("tag soumis avec date", () => {
expect(lireStatut(["mairie:soumis:2026-08-13"])).toEqual({
type: "soumis",
jour: "2026-08-13",
});
});
test("les catégories des bénévoles n'interfèrent pas", () => {
expect(lireStatut(["Concert", "mairie:ignoré"])).toEqual({ type: "ignoré" });
expect(lireStatut(["Concert", "Jazz"])).toEqual({ type: "aucun" });
});
test("tag mairie: inconnu → aucun, sans exception", () => {
expect(lireStatut(["mairie:bidule"])).toEqual({ type: "aucun" });
});
test("plusieurs tags reconnus → le dernier l'emporte", () => {
expect(lireStatut(["mairie:ignoré", "mairie:soumis:2026-08-13"])).toEqual({
type: "soumis",
jour: "2026-08-13",
});
expect(lireStatut(["mairie:soumis:2026-08-13", "mairie:ignoré"])).toEqual({
type: "ignoré",
});
});
test("tag écrit en Unicode décomposé (NFD) → reconnu quand même", () => {
const decompose = "mairie:ignoré".normalize("NFD");
expect(decompose).not.toBe("mairie:ignoré");
expect(lireStatut([decompose])).toEqual({ type: "ignoré" });
});
test("le tag posé est en forme normalisée (NFC)", () => {
expect(poserIgnore([])[0]).toBe("mairie:ignoré".normalize("NFC"));
});
test("soumis sans date ou date malformée → jour null", () => {
expect(lireStatut(["mairie:soumis"])).toEqual({ type: "soumis", jour: null });
expect(lireStatut(["mairie:soumis:hier"])).toEqual({ type: "soumis", jour: null });
});
});
describe("poser / retirer", () => {
test("poserSoumis remplace le tag existant, préserve ordre et casse des autres", () => {
expect(poserSoumis(["Concert", "mairie:ignoré"], "2026-08-13")).toEqual([
"Concert",
"mairie:soumis:2026-08-13",
]);
});
test("poserIgnore deux fois → pas de doublon", () => {
expect(poserIgnore(poserIgnore([]))).toEqual(["mairie:ignoré"]);
});
test("poserIgnore sur une liste vide", () => {
expect(poserIgnore([])).toEqual(["mairie:ignoré"]);
});
test("poser* écrase même un tag mairie: inconnu", () => {
expect(poserIgnore(["Concert", "mairie:bidule"])).toEqual(["Concert", "mairie:ignoré"]);
});
test("retirerStatut enlève le tag et laisse le reste", () => {
expect(retirerStatut(["Concert", "mairie:soumis:2026-08-13"])).toEqual(["Concert"]);
});
test("retirerStatut sur une liste sans tag → inchangée", () => {
expect(retirerStatut(["Concert", "Jazz"])).toEqual(["Concert", "Jazz"]);
});
test("les entrées ne sont jamais mutées", () => {
const categories = ["Concert", "mairie:ignoré"];
poserSoumis(categories, "2026-08-13");
poserIgnore(categories);
retirerStatut(categories);
expect(categories).toEqual(["Concert", "mairie:ignoré"]);
});
});
describe("jourParis", () => {
test("23h30 UTC le 31/12 → déjà le 1er janvier à Paris (+01:00)", () => {
expect(jourParis(new Date("2025-12-31T23:30:00Z"))).toBe("2026-01-01");
});
test("22h30 UTC en août → déjà le lendemain à Paris (+02:00)", () => {
expect(jourParis(new Date("2026-08-13T22:30:00Z"))).toBe("2026-08-14");
});
});