ostacky 0.8.7 → 0.9.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.md CHANGED
@@ -246,37 +246,37 @@ Tras instalar (`--scope local`), el proyecto queda así:
246
246
 
247
247
  ```json
248
248
  {
249
- "version": "0.8.7",
249
+ "version": "0.9.0",
250
250
  "lockedAt": "2025-01-01T00:00:00.000Z",
251
251
  "repo": "JaimeHoracio/Ostacky",
252
- "tag": "v0.8.7",
252
+ "tag": "v0.9.0",
253
253
  "agents": {
254
254
  "ostacky": {
255
- "version": "0.8.7",
255
+ "version": "0.9.0",
256
256
  "installedAt": "2025-01-01T00:00:00.000Z",
257
257
  "sha256": "abc123..."
258
258
  }
259
259
  },
260
260
  "commands": {
261
261
  "install-stack": {
262
- "version": "0.8.7",
262
+ "version": "0.9.0",
263
263
  "installedAt": "2025-01-01T00:00:00.000Z",
264
264
  "sha256": "def456..."
265
265
  },
266
266
  "opsx-sync": {
267
- "version": "0.8.7",
267
+ "version": "0.9.0",
268
268
  "installedAt": "2025-01-01T00:00:00.000Z",
269
269
  "sha256": "ghi789..."
270
270
  }
271
271
  },
272
272
  "skills": {
273
- "brainstorming": { "version": "0.8.7", ... },
274
- "execution-mode-evaluation": { "version": "0.8.7", ... },
275
- "openspec-propose": { "version": "0.8.7", ... }
273
+ "brainstorming": { "version": "0.9.0", ... },
274
+ "execution-mode-evaluation": { "version": "0.9.0", ... },
275
+ "openspec-propose": { "version": "0.9.0", ... }
276
276
  },
277
277
  "mcpServers": {
278
- "ostacky-controller": { "version": "0.8.7", ... },
279
- "openspec": { "version": "0.8.7", ... }
278
+ "ostacky-controller": { "version": "0.9.0", ... },
279
+ "openspec": { "version": "0.9.0", ... }
280
280
  }
281
281
  }
282
282
  ```
@@ -308,7 +308,7 @@ Es opcional y solo necesario si algo falló durante la instalación o si querés
308
308
  ## Seguridad
309
309
 
310
310
  - `opencode.jsonc` se versiona en el repo para compartir permisos y MCP de forma reproducible.
311
- - Las URLs de descarga usan **tags de GitHub** (ej. `v0.8.7`), nunca `main` — instalaciones reproducibles
311
+ - Las URLs de descarga usan **tags de GitHub** (ej. `v0.9.0`), nunca `main` — instalaciones reproducibles
312
312
  - Cada path de archivo descargado es validado para prevenir **path traversal**
313
313
  - Los archivos incluyen **checksum SHA-256** opcional; si el manifest lo define, el contenido se verifica antes de escribir
314
314
  - El cache local (`.opencode/cache/`) también valida integridad al servir archivos cacheados
@@ -324,7 +324,7 @@ Es opcional y solo necesario si algo falló durante la instalación o si querés
324
324
  - Variable `OSTACKY_SENSITIVE_PATTERNS` overridea los patrones por defecto (`**/.env*`, `**/.secrets/**`, `**/*.pem`, `**/*.key`, `**/.aws/**`, `**/.ssh/**`, `**/credentials.json`, `**/.npmrc`).
325
325
  - Ejemplo: `OSTACKY_SENSITIVE_PATTERNS="**/.env*,**/.secrets/**" bunx ostacky doctor` — `doctor` imprime el patrón efectivo.
326
326
  - Allowlist: `.env.example`, `.env.template`, `.env.sample` nunca se bloquean.
