@andresmassello/uscha 1.51.1 → 1.53.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.
Files changed (98) hide show
  1. package/README.md +24 -5
  2. package/package.json +3 -2
  3. package/uscha-kit/.claude/skills/uscha-adr-refine/SKILL.md +203 -161
  4. package/uscha-kit/.claude/skills/uscha-characterize/SKILL.md +40 -0
  5. package/uscha-kit/.claude/skills/uscha-devloop/SKILL.md +40 -0
  6. package/uscha-kit/.claude/skills/uscha-discovery/SKILL.md +203 -161
  7. package/uscha-kit/.claude/skills/uscha-mirador/SKILL.md +192 -161
  8. package/uscha-kit/.claude/skills/uscha-mirador/mirador-render.py +16 -8
  9. package/uscha-kit/.claude/skills/uscha-reverse-discovery/SKILL.md +42 -0
  10. package/uscha-kit/.claude/skills/uscha-rubric/SKILL.md +119 -79
  11. package/uscha-kit/.claude/skills/uscha-status/SKILL.md +24 -0
  12. package/uscha-kit/.claude/skills/uscha-sysdoc/SKILL.md +128 -88
  13. package/uscha-kit/.claude-plugin/plugin.json +2 -2
  14. package/uscha-kit/.codex-plugin/plugin.json +2 -2
  15. package/uscha-kit/INSTALL.md +3 -0
  16. package/uscha-kit/README.md +1 -1
  17. package/uscha-kit/VERSION +1 -1
  18. package/uscha-kit/install-uscha.py +77 -43
  19. package/uscha-kit/skills/uscha-adr-refine/SKILL.md +203 -161
  20. package/uscha-kit/skills/uscha-characterize/SKILL.md +40 -0
  21. package/uscha-kit/skills/uscha-devloop/SKILL.md +40 -0
  22. package/uscha-kit/skills/uscha-discovery/SKILL.md +203 -161
  23. package/uscha-kit/skills/uscha-mirador/SKILL.md +192 -161
  24. package/uscha-kit/skills/uscha-mirador/mirador-render.py +16 -8
  25. package/uscha-kit/skills/uscha-reverse-discovery/SKILL.md +42 -0
  26. package/uscha-kit/skills/uscha-rubric/SKILL.md +119 -79
  27. package/uscha-kit/skills/uscha-status/SKILL.md +24 -0
  28. package/uscha-kit/skills/uscha-sysdoc/SKILL.md +128 -88
  29. package/uscha-kit/uscha.config.json +1 -1
  30. package/uscha-kit/CHANGELOG-1.10.0.md +0 -84
  31. package/uscha-kit/CHANGELOG-1.11.0.md +0 -67
  32. package/uscha-kit/CHANGELOG-1.12.0.md +0 -46
  33. package/uscha-kit/CHANGELOG-1.13.0.md +0 -33
  34. package/uscha-kit/CHANGELOG-1.14.0.md +0 -42
  35. package/uscha-kit/CHANGELOG-1.15.0.md +0 -58
  36. package/uscha-kit/CHANGELOG-1.16.0.md +0 -55
  37. package/uscha-kit/CHANGELOG-1.17.0.md +0 -44
  38. package/uscha-kit/CHANGELOG-1.18.0.md +0 -42
  39. package/uscha-kit/CHANGELOG-1.19.0.md +0 -41
  40. package/uscha-kit/CHANGELOG-1.2.2.md +0 -16
  41. package/uscha-kit/CHANGELOG-1.2.3.md +0 -20
  42. package/uscha-kit/CHANGELOG-1.2.4.md +0 -10
  43. package/uscha-kit/CHANGELOG-1.2.5.md +0 -23
  44. package/uscha-kit/CHANGELOG-1.2.6.md +0 -11
  45. package/uscha-kit/CHANGELOG-1.2.7.md +0 -15
  46. package/uscha-kit/CHANGELOG-1.2.8.md +0 -24
  47. package/uscha-kit/CHANGELOG-1.2.9.md +0 -4
  48. package/uscha-kit/CHANGELOG-1.20.0.md +0 -29
  49. package/uscha-kit/CHANGELOG-1.21.0.md +0 -33
  50. package/uscha-kit/CHANGELOG-1.22.0.md +0 -60
  51. package/uscha-kit/CHANGELOG-1.23.0.md +0 -75
  52. package/uscha-kit/CHANGELOG-1.24.0.md +0 -50
  53. package/uscha-kit/CHANGELOG-1.25.0.md +0 -55
  54. package/uscha-kit/CHANGELOG-1.26.0.md +0 -70
  55. package/uscha-kit/CHANGELOG-1.27.0.md +0 -45
  56. package/uscha-kit/CHANGELOG-1.28.0.md +0 -35
  57. package/uscha-kit/CHANGELOG-1.29.0.md +0 -20
  58. package/uscha-kit/CHANGELOG-1.3.0.md +0 -74
  59. package/uscha-kit/CHANGELOG-1.30.0.md +0 -46
  60. package/uscha-kit/CHANGELOG-1.31.0.md +0 -59
  61. package/uscha-kit/CHANGELOG-1.32.0.md +0 -50
  62. package/uscha-kit/CHANGELOG-1.33.0.md +0 -46
  63. package/uscha-kit/CHANGELOG-1.34.0.md +0 -55
  64. package/uscha-kit/CHANGELOG-1.35.0.md +0 -30
  65. package/uscha-kit/CHANGELOG-1.36.0.md +0 -33
  66. package/uscha-kit/CHANGELOG-1.37.0.md +0 -41
  67. package/uscha-kit/CHANGELOG-1.38.0.md +0 -11
  68. package/uscha-kit/CHANGELOG-1.39.0.md +0 -14
  69. package/uscha-kit/CHANGELOG-1.4.0.md +0 -68
  70. package/uscha-kit/CHANGELOG-1.40.0.md +0 -16
  71. package/uscha-kit/CHANGELOG-1.40.1.md +0 -11
  72. package/uscha-kit/CHANGELOG-1.40.2.md +0 -13
  73. package/uscha-kit/CHANGELOG-1.41.0.md +0 -18
  74. package/uscha-kit/CHANGELOG-1.41.1.md +0 -53
  75. package/uscha-kit/CHANGELOG-1.41.2.md +0 -34
  76. package/uscha-kit/CHANGELOG-1.41.3.md +0 -30
  77. package/uscha-kit/CHANGELOG-1.42.0.md +0 -41
  78. package/uscha-kit/CHANGELOG-1.43.0.md +0 -37
  79. package/uscha-kit/CHANGELOG-1.44.0.md +0 -90
  80. package/uscha-kit/CHANGELOG-1.44.1.md +0 -26
  81. package/uscha-kit/CHANGELOG-1.45.0.md +0 -58
  82. package/uscha-kit/CHANGELOG-1.46.0.md +0 -50
  83. package/uscha-kit/CHANGELOG-1.46.1.md +0 -35
  84. package/uscha-kit/CHANGELOG-1.47.0.md +0 -45
  85. package/uscha-kit/CHANGELOG-1.48.0.md +0 -35
  86. package/uscha-kit/CHANGELOG-1.48.1.md +0 -55
  87. package/uscha-kit/CHANGELOG-1.48.2.md +0 -47
  88. package/uscha-kit/CHANGELOG-1.49.0.md +0 -45
  89. package/uscha-kit/CHANGELOG-1.5.0.md +0 -64
  90. package/uscha-kit/CHANGELOG-1.50.0.md +0 -52
  91. package/uscha-kit/CHANGELOG-1.50.1.md +0 -52
  92. package/uscha-kit/CHANGELOG-1.50.2.md +0 -62
  93. package/uscha-kit/CHANGELOG-1.51.0.md +0 -44
  94. package/uscha-kit/CHANGELOG-1.51.1.md +0 -33
  95. package/uscha-kit/CHANGELOG-1.6.0.md +0 -57
  96. package/uscha-kit/CHANGELOG-1.7.0.md +0 -74
  97. package/uscha-kit/CHANGELOG-1.8.0.md +0 -46
  98. package/uscha-kit/CHANGELOG-1.9.0.md +0 -112
