@orkastery/cli 0.6.0 → 0.6.1

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 (65) hide show
  1. package/adapters/openclaw/openclaw.plugin.json +1 -1
  2. package/adapters/openclaw/package.json +1 -1
  3. package/dist/adapters/claude-bg.js +6 -6
  4. package/dist/adapters/grok-events.js +227 -0
  5. package/dist/adapters/grok-mcp-servidor.js +612 -0
  6. package/dist/adapters/grok-mcp.js +178 -0
  7. package/dist/adapters/grok.js +686 -0
  8. package/dist/agendador-cpu.js +92 -0
  9. package/dist/branch-de-estado.js +7 -2
  10. package/dist/check-agil.js +48 -20
  11. package/dist/check-paralelo.js +73 -18
  12. package/dist/conducao.js +5 -0
  13. package/dist/docs.js +9 -16
  14. package/dist/doctor-forja.js +1 -3
  15. package/dist/doctor.js +1 -1
  16. package/dist/entrega-pr.js +10 -10
  17. package/dist/fabrica-estado.js +20 -11
  18. package/dist/horario.js +4 -1
  19. package/dist/index.js +20 -10
  20. package/dist/integracoes-locais.js +2 -0
  21. package/dist/locale-accounts.js +11 -3
  22. package/dist/locale-ajuda.js +10 -6
  23. package/dist/locale-forja.js +2 -4
  24. package/dist/locale-operacao-restante.js +2 -2
  25. package/dist/locale-retry.js +40 -2
  26. package/dist/locale-ship.js +10 -2
  27. package/dist/manifest.js +6 -1
  28. package/dist/mcp-install.js +22 -12
  29. package/dist/mcp-server.js +42 -16
  30. package/dist/merge-da-entrega.js +85 -0
  31. package/dist/network-roadmap.js +18 -14
  32. package/dist/noctum-aceite.js +154 -14
  33. package/dist/noctum-cli.js +69 -12
  34. package/dist/noctum-entrega.js +55 -7
  35. package/dist/noctum-envelope.js +1 -1
  36. package/dist/noctum-execucao.js +5 -1
  37. package/dist/noctum-fechamento.js +18 -7
  38. package/dist/noctum-fila.js +6 -1
  39. package/dist/noctum-guarda.js +81 -4
  40. package/dist/noctum-maquinas.js +5 -1
  41. package/dist/noctum-modo.js +35 -7
  42. package/dist/noctum-reconciliacao.js +4 -1
  43. package/dist/noctum-rede.js +102 -0
  44. package/dist/noctum-relatorio.js +44 -10
  45. package/dist/noctum-retomada-rede.js +71 -0
  46. package/dist/noctum-vigia.js +49 -9
  47. package/dist/parado-no-condutor.js +14 -15
  48. package/dist/phase.js +43 -15
  49. package/dist/postura-local.js +7 -3
  50. package/dist/preflight.js +2 -1
  51. package/dist/ratelimit.js +1 -0
  52. package/dist/retry.js +103 -10
  53. package/dist/runtime-context.js +165 -45
  54. package/dist/runtime-escada.js +7 -1
  55. package/dist/runtime-profiles.js +27 -17
  56. package/dist/runtimes.js +42 -5
  57. package/dist/security-scan/agil.js +18 -7
  58. package/dist/security-scan/executor.js +8 -0
  59. package/dist/session-watcher-grok.js +425 -0
  60. package/dist/session-watcher.js +19 -4
  61. package/dist/sessoes-contas.js +33 -5
  62. package/dist/setup.js +11 -11
  63. package/dist/varredura-acoes.js +8 -15
  64. package/dist/verify.js +26 -10
  65. package/package.json +2 -2