327
- - Fuente única: `src/security.ts` (`SENSITIVE_DEFAULT`, `isSensitive`, `BASH_SENSITIVE_RE`) — `ostacky-plugin.ts` importa de ahí (legacy `ostacky-guard.ts` eliminado, fusionado en el plugin). Ver `doctor` para verificar.
327
+ - Fuente única: `src/security.ts` (`SENSITIVE_DEFAULT`, `isSensitive`, `BASH_SENSITIVE_RE`) — mirrors generados en `assets/plugins/security.ts` y `assets/mcp/ostacky-controller/security.js` vía `bun run scripts/sync-controller-core.ts`; `ostacky-plugin.ts` importa de `./security.ts` (self-contained). Ver `doctor` para verificar.
328
328
 
329
329
  #### Aislamiento de worktrees (harness-prod-hardening)
330
330
 
@@ -365,7 +365,7 @@ CodeGraph está instalado en `.opencode/tools/codegraph/bin/codegraph` y se conf
365
365
  | `.opencode/tools/codegraph/bin/codegraph status` | Muestra estado del index y archivos pendientes |
366
366
  | `.opencode/tools/codegraph/bin/codegraph install --target opencode --location local --yes` | Configura CodeGraph para OpenCode y genera AGENTS.md |
367
367
 
368
- > **Windows:** si ves `Command failed: cmd.exe /d /c call ... codegraph.cmd init -i` durante `npx ostacky install`, es un _warning_ no fatal — el binario se instaló pero el índice no se pudo crear. Reintentá con `npx ostacky install-stack --scope local` o ejecutá manualmente `.opencode\tools\codegraph\bin\codegraph.exe init -i` (o `codegraph.cmd` si no hay `.exe`) dentro del proyecto. Desde v0.8.7 el instalador usa el patrón resiliente de Engram (strip 0 + búsqueda recursiva) y loguea `projectRoot|toolsDir` para diagnosticar scope.
368
+ > **Windows:** si ves `Command failed: cmd.exe /d /c call ... codegraph.cmd init -i` durante `npx ostacky install`, es un _warning_ no fatal — el binario se instaló pero el índice no se pudo crear. Reintentá con `npx ostacky install-stack --scope local` o ejecutá manualmente `.opencode\tools\codegraph\bin\codegraph.exe init -i` (o `codegraph.cmd` si no hay `.exe`) dentro del proyecto. Desde v0.9.0 el instalador usa el patrón resiliente de Engram (strip 0 + búsqueda recursiva) y loguea `projectRoot|toolsDir` para diagnosticar scope.
369
369
 
370
370
  ## Licencia
371
371
 
@@ -1,18 +1,18 @@
1
1
  ---
2
2
  description: Orquestador principal — rutea por nivel, orquesta CodeGraph + OpenSpec + Superpowers.
3
3
  mode: primary
4
- version: 0.8.7
4
+ version: 0.9.0
5
5
  ---
6
6
 
7
- Sos **Ostacky v0.8.7**, orquestás, no implementás. Interpretás, clasificás (0/0+1/1+), ruteás y coordinás.
7
+ Sos **Ostacky v0.9.0**, orquestás, no implementás. Interpretás, clasificás (0/0+1/1+), ruteás y coordinás.
8
8
 
9
- > **Versión:** `0.8.7` (sincronizada desde `package.json` vía `scripts/sync-version.ts`). Cuando te pregunten qué versión tenés, qué versión sos, o `¿qué versión tenés?` / `version` / `¿en qué versión estás?`, respondé exactamente: **"Ostacky v0.8.7"** (o `v0.8.7` si te piden solo el número). No inventes otra versión.
9
+ > **Versión:** `0.9.0` (sincronizada desde `package.json` vía `scripts/sync-version.ts`). Cuando te pregunten qué versión tenés, qué versión sos, o `¿qué versión tenés?` / `version` / `¿en qué versión estás?`, respondé exactamente: **"Ostacky v0.9.0"** (o `v0.9.0` si te piden solo el número). No inventes otra versión.
10
10
 
11
11
  ## Reglas innegociables
12
12
 
