sincron-plan 1.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/bin/install.js ADDED
@@ -0,0 +1,423 @@
1
+ #!/usr/bin/env node
2
+
3
+ const fs = require('fs');
4
+ const path = require('path');
5
+ const os = require('os');
6
+ const readline = require('readline');
7
+
8
+ // Colors
9
+ const cyan = '\x1b[36m';
10
+ const green = '\x1b[32m';
11
+ const yellow = '\x1b[33m';
12
+ const dim = '\x1b[2m';
13
+ const reset = '\x1b[0m';
14
+
15
+ // Get version from package.json
16
+ const pkg = require('../package.json');
17
+
18
+ // Parse args
19
+ const args = process.argv.slice(2);
20
+ const hasGlobal = args.includes('--global') || args.includes('-g');
21
+ const hasLocal = args.includes('--local') || args.includes('-l');
22
+ const hasUninstall = args.includes('--uninstall') || args.includes('-u');
23
+ const hasHelp = args.includes('--help') || args.includes('-h');
24
+
25
+ // Parse --config-dir argument
26
+ function parseConfigDirArg() {
27
+ const configDirIndex = args.findIndex(arg => arg === '--config-dir' || arg === '-c');
28
+ if (configDirIndex !== -1) {
29
+ const nextArg = args[configDirIndex + 1];
30
+ if (!nextArg || nextArg.startsWith('-')) {
31
+ console.error(` ${yellow}--config-dir requires a path argument${reset}`);
32
+ process.exit(1);
33
+ }
34
+ return nextArg;
35
+ }
36
+ const configDirArg = args.find(arg => arg.startsWith('--config-dir=') || arg.startsWith('-c='));
37
+ if (configDirArg) {
38
+ const value = configDirArg.split('=')[1];
39
+ if (!value) {
40
+ console.error(` ${yellow}--config-dir requires a non-empty path${reset}`);
41
+ process.exit(1);
42
+ }
43
+ return value;
44
+ }
45
+ return null;
46
+ }
47
+ const explicitConfigDir = parseConfigDirArg();
48
+
49
+ const banner = `
50
+ ${cyan} ███████╗ ██╗ ███╗ ██╗ ██████╗ ██████╗ ██████╗ ███╗ ██╗
51
+ ██╔════╝ ██║ ████╗ ██║ ██╔════╝ ██╔══██╗ ██╔═══██╗ ████╗ ██║
52
+ ███████╗ ██║ ██╔██╗ ██║ ██║ ██████╔╝ ██║ ██║ ██╔██╗ ██║
53
+ ╚════██║ ██║ ██║╚██╗██║ ██║ ██╔══██╗ ██║ ██║ ██║╚██╗██║
54
+ ███████║ ██║ ██║ ╚████║ ╚██████╗ ██║ ██║ ╚██████╔╝ ██║ ╚████║
55
+ ╚══════╝ ╚═╝ ╚═╝ ╚═══╝ ╚═════╝ ╚═╝ ╚═╝ ╚═════╝ ╚═╝ ╚═══╝${reset}
56
+
57
+ ${green}Sincron-Plan${reset} ${dim}v${pkg.version}${reset}
58
+ Plugin de planejamento estruturado para Claude Code.
59
+ Do requisito ao PRD, com questionamento inteligente.
60
+ `;
61
+
62
+ console.log(banner);
63
+
64
+ // Show help if requested
65
+ if (hasHelp) {
66
+ console.log(` ${yellow}Uso:${reset} npx sincron-plan [opções]
67
+
68
+ ${yellow}Opções:${reset}
69
+ ${cyan}-g, --global${reset} Instalar globalmente (~/.claude)
70
+ ${cyan}-l, --local${reset} Instalar localmente (./.claude)
71
+ ${cyan}-u, --uninstall${reset} Desinstalar Sincron-Plan
72
+ ${cyan}-c, --config-dir <path>${reset} Especificar diretório de config
73
+ ${cyan}-h, --help${reset} Mostrar esta ajuda
74
+
75
+ ${yellow}Exemplos:${reset}
76
+ ${dim}# Instalação interativa${reset}
77
+ npx sincron-plan
78
+
79
+ ${dim}# Instalar globalmente${reset}
80
+ npx sincron-plan --global
81
+
82
+ ${dim}# Instalar apenas no projeto atual${reset}
83
+ npx sincron-plan --local
84
+
85
+ ${dim}# Desinstalar globalmente${reset}
86
+ npx sincron-plan --global --uninstall
87
+
88
+ ${yellow}Comandos disponíveis após instalação:${reset}
89
+ ${cyan}/sincron-plan${reset} [descrição] - Planejamento estruturado com PRD
90
+ ${cyan}/sincron-map${reset} - Mapear codebase existente
91
+ `);
92
+ process.exit(0);
93
+ }
94
+
95
+ /**
96
+ * Expand ~ to home directory
97
+ */
98
+ function expandTilde(filePath) {
99
+ if (filePath && filePath.startsWith('~/')) {
100
+ return path.join(os.homedir(), filePath.slice(2));
101
+ }
102
+ return filePath;
103
+ }
104
+
105
+ /**
106
+ * Get the global config directory for Claude Code
107
+ */
108
+ function getGlobalDir(explicitDir = null) {
109
+ if (explicitDir) {
110
+ return expandTilde(explicitDir);
111
+ }
112
+ if (process.env.CLAUDE_CONFIG_DIR) {
113
+ return expandTilde(process.env.CLAUDE_CONFIG_DIR);
114
+ }
115
+ return path.join(os.homedir(), '.claude');
116
+ }
117
+
118
+ /**
119
+ * Read and parse settings.json
120
+ */
121
+ function readSettings(settingsPath) {
122
+ if (fs.existsSync(settingsPath)) {
123
+ try {
124
+ return JSON.parse(fs.readFileSync(settingsPath, 'utf8'));
125
+ } catch (e) {
126
+ return {};
127
+ }
128
+ }
129
+ return {};
130
+ }
131
+
132
+ /**
133
+ * Write settings.json with proper formatting
134
+ */
135
+ function writeSettings(settingsPath, settings) {
136
+ fs.writeFileSync(settingsPath, JSON.stringify(settings, null, 2) + '\n');
137
+ }
138
+
139
+ /**
140
+ * Recursively copy directory, replacing paths in .md files
141
+ */
142
+ function copyWithPathReplacement(srcDir, destDir, pathPrefix) {
143
+ if (fs.existsSync(destDir)) {
144
+ fs.rmSync(destDir, { recursive: true });
145
+ }
146
+ fs.mkdirSync(destDir, { recursive: true });
147
+
148
+ const entries = fs.readdirSync(srcDir, { withFileTypes: true });
149
+
150
+ for (const entry of entries) {
151
+ const srcPath = path.join(srcDir, entry.name);
152
+ const destPath = path.join(destDir, entry.name);
153
+
154
+ if (entry.isDirectory()) {
155
+ copyWithPathReplacement(srcPath, destPath, pathPrefix);
156
+ } else if (entry.name.endsWith('.md')) {
157
+ let content = fs.readFileSync(srcPath, 'utf8');
158
+ content = content.replace(/~\/\.claude\//g, pathPrefix);
159
+ fs.writeFileSync(destPath, content);
160
+ } else {
161
+ fs.copyFileSync(srcPath, destPath);
162
+ }
163
+ }
164
+ }
165
+
166
+ /**
167
+ * Verify a directory exists and contains files
168
+ */
169
+ function verifyInstalled(dirPath, description) {
170
+ if (!fs.existsSync(dirPath)) {
171
+ console.error(` ${yellow}✗${reset} Falha ao instalar ${description}: diretório não criado`);
172
+ return false;
173
+ }
174
+ try {
175
+ const entries = fs.readdirSync(dirPath);
176
+ if (entries.length === 0) {
177
+ console.error(` ${yellow}✗${reset} Falha ao instalar ${description}: diretório vazio`);
178
+ return false;
179
+ }
180
+ } catch (e) {
181
+ console.error(` ${yellow}✗${reset} Falha ao instalar ${description}: ${e.message}`);
182
+ return false;
183
+ }
184
+ return true;
185
+ }
186
+
187
+ /**
188
+ * Uninstall Sincron-Plan from the specified directory
189
+ */
190
+ function uninstall(isGlobal) {
191
+ const targetDir = isGlobal
192
+ ? getGlobalDir(explicitConfigDir)
193
+ : path.join(process.cwd(), '.claude');
194
+
195
+ const locationLabel = isGlobal
196
+ ? targetDir.replace(os.homedir(), '~')
197
+ : targetDir.replace(process.cwd(), '.');
198
+
199
+ console.log(` Desinstalando Sincron-Plan de ${cyan}${locationLabel}${reset}\n`);
200
+
201
+ if (!fs.existsSync(targetDir)) {
202
+ console.log(` ${yellow}⚠${reset} Diretório não existe: ${locationLabel}`);
203
+ console.log(` Nada para desinstalar.\n`);
204
+ return;
205
+ }
206
+
207
+ let removedCount = 0;
208
+
209
+ // 1. Remove sincron-plan commands
210
+ const commandsToRemove = ['sincron-plan.md', 'sincron-map.md'];
211
+ const commandsDir = path.join(targetDir, 'commands');
212
+ if (fs.existsSync(commandsDir)) {
213
+ for (const cmd of commandsToRemove) {
214
+ const cmdPath = path.join(commandsDir, cmd);
215
+ if (fs.existsSync(cmdPath)) {
216
+ fs.unlinkSync(cmdPath);
217
+ removedCount++;
218
+ }
219
+ }
220
+ if (removedCount > 0) {
221
+ console.log(` ${green}✓${reset} Removidos ${removedCount} comandos`);
222
+ }
223
+ }
224
+
225
+ // 2. Remove sincron-plan agents
226
+ const agentsDir = path.join(targetDir, 'agents');
227
+ if (fs.existsSync(agentsDir)) {
228
+ const agentsToRemove = ['questionador.md', 'pesquisador.md', 'mapeador.md', 'planejador.md'];
229
+ let agentCount = 0;
230
+ for (const agent of agentsToRemove) {
231
+ const agentPath = path.join(agentsDir, agent);
232
+ if (fs.existsSync(agentPath)) {
233
+ fs.unlinkSync(agentPath);
234
+ agentCount++;
235
+ }
236
+ }
237
+ if (agentCount > 0) {
238
+ removedCount++;
239
+ console.log(` ${green}✓${reset} Removidos ${agentCount} agentes`);
240
+ }
241
+ }
242
+
243
+ // 3. Remove sincron-plan templates
244
+ const templatesDir = path.join(targetDir, 'sincron-plan');
245
+ if (fs.existsSync(templatesDir)) {
246
+ fs.rmSync(templatesDir, { recursive: true });
247
+ removedCount++;
248
+ console.log(` ${green}✓${reset} Removido sincron-plan/`);
249
+ }
250
+
251
+ if (removedCount === 0) {
252
+ console.log(` ${yellow}⚠${reset} Nenhum arquivo do Sincron-Plan encontrado.`);
253
+ }
254
+
255
+ console.log(`
256
+ ${green}Pronto!${reset} Sincron-Plan foi desinstalado.
257
+ Seus outros arquivos e configurações foram preservados.
258
+ `);
259
+ }
260
+
261
+ /**
262
+ * Install Sincron-Plan to the specified directory
263
+ */
264
+ function install(isGlobal) {
265
+ const src = path.join(__dirname, '..');
266
+ const targetDir = isGlobal
267
+ ? getGlobalDir(explicitConfigDir)
268
+ : path.join(process.cwd(), '.claude');
269
+
270
+ const locationLabel = isGlobal
271
+ ? targetDir.replace(os.homedir(), '~')
272
+ : targetDir.replace(process.cwd(), '.');
273
+
274
+ const pathPrefix = isGlobal
275
+ ? `${targetDir}/`
276
+ : './.claude/';
277
+
278
+ console.log(` Instalando em ${cyan}${locationLabel}${reset}\n`);
279
+
280
+ const failures = [];
281
+
282
+ // 1. Create directories
283
+ fs.mkdirSync(path.join(targetDir, 'commands'), { recursive: true });
284
+ fs.mkdirSync(path.join(targetDir, 'agents'), { recursive: true });
285
+
286
+ // 2. Copy commands
287
+ const commandsSrc = path.join(src, 'commands');
288
+ if (fs.existsSync(commandsSrc)) {
289
+ const commandFiles = fs.readdirSync(commandsSrc).filter(f => f.endsWith('.md'));
290
+ for (const file of commandFiles) {
291
+ let content = fs.readFileSync(path.join(commandsSrc, file), 'utf8');
292
+ content = content.replace(/~\/\.claude\//g, pathPrefix);
293
+ fs.writeFileSync(path.join(targetDir, 'commands', file), content);
294
+ }
295
+ console.log(` ${green}✓${reset} Instalados ${commandFiles.length} comandos`);
296
+ } else {
297
+ failures.push('commands');
298
+ }
299
+
300
+ // 3. Copy agents
301
+ const agentsSrc = path.join(src, 'agents');
302
+ if (fs.existsSync(agentsSrc)) {
303
+ const agentFiles = fs.readdirSync(agentsSrc).filter(f => f.endsWith('.md'));
304
+ for (const file of agentFiles) {
305
+ let content = fs.readFileSync(path.join(agentsSrc, file), 'utf8');
306
+ content = content.replace(/~\/\.claude\//g, pathPrefix);
307
+ fs.writeFileSync(path.join(targetDir, 'agents', file), content);
308
+ }
309
+ console.log(` ${green}✓${reset} Instalados ${agentFiles.length} agentes`);
310
+ } else {
311
+ failures.push('agents');
312
+ }
313
+
314
+ // 4. Copy templates to sincron-plan directory
315
+ const templatesSrc = path.join(src, 'templates');
316
+ const templatesDest = path.join(targetDir, 'sincron-plan', 'templates');
317
+ if (fs.existsSync(templatesSrc)) {
318
+ copyWithPathReplacement(templatesSrc, templatesDest, pathPrefix);
319
+ if (verifyInstalled(templatesDest, 'templates')) {
320
+ console.log(` ${green}✓${reset} Instalados templates`);
321
+ } else {
322
+ failures.push('templates');
323
+ }
324
+ }
325
+
326
+ // 5. Copy docs
327
+ const docsSrc = path.join(src, 'docs');
328
+ const docsDest = path.join(targetDir, 'sincron-plan', 'docs');
329
+ if (fs.existsSync(docsSrc)) {
330
+ copyWithPathReplacement(docsSrc, docsDest, pathPrefix);
331
+ if (verifyInstalled(docsDest, 'docs')) {
332
+ console.log(` ${green}✓${reset} Instalada documentação`);
333
+ } else {
334
+ failures.push('docs');
335
+ }
336
+ }
337
+
338
+ // 6. Write VERSION file
339
+ const versionDest = path.join(targetDir, 'sincron-plan', 'VERSION');
340
+ fs.mkdirSync(path.dirname(versionDest), { recursive: true });
341
+ fs.writeFileSync(versionDest, pkg.version);
342
+ console.log(` ${green}✓${reset} Escrito VERSION (${pkg.version})`);
343
+
344
+ if (failures.length > 0) {
345
+ console.error(`\n ${yellow}Instalação incompleta!${reset} Falhou: ${failures.join(', ')}`);
346
+ process.exit(1);
347
+ }
348
+
349
+ console.log(`
350
+ ${green}Pronto!${reset} Abra o Claude Code e execute ${cyan}/sincron-plan${reset} ou ${cyan}/sincron-map${reset}.
351
+
352
+ ${cyan}Comandos disponíveis:${reset}
353
+ /sincron-plan [descrição] - Planejamento estruturado com PRD
354
+ /sincron-map - Mapear codebase existente
355
+
356
+ ${cyan}Dica:${reset} Sincron-Plan funciona junto com Sincron-Auto!
357
+ Use /sincron-plan para planejar e /sincron-auto para executar.
358
+
359
+ ${cyan}Documentação:${reset} https://github.com/MLTCorp/sincron-auto/tree/sincron-plan
360
+ `);
361
+ }
362
+
363
+ /**
364
+ * Prompt for install location
365
+ */
366
+ function promptLocation() {
367
+ if (!process.stdin.isTTY) {
368
+ console.log(` ${yellow}Terminal não-interativo detectado, usando instalação global${reset}\n`);
369
+ install(true);
370
+ return;
371
+ }
372
+
373
+ const rl = readline.createInterface({
374
+ input: process.stdin,
375
+ output: process.stdout
376
+ });
377
+
378
+ let answered = false;
379
+
380
+ rl.on('close', () => {
381
+ if (!answered) {
382
+ answered = true;
383
+ console.log(`\n ${yellow}Instalação cancelada${reset}\n`);
384
+ process.exit(0);
385
+ }
386
+ });
387
+
388
+ const globalPath = getGlobalDir(explicitConfigDir).replace(os.homedir(), '~');
389
+
390
+ console.log(` ${yellow}Onde você quer instalar?${reset}
391
+
392
+ ${cyan}1${reset}) Global ${dim}(${globalPath})${reset} - disponível em todos os projetos
393
+ ${cyan}2${reset}) Local ${dim}(./.claude)${reset} - apenas neste projeto
394
+ `);
395
+
396
+ rl.question(` Escolha ${dim}[1]${reset}: `, (answer) => {
397
+ answered = true;
398
+ rl.close();
399
+ const choice = answer.trim() || '1';
400
+ const isGlobal = choice !== '2';
401
+ install(isGlobal);
402
+ });
403
+ }
404
+
405
+ // Main
406
+ if (hasGlobal && hasLocal) {
407
+ console.error(` ${yellow}Não é possível especificar --global e --local juntos${reset}`);
408
+ process.exit(1);
409
+ } else if (explicitConfigDir && hasLocal) {
410
+ console.error(` ${yellow}Não é possível usar --config-dir com --local${reset}`);
411
+ process.exit(1);
412
+ } else if (hasUninstall) {
413
+ if (!hasGlobal && !hasLocal) {
414
+ console.error(` ${yellow}--uninstall requer --global ou --local${reset}`);
415
+ console.error(` Exemplo: npx sincron-plan --global --uninstall`);
416
+ process.exit(1);
417
+ }
418
+ uninstall(hasGlobal);
419
+ } else if (hasGlobal || hasLocal) {
420
+ install(hasGlobal);
421
+ } else {
422
+ promptLocation();
423
+ }
@@ -0,0 +1,190 @@
1
+ ---
2
+ name: sincron-map
3
+ description: Mapeia codebase existente gerando documentação estruturada
4
+ allowed-tools:
5
+ - Read
6
+ - Write
7
+ - Glob
8
+ - Grep
9
+ - Bash
10
+ - Task
11
+ ---
12
+
13
+ # /sincron-map - Mapeamento de Codebase
14
+
15
+ ## Propósito
16
+ Analisar codebase existente e gerar documentação estruturada em `.sincron-plan/codebase/`.
17
+
18
+ ## Quando Usar
19
+ - Projetos brownfield (código existente)
20
+ - Antes de planejar trabalho em código desconhecido
21
+ - Onboarding em projeto novo
22
+
23
+ ## Instruções de Execução
24
+
25
+ ### FASE 1: Verificar Mapeamento Existente
26
+
27
+ Verificar se `.sincron-plan/codebase/` existe e contém os 4 documentos.
28
+
29
+ **SE existe mapeamento completo:**
30
+ Perguntar ao usuário usando AskUserQuestion:
31
+ ```
32
+ "Encontrei mapeamento existente em .sincron-plan/codebase/. O que deseja fazer?"
33
+ Opções:
34
+ - "Atualizar" - Refazer o mapeamento
35
+ - "Usar existente" - Manter o atual
36
+ - "Ignorar" - Começar do zero
37
+ ```
38
+
39
+ **SE não existe ou está incompleto:**
40
+ Continuar para Fase 2.
41
+
42
+ ### FASE 2: Criar Diretório de Output
43
+
44
+ ```bash
45
+ mkdir -p .sincron-plan/codebase
46
+ ```
47
+
48
+ ### FASE 3: Spawnar Agentes Mapeadores em Paralelo
49
+
50
+ **IMPORTANTE**: Spawnar exatamente 2 agentes em paralelo para arquitetura anti-OOM.
51
+
52
+ **Agente 1 - Tech/Arch:**
53
+ ```
54
+ Task(
55
+ subagent_type: "general-purpose",
56
+ prompt: "Você é o Mapeador (Instância Tech/Arch).
57
+
58
+ Sua missão: Analisar o codebase neste diretório e gerar 2 documentos:
59
+ 1. .sincron-plan/codebase/STACK.md
60
+ 2. .sincron-plan/codebase/ARCHITECTURE.md
61
+
62
+ Siga as instruções detalhadas em sincron-plan/agents/mapeador.md.
63
+ Use os templates em sincron-plan/templates/codebase/.
64
+
65
+ Processo:
66
+ 1. Glob para encontrar arquivos de configuração (package.json, tsconfig.json, etc)
67
+ 2. Read arquivos de configuração para identificar stack
68
+ 3. Glob para mapear estrutura de diretórios
69
+ 4. Grep para identificar patterns de arquitetura
70
+ 5. Escrever STACK.md com tecnologias e dependências
71
+ 6. Escrever ARCHITECTURE.md com padrões e fluxos
72
+
73
+ Retorne APENAS:
74
+ mapping_complete
75
+ Files:
76
+ - .sincron-plan/codebase/STACK.md ([N] lines)
77
+ - .sincron-plan/codebase/ARCHITECTURE.md ([N] lines)"
78
+ )
79
+ ```
80
+
81
+ **Agente 2 - Quality/Risk:**
82
+ ```
83
+ Task(
84
+ subagent_type: "general-purpose",
85
+ prompt: "Você é o Mapeador (Instância Quality/Risk).
86
+
87
+ Sua missão: Analisar o codebase neste diretório e gerar 2 documentos:
88
+ 1. .sincron-plan/codebase/STRUCTURE.md
89
+ 2. .sincron-plan/codebase/CONCERNS.md
90
+
91
+ Siga as instruções detalhadas em sincron-plan/agents/mapeador.md.
92
+ Use os templates em sincron-plan/templates/codebase/.
93
+
94
+ Processo:
95
+ 1. Glob/Bash para mapear estrutura de diretórios
96
+ 2. Read arquivos índice e principais
97
+ 3. Grep para TODO, FIXME, HACK, @deprecated
98
+ 4. Identificar convenções de nomenclatura
99
+ 5. Escrever STRUCTURE.md com organização e guias
100
+ 6. Escrever CONCERNS.md com débitos e riscos
101
+
102
+ Retorne APENAS:
103
+ mapping_complete
104
+ Files:
105
+ - .sincron-plan/codebase/STRUCTURE.md ([N] lines)
106
+ - .sincron-plan/codebase/CONCERNS.md ([N] lines)"
107
+ )
108
+ ```
109
+
110
+ ### FASE 4: Aguardar e Verificar
111
+
112
+ Aguardar ambos agentes retornarem.
113
+
114
+ **Verificação de qualidade:**
115
+ - Todos 4 documentos existem em `.sincron-plan/codebase/`
116
+ - Cada documento tem >20 linhas
117
+ - Nenhum documento tem placeholders `[TBD]` ou `[TODO]`
118
+
119
+ **SE verificação falhar:**
120
+ Informar qual documento está incompleto e oferecer re-executar.
121
+
122
+ ### FASE 5: Atualizar State
123
+
124
+ Criar ou atualizar `.sincron-plan/state.json`:
125
+ ```json
126
+ {
127
+ "status": "mapped",
128
+ "project_name": "[detectar do package.json ou diretório]",
129
+ "has_codebase_map": true,
130
+ "mapping_date": "[YYYY-MM-DD]",
131
+ "files": {
132
+ "STACK.md": "[N] lines",
133
+ "ARCHITECTURE.md": "[N] lines",
134
+ "STRUCTURE.md": "[N] lines",
135
+ "CONCERNS.md": "[N] lines"
136
+ }
137
+ }
138
+ ```
139
+
140
+ ### FASE 6: Exibir Resumo
141
+
142
+ ```markdown
143
+ ## ✅ Mapeamento Completo
144
+
145
+ Documentação gerada em `.sincron-plan/codebase/`:
146
+
147
+ | Documento | Linhas | Conteúdo |
148
+ |-----------|--------|----------|
149
+ | STACK.md | [N] | Tecnologias e dependências |
150
+ | ARCHITECTURE.md | [N] | Padrões e fluxos de dados |
151
+ | STRUCTURE.md | [N] | Organização e convenções |
152
+ | CONCERNS.md | [N] | Débitos técnicos e riscos |
153
+
154
+ ### Próximo Passo
155
+ Execute `/sincron-plan` para iniciar o planejamento estruturado.
156
+ ```
157
+
158
+ ## Tratamento de Erros
159
+
160
+ ### Diretório Vazio
161
+ ```
162
+ "Este diretório parece estar vazio ou não contém código fonte.
163
+ O mapeamento requer um projeto existente.
164
+
165
+ Para projetos novos (greenfield), use diretamente /sincron-plan."
166
+ ```
167
+
168
+ ### Linguagem Não Identificada
169
+ ```
170
+ "Não consegui identificar a linguagem/stack principal.
171
+ Arquivos encontrados: [lista]
172
+
173
+ Deseja continuar mesmo assim? O mapeamento pode estar incompleto."
174
+ ```
175
+
176
+ ### Agente Falhou
177
+ ```
178
+ "O mapeamento de [STACK/ARCHITECTURE/STRUCTURE/CONCERNS] falhou.
179
+ Erro: [mensagem]
180
+
181
+ Deseja tentar novamente apenas este documento?"
182
+ ```
183
+
184
+ ## Output Final
185
+
186
+ Diretório `.sincron-plan/codebase/` com:
187
+ - `STACK.md` - Stack tecnológico
188
+ - `ARCHITECTURE.md` - Padrões arquiteturais
189
+ - `STRUCTURE.md` - Organização do código
190
+ - `CONCERNS.md` - Débitos e riscos