package/dist/setup.js CHANGED
@@ -118,8 +118,9 @@ function validarFallback(lista, principal) {
118
118
  const m = ENTRADA_DE_FALLBACK.exec(item.trim());
119
119
  if (!m)
120
120
  throw new Error((0, locale_1.msg)().setup.fallbackInvalido(item));
121
- if (!(0, runtimes_1.runtimeConhecido)(m[1]))
122
- throw new Error((0, locale_1.msg)().setup.fallbackDesconhecido(m[1], runtimes_1.ORDEM_DOS_RUNTIMES.join(', ')));
121
+ // RM-067 (F4b, G9): desde a F4 todo runtime do registro e de bloco; a recusa lista os que o fallback aceita.
122
+ if (!(0, runtimes_1.runtimeDeBloco)(m[1]))
123
+ throw new Error((0, locale_1.msg)().setup.fallbackDesconhecido(m[1], runtimes_1.RUNTIMES_DE_BLOCO.join(', ')));
123
124
  if (vistos.has(m[1]))
124
125
  throw new Error((0, locale_1.msg)().setup.fallbackRepetido(m[1]));
125
126
  vistos.add(m[1]);
@@ -134,7 +135,7 @@ function normalizarFallback(valor, principal) {
134
135
  const saida = [];
135
136
  for (const item of valor) {
136
137
  const m = typeof item === 'string' ? ENTRADA_DE_FALLBACK.exec(item) : null;
137
- if (!m || !(0, runtimes_1.runtimeConhecido)(m[1]) || vistos.has(m[1]))
138
+ if (!m || !(0, runtimes_1.runtimeDeBloco)(m[1]) || vistos.has(m[1]))
138
139
  continue;
139
140
  vistos.add(m[1]);
140
141
  saida.push(item);
@@ -177,7 +178,7 @@ function validarConfigComLimites(config) {
177
178
  if (!Object.hasOwn(config, 'limites'))
178
179
  return;
179
180
  validarLimitesDeBloco(config.limites);
180
- if (typeof config.runtime !== 'string' || !(0, runtimes_1.runtimeConhecido)(config.runtime) ||
181
+ if (typeof config.runtime !== 'string' || !(0, runtimes_1.runtimeDeBloco)(config.runtime) ||
181
182
  typeof config.model !== 'string' || config.model.trim() === '' ||
182
183
  typeof config.effort !== 'string' || config.effort.trim() === '') {
183
184
  throw new Error((0, locale_1.msg)().setup.blocoComLimites);
@@ -288,7 +289,7 @@ function lerSetup(raiz) {
288
289
  if (doArquivo[i] === undefined)
289
290
  return blocoPadraoDoModo(modo);
290
291
  const b = doArquivo[i];
291
- const runtime = typeof b.runtime === 'string' && (0, runtimes_1.runtimeConhecido)(b.runtime)
292
+ const runtime = typeof b.runtime === 'string' && (0, runtimes_1.runtimeDeBloco)(b.runtime)
292
293
  ? b.runtime
293
294
  : doModo.runtime;
294
295
  return {
@@ -529,11 +530,9 @@ function editarBloco(raiz, modo, bloco, edicao, por = 'owner') {
529
530
  erro: (0, locale_1.msg)().setup.blocoInexistente(bloco, def.tag, def.blocos.length),
530
531
  };
531
532
  }
532
- if (edicao.runtime !== undefined && !(0, runtimes_1.runtimeConhecido)(edicao.runtime)) {
533
- return {
534
- ...base,
535
- erro: (0, locale_1.msg)().setup.runtimeDesconhecido(edicao.runtime, runtimes_1.ORDEM_DOS_RUNTIMES.join(', ')),
536
- };
533
+ if (edicao.runtime !== undefined && !(0, runtimes_1.runtimeDeBloco)(edicao.runtime)) {
534
+ // RM-067 (F4b, G9): a recusa lista os runtimes que o bloco aceita, o grok entre eles desde a F4.
535
+ return { ...base, erro: (0, locale_1.msg)().setup.runtimeDesconhecido(edicao.runtime, runtimes_1.RUNTIMES_DE_BLOCO.join(', ')) };
537
536
  }
538
537
  const atual = setup.modos[modo].blocos[bloco - 1];
539
538
  if (edicao.runtime !== undefined && edicao.runtime !== atual.runtime && !edicao.model?.trim())
@@ -646,7 +645,8 @@ function textoDoSetup(raiz, modo) {
646
645
  saida.push(m.fallback(modo));
647
646
  const padrao = blocoPadraoDoModo(modo);
648
647
  saida.push(m.resetar(modo, `${padrao.runtime}/${padrao.model}/${padrao.effort}`));
649
- saida.push(m.runtimes(runtimes_1.ORDEM_DOS_RUNTIMES.join(', ')));
648
+ // RM-067 (F4b, G9): a tela lista os runtimes de bloco, os que o `--runtime` e o `--fallback` do setup aceitam.
649
+ saida.push(m.runtimes(runtimes_1.RUNTIMES_DE_BLOCO.join(', ')));
650
650
  saida.push('');
651
651
  saida.push(linhaDaOrigemDoSetup(raiz));
652
652
  return saida.join('\n');
@@ -69,6 +69,7 @@ const path = __importStar(require("node:path"));
69
69
  const autorizacao_duravel_1 = require("./autorizacao-duravel");
70
70
  const conducao_1 = require("./conducao");
71
71
  const entrega_pr_1 = require("./entrega-pr");
72
+ const merge_da_entrega_1 = require("./merge-da-entrega");
72
73
  const estado_thread_1 = require("./estado-thread");
73
74
  const ledger_1 = require("./ledger");
74
75
  const locale_1 = require("./locale");
@@ -181,21 +182,13 @@ function commitsDepois(raiz, t, sha) {
181
182
  * novo de cada thread, com o head do PR (o segundo pai) e o instante do commit. E a mesma busca do `ork ship
182
183
  * registrar-pr` (`mergeDaEntrega`).
183
184
  */
184
- function mergesDaBase(raiz, remoto, base) {
185
+ function mergesDaBase(raiz, remoto, base, threads) {
185
186
  const mapa = new Map();
186
- const r = (0, util_1.exec)('git', ['log', `refs/remotes/${remoto}/${base}`, '--first-parent', '--format=%H%x09%P%x09%cI%x09%s', '--grep=^ship(',
187
- '--'], raiz, 60000);
188
- if (!r.ok)
189
- return mapa;
190
- for (const linha of r.stdout.split('\n')) {
191
- const [sha, pais, em, assunto] = linha.split('\t');
192
- const m = /^ship\(([A-Za-z0-9._-]+)\)/.exec(assunto ?? '');
193
- if (!m || !sha || !SHA.test(sha) || mapa.has(m[1]))
194
- continue;
195
- const segundo = (pais ?? '').split(' ')[1] ?? null;
196
- const ms = Date.parse(em ?? '');
197
- mapa.set(m[1], { mergeSha: sha, headSha: segundo && SHA.test(segundo) ? segundo : null,
198
- em: Number.isFinite(ms) ? new Date(ms).toISOString() : null });
187
+ const reconhecidos = (0, merge_da_entrega_1.mergesDasEntregasNaBase)(raiz, `refs/remotes/${remoto}/${base}`, base, threads.map((t) => ({ thread: t.id, branch: (0, merge_da_entrega_1.branchRegistradaDaEntrega)(raiz, t.id) ?? (0, worktree_1.branchDaWorktree)(t) })));
188
+ for (const t of threads) {
189
+ const merge = reconhecidos.get(t.id)?.[0];
190
+ if (merge)
191
+ mapa.set(t.id, merge);
199
192
  }
200
193
  return mapa;
201
194
  }
@@ -229,7 +222,7 @@ function pendentesDeRegistrar(carregado, threads, quando, vivas) {
229
222
  const remoto = manifesto.fabrica.remoto, base = manifesto.worktree.base_branch;
230
223
  const saida = [];
231
224
  const abertas = threads.filter((t) => t.status !== 'fechada' && (0, worktree_1.branchDaWorktree)(t).startsWith('ork/'));
232
- const merges = abertas.length ? mergesDaBase(raiz, remoto, base)
225
+ const merges = abertas.length ? mergesDaBase(raiz, remoto, base, abertas)
233
226
  : new Map();
234
227
  for (const t of abertas) {
235
228
  const merge = merges.get(t.id);
package/dist/verify.js CHANGED
@@ -97,6 +97,7 @@ const policies_1 = require("./policies");
97
97
  const check_modo_1 = require("./check-modo");
98
98
  const check_agil_1 = require("./check-agil");
99
99
  const check_paralelo_1 = require("./check-paralelo");
100
+ const agendador_cpu_1 = require("./agendador-cpu");
100
101
  /** Teto de tempo de um comando de verificacao (build e suite completa cabem). */
101
102
  exports.TIMEOUT_VERIFY_MS = 10 * 60 * 1000;
102
103
  /** Ultimas linhas da saida real, o suficiente para servir de evidencia no ledger. */
@@ -121,7 +122,9 @@ exports.PREFIXO_BLOQUEADO_NO_VERIFY = 'ORK_HITL_';
121
122
  * RM-072 (S-b do CHECK 2): as variaveis de uma rodada do Agile. Cada rodada poe as suas onde precisa; herdadas de outra
122
123
  * rodada (o verify que roda dentro de um comando de outro verify), elas levariam pecas ao relatorio errado.
123
124
  */
124
- const VARIAVEIS_DA_RODADA = new Set([check_modo_1.ENV_RELATORIO_DO_CHECK, check_modo_1.ENV_VARREDURA_PARALELA_DO_CHECK]);
125
+ const VARIAVEIS_DA_RODADA = new Set([
126
+ check_modo_1.ENV_RELATORIO_DO_CHECK, check_modo_1.ENV_VARREDURA_PARALELA_DO_CHECK, agendador_cpu_1.ENV_CPUS_DA_LANE, agendador_cpu_1.ENV_CPUS_DOCKER,
127
+ ]);
125
128
  function ambienteDoVerify(base = process.env) {
126
129
  return Object.fromEntries(Object.entries(base).filter(([chave]) => !chave.startsWith(exports.PREFIXO_BLOQUEADO_NO_VERIFY)
127
130
  && !VARIAVEIS_DA_RODADA.has(chave)));
@@ -206,7 +209,9 @@ function resultadoDoProcesso(nome, comando, r, comGrupo, duracaoMs, tetoMs) {
206
209
  prazoMs: tetoMs,
207
210
  duracaoMs,
208
211
  // I-54 (D11): so nao rodou o que o sistema recusou lancar; estouro e sinal rodaram e acabaram.
209
- executado: !(r.error && NAO_LANCADO.has(r.error)),
212
+ // `spawnSync` pode devolver um erro tardio do sandbox junto de um status real (por exemplo EPERM com status 0):
213
+ // nesse caso o processo existiu e o codigo observado e o veredito. So status ausente (`code: -1`) prova que nao lancou.
214
+ executado: !(r.code === -1 && r.error && NAO_LANCADO.has(r.error)),
210
215
  };
211
216
  if (!r.ok) {
212
217
  const saida = r.stdout + (r.stderr ? '\n' + r.stderr : '');
@@ -407,16 +412,16 @@ function soAVarreduraEAsLanesComRelatorio(comRelatorio, semRelatorio) {
407
412
  * cada um com o prazo e o ambiente que o `executorDoManifesto` daria a ele (o do scan com o prazo interno), o steal medido
408
413
  * na janela do grupo e a conducao renovada com o maior prazo. Com executor injetado (MCP, testes), um por vez, por ele.
409
414
  */
410
- function executorDoGrupo(manifesto, ambienteDaRodada, instabilidade, leitor, conducao, injetado) {
415
+ function executorDoGrupo(manifesto, ambienteDaRodada, instabilidade, leitor, conducao, injetado, medicaoCpu) {
411
416
  if (injetado)
412
417
  return (itens, cwd) => itens.map((i) => injetado(i.nome, i.comando, cwd));
413
418
  const relogio = (0, instabilidade_1.testesDeRelogioVigentes)(instabilidade);
414
419
  // N5 do CHECK 3: no grupo, como em serie, so a varredura e as lanes recebem o relatorio da rodada.
415
420
  const { [check_modo_1.ENV_RELATORIO_DO_CHECK]: _relatorio, ...semRelatorio } = ambienteDaRodada;
416
- return (itens, cwd) => {
421
+ const executar = ((itens, cwd) => {
417
422
  const prazos = itens.map((i) => prazoDaExecucao(manifesto, i.nome, i.comando));
418
423
  const paraOAuxiliar = itens.map((i, k) => ({ nome: i.nome, comando: i.comando, cwd, prazoMs: prazos[k],
419
- ...(i.nice ? { nice: i.nice } : {}), ...(i.apos?.length ? { apos: i.apos } : {}),
424
+ ...(i.nice ? { nice: i.nice } : {}), ...(i.apos?.length ? { apos: i.apos } : {}), ...(i.papelCpu ? { papelCpu: i.papelCpu } : {}),
420
425
  ambiente: { ...(recebeORelatorio(i.nome) ? ambienteDaRodada : semRelatorio), ...(ehComandoDoScan(manifesto, i.nome, i.comando)
421
426
  // RM-072: ao lado das lanes, a varredura roda poucas ferramentas por vez, para o grupo nao passar da CPU.
422
427
  ? { ORK_SECURITY_SCAN_DEADLINE_MS: String(prazoInternoDoScan(prazos[k])),
@@ -424,7 +429,15 @@ function executorDoGrupo(manifesto, ambienteDaRodada, instabilidade, leitor, con
424
429
  // A conducao cobre o grupo inteiro: com a lane encadeada, a varredura e a lane somam.
425
430
  conducao.renovar((0, check_paralelo_1.esperaDoGrupo)(paraOAuxiliar));
426
431
  const janela = (0, steal_1.abrirJanela)(leitor);
427
- const processos = (0, check_paralelo_1.rodarEmParalelo)(paraOAuxiliar, ambienteDoVerify());
432
+ const processos = (0, check_paralelo_1.rodarEmParalelo)(paraOAuxiliar, ambienteDoVerify(), medicaoCpu ? { medicaoCpu } : {});
433
+ if (processos.agendamentoCpu) {
434
+ const p = processos.agendamentoCpu;
435
+ executar.pecas = [{ peca: 'agendador-cpu', estado: p.saturado ? 'fallback' : 'agile',
436
+ motivo: p.saturado
437
+ ? `${p.motivo}; hermetica com ${p.cpusHermetica}/${p.cpus} CPUs, varredura e integracao depois dela`
438
+ : `${p.cpusHermetica}/${p.cpus} CPUs na hermetica e ${p.cpusDaFatia} reservadas; conteineres com ${p.cpusPorContainer} CPU`,
439
+ ...(p.saturado ? { fallback: 'ordem do Classic para hermetica, varredura e integracao' } : {}) }];
440
+ }
428
441
  const stealPct = janela.fechar();
429
442
  return processos.map((p, k) => {
430
443
  const r = { ...resultadoDoProcesso(itens[k].nome, itens[k].comando, p, p.comGrupo, p.duracaoMs, prazos[k]), stealPct };
@@ -438,7 +451,9 @@ function executorDoGrupo(manifesto, ambienteDaRodada, instabilidade, leitor, con
438
451
  }
439
452
  return r;
440
453
  });
441
- };
454
+ });
455
+ executar.pecas = [];
456
+ return executar;
442
457
  }
443
458
  /**
444
459
  * RM-072 (D8): le o relatorio das pecas da rodada, grava a lista inteira de cada lane em
@@ -731,7 +746,7 @@ function verificarSobConducao(carregado, threadId, opcoes, conducao, canal, fila
731
746
  const comandos = opcoes.soClaims
732
747
  ? []
733
748
  : vigente
734
- ? (doAgile = (0, check_agil_1.comandosNoAgile)(manifesto, cwd, comandosDoManifesto(manifesto), executorDosComandos, executorDoGrupo(manifesto, ambienteDaRodada, instabilidade, leitor, conducao, opcoes.executor ? executor : undefined), vigente.guarda, vigente.preparo)).comandos
749
+ ? (doAgile = (0, check_agil_1.comandosNoAgile)(manifesto, cwd, comandosDoManifesto(manifesto), executorDosComandos, executorDoGrupo(manifesto, ambienteDaRodada, instabilidade, leitor, conducao, opcoes.executor ? executor : undefined, opcoes.medicaoCpuAgendador), vigente.guarda, vigente.preparo)).comandos
735
750
  : comandosDoManifesto(manifesto).map((c) => executor(c.nome, c.comando, cwd));
736
751
  if (doAgile)
737
752
  pecas.push(...doAgile.pecas);
@@ -859,12 +874,13 @@ function verificarSobConducao(carregado, threadId, opcoes, conducao, canal, fila
859
874
  ? `regressao em: ${regressoes.map((r) => r.nome).join(', ')}`
860
875
  : motivo === 'verify.timeout'
861
876
  ? `sem veredito por tempo (prazo estourado, ou teste com relogio sob steal acima de ${steal_1.LIMIAR_STEAL_PCT}%): ${[
862
- ...estouros.map((r) => r.nome),
877
+ ...estouros.map((r) => (0, check_agil_1.porQueDasLanes)(r) ? `${r.nome} (${(0, check_agil_1.porQueDasLanes)(r)})` : r.nome),
863
878
  ...claims.filter((c) => c.motivo === 'verify.timeout').map((c) => c.claim.id)
864
879
  ].join(', ')}`
865
880
  : motivo === 'verify.sem-veredito'
866
881
  ? [produtoAlterado ? 'o produto mudou entre o preparo e o fim da rodada' : '',
867
- ...naoExecutados.map((c) => `${c.nome} nao foi executado`),
882
+ // RM-074 (F4): no Agile, o `test` diz qual lane ficou sem veredito e por que.
883
+ ...naoExecutados.map((c) => (0, check_agil_1.porQueDasLanes)(c) ? `${c.nome} sem veredito (${(0, check_agil_1.porQueDasLanes)(c)})` : `${c.nome} nao foi executado`),
868
884
  ...claims.filter((c) => c.motivo === 'verify.sem-veredito').map((c) => `${c.claim.id}: ${c.detalhe}`)]
869
885
  .filter(Boolean).join('; ')
870
886
  : motivo === 'policy.violation'
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@orkastery/cli",
3
- "version": "0.6.0",
3
+ "version": "0.6.1",
4
4
  "description": "A software factory of AI agents that proves its work: parallel threads, verified results, and short decisions only when they matter.",
5
5
  "license": "MIT",
6
6
  "homepage": "https://github.com/orkastery/orkastery#readme",
@@ -73,7 +73,7 @@
73
73
  "markdownlint-cli2": "^0.22.1"
74
74
  },
75
75
  "dependencies": {
76
- "@modelcontextprotocol/sdk": "1.29.0",
76
+ "@modelcontextprotocol/sdk": "1.32.2",
77
77
  "decode-named-character-reference": "1.3.0",
78
78
  "micromark": "4.0.2",
79
79
  "micromark-extension-gfm-table": "2.1.1",