13
13
  1. **NUNCA te congeles.** Plan B antes de tool, no reintentes fallida.
14
14
  2. **CodeGraph primero.** Nunca `rg/grep` para código. `Grep` solo literales.
15
- 3. **El plugin hace cumplir PENDING.** Hard gate en `tool.execute.before`; no llames `check_*` manual.
15
+ 3. **El plugin hace cumplir PENDING.** Hard gate en `ctx.tool.hook("execute.before")`; no llames `check_*` manual.
16
16
  4. **No edites sin Read fresco.** Nunca cache de turno anterior.
17
17
  5. **Una pregunta por turno.** Natural, sin tool, STOP y esperar. Respuesta vinculante.
18
18
 
@@ -85,13 +85,13 @@ Router `brainstorming`↔`OpenSpec` por `level`/`estLines`/`fileCount`/`hasAPI`
85
85
 
86
86
  1. `skill(execution-mode-evaluation)` en memoria, reusa discovery.
87
87
  2. Mostrar análisis → `¿Procedo?` → `record_execution_analysis` → `consume_execution_decision`.
88
- 3. Por task: `Read` fresco → plugin valida edición in-process → `edit` → `complete_task`.
88
+ 3. Por task: `Read` fresco → plugin valida edición in-process → `edit` → `verifyTask` (genérico: `codegraph:<Symbol>` con `codegraph_codegraph_explore`, `file:<path> contiene <string>` con `Read`/`Grep`, `test:<cmd>` con `shell` acotado — según `— verificar:` de `tasks.md`) → solo si `verifyTask.ok` → `complete_task`. **NUNCA marques `complete_task` a ojo**; si `verifyTask` falla, reintentá el fix.
89
89
 
90
90
  ### 5. Sync y cierre
91
91
 
92
92
  1. Tests + review
93
93
  2. `saveSessionClose` → `mem_session_summary` + `set_handoff` paralelo
94
- 3. `verifyIntegrity` + `implementation_complete` + `sync_complete`
94
+ 3. `verifyIntegrity` → **si `pending.length > 0` NO llames `implementation_complete`**; lista explícita `Te faltan N tasks: [...]` y pide `complete_task`. Solo si `pending === 0` y `staleFiles === 0`, `implementation_complete` → `sync_complete`. **NUNCA llames `implementation_complete` automáticamente con pendientes** — espera a que el usuario complete o escriba literal `"confirmo forzar"` para `force:true` (queda auditado).
95
95
 
96
96
  ## Guardrails
97
97
 
@@ -99,4 +99,4 @@ Router `brainstorming`↔`OpenSpec` por `level`/`estLines`/`fileCount`/`hasAPI`
99
99
  - Una pregunta por turno, sin deadlock
100
100
  - Fase gate: en EXECUTING/SYNC no volver a DISCOVERY
101
101
  - Audit: log antes de gate + `mem_save` solo en gates
102
- - **Tasks son verificables, no instruccionales:** `tasks.md` SHALL describir `qué` + `cómo verificar` (`bun test`, `grep`, archivo entregado). Nunca SHALL contener instrucciones de comportamiento genéricas (`“sé cuidadoso”, “no inventes”`) — eso vive acá en § Principios y se inyecta automáticamente por tier (ver § Core tiered). Para `Level 0` trivial, tasks SHALL ser de 1 línea sin overhead de honestidad.
102
+ - **Tasks son verificables, no instruccionales (genérico):** `tasks.md` SHALL describir `qué` + `cómo verificar` con formato `— verificar: codegraph:<Symbol> | file:<path> contiene <string> | test:<cmd>` (ej: `— verificar: codegraph:CurrencyContext` o `— verificar: test: bun test tests/domains/settle.test.ts`). El controller parsea `taskVerifications` y `verifyTask` lo re-verifica con `CodeGraph`/`Read`/`test`; `complete_task` solo pasa si `verifyTask.ok`. Nunca SHALL contener instrucciones genéricas (`“sé cuidadoso”`) — eso vive acá. Para `Level 0` trivial, tasks SHALL ser de 1 línea sin overhead.
@@ -5,13 +5,13 @@ agent: build
5
5
 
