mjolnir-qa 4.0.0 → 6.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.de.md DELETED
@@ -1,647 +0,0 @@
1
- <div align="center">
2
-
3
- <img src="assets/readme/hero.svg" alt="Mjölnir. Tests sagen dir, was bestanden hat. Mjölnir sagt dir, worauf du dich verlassen kannst." width="100%" />
4
-
5
- <br />
6
-
7
- Mjölnir findet Tests, die nicht fehlschlagen können, und Pipelines, die nie rot werden können,<br />
8
- und bewertet dann, wie weit dem Ergebnis zu trauen ist – mit der Evidenz für jeden Punkt.
9
-
10
- <br />
11
-
12
- [![npm](https://img.shields.io/npm/v/mjolnir-qa.svg?style=flat-square&color=1F6F7C&labelColor=0A1119)](https://www.npmjs.com/package/mjolnir-qa)
13
- [![downloads](https://img.shields.io/npm/dm/mjolnir-qa.svg?style=flat-square&color=1F6F7C&labelColor=0A1119)](https://www.npmjs.com/package/mjolnir-qa)
14
- [![ci](https://img.shields.io/github/actions/workflow/status/Sergey-Bar/Mjolnir/ci.yml?branch=main&style=flat-square&label=ci&labelColor=0A1119)](https://github.com/Sergey-Bar/Mjolnir/actions/workflows/ci.yml)
15
- [![coverage](https://img.shields.io/codecov/c/github/Sergey-Bar/Mjolnir?style=flat-square&color=1F6F7C&labelColor=0A1119&label=coverage)](https://codecov.io/gh/Sergey-Bar/Mjolnir)
16
- [![OpenSSF Scorecard](https://api.scorecard.dev/projects/github.com/Sergey-Bar/Mjolnir/badge)](https://scorecard.dev/viewer/?uri=github.com/Sergey-Bar/Mjolnir)
17
- [![license](https://img.shields.io/badge/license-MIT-1F6F7C.svg?style=flat-square&labelColor=0A1119)](LICENSE)
18
- [![node](https://img.shields.io/badge/node-%E2%89%A5%2022.18-1F6F7C.svg?style=flat-square&labelColor=0A1119)](https://nodejs.org)
19
-
20
- ```bash
21
- npx mjolnir-qa@3.0.0
22
- ```
23
-
24
- [So sieht es aus](#so-sieht-es-aus) · [Schnellstart](#schnellstart) · [Was es findet](#was-mjölnir-findet) · [Score](#der-worthiness-score) · [Evidenz](#das-evidenzmodell) · [Forensik](#laufzeit-forensik) · [CI](#ci-integrität) · [Agenten](#ki-agenten) · [Sicherheit](#vertrauen-und-sicherheit) · [Grenzen](#was-mjölnir-dir-nicht-sagen-kann) · [Doku](#dokumentation)
25
-
26
- <details>
27
- <summary>In einer anderen Sprache lesen – 22 Übersetzungen</summary>
28
-
29
- [English](README.md) | [简体中文](README.zh.md) | [繁體中文](README.zht.md) | [한국어](README.ko.md) | Deutsch | [Español](README.es.md) | [Français](README.fr.md) | [Italiano](README.it.md) | [Dansk](README.da.md) | [日本語](README.ja.md) | [Polski](README.pl.md) | [Русский](README.ru.md) | [Norsk](README.no.md) | [Português (Brasil)](README.br.md) | [ไทย](README.th.md) | [Türkçe](README.tr.md) | [Українська](README.uk.md) | [বাংলা](README.bn.md) | [Ελληνικά](README.gr.md) | [Tiếng Việt](README.vi.md) | [עברית](README.he.md) | [العربية](README.ar.md) | [Bosanski](README.bs.md)
30
-
31
- > 🤖 Machine-assisted translation. The [English README](README.md) is canonical. Last synced: 2026-09-26.
32
-
33
- <!-- Source hash: `de04dfb1677b` -->
34
-
35
- </details>
36
-
37
- </div>
38
-
39
- <br />
40
-
41
- ## Release status (English canonical)
42
-
43
- The published line is `3.0.0`; this working tree is the `4.0.0-rc.1`
44
- candidate. `3.0.0` must not be republished or retagged. The M26–M50 program is
45
- tracked in
46
- [`docs/ROADMAP.yaml`](docs/ROADMAP.yaml); provisional capability contracts
47
- are not automatically enabled or certified. Repository-owned checks pass, but
48
- Trust certification remains `NOT_CERTIFIED` until the protected holdout,
49
- real-world, platform/consumer, remote-workflow, support-matrix, and corpus
50
- evidence gates pass. Run `npm run m26:readiness` before treating any candidate
51
- as releasable. This document does not publish a tag or authorize a release.
52
-
53
- > Machine-assisted canonical text. Translate this block before treating it as localized copy.
54
-
55
- ## Ein grüner Haken ist eine Behauptung, kein Beweis
56
-
57
- Ein grüner Haken bedeutet, dass die Pipeline nicht fehlgeschlagen ist. Er bedeutet nicht, dass die Tests gelaufen sind oder dass sie hätten fehlschlagen können. Jeder dieser Fälle geht grün durch:
58
-
59
- - ein committetes `.only`, das 3 statt 900 Tests ausgeführt hat
60
- - `continue-on-error: true` auf dem Job, der eigentlich blockieren sollte
61
- - `|| true` nach dem Testbefehl
62
- - ein Test, der nichts prüft oder einen leeren Rumpf hat
63
- - ein Retry-Wrapper, der einen echten Fehlschlag in einen Glückstreffer verwandelt
64
- - ein Report, den der Workflow hochlädt, aber nie erzeugt hat
65
- - ein hartes Sleep, das eine Race Condition zusammenhält
66
-
67
- Keiner davon färbt die Pipeline rot, und jeder wirkt im Review beabsichtigt. Genau deshalb überleben sie. Hier liest Mjölnir einen echten Workflow:
68
-
69
- <p align="center">
70
- <img src="assets/readme/scan.svg" alt="Der CI-Workflow des Demo-Repositorys, Zeile für Zeile gelesen. Mjölnir markiert jeden Befund in der gemeldeten Zeile, mit seiner Regel, dem Problem, seinem Evidenzlevel und seiner gemessenen Falsch-Positiv-Rate." width="800" />
71
- </p>
72
-
73
- <sub>Jeder Befund, den der Demo-Scan für diesen Workflow gemeldet hat, in der gemeldeten Zeile. Erzeugt mit `npm run docs:readme-brand` aus [`demo-report.json`](assets/readme/demo-report.json) und in der CI gegen Abweichungen gesichert.</sub>
74
-
75
- **Strenger Modus.** Die aggressivsten Erkennungen — `.only`, `continue-on-error`, leere Tests, Retry-Missbrauch — leben in der Quarantäne-Stufe. Sie laufen nur unter `--strict` und sind auf `info`-Schweregrad begrenzt: sie kennzeichnen, blocken aber nie. Der Standardscan (`npx mjolnir-qa@3.0.0` ohne `--strict`) deckt nur Kern- und erweiterte Regeln ab. Fügen Sie `--strict` hinzu, wenn Sie auch die Beratungsebene wollen.
76
-
77
- Mjölnir liest die Testsuite, die CI-Workflows und, falls vorhanden, den Report eines echten Laufs. Es führt deine Tests nicht aus, installiert keine Abhängigkeiten und führt den gescannten Code nicht aus. Und wenn es keine Evidenz hat, sagt es das, statt Zuversicht zu erfinden:
78
-
79
- | Situation | Was Mjölnir meldet |
80
- | ------------------------------------------------ | ---------------------------------------------------------------- |
81
- | Keine Testdeklarationen gefunden | Score `null`, angezeigt als **UNKNOWN**. Nie eine erfundene 100. |
82
- | Keine Baseline oder vergleichbare Revision | **UNKNOWN**, mit benanntem Grund. Nie eine angenommene 0. |
83
- | Scan abgebrochen (Zeitbudget, unlesbare Dateien) | **PARTIAL**, Exit `2`. Nie als sauber dargestellt. |
84
-
85
- <p align="center">
86
- <img src="assets/readme/how-it-works.svg" alt="So funktioniert Mjölnir. Es liest die Testsuite und die CI-Pipeline statisch sowie den Report eines echten Laufs, wenn es einen gibt. Es gewichtet jeden Befund nach Evidenzlevel und Vertrauensstufe, wobei nur ein echter Lauf L3 bis L5 erreichen kann, und liefert Befunde, einen Worthiness-Score und ein CI-Gate mit eingefrorenen Exit-Codes. In der Agentenschleife schreibt die KI den Fix und Mjölnir scannt erneut, um ihn zu beweisen." width="880" />
87
- </p>
88
-
89
- <sub>Für diese Seite gestaltet und in 1:1 gezeigt. Erzeugt mit `npm run docs:readme-brand` und in der CI gegen Abweichungen gesichert; Score, Zahlen und Regel-ID stammen aus [`script.demo.json`](assets/video/script.demo.json), [`demo-report.json`](assets/readme/demo-report.json) und der Regel-Registry, nie von Hand getippt. Dasselbe Bild als Poster: [`architecture.svg`](assets/readme/architecture.svg).</sub>
90
-
91
- <br />
92
-
93
- ## So sieht es aus
94
-
95
- Ein echter Scan von [`examples/demo-repo`](examples/demo-repo), einer kleinen Playwright-Suite mit CI-Workflow. Hier sind seine Punkte geblieben:
96
-
97
- <p align="center">
98
- <img src="assets/readme/terminal-hero.svg" alt="Mjölnirs Abzugsaufschlüsselung: WORTHINESS 80/100 WORTHY, der Score nach Kategorie, die Abzugsbox nach Schweregrad und eine FIX THIS FIRST-Liste" width="520" />
99
- </p>
100
-
101
- <sub>Erzeugt mit `npm run docs:hero` aus einem echten Scan und in der CI gegen Abweichungen gesichert. Der vollständige `--verbose`-Report desselben Scans ist [`demo.svg`](assets/readme/demo.svg) (`npm run docs:demo`).</sub>
102
-
103
- <details>
104
- <summary><strong>Ansehen</strong> – ein Scan, der Fix, den er ausgibt, und der erneute Scan, der ihn beweist</summary>
105
-
106
- <br />
107
-
108
- <p align="center">
109
- <a href="assets/video/mjolnir-demo.mp4">
110
- <img src="assets/video/mjolnir-demo-poster.png" alt="Ein Frame der Demo-Aufnahme: npx mjolnir-qa@3.0.0 scannt das Demo-Repository in einem Terminalfenster" width="900" />
111
- </a>
112
- </p>
113
-
114
- <sub>Frame für Frame aus einem echten Scan gerendert mit `npm run docs:video`; nie per Bildschirmaufnahme. Wähle den Frame, um [`mjolnir-demo.mp4`](assets/video/mjolnir-demo.mp4) zu öffnen.</sub>
115
-
116
- </details>
117
-
118
- ### Ein Befund aus der Nähe
119
-
120
- Jeder Befund beantwortet vier Fragen: wo er ist, wie sicher Mjölnir ist, wie oft die Regel falsch liegt und wie man ihn behebt.
121
-
122
- <p align="center">
123
- <img src="assets/readme/finding-anatomy.svg" alt="Der erste Befund des Demo-Scans, genau so, wie das Terminal ihn ausgibt, mit seinen vier markierten Teilen: wo, wie sicher, wie oft die Regel falsch liegt, und der Fix." width="100%" />
124
- </p>
125
-
126
- `mjolnir explain QA-CI-001` gibt die gesamte Vertrauensakte einer Regel aus, einschließlich ihrer gemessenen Falsch-Positiv-Rate und der Stufe, die ihr diese Rate eingebracht hat:
127
-
128
- ```text
129
- ▍ QA-CI-001 — continue-on-error masks a failing verification gate
130
-
131
- Severity: error
132
- Confidence: high
133
- Tier: quarantine
134
- Evidence: E2
135
- QA impact: False-green risk (FALSE-GREEN)
136
- Measured FP: 11% (19 hand-classified corpus verdicts)
137
- FP risk: low (author estimate)
138
- Languages: yaml
139
- Frameworks: github-actions, azure-pipelines
140
-
141
- WHAT WAS FOUND (real detector output, not a mockup)
142
- Job `security-scan` runs a verification gate under `continue-on-error: true`.
143
-
144
- WHY IT MATTERS
145
- This job can fail every day and CI will still show green. The checkmark on
146
- this workflow cannot be trusted.
147
-
148
- HOW TO FIX
149
- Remove continue-on-error, or scope it to individual non-blocking steps only.
150
-
151
- Example from this rule's own must-fire fixture: QA-CI-001/must-fire/masked.yml
152
-
153
- WHAT WOULD CHANGE THE VERDICT
154
- - a run report next to the scan target (mjolnir.report.json or test-results/)
155
- corroborating this file lifts its findings to L3–L5
156
- - a documented suppression (mjolnir.config.json) lowers the finding count
157
- without claiming correctness
158
- - quarantine findings run only under --strict and are advisory (E0) — they can
159
- never gate CI
160
-
161
- NEXT ACTION
162
- Fix the first occurrence, then re-run: `mjolnir --scope changed`. Every
163
- occurrence of this rule is listed in the scan output.
164
-
165
- HOW TO VERIFY THE FIX
166
- Re-run `mjolnir` on the changed file(s) — this finding should no longer
167
- appear. `mjolnir --scope changed` scopes the check to just what you touched.
168
-
169
- Docs: mjolnir rules --md (full catalog, this rule included)
170
- ```
171
-
172
- Das ist die Werteinheit: eine Stelle, an der die CI ein Bestehen meldet, das sie nicht verdient hat.
173
-
174
- <br />
175
-
176
- ## Schnellstart
177
-
178
- ```bash
179
- npx mjolnir-qa@3.0.0
180
- ```
181
-
182
- Es scannt das aktuelle Verzeichnis und gibt den Trust Report aus: was es gefunden hat, wie weit du dem trauen kannst, warum und was als Nächstes zu tun ist. Es endet mit `0`, wenn nichts auf oder über dem Gate gefunden wurde.
183
-
184
- Scanne in der CI nur, was der Branch eingeführt hat, damit eine Legacy-Suite deinen ersten Pull Request nicht ertränkt:
185
-
186
- ```bash
187
- npx mjolnir-qa@3.0.0 --scope changed
188
- ```
189
-
190
- `mjolnir ci install` schreibt das als GitHub-Actions-Workflow, mit der [Action](https://github.com/Sergey-Bar/Mjolnir#readme), gepinnt auf das Major-Tag `v3` (oder schlichtes `npx` mit `--no-action`). Er bleibt beratend, bis du entscheidest, dass er blockieren soll.
191
-
192
- | Befehl | Was er tut |
193
- | --------------------------------------------- | -------------------------------------------------------------- |
194
- | `mjolnir` | Trust Report: Urteil, Konfidenz, nächster Schritt |
195
- | `mjolnir --scope changed` | Nur was dein Branch eingeführt hat (die CI-Form) |
196
- | `mjolnir ci install` | Beratenden PR-Workflow erzeugen (Action-basiert) |
197
- | `mjolnir business-case` | ROI estimate: projected savings per finding |
198
- | `mjolnir release-report` | Release readiness: GO, CONDITIONAL GO, or NO-GO |
199
- | `mjolnir release-trust` | 12-dimension release assurance verdict |
200
- | `mjolnir report` | Generate a Playwright-compatible report |
201
- | `mjolnir trend` | Record, show, or diff local quality snapshots |
202
- | `mjolnir policy` | Initialize, validate, or check policy gates |
203
- | `mjolnir quarantine` | Review deterministic proposals (prototype) |
204
- | `mjolnir analyze --cross-file` | Bounded cross-file analysis |
205
- | `mjolnir ci-adapter github .` | Generate CI templates for supported providers |
206
- | `mjolnir dashboard` | Generate a self-contained quality dashboard |
207
- | `mjolnir exec-report` | Executive KPIs and recommendations (advisory) |
208
- | `mjolnir enterprise` | Self-hosted templates (prototype) |
209
- | `mjolnir maturity` | Assess maturity or display maturity levels |
210
- | `mjolnir mutation tests/mutation-report.json` | Analyze mutation reports; never promotes trust |
211
- | `mjolnir mcp` | Read-only MCP tools over stdio |
212
- | `mjolnir explain QA-CI-001` | Was, warum und Fix, plus die gemessene FP-Rate |
213
- | `mjolnir why src/a.spec.ts:42` | Warum genau diese Zeile markiert wurde. Blockiert nie. |
214
- | `mjolnir forensics ./test-results/` | Laufzeit-Evidenz aus einem echten Lauf |
215
- | `mjolnir trust-report` | Eigenständiges Trust-Artefakt (md + json) |
216
- | `mjolnir handoff` | Behebungsplan für einen Coding-Agenten |
217
- | `mjolnir --json` / `--format sarif` | Maschinenlesbare Ausgabe, GitHub Code Scanning |
218
- | `mjolnir --format codequality` | GitLab-Code-Quality-Report (MR-Widget-Artefakt) |
219
- | `mjolnir --strict` | Auch Regeln der Stufe quarantine ausführen (höheres FP-Risiko) |
220
-
221
- <details>
222
- <summary><strong>Alle weiteren Befehle</strong> – Flake-Triage, Reporting, Governance</summary>
223
-
224
- <br />
225
-
226
- | Befehl | Was er tut |
227
- | ----------------------------------- | -------------------------------------------------------------------------------- |
228
- | `mjolnir --classic` | Das Score-Banner aus der Zeit vor dem Trust Report |
229
- | `mjolnir explain verdict` | Warum das Urteil des gespeicherten Scans so ist, wie es ist |
230
- | `mjolnir triage ./test-results/` | Geführte Triage. Jede Zeile endet mit einem nächsten Schritt. |
231
- | `mjolnir pw-report ./test-results/` | Playwright-Laufzusammenfassung: Retries, Flakes, langsamste Tests |
232
- | `mjolnir doctor:playwright` | Tiefenscan nur für Playwright plus Selector Health Score |
233
- | `mjolnir fix --dry-run` / `fix` | Sichere Auto-Fixes, jeder erneut gescannt, um zu beweisen, dass er gegriffen hat |
234
- | `mjolnir baseline` / `diff` | Befunde als Snapshot sichern, dann nur neue oder schlimmere melden |
235
- | `mjolnir impact --since <ref>` | Was ein Commit eingeführt und behoben hat |
236
- | `mjolnir summary` | CI-Annotationen und eine Step-Zusammenfassung aus einem Report |
237
- | `mjolnir pr-comment` | Ein auf den PR zugeschnittener Kommentar, als Markdown |
238
- | `mjolnir debt` | Testschulden-Register mit Kostenmodell |
239
- | `mjolnir handover` | Einarbeitungskarte der Suite für neue QA-Engineers |
240
- | `mjolnir init` | Frameworks erkennen, Setup-Checkliste ausgeben |
241
- | `mjolnir suppressions` | Unterdrückte Befunde auflisten, für die Governance |
242
- | `mjolnir rules --unmeasured` | Die Regeln, die auf Annahme statt Messung laufen |
243
- | `mjolnir rules --md` | Vollständiger Regelkatalog (JSON oder Markdown) |
244
- | `mjolnir doctor` | Selbstaudit von Mjölnirs eigener Regelbasis |
245
- | `mjolnir create-rule <ID>` | Gerüst für eine neue Regel und ihre Fixtures |
246
- | `mjolnir stats` | Lokale Zähler aller jemals gesehenen Fixes |
247
- | `mjolnir badge` | shields.io-Endpoint-JSON und Snippet |
248
- | `mjolnir --cache` | Inkrementelle Re-Scans über einen lokalen Urteils-Cache |
249
- | `mjolnir --format mermaid` | Testarchitektur-Diagramm für einen PR-Kommentar |
250
-
251
- `mjolnir help <command>` gibt für jeden davon Verwendung, Beispiele und den nächsten Schritt aus.
252
-
253
- </details>
254
-
255
- Benötigt **Node.js ≥ 22.18** unter Windows, macOS oder Linux. Lieber global installieren? `npm i -g mjolnir-qa`. Die Untergrenze kommt von der Build-Toolchain (tsdown zielt darauf, und die Release-Pipeline macht Smoke-Tests dagegen); die Laufzeitabhängigkeiten brauchen nicht mehr.
256
-
257
- <br />
258
-
259
- ## Was Mjölnir findet
260
-
261
- <p align="center">
262
- <img src="assets/readme/stack.svg" alt="Funktioniert mit deinem Stack: die Sprachen, Test-Frameworks und CI-Systeme, die seine Regeln abdecken, aus der Regel-Registry." width="100%" />
263
- </p>
264
-
265
- **79 Regeln** in vier Familien – Testhygiene, Testqualität, Playwright und CI-Integrität – für TypeScript und JavaScript, Python, Java, C# und GitHub-Actions-YAML. Sie decken Playwright in allen vier Bindings ab, dazu pytest, JUnit, TestNG, NUnit, xUnit, MSTest, Jest, Vitest und Mocha, mit Einstiegsabdeckung für Cypress und Selenium. Neun davon, um die Form zu zeigen:
266
-
267
- | ID | Regel | Schweregrad | Stufe |
268
- | ------------ | -------------------------------------------------------------------- | ----------- | ---------- |
269
- | QA-CI-001 | `continue-on-error` maskiert ein fehlschlagendes Verifikations-Gate | error | quarantine |
270
- | QA-CI-009 | Test-Exit-Code nicht weitergereicht (`\|` ohne pipefail, `;`-Ketten) | error | extended |
271
- | QA-TEST-001 | Fokussierter Test committet (`.only`, `fit`) | error | quarantine |
272
- | QA-TEST-003 | Test ohne Assertions | error | quarantine |
273
- | QA-TQUAL-009 | Promise-Assertion ohne await | error | quarantine |
274
- | QA-PW-002 | Locator-Assertion ohne await | error | core |
275
- | QA-PW-004 | Fragile CSS/XPath-Selektoren | warning | quarantine |
276
- | QA-PY-002 | Übersprungener Test (`skip`, nicht-striktes `xfail`) | warning | core |
277
- | QA-CS-103 | Testmethode ohne Assertions | error | core |
278
-
279
- Der vollständige Katalog wird aus der Registry erzeugt, nie von Hand gepflegt: `mjolnir rules --md`, [`docs/rules/`](docs/rules/) oder der [What-it-checks-Leitfaden](https://sergey-bar.github.io/Mjolnir/guide/what-it-checks).
280
-
281
- <details>
282
- <summary><strong>Jede in diesem README genannte Regel</strong>, in einer Tabelle</summary>
283
-
284
- <br />
285
-
286
- > `quarantine`-Regeln laufen nur unter `--strict` und blockieren nie (sie sind auf info begrenzt). Der gezeigte Schweregrad ist der vom Autor festgelegte.
287
-
288
- | ID | Familie | Regel | Schweregrad | Stufe |
289
- | ------------ | ---------- | -------------------------------------------------------------------- | ----------- | ---------- |
290
- | QA-TEST-001 | Hygiene | Fokussierter Test committet (`.only`, `fit`) | error | quarantine |
291
- | QA-TEST-002 | Hygiene | Übersprungener Test. Eskaliert ohne nachverfolgten Grund zu `error`. | warning | quarantine |
292
- | QA-TEST-003 | Hygiene | Test ohne Assertions | error | quarantine |
293
- | QA-TEST-004 | Hygiene | Hartes Sleep (`waitForTimeout`, `sleep()`, `delay()`) | warning | extended |
294
- | QA-TEST-006 | Hygiene | Retry-Missbrauch, der Flakiness verbirgt | warning | quarantine |
295
- | QA-TEST-010 | Hygiene | Leerer Testrumpf | error | quarantine |
296
- | QA-TQUAL-002 | Qualität | Tautologische Assertion | error | quarantine |
297
- | QA-TQUAL-009 | Qualität | Promise-Assertion ohne await | error | quarantine |
298
- | QA-TQUAL-011 | Qualität | Auskommentierte Tests | warning | extended |
299
- | QA-PW-002 | Playwright | Locator-Assertion ohne await | error | core |
300
- | QA-PW-003 | Playwright | `page.pause()` / `test.only()` committet | error | core |
301
- | QA-PW-004 | Playwright | Fragile CSS/XPath-Selektoren | warning | quarantine |
302
- | QA-PW-123 | Playwright | Fest codierte Umgebungs-URLs | warning | quarantine |
303
- | QA-PW-140 | Playwright | Screenshot ohne `maxDiffPixelRatio` | warning | core |
304
- | QA-CI-001 | CI | `continue-on-error` maskiert ein fehlschlagendes Gate | error | quarantine |
305
- | QA-CI-002 | CI | `\|\| true` verschluckt Exit-Codes | error | extended |
306
- | QA-CI-005 | CI | Report verwendet, aber nie erzeugt | error | quarantine |
307
- | QA-CI-007 | CI | Retry-Wrapper um Tests | warning | extended |
308
- | QA-CI-008 | CI | Immer erfolgreicher Step maskiert Fehlschläge | error | quarantine |
309
- | QA-CI-009 | CI | Exit-Code nicht weitergereicht (`\|` ohne pipefail, `;`-Ketten) | error | extended |
310
- | QA-CI-010 | CI | Tests übersprungen, wo sie blockieren müssen | error | quarantine |
311
- | QA-PY-002 | Python | Übersprungener Test (`skip`, nicht-striktes `xfail`) | warning | core |
312
- | QA-PY-003 | Python | Testfunktion ohne Assertions | error | quarantine |
313
- | QA-PY-005 | Python | `time.sleep()` in Tests | warning | extended |
314
- | QA-PY-012 | Python | Tautologische Assertion | error | quarantine |
315
- | QA-JV-101 | Java | Deaktivierter Test (`@Disabled`) | warning | core |
316
- | QA-JV-102 | Java | Hartes Sleep (`Thread.sleep()`) | warning | extended |
317
- | QA-JV-103 | Java | Testmethode ohne Assertions | error | extended |
318
- | QA-JV-105 | Java | Playwright-`waitForTimeout()` als hartes Sleep | warning | core |
319
- | QA-JV-106 | Java | Fragiler Selektor statt Role-Locator | warning | quarantine |
320
- | QA-CS-101 | C# | Übersprungener Test (`[Ignore]`, `[Fact(Skip=)]`) | warning | core |
321
- | QA-CS-102 | C# | Hartes Sleep (`Thread.Sleep` / `Task.Delay`) | warning | core |
322
- | QA-CS-103 | C# | Testmethode ohne Assertions | error | core |
323
- | QA-CS-105 | C# | `WaitForTimeoutAsync()` als hartes Sleep | warning | extended |
324
- | QA-CS-106 | C# | Fragiler Selektor statt Role-Locator | warning | quarantine |
325
-
326
- Python bringt außerdem QA-PY-001…012 (pytest-Hygiene) und QA-PY-101…108 (Playwright für Python) mit. Cypress und Selenium haben Einstiegssets mit je drei Regeln.
327
-
328
- </details>
329
-
330
- Jede Regel wird mit einem Must-fire- **und** einem Must-not-fire-Fixture ausgeliefert, und eine Regel, die auf ihrem eigenen Negativ-Fixture anschlägt, kann nicht ausgeliefert werden. Das ist die Falsch-Positiv-Firewall; `mjolnir doctor` erzwingt sie in der eigenen CI dieses Repositorys.
331
-
332
- ### Selector Health Score
333
-
334
- `mjolnir doctor:playwright` bewertet jeden Locator danach, wie er ein Element findet: so wie ein Nutzer (Rolle, Label, Text), über einen expliziten Vertrag (`data-testid`) oder über einen strukturellen Zufall (CSS-Ketten, XPath). Jede Datei bekommt einen Score von 0 bis 100:
335
-
336
- ```text
337
- ▍ SELECTOR HEALTH
338
-
339
- e2e/login.spec.ts
340
- [█████████████░░░░░░░] 65 / 100
341
- role/text: 1 · testid: 0 · plain-css: 0 · css-chains: 1 ⚠ · xpath: 0
342
-
343
- e2e/checkout.spec.ts
344
- [██████████████████░░] 88 / 100
345
- role/text: 4 · testid: 1 · plain-css: 0 · css-chains: 1 ⚠ · xpath: 0
346
- ```
347
-
348
- Das misst **Robustheit, nicht Korrektheit**. `.btn.btn-primary > div:nth-child(2)` besteht heute und besteht weiter, bis jemand das Markup anfasst. Ein niedriger Score behauptet nie, der Test sei kaputt, nur dass er von Markup abhängt, dessen Erhalt niemand versprochen hat.
349
-
350
- <br />
351
-
352
- ## Der Worthiness-Score
353
-
354
- <p align="center">
355
- <img src="assets/readme/score-gauge.svg" alt="Die Worthiness-Skala von 0 bis 100, mit einer Markierung, die jeden Score durchläuft: UNWORTHY unter 50, NEEDS WORK von 50 bis 79, WORTHY von 80 bis 99, FORGED bei 100" width="720" />
356
- </p>
357
-
358
- <sub>Jeder Score von 0 bis 100, platziert vom echten `deriveScoreState`. Erzeugt mit `npm run docs:gauge` und in der CI gegen Abweichungen gesichert.</sub>
359
-
360
- | Score | Urteil |
361
- | --------- | --------------------------------------------- |
362
- | `0 – 49` | **UNWORTHY** |
363
- | `50 – 79` | **NEEDS WORK** |
364
- | `80 – 99` | **WORTHY** |
365
- | `100` | **FORGED** |
366
- | `null` | **UNKNOWN**: keine Testdeklarationen gefunden |
367
-
368
- **Wie er berechnet wird.** Der Schweregrad legt einen Grundabzug fest (`error −8`, `warning −3`, `info −1`), und das Evidenzlevel rabattiert ihn: E2 zählt voll, E1 halb (abgerundet), E0 gar nicht. Die Summe wird nach der Exposition der Suite normalisiert, also Abzüge pro Testdeklaration statt pro Datei. Das Terminal gibt dieselben rabattierten Zahlen aus, die der Score verwendet hat; es gibt kein verstecktes zweites Modell. Details: [docs/SCORING.md](docs/SCORING.md) und der [Scoring-Leitfaden](https://sergey-bar.github.io/Mjolnir/guide/scoring).
369
-
370
- **Was 100 nicht bedeutet.** Es bedeutet nicht, dass die Software korrekt, die Suite ausreichend oder das Produkt fehlerfrei ist. Es bedeutet genau eines: **keine der von Mjölnir ausgewerteten Regeln hat unter diesem Scan und diesem Evidenzmodell einen Abzug erzeugt.**
371
-
372
- <br />
373
-
374
- ## Das Evidenzmodell
375
-
376
- Jeder Befund trägt zwei Labels: wie sicher Mjölnir ist und wie weit der Befund geprüft wurde. Das ist der Unterschied zwischen einem Tool, das Muster meldet, und einem Tool, an dem du ein Release festmachen kannst.
377
-
378
- **Wie sicher – das Evidenzlevel.**
379
-
380
- | Level | Name | Bedeutet | Abzug |
381
- | ------ | ------------------------ | --------------------------------------------------------------- | ----- |
382
- | **E2** | Deterministischer Beweis | Der Defekt steckt im Code, so wie er geschrieben ist | Voll |
383
- | **E1** | Musterevidenz | Ein Muster, das eng mit dem Defekt verbunden ist, hat gegriffen | Halb |
384
- | **E0** | Beobachtung | Gut zu wissen. Keine Behauptung, dass etwas falsch ist. | Null |
385
-
386
- Konfidenz in einer Erkennung ist nicht die Stärke des Beweises. Eine Regel kann sicher sein, gefunden zu haben, wonach sie gesucht hat, und trotzdem auf eine Heuristik blicken. E1-Befunde sind dazu da, gelesen und beurteilt zu werden, nie blind angewendet, und diese Grenze ist auf dem Befund vermerkt – im Terminal, im JSON und in der Agenten-Übergabe.
387
-
388
- **Wie weit geprüft – die Vertrauensstufe.** Die meisten Befunde entstehen durch das Lesen deines Codes. Gib Mjölnir den Report eines echten Testlaufs, und es kann bestätigen, dass der Code tatsächlich gelaufen ist.
389
-
390
- <p align="center">
391
- <img src="assets/readme/trust-ladder.svg" alt="Die Vertrauensleiter von L0 bis L5. L0 bis L2 entstehen durch das Lesen des Codes; L3 bis L5 brauchen einen echten Laufreport, markiert durch eine Lücke in der Leiter." width="100%" />
392
- </p>
393
-
394
- | Level | In einfachen Worten | Was es braucht |
395
- | ------ | -------------------------- | ----------------------------------------------------------------- |
396
- | **L0** | Notiert | Den Code lesen |
397
- | **L1** | Sieht nach dem Problem aus | Den Code lesen: ein Muster hat gegriffen |
398
- | **L2** | Im Code bewiesen | Den Code lesen: der Defekt ist strukturell |
399
- | **L3** | Die Datei lief | Ein Laufreport zeigt, dass die Datei des Befunds ausgeführt wurde |
400
- | **L4** | Der Test lief | Ein Laufreport zeigt, dass der Test des Befunds ausgeführt wurde |
401
- | **L5** | Der Lauf stimmt zu | Das Ergebnis des Laufs selbst bestätigt die Defektklasse |
402
-
403
- Ein statischer Scan endet bei L2. Nur ein echter Laufreport (Playwright JSON, Jest oder Vitest JSON, JUnit XML) kann einen Befund auf L3 oder höher heben, sodass ein Befund, der nie beim Laufen gesehen wurde, das auch nie behaupten kann. Definitionen: [docs/TERMINOLOGY.md](docs/TERMINOLOGY.md).
404
-
405
- ### Wie viel davon gemessen ist
406
-
407
- **74 von 79 Regeln haben eine gegen echten OSS-Code gemessene Falsch-Positiv-Rate** (mindestens 10 von Hand klassifizierte Befunde je Regel; siehe [docs/FP-AUDIT.md](docs/FP-AUDIT.md)). Die übrigen 5 laufen auf der Schätzung des Autors und sagen das Regel für Regel in `mjolnir explain`. `mjolnir rules --unmeasured` listet sie auf, und jede Scan-Fußzeile meldet, wie viele der tatsächlich _ausgelösten_ Regeln gemessen sind.
408
-
409
- Raten bleiben öffentlich, auch wenn sie schlecht sind. QA-TEST-001 (ein committetes `.only`) schneidet auf echten Repositorys schlecht ab und sitzt deshalb in quarantine. Die aktuelle Zahl für jede Regel, QA-PW-141 eingeschlossen, steht im Audit.
410
-
411
- ### Vertrauensstufen
412
-
413
- Die Stufen folgen der gemessenen Falsch-Positiv-Rate, nicht einer Meinung:
414
-
415
- | Stufe | Gemessene FP | Verhalten |
416
- | -------------- | ------------------------------ | ------------------------------------------------ |
417
- | **core** | ≤ 10% | Standardreport, blockiert |
418
- | **extended** | ≤ 30% | Standardreport, geringere Konfidenz |
419
- | **quarantine** | > 30% oder explizit deklariert | Nur `--strict`, auf info begrenzt, blockiert nie |
420
- | _ungemessen_ | n < 10 | Kann erst nach Messung zu core befördert werden |
421
-
422
- FP-Bänder können nur herabstufen — sie befördern eine Regel nie aus `quarantine` heraus, wenn sie dort explizit deklariert wurde. Eine explizit unter Quarantäne gestellte Regel bleibt in quarantine, unabhängig von ihrer gemessenen FP-Rate.
423
-
424
- Beförderung, Herabstufung und Reife pro Sprache: [Regel-Lebenszyklus](https://sergey-bar.github.io/Mjolnir/reference/rule-lifecycle).
425
-
426
- ### Warum das kein Linter ist
427
-
428
- Linter sagen dir, ob Code Regeln befolgt. Mjölnir sagt dir, ob deiner Verifikation zu trauen ist.
429
-
430
- | | Linter (ESLint, SonarQube) | Coverage-Tools | KI-Code-Review | **Mjölnir** |
431
- | ----------------------------------------------------------------- | :------------------------: | :------------: | :------------: | :--------------: |
432
- | Bewertet das **Verifikationssystem**, nicht den Produktcode | Nein | Nein | Nein | Ja |
433
- | Integrität von CI-Workflows (`continue-on-error`, `\|\| true`) | Nein | Nein | nur den Diff | Ja |
434
- | Bewertet die Robustheit von Playwright-Locators (Selector Health) | Nein | Nein | Nein | Ja |
435
- | Liest echte Laufdaten für `TRUE-FLAKE`-Urteile | Nein | Nein | Nein | Ja |
436
- | Veröffentlicht eine gemessene Falsch-Positiv-Rate pro Regel | Nein | Nein | Nein | Ja |
437
- | Markiert Tests ohne Assertions | Ja\* | Nein | manchmal | Ja |
438
- | Findet harte Sleeps (`waitForTimeout`, `time.sleep`) | Ja\* | Nein | manchmal | Ja |
439
- | Deterministisch (gleiche Eingabe, gleiche Ausgabe) | Ja | Ja | Nein | Ja |
440
- | Kosten pro Scan | kostenlos | kostenlos | Tokens | **null** (lokal) |
441
-
442
- <sub>\*Abgedeckt durch `eslint-plugin-jest` und `eslint-plugin-playwright` (`expect-expect`, `no-wait-for-timeout`) sowie durch SonarQubes eigene Assertion-Regeln. Die Spalten beschreiben das Standardverhalten bei der Verifikation von Testsuiten; Plugins, bezahlte Stufen und eigene Regeln ändern manche Antworten. Das ist eine Positionierungsübersicht, kein Benchmark.</sub>
443
-
444
- Nutze auch KI-Review. Es erkennt Nuancen, Absicht und Designfehler, die kein Muster findet. Mjölnir findet, was KI-Review übersieht, weil es beabsichtigt aussieht: ein committetes `.only`, ein verschluckter Exit-Code, ein `continue-on-error` auf einem Test-Job. Dafür braucht es Scannen, nicht Schlussfolgern.
445
-
446
- <br />
447
-
448
- ## Laufzeit-Forensik
449
-
450
- Statische Analyse argumentiert über Code, der nie gelaufen ist. Die Forensik liest, was tatsächlich passiert ist: Playwright JSON, Jest JSON, Vitest JSON und JUnit XML von jedem Runner.
451
-
452
- ```bash
453
- mjolnir forensics ./test-results/
454
- ```
455
-
456
- ```text
457
- ▍ FLAKINESS LEADERBOARD
458
-
459
- 3 tests · 1 failed · 1 flaky · 1 retried
460
-
461
- TRUE-FLAKE completes checkout with saved card (e2e/checkout.spec.ts)
462
- ████████████████████ 6.0s · 2 attempts
463
- FAILING declines an expired card (e2e/checkout.spec.ts)
464
- ████░░░░░░░░░░░░░░░░ 1.1s · 1 attempt
465
- ```
466
-
467
- `TRUE-FLAKE` bedeutet nicht, dass der Test wiederholt wurde. Es bedeutet, dass der Test **mindestens einen Versuch nicht bestanden und dann grün geendet hat**: ein Glückstreffer, markiert unabhängig davon, was der letzte Haken sagt. `mjolnir triage` macht aus diesem Verlauf einen Quarantäne-Vorschlag, und `mjolnir pw-report` fasst einen Lauf zusammen. Dieselben Laufreports sind es, die Befunde auf die Vertrauensstufen L3 und höher heben.
468
-
469
- <br />
470
-
471
- ## CI-Integrität
472
-
473
- Ein Test kann bestehen, während die Pipeline um ihn herum nicht fehlschlagen kann. Mjölnir liest auch die Workflows: `continue-on-error`, `|| true`, Exit-Codes, die nie weitergereicht werden, immer erfolgreiche Steps, Reports, die verwendet, aber nie erzeugt werden, und Gates, die bei genau den Events übersprungen werden, die blockieren sollten. Jeder Befund nennt Job, Step und Zeile und trägt sein eigenes Evidenzlevel.
474
-
475
- Erzeuge den PR-Workflow, standardmäßig beratend:
476
-
477
- ```bash
478
- mjolnir ci install
479
- ```
480
-
481
- Oder füge die Marketplace-Action zu einem bestehenden Workflow hinzu:
482
-
483
- ```yaml
484
- - uses: Sergey-Bar/Mjolnir@v3
485
- with:
486
- scope: changed
487
- fail-on: error
488
- ```
489
-
490
- Pinne `@v3`, um der Major-Linie zu folgen, oder ein exaktes Tag (`@v0.5.32`) für ein reproduzierbares Gate. [docs/DISTRIBUTION-KIT.md](docs/DISTRIBUTION-KIT.md) behandelt den Marketplace, Smithery und die MCP-Registries.
491
-
492
- Um Befunde in GitHub Code Scanning zu bringen, lade SARIF hoch (erfordert `security-events: write` auf Workflow- oder Job-Ebene):
493
-
494
- ```yaml
495
- - run: npx mjolnir-qa@3.0.0 --format sarif > mjolnir.sarif
496
- continue-on-error: true
497
- - uses: github/codeql-action/upload-sarif@v3
498
- if: ${{ !cancelled() }}
499
- with:
500
- sarif_file: mjolnir.sarif
501
- ```
502
-
503
- Auf GitLab schreibt `--format codequality` den Code-Quality-Report, den das MR-Widget und die Diff-Annotationen lesen ([docs/GITLAB-CI.md](docs/GITLAB-CI.md)). Editor- und Pipeline-Einrichtung: [docs/SARIF-INTEGRATION.md](docs/SARIF-INTEGRATION.md).
504
-
505
- ### Zuordnung im Changed-Scope
506
-
507
- ```bash
508
- npx mjolnir-qa@3.0.0 --scope changed
509
- ```
510
-
511
- Befunde werden den Zeilen zugeordnet, die dein Branch hinzugefügt hat, gemessen gegen die **merge-base**. Der Scope ist dieselbe Dateimenge, die ein vollständiger Scan findet (TS/JS-Specs und Adapter-Konfigurationen, `test_*.py`, `*Test.java`, `*Tests.cs`, `.github/workflows/*.yml`), plus nicht committete und nicht verfolgte Änderungen, sodass es schon vor dem Commit funktioniert. Die Basis wird aufgelöst als `main → master → origin/main → origin/master → origin/HEAD`; überschreibe sie mit `--base <ref>`.
512
-
513
- Wenn die merge-base nicht aufgelöst werden kann (ein Shallow Clone, ein Detached HEAD, ein Ziel außerhalb von git), fallen die Befunde auf eine Zuordnung zur ganzen Datei zurück, **und der Report sagt das.** Ein stiller Fallback wäre genau die Art von Defekt, die dieses Tool finden soll.
514
-
515
- <br />
516
-
517
- ## KI-Agenten
518
-
519
- Befunde sind nur etwas wert, wenn etwas auf sie reagiert.
520
-
521
- ```text
522
- SCAN → EVIDENCE → HANDOFF → AGENT → RE-SCAN → PROOF
523
- ```
524
-
525
- **Die KI schreibt den Fix. Mjölnir verifiziert ihn.** Der Beweis kommt vom erneuten Scan, nie vom Erfolgsbericht des Agenten selbst.
526
-
527
- | Befehl | Was der Agent bekommt |
528
- | ----------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
529
- | `mjolnir mcp` | Ein [MCP](https://modelcontextprotocol.io)-Server über stdio. `scan`, `explain` und `diff` werden zu aufrufbaren Tools. |
530
- | `mjolnir handoff` | Ein gespeicherter `--json`-Report wird zu einem deterministischen Markdown-Plan: was erkannt wurde, die Evidenzgrenze pro Befund, was sich **nicht** ändern darf, wie zu verifizieren ist. |
531
- | `mjolnir install` | Schreibt in die Agenten-Oberflächen, die dein Repo bereits hat (`.claude/`, `.cursor/`, `.kilo/`, `AGENTS.md`), damit der Agent erneut scannt, bevor er behauptet, fertig zu sein. |
532
-
533
- Füge es einem Client hinzu, der eine eigene CLI mitbringt:
534
-
535
- ```bash
536
- claude mcp add mjolnir -- npx -y mjolnir-qa@3.0.0 mcp
537
- ```
538
-
539
- Oder jedem Client, der einen `mcpServers`-Block akzeptiert:
540
-
541
- ```json
542
- {
543
- "mcpServers": {
544
- "mjolnir": { "command": "npx", "args": ["-y", "mjolnir-qa@3.0.0", "mcp"] }
545
- }
546
- }
547
- ```
548
-
549
- **Die Leitplanke zählt mehr als die Bequemlichkeit.** Jeder Befund in einer Übergabe trägt seine Grenze. **E2** sagt _deterministisch: Stelle prüfen und den Fix anwenden_. **E1** sagt _BESTÄTIGUNG ERFORDERLICH: die Beobachtung allein beweist den Defekt nicht_. Ein Agent, der E1 blind behebt, eine Regel unterdrückt oder eine Regel ändert, um den Score zu heben, tut genau das, was dieses Tool finden soll – deshalb sagt die Übergabe das im Prompt, direkt neben dem Befund.
550
-
551
- <br />
552
-
553
- ## Vertrauen und Sicherheit
554
-
555
- **Local-first, null Telemetrie.** Keine netzwerkfähige API (`fetch`, `http`, `https`, `net`, `dns`, `dgram`, WebSocket) existiert irgendwo in `src/`, und [`privacy-network-isolation.spec.ts`](tests/contract/privacy-network-isolation.spec.ts) lässt den Build fehlschlagen, sobald eine auftaucht. Es verbietet auch `eval` und `new Function`. Das Scannen nicht vertrauenswürdigen Codes führt ihn nie aus: Die statische Analyse liest Quelltext, und die Forensik parst Reportdateien, die bereits auf der Platte liegen.
556
-
557
- Zwei Einschränkungen: `npx` selbst lädt das Paket herunter, bevor irgendetwas läuft, und die Garantie gilt für `src/`, nicht für Plugins von Drittanbietern.
558
-
559
- **Plugins laufen nicht in einer Sandbox.** JS-Plugins (`mjolnir-rules/*.mjs` oder unter `"plugins"` gelistete npm-Pakete) laufen mit vollen Node-Rechten, dasselbe Vertrauensmodell wie bei ESLint- oder Vitest-Plugins. Sie zu laden ist ein Opt-in **pro Scan**: Ohne `--enable-plugins` (oder `MJOLNIR_ENABLE_PLUGINS=1`) werden ihre Quellen nie geladen, und ein Hinweis auf stderr listet auf, was übersprungen wurde. JSON-Regelmanifeste führen keinen Code aus, und die Präfixe der Core-Regel-IDs sind reserviert, damit sich kein Plugin als eine davon ausgeben kann. Melde Schwachstellen über [SECURITY.md](SECURITY.md).
560
-
561
- **Es läuft auf sich selbst.** Eine Verification Trust Engine hat keine Glaubwürdigkeit, wenn sie nicht selbst verifizierbar ist. Jeder CI-Lauf scannt dieses Repository mit dem Build, den derselbe Lauf erzeugt hat. Das Gate schlägt bei jedem Befund mit Schweregrad error fehl, und ebenso bei einem **partiellen** Scan oder einer **abgestürzten Regel**, denn ein abgeschnittener Selbstscan, der nichts meldet, ist genau das falsche Grün, das dieses Projekt finden soll. `mjolnir doctor` prüft die Regelbasis im selben Lauf erneut (Fixture-Firewall, Ehrlichkeit der Stufen, die Obergrenze für core), und eine INCONCLUSIVE-Prüfung schlägt genauso fehl wie eine fehlgeschlagene. Beide Reports werden als Build-Artefakte hochgeladen.
562
-
563
- ### Exit-Codes und der Maschinenvertrag
564
-
565
- Eingefroren, damit du CI-Logik darauf bauen kannst:
566
-
567
- | Exit-Code | Bedeutung |
568
- | --------- | ------------------------------------------------------------------------ |
569
- | `0` | Sauber: keine Befunde auf oder über dem Gate |
570
- | `1` | Befunde auf oder über dem Gate |
571
- | `2` | Partieller Scan (Zeitbudget erreicht, unlesbare Dateien). Blockiert nie. |
572
- | `10` | Bedienfehler (falsches Flag, fehlendes Ziel) |
573
- | `20` | Interner Fehler |
574
-
575
- `2` ist bewusst von `0` verschieden: Ein Scan, der nicht fertig wurde, hat nicht nichts gefunden. Er ist nur mit dem Suchen nicht fertig geworden.
576
-
577
- Alles, was eine Maschine konsumiert (MCP-Tool-Ergebnisse, `--json`, SARIF 2.1), stammt aus einem kanonischen Ergebnis unter einem versionierten, **nur additiv erweiterten** Schema (`schemaVersion: 1`, `contractVersion: 1`), sodass kein Konsument Bedeutung aus gerendertem Text rekonstruieren muss. Siehe [den Maschinenvertrag](docs/machine-contract.md). Regel-IDs (`QA-<FAMILY>-NNN`) sind nach der Auslieferung unveränderlich und werden nie wiederverwendet.
578
-
579
- <br />
580
-
581
- ## Was Mjölnir dir nicht sagen kann
582
-
583
- - **Es führt deine Tests nicht aus.** Ein sauberer Scan ist keine bestandene Suite.
584
- - **Es kann dir nicht sagen, dass eine Assertion _falsch_ ist.** `expect(total).toBe(41)` sieht gesund aus. Mjölnir findet Tests, die _nicht fehlschlagen können_, und Pipelines, die _nicht rot werden können_, keine Tests, die das Falsche prüfen.
585
- - **Es beweist keine fachliche Korrektheit.** Nichts hier sagt, dass dein Produkt tut, was die Anforderung verlangt hat.
586
- - **Eine 100 ist kein Beweis für eine gute Suite.** Ob deine Suite dein echtes Risiko abdeckt, ist eine andere Frage, und dieses Tool beantwortet sie nicht.
587
- - **5 von 79 Regeln laufen auf einer Schätzung**, nicht auf einer gemessenen Rate. Jede davon sagt das auf ihrem eigenen Befund.
588
- - **E1 ist nicht E2.** Heuristische Befunde sind es wert, gelesen zu werden, nicht, blind angewendet zu werden.
589
- - **Ein leeres Repo bekommt `null`, nie 100.**
590
- - **Eine Datei namens `*.spec.ts` ohne Testdeklarationen zählt nicht als Abdeckung.** Ein Repo, dessen einzige Spec-Dateien Imports oder Typen enthalten (null `it`/`test`-Aufrufe), bekommt `null`, nicht 100.
591
-
592
- <br />
593
-
594
- ## Dokumentation
595
-
596
- Die vollständige Doku-Website findest du unter <https://sergey-bar.github.io/Mjolnir/>.
597
-
598
- | Dokument | Was drinsteht |
599
- | ------------------------------------------------------ | ------------------------------------------------------------------ |
600
- | [docs/SCORING.md](docs/SCORING.md) | Score-Normalisierung und Evidenzgewichtung |
601
- | [docs/TERMINOLOGY.md](docs/TERMINOLOGY.md) | Kanonisches Vokabular: ein Wort pro Begriff |
602
- | [docs/FP-AUDIT.md](docs/FP-AUDIT.md) | Gemessene Falsch-Positiv-Raten und die Methode |
603
- | [docs/RULE-LIFECYCLE.md](docs/RULE-LIFECYCLE.md) | Regelzustände, Stufen, Unterdrückung, Abkündigung |
604
- | [docs/VERSIONING.md](docs/VERSIONING.md) | Semver-Richtlinie, eingefrorene Schnittstellen, Abkündigungszyklus |
605
- | [docs/machine-contract.md](docs/machine-contract.md) | Das kanonische maschinenlesbare Ergebnis |
606
- | [docs/SARIF-INTEGRATION.md](docs/SARIF-INTEGRATION.md) | SARIF-Ausgabe und Editor- oder CI-Einrichtung |
607
- | [docs/GITLAB-CI.md](docs/GITLAB-CI.md) | GitLab: Code-Quality-Report, MR-Rezept, Gate |
608
- | [docs/rules/](docs/rules/) | Generierter Katalog pro Regel |
609
- | [CONTRIBUTING.md](CONTRIBUTING.md) | Entwicklungsumgebung und Beitrags-Workflow |
610
- | [SUPPORT.md](SUPPORT.md) | Wo man fragt, meldet und Hilfe bekommt |
611
- | [SECURITY.md](SECURITY.md) | Melden von Schwachstellen |
612
- | [CHANGELOG.md](CHANGELOG.md) | Versionshistorie |
613
-
614
- ### Status
615
-
616
- **Version 3.0.0.** Das JSON-Schema und die Exit-Codes sind eingefrorene Verträge. TypeScript und Python haben die breiteste gemessene Abdeckung. Java und C# sind neuer; lies sie durch die [Reifetabelle](https://sergey-bar.github.io/Mjolnir/reference/rule-lifecycle). Was als Nächstes kommt, ohne erfundene Termine: [die öffentliche Roadmap](https://sergey-bar.github.io/Mjolnir/reference/roadmap).
617
-
618
- ### Mitwirken
619
-
620
- Neue Regeln sind der einfachste erste Beitrag. Ein Befehl erzeugt das Gerüst der Regel mit ihren Must-fire- **und** Must-not-fire-Fixtures. Die erzeugte Regel besteht ihre eigenen Fixtures absichtlich nicht, bis echte Erkennung geschrieben ist, denn ein ausgelieferter Stub ist eine Regel, die niemand gemessen hat:
621
-
622
- ```bash
623
- mjolnir create-rule QA-PW-140 --title "Screenshot without diff bound"
624
- ```
625
-
626
- Die Entwicklungsumgebung, die Befehle der ständigen Gates sowie die Anti-Creep- und Fixture-Firewall-Gesetze stehen in [CONTRIBUTING.md](CONTRIBUTING.md).
627
-
628
- <br />
629
-
630
- <div align="center">
631
-
632
- <img src="assets/readme/closing.svg" alt="Lass es auf dein Repo los." width="100%" />
633
-
634
- ```bash
635
- npx mjolnir-qa@3.0.0
636
- ```
637
-
638
- [Zum Leitfaden](https://sergey-bar.github.io/Mjolnir/guide/getting-started) · [Doku-Website](https://sergey-bar.github.io/Mjolnir/) · [npm](https://www.npmjs.com/package/mjolnir-qa)
639
-
640
- <br />
641
-
642
- Frag nicht, ob die Tests bestanden haben.<br />
643
- Frag, ob die Evidenz beweist, dass sie Vertrauen verdienen.
644
-
645
- <sub>Entwickelt von [Sergey Bar](https://www.linkedin.com/in/sergeybar/) · MIT-lizenziert</sub>
646
-
647
- </div>