@@ -1,44 +0,0 @@
1
- # uscha-kit 1.51.0 — a third install target: pi (Earendil) (2026-07-24)
2
-
3
- After the 1.50.2 portability patch made the kit run everywhere, this adds **pi** — Earendil's
4
- `@earendil-works/pi-coding-agent` — as a first-class install target alongside `codex` and
5
- `claude`. The 9 skills implement the Agent Skills standard, so they load into pi unmodified.
6
- Smoke suite: 386/386.
7
-
8
- ## The target
9
- `install --target pi` places the 9 `uscha-*` skill directories flat under **`~/.agents/skills/`**
10
- — the harness-neutral sibling of the `codex` target's `~/.agents/plugins/` — plus an install
11
- marker so the doctor can measure presence and version. Skills only: no plugin manifest, no
12
- `settings.json`, no hook. It uses the same transactional install as the Claude target (stage →
13
- back up → atomic replace → marker last), so a late failure rolls the target back with nothing
14
- lost.
15
-
16
- - **`--target all`** installs codex + claude + pi in one run. **`both` stays a legacy alias**
17
- for codex + claude, so existing scripts and users keep their exact prior behavior.
18
- - `doctor --target pi` reports `healthy`, `version_match`, and the skill roster, exactly like
19
- the other targets.
20
-
21
- ## `golden_guard`: INV-GOLDEN-01 per target, reported honestly
22
- The doctor now reports, per target, whether the golden-write guard is **mechanical** or
23
- **advisory** — the field `golden_guard`:
24
-
25
- - **claude: `enforced`** when the PreToolUse hook is registered (else `advisory`).
26
- - **codex: `advisory`** — the Codex plugin has no hooks mechanism, so INV-GOLDEN-01 has always
27
- been advisory there (this just makes it visible).
28
- - **pi: `advisory`.** pi's blocking `tool_call` event can enforce the invariant, and the guard
29
- ships as a precompiled extension — `uscha-kit/pi/golden-guard.js`, plain JS, no build step, to
30
- respect the kit's stdlib-only limit. But the kit reports **advisory, not enforced**, because
31
- the block has not been measured against a real pi run — the same honesty the plugin
32
- `hooks.json` gap follows. A verified pi run flips it to enforced; until then the kit does not
33
- claim enforcement it hasn't seen.
34
-
35
- ## Not done (out of this release)
36
- Verified against a real pi install: the extension's actual load path and the `tool_call` block
37
- (the `advisory` above is exactly this gap). Also unverified: the Codex install roots on POSIX,
38
- and a real macOS end-to-end `npx` install (the CI matrix runs the suite on macOS runners, but
39
- not a user-style install flow). `AGENTS.md` (shipped 1.50.2) is the context file pi reads.
40
-
41
- Regression: smoke **T101** — pi installs 9 skills + marker under `~/.agents/skills`; doctor
42
- reads healthy for a real install and unhealthy for an empty home; `golden_guard` is `advisory`
43
- for pi and `enforced` for a hook-registered Claude install; `--target all` resolves to all
44
- three while `both` stays codex+claude.
@@ -1,33 +0,0 @@
1
- # uscha-kit 1.51.1 — the doctor recognizes the golden hook across an interpreter change (2026-07-24)
2
-
3
- A patch on 1.51.0, surfaced by the CI matrix's new real-installer end-to-end step (install
4
- `--target all` → doctor on every OS). On **Windows / Python 3.8** the step failed: `doctor
5
- --target claude` reported `hook_registered: False` for a hook that was, in fact, correctly
6
- installed. Not a CI artifact — a real doctor false-negative. Smoke suite: 388/388.
7
-
8
- ## Root cause
9
- The installer writes the INV-GOLDEN PreToolUse hook command via
10
- `list2cmdline([sys.executable, <hook path>])` — an **absolute interpreter path** plus the hook
11
- script. The doctor's `hook_registered` then checked for that command by **exact string
12
- equality**. When install-time and doctor-time run under different interpreters — a bare
13
- `python` that resolves to a different `sys.executable` between two invocations, as happened on
14
- the Windows 3.8 runner — the two command strings differ only in their interpreter prefix, and
15
- the exact-match reported the healthy hook as unregistered. That flipped `healthy` and the
16
- `golden_guard` trust signal to a false negative on an otherwise correct install.
17
-
18
- ## Fix
19
- `hook_registered` now matches a registered `"*"` hook by the **guard script it references**,
20
- not by the full command string — the same robustness the N-1 reinstall prune already uses. The
21
- match is **path-anchored** (`/block-approved-writes.py` or `\block-approved-writes.py`) so a
22
- foreign command that merely *mentions* the name — `...not-block-approved-writes.py`, or the
23
- literal inside a `-c` snippet — cannot read as our enforced guard, since this check feeds
24
- `golden_guard`. Exact command stays a fallback; a `None` command entry is skipped, not a crash.
25
-
26
- The interpreter-path sensitivity was latent before 1.51.0 (any Python move after install would
27
- trip it); the real-installer CI step is what finally measured it. This is the step doing its
28
- job — the same way the first matrix run caught the T75 router substring bug.
29
-
30
- Regression: smoke **T103** — `hook_registered` matches across an interpreter change (install
31
- wrote interpreter A, doctor computes B, same script → recognized), and does **not** match a
32
- suffix-collision script, a bare `-c` mention, a foreign hook, a `None` command, or empty
33
- settings. The CI real-installer step (all three OSes × Python 3.8/3.13) is the end-to-end proof.
@@ -1,57 +0,0 @@
1
- # dev-loop-kit 1.6.0 — adapter `type: go` (2026-07-02)
2
-
3
- Tercer adapter consecutivo donde el costo baja porque el engine habla FORMATOS, no
4
- lenguajes: el linter reusa `parse_checkstyle` (golangci-lint emite checkstyle) y los
5
- tests reusan `junit_test_count` (gotestsum emite JUnit). Lo único nuevo: el parser del
6
- cover profile nativo de Go. Smoke suite: 37/37 (31 previos intactos + 6 go).
7
-
8
- ## Engine (qa_ledger.py)
9
-
10
- - **`type: go`**.
11
- - **`go_coverage()`** — cover profile nativo (`go test -coverprofile=coverage.out`):
12
- formato `import/path/file.go:S.C,E.C numStatements hitCount`; cobertura por
13
- **SENTENCIAS** (la convención Go, no líneas). First match: `coverage.out`,
14
- `cover.out`, `reports/coverage.out`. Profile vacío (solo línea `mode:`) → 0.0
15
- fail-closed, nunca un verde inventado.
16
- - Test count: **reusa `junit_test_count`** vía `gotestsum --junitfile` (root envuelto
17
- ya soportado).
18
- - Linter: **reusa `parse_checkstyle` parametrizado** (`tool="golangci"`) — golangci-lint
19
- `--out-format checkstyle`; error→HIGH, warning→MEDIUM; gosec entra por el mismo
20
- reporte si está habilitado en la config del linter. Los IDs de finding llevan
21
- `golangci:` (los de Java siguen `checkstyle:` — sin migración de IDs).
22
- - `ingest-gate`: branch go (`reports/golangci.xml` / `golangci.xml`, o `--golangci`);
23
- combinado = `go-qa-gate`. Mismo contrato de ausencia.
24
- - Guard UNMEASURED: `maven`/`python`/`node`/`go`.
25
- - LOC go: test = sufijo `_test.go` (la convención — los tests viven junto al código);
26
- prod = el resto. `SKIP_DIRS` += `vendor` (dependencias vendorizadas explotarían el
27
- LOC) y `testdata` (fixtures no compilables).
28
-
29
- ## Config / docs
30
-
31
- - `test_command_go` (gotestsum + coverprofile) + repo de ejemplo `api-svc`;
32
- version 1.6.0 (triple sync).
33
- - Kit README: tabla Go; SKILL.md types + `go test`; docs ES/EN tipos y versión.
34
-
35
- ## Smoke (tests/smoke-engine.sh)
36
-
37
- - `repo-e` (`type: go`): cover profile 3/5 sentencias → 60.0%, gotestsum junit → 4
38
- tests, LOC prod=4/test=2 (`_test.go` junto al código), golangci checkstyle
39
- (error gateado HIGH + warning MEDIUM), UNMEASURED pre-ingest → medido post-ingest.
40
-
41
- ## Nota estructural (regla de tres cumplida)
42
-
43
- Con 5 types, los dispatchers siguen siendo ifs de 3 ramas y cada adapter nuevo reusó
44
- parsers existentes — la presión para refactorizar `type` → perfiles de reporte
45
- (cobertura+junit+linters como config, no código) existe pero todavía no duele. Si
46
- entra un 6º type o un type necesita MEZCLAR formatos, ese es el momento.
47
-
48
- ## Criterio pendiente (mismo contrato que python/node)
49
-
50
- Dry-run de solo lectura contra un repo Go real — el adapter entra sin repo de
51
- dogfooding detrás, mismo criterio abierto que 1.4.0/1.5.0.
52
-
53
- ## Diferido consciente (sin cambios)
54
-
55
- - rebuild: densidad de asserts por test-file. Perfiles A-E mecanizados (`--profile`).
56
- - Rust: cargo-llvm-cov emite Cobertura (reusa `python_coverage`) + cargo-nextest emite
57
- JUnit — entra cuando haya repo real.
@@ -1,74 +0,0 @@
1
- # dev-loop-kit 1.7.0 — adapters `type: rust` y `type: dotnet` (2026-07-02)
2
-
3
- > Publicado junto con 1.8.0 y 1.9.0 en un único commit (no existe commit
4
- > standalone de 1.7.0); la suite final de ese commit es 63/63. Los fixes que
5
- > el review fresco de este adapter encontró (blocker de clippy incluido)
6
- > están aplicados y documentados en CHANGELOG-1.9.0.
7
-
8
- Dos adapters en un release porque ambos REUSAN la infraestructura existente:
9
- coverage vía Cobertura (`cobertura_coverage`, renombrado desde `python_coverage`) y
10
- tests vía `junit_test_count`. Nuevo de verdad: `parse_clippy` (JSONL de cargo) y
11
- `parse_sarif` (SARIF v2 — el formato universal de análisis estático). Incluye los
12
- fixes del review fresco de 1.6.0.
13
-
14
- ## Rust (`type: rust`)
15
-
16
- - Coverage: `cargo llvm-cov --cobertura --output-path reports/coverage.xml` —
17
- **reusa `cobertura_coverage`** sin cambios.
18
- - Tests: cargo-nextest con reporter junit — **reusa `junit_test_count`**.
19
- - **`parse_clippy()`** — `cargo clippy --message-format=json` (JSON Lines):
20
- `error`→HIGH, `warning`→MEDIUM; **`code: null`** (error de compilación de rustc,
21
- no un lint) → HIGH siempre — la lección del ruff/tsc, tercera aplicación.
22
- Los IDs preservan el path del span primario (`_mk_id_rel`).
23
- - LOC: `tests/` = integración; los tests inline `#[cfg(test)]` cuentan como prod
24
- (limitación documentada de la clasificación por path). `target/` ya estaba en
25
- SKIP_DIRS (cargo y maven comparten el nombre).
26
-
27
- ## C#/.NET (`type: dotnet`)
28
-
29
- - Coverage: coverlet.msbuild → Cobertura — **reusa `cobertura_coverage`**.
30
- - Tests: `dotnet test --logger "junit;LogFilePath=reports/junit.xml"`
31
- (JUnitXml.TestLogger) — **reusa `junit_test_count`**.
32
- - **`parse_sarif()`** — SARIF v2 (Roslyn vía `dotnet build /p:ErrorLog=...`):
33
- `error`→HIGH, `warning`→MEDIUM, `note`→INFO. El parser sirve para CUALQUIER
34
- herramienta que emita SARIF (semgrep, CodeQL, etc.) — inversión, no solo .NET.
35
- - LOC: proyectos `*.Tests/` y archivos `*Test(s).cs` = test. SKIP_DIRS += `obj`,
36
- `TestResults`.
37
-
38
- ## Fixes del review fresco de 1.6.0 (incluidos acá)
39
-
40
- - **BLOCKER**: la tabla Go del kit README había pisado el heading `## Instalación`
41
- — restaurado.
42
- - **HIGH**: el comando documentado de golangci-lint usaba el flag v1
43
- (`--out-format`), **eliminado en golangci-lint v2** (2025) — documentado el flag
44
- v2 (`--output.checkstyle.path=...`) con fallback v1.
45
- - **MEDIUM**: gotestsum pone `errors` SOLO en el root `<testsuites>` (un paquete
46
- que no compila tenía errors>0 invisibles) — `junit_test_count` ahora toma
47
- `max(root, suma de hijos)` por contador.
48
- - **LOW**: `go_coverage` dedupea bloques repetidos (perfiles `-coverpkg` merged);
49
- IDs de golangci preservan el path repo-relativo (basename colisionaba en repos
50
- Go idiomáticos); nota de severidades de golangci en README.
51
-
52
- ## Trade-off documentado (global, igual que `coverage/` en 1.5.0)
53
-
54
- `vendor/`, `testdata/`, `obj/`, `TestResults/` en SKIP_DIRS son globales: un paquete
55
- fuente legítimamente llamado así en OTRO type queda fuera del LOC (métrica advisory;
56
- la detección de reportes es por glob/paths y no se afecta).
57
-
58
- ## Nota estructural (regla de tres, re-evaluada en el 7º type)
59
-
60
- Siete types y los dispatchers siguen siendo ifs por FORMATO (jacoco / cobertura /
61
- lcov / cover-profile · surefire / junit / aproximado). El refactor a perfiles
62
- declarativos sigue sin pagar: no eliminaría los parsers (el costo real) y agregaría
63
- indirección. Se re-evalúa si un type necesita MEZCLAR formatos por config.
64
-
65
- ## Criterio pendiente (mismo contrato que python/node/go)
66
-
67
- Dry-run de solo lectura contra repos Rust/.NET reales — ambos adapters entran sin
68
- repo de dogfooding detrás.
69
-
70
- ## Diferido consciente (sin cambios)
71
-
72
- - rebuild: densidad de asserts. Perfiles A-E mecanizados.
73
- - C++: viable (gcovr emite Cobertura/lcov — parsers existentes; gtest/catch2 emiten
74
- JUnit; clang-tidy necesitaría un parser tipo mypy) — entra cuando haya repo real.
@@ -1,46 +0,0 @@
1
- # dev-loop-kit 1.8.0 — adapter `type: cpp` (2026-07-02)
2
-
3
- > Publicado junto con 1.7.0 y 1.9.0 en un único commit (no existe commit
4
- > standalone de 1.8.0); la suite final de ese commit es 63/63. Los fixes que el
5
- > review fresco de este adapter encontró están aplicados y documentados en
6
- > CHANGELOG-1.9.0.
7
-
8
- Séptimo lenguaje, UN parser nuevo: clang-tidy. Coverage vía gcovr→Cobertura (reusa
9
- `cobertura_coverage`) y tests vía ctest `--output-junit`/GoogleTest (reusa
10
- `junit_test_count` — el fixture de smoke usa el root PLANO `<testsuite>` para
11
- ejercitar la rama que los demás types no tocan).
12
-
13
- ## Engine (qa_ledger.py)
14
-
15
- - **`type: cpp`** — extensiones `.cpp .cc .cxx .c .h .hpp .hh .hxx`.
16
- - Coverage: `gcovr --cobertura reports/coverage.xml` — **reusa `cobertura_coverage`**.
17
- - Tests: `ctest --test-dir build --output-junit ../reports/junit.xml` (CMake ≥3.21;
18
- root plano) o `--gtest_output=xml:` (root envuelto) — **reusa `junit_test_count`**,
19
- ambas formas de root ya soportadas.
20
- - **`parse_clang_tidy()`** — texto (`file:line:col: warning: msg [check-a,check-b]`):
21
- error→HIGH, warning→MEDIUM; checks de seguridad (`cert-*`, o que contengan
22
- `security`) con floor HIGH — misma disciplina que findsecbugs/eslint-security.
23
- Líneas sin `[check]` (diagnósticos crudos del compilador) → rule `diagnostic`.
24
- IDs con path preservado (`_mk_id_rel`).
25
- - `ingest-gate`: branch cpp (`reports/clang-tidy.txt`, o `--clang-tidy`);
26
- combinado = `cpp-qa-gate`. Mismo contrato de ausencia.
27
- - Guard UNMEASURED: los 7 types linteables.
28
- - LOC: `test`/`tests` en el path, prefijo `test_` o sufijos `_test.cpp/.cc/.cxx`,
29
- `Test.cpp`. `SKIP_DIRS` += `cmake-build-debug`, `cmake-build-release`, `_deps`
30
- (FetchContent) — mismo trade-off global documentado.
31
-
32
- ## Nota honesta sobre C++
33
-
34
- El ecosistema no tiene UNA convención de build (CMake/Bazel/make) — el kit no la
35
- elige: pide que los REPORTES existan (Cobertura + JUnit + texto de clang-tidy) y el
36
- cómo se generan vive en el adapter por-repo (`CLAUDE.md` del proyecto). Es el
37
- contrato de siempre, explícito.
38
-
39
- ## Criterio pendiente (mismo contrato que python/node/go/rust/dotnet)
40
-
41
- Dry-run de solo lectura contra un repo C++ real — entra sin repo de dogfooding.
42
-
43
- ## Diferido consciente
44
-
45
- - rebuild: densidad de asserts. Perfiles A-E mecanizados. cppcheck (`--xml`) como
46
- segundo linter cpp si un repo real lo pide.
@@ -1,112 +0,0 @@
1
- # dev-loop-kit 1.9.0 — adapters `type: gradle` (Kotlin/JVM) y `type: swift` + fixes de los reviews 1.7.0/1.8.0 (2026-07-02)
2
-
3
- Los dos adapters más baratos hasta ahora: **CERO parsers nuevos**. Todo es reuso
4
- de formatos ya soportados en paths nuevos. Nota clave: **Kotlin sobre Maven ya
5
- funcionaba con `type: maven`** (`.kt` está en SOURCE_EXT maven desde 1.0) —
6
- `gradle` cubre el caso común Gradle. Smoke suite: 63/63.
7
-
8
- ## Engine (qa_ledger.py)
9
-
10
- ### `type: gradle` (Kotlin/JVM + Java-sobre-Gradle)
11
-
12
- - Extensiones `.kt .kts .java`. LOC: `src/main` = prod; `src/test` y source
13
- sets custom (`src/*Test`: integrationTest, functionalTest) = test.
14
- - Coverage: **reusa el parser JaCoCo de maven** (`_jacoco_line_counter`) en los
15
- paths Gradle (`build/reports/jacoco/test/jacocoTestReport.xml`).
16
- - Tests: **reusa la suma per-clase de surefire** — `maven_test_count` y
17
- `gradle_test_count` ahora comparten `_perclass_xml_count()`; los
18
- `build/test-results/**/TEST-*.xml` de Gradle son el mismo formato.
19
- - Linter: **detekt** emite formato checkstyle — `parse_checkstyle(tool="detekt")`
20
- parametrizado, igual que golangci. `--detekt` explícito o por type;
21
- combinado = `gradle-qa-gate`.
22
-
23
- ### `type: swift`
24
-
25
- - Extensión `.swift`. LOC: convención SwiftPM (`Sources/` prod, `Tests/` +
26
- `*Tests.swift`/`*Test.swift` test).
27
- - Coverage: **reusa el parser lcov** (Flutter/node) — `llvm-cov export
28
- -format=lcov` sobre el `.profdata` de `swift test --enable-code-coverage`.
29
- - Tests: **reusa `junit_test_count`** — `swift test --xunit-output
30
- reports/junit.xml` emite JUnit directo; el archivo hermano
31
- `junit-swift-testing.xml` (Swift Testing) se SUMA (ver fixes 1.9.0).
32
- - Linter: **SwiftLint** también emite checkstyle —
33
- `parse_checkstyle(tool="swiftlint")`. `--swiftlint` o por type;
34
- combinado = `swift-qa-gate`.
35
-
36
- ## Fixes del review fresco de 1.7.0 (rust/dotnet)
37
-
38
- - **BLOCKER — clippy contaba los summaries de rustc como HIGH fantasma**:
39
- `1 warning emitted` / `aborting due to N previous errors` son diagnósticos
40
- REALES (level warning/error, `code:null`, `spans:[]`) que el branch code-null
41
- convertía en `compile-error` HIGH — el gate rust no podía converger nunca con
42
- un solo warning MEDIUM vivo. Fix: diagnósticos SIN primary span se saltean
43
- ANTES del check de code (los compile errors reales siempre traen span).
44
- Además dedupe por finding ID (cargo re-emite por target lib/bin/test).
45
- - **SARIF**: Roslyn `ErrorLog` emite **v1** salvo `,version=2` — se documenta el
46
- comando correcto Y el parser gana fallback v1 (`resultFile`/`analysisTarget`);
47
- resultados suprimidos (`suppressions`/`suppressionStates`) se ignoran (un
48
- `#pragma warning disable` no puede gatear un build limpio); URIs absolutas
49
- `file:///` se relativizan contra el repo (IDs estables entre máquinas).
50
- - **Paths dotnet**: `LogFilePath`/`CoverletOutput` relativos resuelven contra el
51
- PROYECTO DE TEST, no la raíz — comando de ejemplo ahora ancla con `$PWD` y el
52
- README lo advierte (+ `MergeWith` para multi-proyecto).
53
- - **Junit de nextest**: no existe sin `[profile.default.junit]` en
54
- `.config/nextest.toml` + copy desde `target/nextest/default/junit.xml` —
55
- documentado y agregado al `test_command_rust`.
56
- - **Regla 5 saldada**: los fixes de 1.6.0 que entraron sin check propio ahora
57
- tienen smoke — junit root-max (gotestsum errors solo en root), dedupe de
58
- bloques del cover profile (-coverpkg), y el summary/dup de clippy (T20/T25).
59
-
60
- ## Fixes del review fresco de 1.8.0 (cpp)
61
-
62
- - **`backtest.cpp` ya no cuenta como test LOC**: el sufijo bare `test.cpp`
63
- (lowercased) tragaba `backtest/protest/contest.cpp`; ahora el patrón CamelCase
64
- gtest (`FooTest.cpp`) se matchea case-sensitive, como hace dotnet con
65
- `Test.cs`. Smoke T25 lo pinnea.
66
- - **`cmake-build-<perfil>` de CLion**: el skip ahora es por prefijo
67
- (`cmake-build-*`), no solo debug/release — el README ya lo prometía y el
68
- código no lo cumplía.
69
- - **clang-tidy con paths absolutos**: se relativizan contra el repo
70
- (`_node_rel`), IDs estables entre checkouts; extensiones `.tpp/.ipp/.inl/
71
- .mm/.cu` entran al regex (un cert-* en un template header ya no desaparece
72
- en silencio).
73
-
74
- ## Fixes del review fresco de 1.9.0 (gradle/swift)
75
-
76
- - **detekt y SwiftLint imprimen paths ABSOLUTOS por default** — el branch
77
- isabs de `parse_checkstyle` colapsaba esos IDs a basename (colisiones entre
78
- módulos Gradle y archivos homónimos Swift, corrompiendo fixed/new/oscillation
79
- que se computan sobre sets de IDs). Fix: `parse_checkstyle` gana `base` y
80
- relativiza SIEMPRE para tools no-java (`_node_rel`), igual que
81
- eslint/tsc/clang-tidy; `golangci` también lo recibe. `_node_rel` dejó de
82
- depender de `os.path.isabs` (su veredicto para paths `/posix` en Windows
83
- cambió entre versiones de Python): intenta `relpath` y descarta si escapa
84
- del repo. Smokes T27/T28 ahora usan paths absolutos (el default real) y
85
- asserten IDs repo-relativos.
86
- - **Swift Testing era invisible**: `--xunit-output` escribe XCTest en
87
- `junit.xml` y Swift Testing en un SEGUNDO `junit-swift-testing.xml` que el
88
- counter no leía — un paquete Swift 6 (donde Swift Testing es el default)
89
- medía `tests=0` con `report_found=True` y un failure real no disparaba el
90
- veto "measured beats narrated": fail-open en la garantía central. Fix:
91
- `junit_test_count` gana `extra_files` (reportes full-run de sets DISJUNTOS
92
- que SÍ se suman) y el dispatch swift pasa ambos archivos. Smoke con failure
93
- real en el archivo swift-testing.
94
- - **detekt fuera del test command**: su default `maxIssues: 0` corta el build
95
- con UN finding — la corrida de tests leería roja aunque los tests pasen,
96
- mezclando el gate de lint (que tiene su canal propio) con el de tests.
97
- `test_command_gradle` queda `./gradlew test jacocoTestReport`.
98
- - **Source sets custom de Gradle**: `src/integrationTest/`, `src/functionalTest/`
99
- (cualquier `src/*Test`) ahora cuentan como test LOC, no prod.
100
- - README swift: variante Linux de `llvm-cov` (sin `xcrun`) + path del binario
101
- de tests documentados.
102
-
103
- ## Contrato de siempre
104
-
105
- Reporte ausente = el gate no corrió (jamás acredita fixes). Guard UNMEASURED:
106
- los 9 types linteables. Criterio pendiente por adapter: dry-run de solo lectura
107
- contra un repo real de cada lenguaje.
108
-
109
- ## Diferido consciente
110
-
111
- - rebuild: densidad de asserts. Perfiles A-E mecanizados. Android (Gradle +
112
- variantes) queda explícitamente FUERA de `type: gradle` hasta un repo real.