6
6
  Instala el stack tecnológico de desarrollo para OpenCode. **IMPORTANTE:** las herramientas se instalan por separado (cada una con su propio CLI/comando). `npx ostacky install` solo instala el agente y commands de Ostacky en `.opencode/`. Este comando (`/install-stack`) es la guía de referencia para la instalación manual completa paso a paso.
7
7
 
8
- **Nota:** A partir de v0.8.7, `npx ostacky install` ya instala automáticamente el stack completo (CodeGraph, OpenSpec, Engram, MCPs bundleados) además del agente y skills. Este comando es útil para instalación manual, verificación, o cuando algo falló y necesita reinstalarse.
8
+ **Nota:** A partir de v0.9.0, `npx ostacky install` ya instala automáticamente el stack completo (CodeGraph, OpenSpec, Engram, MCPs bundleados) además del agente y skills. Este comando es útil para instalación manual, verificación, o cuando algo falló y necesita reinstalarse.
9
9
 
10
10
  **RESTRICCIÓN ABSOLUTA:** instalar ÚNICAMENTE para OpenCode. Está terminantemente prohibido crear o modificar archivos en `.claude/`, `.kiro/`, `.cursor/`, `.gemini/`, `.codex/`, `.antigravity/`, `.windsurf/` o cualquier otro directorio de plataformas externas.
11
11
 
12
12
  **Origen del set curado:** el set de 15 skills referenciado en `assets/agents/ostacky.md` está bundleado en `assets/skills/` dentro del paquete npm. La definición del set y su trazabilidad viven en `manifest.json` y `.opencode/ostacky-lock.json`.
13
13
 
14
- ## Scope de instalación — local vs global (desde v0.8.7)
14
+ ## Scope de instalación — local vs global (desde v0.9.0)
15
15
 
16
16
  `npx ostacky install` soporta `--scope local|global|auto` (también `--scope=...`):
17
17
 
@@ -67,10 +67,12 @@ Verifica que el MCP server esté configurado en `opencode.json` apuntando al bin
67
67
  ```json
68
68
  {
69
69
  "mcp": {
70
- "codegraph": {
71
- "type": "local",
72
- "command": [".opencode/tools/codegraph/bin/codegraph", "serve", "--mcp"],
73
- "enabled": true
70
+ "servers": {
71
+ "codegraph": {
72
+ "type": "local",
73
+ "command": [".opencode/tools/codegraph/bin/codegraph", "serve", "--mcp"],
74
+ "disabled": false
75
+ }
74
76
  }
75
77
  }
76
78
  }
@@ -99,10 +101,12 @@ El controller MCP se configura como server local en `opencode.json`. Si el contr
99
101
  ```json
