Hallo!
Ich arbeite derzeit an einer Markdown-Erweiterung/einem Plugin, das eine ganze Reihe von BBCode-Tags hinzufügt, und ich möchte QUnit-Akzeptanztests dafür schreiben (ich war es leid, sie ständig manuell zu prüfen, und es gibt sehr viele davon).
Bei den betreffenden Tags handelt es sich um eine Mischung aus einfachen Tags, die einfach HTML anwenden, und komplexen Tags, die mit Event-Handler verknüpft sind. Daher muss ich sowohl das HTML des gerenderten Textes als auch die Event-Handler testen.
Ich bin auf einige Akzeptanztests für Markdown-Erweiterungen gestoßen (nämlich local-dates-composer-test.js.es6, spoiler-button-test.js-es6, checklist-test.js.es6 und pretty-text-test.js), die ich als Referenz verwendet habe. Diese lassen sich grob in zwei Methoden zur Durchführung des Tests unterteilen:
- Simuliere das Öffnen der Seite, das Erstellen eines neuen Themas und das Eingeben von Text im Editor, wobei die Ausgabe über einen Selektor im DOM abgerufen wird. (local-dates-composer-test.js.es6, spoiler-button-test.js-es6)
- Erstelle eine Instanz von Pretty Text, um den Text sofort zu rendern („to cook“) und das HTML dort zu vergleichen. (checklist-test.js.es6, pretty-text-test.js) (checklist scheint auch eine Instanz des Post-Modells zu erstellen, um Event-Handling zu testen, und testet insgesamt eher den Initialisierer).
Ich habe beide Methoden ausprobiert und bin mehr oder weniger erfolgreich gewesen. Die erste Methode ist ziemlich einfach und ich habe das Gewollte erreicht, allerdings auf Kosten einer längeren Zeit als bei der zweiten. Die zweite Methode habe ich mit deutlich schnellerer Testzeit erfolgreich durchführen können, aber ich erhalte einen seltsamen Fehler.
Hier sind meine Codes und Ergebnisse:
Methode 1: Öffnen der Seite simulieren
import { acceptance, queryAll } from "discourse/tests/helpers/qunit-helpers";
QUnit.assert.cooked = async function (input, expected, message) {
await fillIn(".d-editor-input", input);
const actual = queryAll(".d-editor-preview")[0].innerHTML;
this.pushResult({
result: actual === expected.replace(/\/>/g, ">"),
actual,
expected,
message,
});
};
acceptance("Methode 1", function (needs) {
needs.user();
test("Rendern über die Seite", async function (assert) {
await visit("/");
await click("#create-topic");
assert.cooked("hello world", "<p>hello world</p>", "dieser Test funktioniert");
});
});
Methode 2: Pretty-Text-Instanz erstellen
import { acceptance} from "discourse/tests/helpers/qunit-helpers";
import { cookAsync } from "discourse/lib/text";
acceptance("Methode 2", function (needs) {
needs.user();
test("Rendern mit cookAsync", async function (assert) {
const cooked = await cookAsync("hello world", {});
assert.equal(cooked, "<p>hello world</p>", "dieser Test funktioniert auch");
});
});
Im Moment testen sie nur ein einfaches Rendern des Texts „hello world“. Ich habe dies gegen meine eigenen benutzerdefinierten Tags getestet, und sie funktionieren.
Ich glaube, bei Methode 2 fehlt mir etwas, da der Fehler afterEach failed ....: this.keyTrapper is null auftritt. Trotzdem funktionieren beide Methoden, und ich sehe, dass ich für einfache Tests des HTMLs Methode 2 verwenden sollte und für Tests, die Event-Handling beinhalten, Methode 1.
Da viele meiner Tags nur einfaches HTML sind, möchte ich Methode 2 neben Methode 1 während des Testens verwenden, um Zeit zu sparen. Ich möchte gerne wissen, was mir fehlt, was diesen Fehler verursacht, oder ob es einen noch besseren Weg gibt, diese Tests insgesamt zu schreiben.

