FrançaisEnglish

Tests

L'approche d'Amalgame en matière de tests est délibérément sans framework. Un test est un programme normal qui affiche des lignes [PASS] / [FAIL] / [SKIP] ; amc test découvre ces programmes, compile et exécute chacun d'eux, puis additionne les tags. Il n'y a aucune bibliothèque d'assertions à apprendre, aucune annotation, aucun DSL de test runner — juste Console.WriteLine et une convention de nommage.


Écrire un test

Un fichier de test est nommé *_test.am et possède un Main() qui affiche une ligne taguée par vérification :

// tests/arith_test.am
class Program {
    public static void Main() {
        let a = 2 + 3
        if (a == 5) {
            Console.WriteLine("[PASS] add: 2 + 3 == 5")
        } else {
            Console.WriteLine("[FAIL] add: expected 5, got " + String_FromInt(a))
        }

        let b = 7 * 6
        if (b == 42) {
            Console.WriteLine("[PASS] mul: 7 * 6 == 42")
        } else {
            Console.WriteLine("[FAIL] mul: expected 42, got " + String_FromInt(b))
        }
    }
}

Les trois tags que le runner comptabilise, en début de ligne :

Tag Signification
[PASS] la vérification est satisfaite
[FAIL] la vérification n'est pas satisfaite — l'exécution échoue
[SKIP] non exécuté intentionnellement (p. ex. nécessite un service, connu pour être instable)
Console.WriteLine("[PASS] sanity: hello")
Console.WriteLine("[FAIL] todo: not implemented yet")
Console.WriteLine("[SKIP] flaky: see issue #42")

C'est tout le contrat. Tout ce que vous pouvez calculer, vous pouvez l'asserter en branchant et en affichant le bon tag.


Lancer la suite

amc test                  # discover *_test.am under . (recursively), run all
amc test ./tests          # restrict discovery to a directory

amc test compile chaque fichier découvert, l'exécute et agrège les tags dans un récapitulatif :

── tests/arith_test.am
  [PASS] add: 2 + 3 == 5
  [PASS] mul: 7 * 6 == 42
── tests/mixed_test.am
  [PASS] sanity: hello
  [FAIL] todo: not implemented yet
  [SKIP] flaky: see issue #42

──────────────────────────────────
PASS: 3  FAIL: 1  SKIP: 1

Un fichier qui plante (ou qui n'émet aucun tag) est remonté comme un échec, de sorte qu'un segfault ou un corps oublié ne peut pas se faire passer pour « 0 failures ».

Options

Flag Effet
--filter <pat> n'exécute que les tests dont le chemin contient <pat>
--ci sortie laconique — supprime les lignes PASS/SKIP, conserve FAIL + le total
--list affiche les chemins découverts et quitte (pas de compilation, pas d'exécution)
amc test --filter parser        # just the parser tests
amc test --ci                   # CI-friendly: noise down, failures up
amc test --list                 # what would run?

Organiser les tests

Les suites plus volumineuses de ce projet sont organisées en bundles — un unique *_test.am dont le Main() pilote de nombreux cas (les propres core_test.am, stdlib_test.am, etc. du compilateur). Un bundle peut même invoquer amc test sur un répertoire de fixtures et grepper sa ligne de récapitulatif, ce qui est la manière dont le runner se teste lui-même. Commencez par un fichier par domaine ; recourez à un bundle lorsque le coût de mise en place vaut la peine d'être amorti.


Un pattern pour les assertions

Comme il n'y a pas de bibliothèque d'assertions, un petit helper local garde les corps de tests lisibles :

class Program {
    public static void check(bool cond, string label) {
        if (cond) {
            Console.WriteLine("[PASS] " + label)
        } else {
            Console.WriteLine("[FAIL] " + label)
        }
    }

    public static void Main() {
        Program.check(2 + 3 == 5,  "add")
        Program.check("ab" + "c" == "abc", "concat")
    }
}

Gardez le label descriptif — c'est ce que vous lirez dans la sortie --ci lorsque quelque chose casse. Notez que le helper est public static et appelé de façon qualifiée (Program.check(...)) — une méthode statique invoquée depuis Main est atteinte via le nom de sa classe.


Pièges

Pour la référence de la CLI (chaque flag de amc test), voir 03-cli-reference.fr.md ; pour le pipeline de build que la CI exécute autour des tests, voir 06-build-and-tooling.fr.md.