100
102
  {
101
103
  "mcp": {
102
- "ostacky-controller": {
103
- "type": "local",
104
- "command": ["node", ".opencode/mcp/ostacky-controller/index.js"],
105
- "enabled": true
104
+ "servers": {
105
+ "ostacky-controller": {
106
+ "type": "local",
107
+ "command": ["node", ".opencode/mcp/ostacky-controller/index.js"],
108
+ "disabled": false
109
+ }
106
110
  }
107
111
  }
108
112
  }
@@ -197,7 +201,7 @@ Leé `opencode.json` (o `opencode.jsonc`) en la raíz del proyecto.
197
201
 
198
202
  **Eliminá** cualquier entrada `"plugin": ["superpowers@git+https://github.com/obra/superpowers.git"]` (y equivalentes). Las skills ya están provistas por el bundle local, no por el plugin.
199
203
 
200
- **Preservá** sin tocar el bloque `mcp.codegraph` configurado en el Paso 1.
204
+ **Preservá** sin tocar el bloque `mcp.servers.codegraph` configurado en el Paso 1.
201
205
 
202
206
  **Resultado final esperado** de `opencode.json` (o `opencode.jsonc`):
203
207
 
@@ -205,20 +209,22 @@ Leé `opencode.json` (o `opencode.jsonc`) en la raíz del proyecto.
205
209
  {
206
210
  "$schema": "https://opencode.ai/config.json",
207
211
  "mcp": {
208
- "codegraph": {
209
- "type": "local",
210
- "command": [".opencode/tools/codegraph/bin/codegraph", "serve", "--mcp"],
211
- "enabled": true
212
- },
213
- "engram": {
214
- "type": "local",
215
- "command": [".opencode/tools/engram/bin/engram", "mcp"],
216
- "enabled": true
217
- },
218
- "ostacky-controller": {
219
- "type": "local",
220
- "command": ["node", ".opencode/mcp/ostacky-controller/index.js"],
221
- "enabled": true
212
+ "servers": {
213
+ "codegraph": {
214
+ "type": "local",
215
+ "command": [".opencode/tools/codegraph/bin/codegraph", "serve", "--mcp"],
216
+ "disabled": false
217
+ },
218
+ "engram": {
219
+ "type": "local",
220
+ "command": [".opencode/tools/engram/bin/engram", "mcp"],
221
+ "disabled": false
222
+ },
223
+ "ostacky-controller": {
224
+ "type": "local",
225
+ "command": ["node", ".opencode/mcp/ostacky-controller/index.js"],
226
+ "disabled": false
227
+ }
222
228
  }
223
229
  }
224
230
  }
@@ -306,10 +312,12 @@ Verificá que `opencode.json` contenga la entrada MCP de Engram apuntando al bin
306
312
  ```json
307
313
  {
308
314
  "mcp": {
309
- "engram": {
310
- "type": "local",
311
- "command": [".opencode/tools/engram/bin/engram", "mcp"],
312
- "enabled": true
315
+ "servers": {
316
+ "engram": {
317
+ "type": "local",
318
+ "command": [".opencode/tools/engram/bin/engram", "mcp"],
319
+ "disabled": false
320
+ }
313
321
  }
314
322
  }
315
323
  }
@@ -50,7 +50,7 @@ Allowlist: `.env.example/.template/.sample` nunca bloquea. `extractPathsFromBash
50
50
 
51
51
  ## Enforcement (plugin)
52
52
 
53
- El plugin hace cumplir `PENDING` en `tool.execute.before`; `lastCheck={revision, result}` cachea ALLOW por revisión, revalida si cambia o >5 tools; `BLOCKED` nunca cacheado. Métricas `stateCheckCount` cuentan checks del plugin (no del LLM).
53
+ El plugin hace cumplir `PENDING` en `ctx.tool.hook("execute.before")`; `lastCheck={revision, result}` cachea ALLOW por revisión, revalida si cambia o >5 tools; `BLOCKED` nunca cacheado. Métricas `stateCheckCount` cuentan checks del plugin (no del LLM).
54
54
 
55
55
  ## Tiered Behaviour
56
56
 
@@ -64,14 +64,22 @@ Principio: **eficacia > recorte** — si recorte rompiera caché y saliera más
64
64
 
65
65
  ## Security single-source
66
66
 
67
- `src/security.ts` único origen de `SENSITIVE_DEFAULT`/`BASH_SENSITIVE_RE`/`isSensitive`/`extractPathsFromBash`; plugin y guard importan, no copian. `BASH_SENSITIVE_RE` arriba. `OSTACKY_SENSITIVE_PATTERNS` override.
67
+ `src/security.ts` único origen de `SENSITIVE_DEFAULT`/`BASH_SENSITIVE_RE`/`isSensitive`/`extractPathsFromBash` (import `node:crypto`); mirrors generados en `assets/plugins/security.ts` (solo Sensitive guard, sin crypto) y `assets/mcp/ostacky-controller/security.js` vía `bun run scripts/sync-controller-core.ts`. `ostacky-plugin.ts` importa de `./security.ts` self-contained (no `../../src`). `BASH_SENSITIVE_RE` arriba. `OSTACKY_SENSITIVE_PATTERNS` override.
68
68
 
69
69
  ## Tiered single-source
70
70
 
71
- `src/tiered.ts` único origen de `isTrivial(msg,state)` + `getControllerState(dir)`. Ambos plugins importan lógica idéntica, no duplican regex. Ver `assets/plugins/ostacky-plugin.ts` y `assets/plugins/engram.ts`.
71
+ `src/tiered.ts` único origen de `isTrivial(msg,state)` + `getControllerState(dir)`. `ostacky-plugin.ts` importa de `./tiered.ts` mirror (generado vía `sync-controller-core.ts`), `engram.ts` inlined (misma regex, evita import dinámico). No duplicar regex. Ver `assets/plugins/ostacky-plugin.ts` y `assets/plugins/engram.ts`.
72
+
73
+ ## Controller single-source
74
+
75
+ `src/controller-core.ts` CANÓNICO para `STATES/TRANSITIONS/DEFAULT_STATE`; mirrors generados en `assets/plugins/controller-core.ts` (TS) y `assets/mcp/ostacky-controller/controller-core.js` (JS strippado) vía `bun run scripts/sync-controller-core.ts` (prebuild). No editar mirrors. `ostacky-plugin.ts` importa de `./controller-core.ts` self-contained.
72
76
 
73
77
  ## Prompt-efficiency
74
78
 
75
79
  - `ostacky.md` 109→72 líneas (diet estable cacheable). Tiered vía suffix, no reemplazo `system[0]`.
76
80
  - `controller` descriptions <150 chars
77
81
  - `MEMORY_INSTRUCTIONS` lazy: siempre pointer (~1 línea) en `system.transform`; full vive en `assets/docs/engram-protocol.md` on-demand via `Read` (ahorro ~1.2k en FULL, trivial ya era pointer)
82
+
83
+ ## Propose Flow (1+)
84
+
85
+ `openspec-propose` SHALL Paso 0: `getDiscoverySnapshot(query)` + `getEngramDedup` → si miss `codegraph_codegraph_explore` + `engram_mem_search` + `putDiscoverySnapshot` **antes** de `openspec new`. Cita símbolos existentes en `proposal/design`; sin esto dispara `WARN:codegraphBypass` y `design.md` alucina API. Ver `assets/skills/openspec-propose/SKILL.md: Paso 0` y `brainstorming` (router por nivel: `brainstorming` decide 0/0+1/1+, `openspec-explore` es stance sin nivel).
@@ -1,7 +1,6 @@
1
1
  /**
2
2
  * controller-core — Single source of truth para TRANSITIONS, STATES, DEFAULT_STATE y helpers.
3
- * Extraído de assets/mcp/ostacky-controller/index.js y assets/plugins/ostacky-plugin.ts
4
- * para eliminar duplicación (D1). Ambos importan de acá.
3
+ * Generado desde src/controller-core.ts — NO EDITAR. Ejecutá `bun run scripts/sync-controller-core.ts`.
5
4
  */
6
5
 
7
6
  import { SENSITIVE_DEFAULT } from "./security.js";
@@ -111,6 +110,8 @@ export const DEFAULT_STATE = {
111
110
  lastHandoff: null,
112
111
  expectedTasks: null,
113
112
  expectedTaskCount: null,
113
+ taskVerifications: null,
114
+ taskVerificationResults: {},
114
115
  auditSeq: 0,
115
116
  degraded: false,
116
117
  schemaVersion: 2,
@@ -142,6 +143,7 @@ export const DEFAULT_STATE = {
142
143
  watchdogEnabled: true,
143
144
  ts: Date.now(),
144
145
  specNotInSync: false,
146
+ engramBypassCount: 0,
145
147
  };
146
148
 
147
149
  export function safeJsonStringify(obj, pretty = false) {