iron-edge 2.3.2 → 2.4.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
@@ -213,6 +213,31 @@ npx iron-edge verify
213
213
 
214
214
  ---
215
215
 
216
+ ## Iron Office
217
+
218
+ Converse com o Iron pelo dashboard ([iron-office.vercel.app](https://iron-office.vercel.app)) e veja os agentes trabalhando no feed e no mapa 3D.
219
+
220
+ ```bash
221
+ npx iron-edge office
222
+ ```
223
+
224
+ Antes, faça o **passo 4** do onboarding do Iron Office (ele salva a sua chave em `~/.claude/iron-office-api-key`).
225
+
226
+ O que esperar:
227
+
228
+ 1. O comando instala (ou atualiza) o plugin de canal `iron-office` e abre o Claude Code com ele ligado.
229
+ 2. O Claude Code mostra um **aviso de tela cheia**: canais ainda são recurso em teste. Aceite.
230
+ 3. Abra a página **Iron** do dashboard. Em até 1 minuto aparece "Iron online". Escreva ali e o Iron responde ali.
231
+ 4. **Deixe essa aba do terminal aberta.** É ela que faz o Iron responder no site.
232
+
233
+ Por padrão a sessão do `office` roda **sem pedir licença** a cada ferramenta (é o que deixa o Iron trabalhar enquanto você está só no site). `npx iron-edge office --safe` abre pedindo licença a cada ferramenta. Qualquer outro argumento vai direto pro `claude`.
234
+
235
+ Mensagem escrita no site com o terminal fechado espera até 15 minutos; depois disso expira e o chat avisa pra mandar de novo (ordem velha não é executada sem você ver).
236
+
237
+ O plugin também manda a atividade das sessões pro seu painel: veja o que sai em "Sobre o que sai da sua máquina", mais abaixo.
238
+
239
+ ---
240
+
216
241
  ## Requisitos
217
242
 
218
243
  - **Node.js** 18 ou superior
@@ -230,12 +255,14 @@ O Iron Edge instala uma equipe de agentes especializados diretamente no Claude C
230
255
 
231
256
  Seus dados ficam locais em `~/.iron/`. Sobre o que sai da sua máquina, com precisão:
232
257
 
233
- - **Para o Iron Office** (`iron-office.vercel.app`, servidor deste projeto) vão dados de apenas **2 agentes**: `iron-auditor` e `iron-shopify`. E só se você criar a chave em `~/.claude/iron-office-api-key`. Confira você mesmo: `grep -rln "iron-office" ~/.claude/agents/`.
258
+ - **Para o Iron Office** (`iron-office.vercel.app`, servidor deste projeto), e só se você criar a chave em `~/.claude/iron-office-api-key`:
259
+ - dados de apenas **2 agentes**, `iron-auditor` e `iron-shopify`. Confira: `grep -rln "iron-office" ~/.claude/agents/`;
260
+ - **se você rodou `npx iron-edge office`**, o plugin `iron-office` fica instalado e manda a atividade de **toda sessão** do Claude Code pro seu painel (feed e mapa 3D): nome da ferramenta, caminho do arquivo (nunca o conteúdo), os primeiros 200 caracteres de cada comando de terminal e a descrição dele, buscas, o domínio dos endereços visitados, nome e descrição dos agentes, a pasta e o identificador da sessão. A resposta das ferramentas nunca sai. Padrões conhecidos de segredo nesses campos (chaves de Stripe, Shopify, Meta, GitHub, OpenAI, Supabase e AWS, `Bearer`, `ALGO_KEY=`, `--password`, `-u usuario:senha`…) são apagados antes do envio; é uma lista de padrões, não garantia. Lista completa no README do plugin (github.com/filipecoff21-code/iron-office-channel). Desligar: `claude plugin disable iron-office@iron-office-channel`. Conferir se está ligado: `claude plugin list`.
234
261
  - **Para a internet aberta**, através das ferramentas do próprio Claude Code (`WebSearch` / `WebFetch`), vão as buscas de **41 dos 44 agentes** — é como o `iron-research` pesquisa mercado e o `iron-spy` lê a biblioteca de anúncios. Isso passa pelo Claude Code, com a visibilidade e a aprovação que ele te dá; não é canal deste pacote. Confira: `grep -rln "WebSearch\|WebFetch" ~/.claude/agents/`.
235
262
  - **A skill `clone-site`** baixa a URL que você mandar clonar. É o trabalho dela.
236
263
 
237
264
 
238
- Sendo exato sobre a força dessa garantia, porque ela não é um sandbox: cada bloco que chama o Iron Office começa com uma guarda (`[ -z "$IRON_KEY" ] && exit 0`) e a regra R20 do lint impede que qualquer bloco novo entre sem ela. Mas esses arquivos são **instruções lidas por um modelo**, não um binário fechado: um agente que execute só a linha do `curl`, isolada da guarda, não é barrado por nada aqui. Se o que você quer é garantia dura, a que existe é não criar o arquivo de chave — sem ele, não há para onde enviar, e todo bloco para na guarda.
265
+ Sendo exato sobre a força dessa garantia, porque ela não é um sandbox: cada bloco que chama o Iron Office começa com uma guarda (`[ -z "$IRON_KEY" ] && exit 0`) e a regra R20 do lint impede que qualquer bloco novo entre sem ela. Mas esses arquivos são **instruções lidas por um modelo**, não um binário fechado: um agente que execute só a linha do `curl`, isolada da guarda, não é barrado por nada aqui. Se o que você quer é garantia dura, a que existe é não criar o arquivo de chave — sem ele, não há para onde enviar, e todo bloco para na guarda (o plugin `iron-office` também: sem a chave, ele não envia nada).
239
266
 
240
267
  ---
241
268
 
package/bin/iron-edge.js CHANGED
@@ -14,6 +14,9 @@
14
14
  * arquivos cujo hash bate com o manifesto — os que
15
15
  * ninguem alterou — e preserva o resto
16
16
  *
17
+ * office [--safe] liga o Iron Office: instala o plugin de canal e abre o
18
+ * Claude Code conversando com o chat do dashboard
19
+ *
17
20
  * Nao existe 'uninstall' automatico: remover continua sendo operacao conduzida, com o
18
21
  * manifesto na mao (o README descreve o procedimento).
19
22
  */
@@ -147,7 +150,12 @@ if (cmd === 'install') {
147
150
  // Reprovam so' divergencia sem registro e arquivo sumido.
148
151
  process.exit(alterados.length + sumidos.length === 0 ? 0 : 1);
149
152
 
153
+ } else if (cmd === 'office') {
154
+ // liga o chat do dashboard (iron-office.vercel.app/chat) na sessao do Claude Code
155
+ const r = spawnSync(process.execPath, [path.join(__dirname, '..', 'installer', 'office.js'), ...rest], { stdio: 'inherit' });
156
+ process.exit(r.status ?? 1);
157
+
150
158
  } else {
151
- console.log('uso: iron-edge <install|update|verify> [--dry-run] [--source <dir>]');
152
- process.exit(cmd ? 1 : 0);
159
+ console.log('uso: iron-edge <install|update|verify|office> [--dry-run] [--source <dir>] [--safe]');
160
+ process.exit(cmd && cmd !== '--help' && cmd !== '-h' ? 1 : 0);
153
161
  }
@@ -0,0 +1,123 @@
1
+ #!/usr/bin/env node
2
+ /**
3
+ * office.js — `npx iron-edge office`: liga o Iron Office (chat do dashboard) no Claude Code.
4
+ *
5
+ * Passos: (1) confere a chave do Iron Office, (2) confere o Claude Code, (3) instala ou
6
+ * atualiza o plugin de canal `iron-office` pelo marketplace do GitHub, (4) abre o Claude Code
7
+ * com o canal ligado. O aluno deixa essa aba aberta: e' ela que faz o Iron responder no site.
8
+ *
9
+ * Flags: --safe tira o `--permission-mode bypassPermissions` (o Claude pede licenca a cada
10
+ * ferramenta). Qualquer outro argumento vai direto pro `claude`.
11
+ *
12
+ * Saida so' em ASCII, como o resto do instalador: console do Windows antigo mostra lixo em
13
+ * acento e simbolo. O `claude` recebe IRON_OFFICE_CHANNEL=1 no ambiente: e' o que diz ao
14
+ * servidor do plugin que ESTA sessao e' o canal (uma aba comum do Claude Code nao puxa o chat).
15
+ */
16
+ const fs = require('fs');
17
+ const path = require('path');
18
+ const os = require('os');
19
+ const { spawnSync } = require('child_process');
20
+
21
+ const MARKETPLACE_REPO = 'filipecoff21-code/iron-office-channel';
22
+ const PLUGIN = 'iron-office@iron-office-channel';
23
+ const CHANNEL = 'plugin:' + PLUGIN;
24
+ const ONBOARDING = 'https://iron-office.vercel.app/onboarding';
25
+ const IS_WIN = process.platform === 'win32';
26
+
27
+ function keyPath(home) {
28
+ return path.join(home || os.homedir(), '.claude', 'iron-office-api-key');
29
+ }
30
+
31
+ // O `echo` do passo 4 no Windows pode gravar UTF-16 com BOM: normaliza antes de decidir.
32
+ function readKey(home) {
33
+ try {
34
+ const buf = fs.readFileSync(keyPath(home));
35
+ const utf16 = buf.length >= 2 && buf[0] === 0xff && buf[1] === 0xfe;
36
+ return buf.toString(utf16 ? 'utf16le' : 'utf8').replace(/[\uFEFF\u0000]/g, '').trim();
37
+ } catch (_) { return ''; }
38
+ }
39
+
40
+ // Argumentos do `claude` que abre a sessao com o canal. Separado pra ser testado sem rede.
41
+ function buildClaudeArgs(argv) {
42
+ const safe = argv.includes('--safe');
43
+ const extra = argv.filter(a => a !== '--safe');
44
+ const args = ['--dangerously-load-development-channels', CHANNEL];
45
+ if (!safe) args.push('--permission-mode', 'bypassPermissions');
46
+ return args.concat(extra);
47
+ }
48
+
49
+ function run(bin, args, opts) {
50
+ return spawnSync(bin, args, { encoding: 'utf8', shell: IS_WIN, ...opts });
51
+ }
52
+
53
+ // No Windows o `claude` instalado pelo npm e' um `claude.cmd`; com shell ele costuma resolver,
54
+ // mas ha PATH em que so' o nome com extensao funciona.
55
+ function resolveClaude() {
56
+ const candidates = IS_WIN ? ['claude', 'claude.cmd'] : ['claude'];
57
+ for (const bin of candidates) {
58
+ const r = run(bin, ['--version']);
59
+ if (!r.error && r.status === 0) return bin;
60
+ }
61
+ return null;
62
+ }
63
+
64
+ function step(claude, label, args, okPatterns) {
65
+ const r = run(claude, args);
66
+ const out = ((r.stdout || '') + (r.stderr || '')).trim();
67
+ if (r.status === 0) { console.log(' [ok] ' + label); return true; }
68
+ if (okPatterns.some(p => p.test(out))) { console.log(' [ok] ' + label + ' (ja estava)'); return true; }
69
+ console.log(' [falhou] ' + label + ': ' + (out.split('\n').pop() || 'sem detalhe'));
70
+ return false;
71
+ }
72
+
73
+ function main(argv) {
74
+ if (!readKey()) {
75
+ console.error('Falta a chave do Iron Office. Faca o passo 4 em ' + ONBOARDING);
76
+ return 1;
77
+ }
78
+
79
+ const claude = resolveClaude();
80
+ if (!claude) {
81
+ console.error('Instale o Claude Code primeiro: https://claude.com/claude-code');
82
+ return 1;
83
+ }
84
+
85
+ console.log('Iron Office - preparando o canal');
86
+ const okMarket = step(claude, 'marketplace ' + MARKETPLACE_REPO, ['plugin', 'marketplace', 'add', MARKETPLACE_REPO], [/already/i]);
87
+ const okPlugin = okMarket && step(claude, 'plugin ' + PLUGIN, ['plugin', 'install', PLUGIN, '--scope', 'user'], [/already/i]);
88
+ if (!okMarket || !okPlugin) {
89
+ console.error('');
90
+ console.error('Nao deu pra instalar o plugin do Iron Office. Confira:');
91
+ console.error(' 1. a internet esta funcionando;');
92
+ console.error(' 2. o git esta instalado (rode: git --version);');
93
+ console.error(' 3. rode de novo: npx iron-edge office');
94
+ console.error('Se continuar, mande um print desta tela pro suporte.');
95
+ return 1;
96
+ }
97
+ // atualizar e' melhor-esforco: sem internet no meio, segue com a versao ja instalada
98
+ step(claude, 'atualizacao do plugin', ['plugin', 'update', PLUGIN], [/already|up.to.date|latest/i]);
99
+
100
+ const safe = argv.includes('--safe');
101
+ console.log('');
102
+ console.log('Abrindo o Claude Code com o Iron Office ligado.');
103
+ console.log('Vai aparecer um aviso de canal (recurso em teste): aceite.');
104
+ if (!safe) {
105
+ console.log('O Iron vai agir SEM pedir licenca a cada passo (e o que deixa ele trabalhar');
106
+ console.log('enquanto voce esta no site). Quer aprovar cada passo? Rode: npx iron-edge office --safe');
107
+ }
108
+ console.log('Deixe esta aba aberta: e ela que faz o Iron responder no site.');
109
+ console.log('');
110
+
111
+ const r = spawnSync(claude, buildClaudeArgs(argv), {
112
+ stdio: 'inherit',
113
+ shell: IS_WIN,
114
+ env: { ...process.env, IRON_OFFICE_CHANNEL: '1' },
115
+ });
116
+ return r.status ?? 1;
117
+ }
118
+
119
+ module.exports = { buildClaudeArgs, keyPath, readKey, CHANNEL, PLUGIN, MARKETPLACE_REPO };
120
+
121
+ if (require.main === module) {
122
+ process.exit(main(process.argv.slice(2)));
123
+ }
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "iron-edge",
3
- "version": "2.3.2",
4
- "description": "Ecossistema de agentes para Claude Code: 44 agentes de topo, 18 squads e 14 skills, com quality gate, memoria e instalador que nunca sobrescreve.",
3
+ "version": "2.4.0",
4
+ "description": "Ecossistema de agentes para Claude Code: 44 agentes de topo, 18 squads e 14 skills, com quality gate, memoria, instalador que nunca sobrescreve e o comando office (chat do Iron Office no dashboard).",
5
5
  "keywords": [
6
6
  "claude",
7
7
  "claude-code",
@@ -32,7 +32,7 @@
32
32
  "node": ">=18.0.0"
33
33
  },
34
34
  "scripts": {
35
- "test": "node scripts/lint.js && node scripts/test-verify.js && node scripts/test-update.js",
35
+ "test": "node scripts/lint.js && node scripts/test-verify.js && node scripts/test-update.js && node scripts/test-office.js",
36
36
  "test:matriz": "node scripts/test-matriz-update.js"
37
37
  },
38
38
  "devDependencies": {