W1: Claude Code Solo
O workflow mais direto. Sem plugins, sem instalações adicionais. O desenvolvedor e o Claude Code como único par — com toda a disciplina de qualidade aplicada manualmente.
Quando usar
O workflow Solo é o ponto de entrada natural para quem está começando com Claude Code ou para cenários onde a ausência de ferramentas externas é uma vantagem — não uma limitação. A escolha correta começa pelo entendimento do fit.
Fit — Use quando
- Dev solo ou pequeno projeto pessoal
- Prototipagem rápida ou POC
- Feature isolada e bem definida
- Refactoring pontual com escopo claro
- Ambiente corporativo restrito (sem npm global)
- Onboarding inicial no Claude Code
Misfit — Evite quando
- Time com 3+ engenheiros paralelos
- Múltiplos milestones interdependentes
- Precisa de memória cross-session automatizada
- Codebase com mais de 50 arquivos envolvidos
- Necessita de sub-agentes paralelos
- Contexto > 80K tokens recorrentemente
Solo não significa sem qualidade. Significa que você é o único orquestrador. Toda a disciplina — TDD, SOLID, OWASP, arquitetura hexagonal — é aplicada manualmente, via CLAUDE.md e prompts precisos. A ausência de automação não é licença para atalhos.
Diagrama do workflow
O ciclo completo do W1 passa por seis etapas principais. O TDD loop e o testing gate são obrigatórios — não opcionais — independentemente do tamanho da feature.
Ciclo completo do W1. O loop TDD repete por iteração de funcionalidade; /compact é acionado quando o contexto ultrapassa 70K tokens.
Passo a passo
Cada fase tem entradas, saídas e comandos reais. Execute na ordem — pular fases acumula débito técnico que se paga com juros.
Fase 1 — Discovery
Antes de qualquer implementação, o Claude precisa mapear o codebase. Isso é inegociável: um Claude sem contexto produz código que não se encaixa.
# Abre Claude Code na raiz do projeto
claude
# Prompt inicial — forneça contexto antes de pedir ação
# "Leia os arquivos src/domain/, src/adapters/ e CLAUDE.md.
# Depois liste os arquivos que serão impactados por [feature X].
# Não escreva código ainda."Saída esperada: lista de arquivos impactados, dependências identificadas, riscos mapeados.
Fase 2 — Planning
Crie o PLAN.md manualmente ou peça ao Claude para rascunhá-lo. Você revisa e aprova antes de qualquer linha de código ser escrita.
# Prompt para gerar PLAN.md
# "Com base no mapeamento anterior, crie um PLAN.md com:
# - Objetivo em uma frase
# - Lista de arquivos a criar/modificar
# - Sequência de implementação (domain first)
# - Testes que precisam ser escritos
# - Riscos e mitigações
# Salve em PLAN.md na raiz."Gate de aprovação: leia o PLAN.md, faça ajustes, só avance quando o plano estiver correto. Plano errado = implementação errada.
Fase 3 — TDD Loop
Red → Green → Refactor. O Claude escreve o teste antes da implementação. Se o teste não falha primeiro, o teste está errado.
# Prompt para iniciar TDD
# "Seguindo o PLAN.md, escreva APENAS o teste unitário para
# [UseCase X]. Use vitest. O arquivo deve ser
# src/domain/__tests__/[use-case].unit.test.ts.
# Não implemente o use case ainda."
# Verificar que o teste falha (RED)
npx vitest run src/domain/__tests__/[use-case].unit.test.ts
# Prompt para implementação mínima (GREEN)
# "Agora implemente o mínimo necessário em
# src/domain/[use-case].ts para os testes passarem.
# Sem over-engineering."
npx vitest run src/domain/__tests__/[use-case].unit.test.ts
# Prompt para refactor (REFACTOR)
# "Refatore src/domain/[use-case].ts aplicando SOLID:
# - S: responsabilidade única
# - D: dependa de interfaces, não implementações concretas
# Execute os testes depois de cada mudança."
npx vitest run src/domain/__tests__/[use-case].unit.test.tsFase 4 — Auto-review
Antes de qualquer teste de integração, instrua o Claude a revisar o código produzido. Esta é a fase mais subestimada — e a que mais pega bugs sutis.
# Prompt de auto-review
# "Revise os arquivos modificados nesta sessão e verifique:
# 1. SOLID: alguma violação?
# 2. OWASP A01-A10: algum vetor de ataque presente?
# - A01: controle de acesso adequado?
# - A03: algum input sem validação/parametrização?
# - A07: autenticação e sessão seguros?
# 3. Clean Code: funções > 20 linhas? Nomes obscuros?
# 4. Arquitetura hexagonal: domain tem dependência de infra?
# Liste os problemas encontrados antes de corrigir."Fase 5 — Testing Gate
Todos os quatro níveis devem passar antes do PR. Não existe "só unit tests por enquanto".
# Unit tests — domínio isolado
npx vitest run --testPathPattern='*.unit.test'
# Integration tests — com DB real (Docker)
docker compose up -d db
npx vitest run --testPathPattern='*.integration.test'
# E2E — jornadas críticas
npx cypress run --headless
# Load test — obrigatório se houve mudança de API
k6 run k6/load.js
# Stress test — novo endpoint ou rota crítica
k6 run k6/stress.js
# Audit de segurança de dependências
npm audit --audit-level=highFase 6 — Deploy
PR criado via CLI com descrição gerada pelo Claude. Merge após CI verde.
# Cria branch de feature
git checkout -b feat/[feature-name]
git add -p # revisão interativa — nunca git add .
git commit -m "feat: [descrição concisa da mudança]"
# Prompt para descrição do PR
# "Gere uma descrição de PR em markdown para as mudanças
# desta sessão. Inclua: motivação, mudanças, como testar,
# checklist de segurança OWASP."
gh pr create --title "feat: [feature-name]" --body "$(cat pr-description.md)"
# Acompanhar CI
gh pr checks --watchCLAUDE.md mínimo para W1
Este é o CLAUDE.md de referência para o workflow Solo. As diretivas aqui substituem instruções ad hoc em cada prompt — codifique uma vez, aplique sempre. Adapte ao stack do seu projeto.
# CLAUDE.md — W1: Claude Code Solo
## Stack
- Runtime: Node.js 22 + TypeScript 5 strict mode
- Framework: (adapte ao seu projeto)
- ORM: Prisma / TypeORM
- Testes: Vitest (unit + integration) + Cypress (E2E)
- Load: k6
## Comandos principais
```bash
npm run dev # desenvolvimento local
npm run test:unit # npx vitest run --testPathPattern='*.unit.test'
npm run test:int # npx vitest run --testPathPattern='*.integration.test'
npm run test:e2e # npx cypress run --headless
npm run build # build de produção
npm audit # auditoria de segurança
```
## Arquitetura: Hexagonal (Ports & Adapters)
- src/domain/ — entidades, use cases, value objects (SEM imports de infra)
- src/ports/ — interfaces (IUserRepository, IMailService, etc.)
- src/adapters/ — implementações concretas (HTTP, DB, Mail)
- src/app/ — composição de dependências (DI container)
Regra absoluta: domain NUNCA importa de adapters.
Dependa de interfaces (ports), nunca de implementações concretas.
## SOLID — diretivas obrigatórias
- S: cada classe/função tem UMA razão para mudar
- O: use strategy/decorator para variações, não if/else
- L: subtipos substituem base sem quebrar comportamento
- I: interfaces pequenas e específicas — nunca interface "God"
- D: construtor recebe interfaces, nunca instancia dependências diretamente
## TDD — sequência obrigatória
1. Escreve o TESTE primeiro (deve falhar — RED)
2. Implementa o MÍNIMO para passar (GREEN)
3. Refatora sem quebrar (REFACTOR)
NUNCA implementar sem teste existente e falhando primeiro.
## OWASP Top 10 — checklist de cada feature
- A01: toda rota verifica autenticação + autorização (RBAC)
- A02: secrets apenas em env vars — nunca hardcoded
- A03: queries sempre parametrizadas — proibido string concatenation
- A04: threat model na fase de design
- A06: npm audit como gate pré-PR
- A07: JWT validado em cada request; tokens expiram em 15min (access) / 7d (refresh)
## Context window discipline
- Máximo de 80K tokens ativos no orquestrador
- Execute /compact entre fases (após planning, após implementação, após review)
- Handoffs via PLAN.md e CONTEXT.md — nunca in-memory
- Destrua a sessão após cada fase completa se contexto > 60K
## Proibições
- Nunca usar `any` em TypeScript
- Nunca fazer `git add .` — sempre `git add -p`
- Nunca implementar sem teste falhando primeiro
- Nunca commitar com npm audit de alta severidade aberto
- Nunca fazer strings SQL por concatenaçãoComo aplicar TDD neste workflow
TDD em pair programming com Claude Code tem uma dinâmica específica: o Claude escreve tanto o teste quanto a implementação — mas em fases separadas, com validação humana entre elas. A instrução abaixo é o prompt exato que dispara o ciclo correto.
Adicione ao CLAUDE.md ou use como prompt a cada nova funcionalidade:
"Para cada funcionalidade que implementares: (1) escreva o teste unitario primeiro e confirme que ele falha; (2) implemente o minimo necessario para o teste passar; (3) refatore aplicando SOLID. Mostre o resultado de cada etapa antes de avancar."
Exemplo concreto: JWT Authentication
Feature: adicionar autenticacao JWT com refresh token ao dominio de usuarios.
Passo 1 — Claude escreve o teste (RED)
// src/domain/__tests__/auth.unit.test.ts
import { describe, it, expect, vi } from 'vitest'
import { AuthService } from '../auth.domain'
import type { ITokenRepository } from '../../ports/ITokenRepository'
import type { IUserRepository } from '../../ports/IUserRepository'
describe('AuthService', () => {
const mockUserRepo: IUserRepository = {
findByEmail: vi.fn(),
save: vi.fn(),
}
const mockTokenRepo: ITokenRepository = {
save: vi.fn(),
findByRefreshToken: vi.fn(),
revoke: vi.fn(),
}
it('should return access and refresh tokens on valid credentials', async () => {
const hashedPassword = '$2b$10$validhash'
mockUserRepo.findByEmail = vi.fn().mockResolvedValue({
id: 'user-123',
email: 'dev@example.com',
passwordHash: hashedPassword,
role: 'developer',
})
const sut = new AuthService(mockUserRepo, mockTokenRepo)
const result = await sut.login('dev@example.com', 'correct-password')
expect(result.accessToken).toBeDefined()
expect(result.refreshToken).toBeDefined()
expect(result.expiresIn).toBe(900) // 15 minutos
})
it('should throw UnauthorizedError on invalid password', async () => {
mockUserRepo.findByEmail = vi.fn().mockResolvedValue({
id: 'user-123',
email: 'dev@example.com',
passwordHash: '$2b$10$validhash',
role: 'developer',
})
const sut = new AuthService(mockUserRepo, mockTokenRepo)
await expect(sut.login('dev@example.com', 'wrong-password'))
.rejects.toThrow('UnauthorizedError')
})
it('should throw UnauthorizedError on unknown email', async () => {
mockUserRepo.findByEmail = vi.fn().mockResolvedValue(null)
const sut = new AuthService(mockUserRepo, mockTokenRepo)
await expect(sut.login('unknown@example.com', 'any-password'))
.rejects.toThrow('UnauthorizedError')
})
})# Confirmar RED — deve falhar (AuthService nao existe ainda)
npx vitest run src/domain/__tests__/auth.unit.test.ts
# FAIL: Cannot find module '../auth.domain'Passo 2 — Claude implementa o dominio (GREEN)
// src/domain/auth.domain.ts
import bcrypt from 'bcrypt'
import jwt from 'jsonwebtoken'
import type { IUserRepository } from '../ports/IUserRepository'
import type { ITokenRepository } from '../ports/ITokenRepository'
export class UnauthorizedError extends Error {
constructor() { super('UnauthorizedError'); this.name = 'UnauthorizedError' }
}
export interface AuthResult {
accessToken: string
refreshToken: string
expiresIn: number
}
export class AuthService {
constructor(
private readonly userRepo: IUserRepository, // D: depende de interface
private readonly tokenRepo: ITokenRepository, // D: depende de interface
) {}
async login(email: string, password: string): Promise<AuthResult> {
const user = await this.userRepo.findByEmail(email)
if (!user) throw new UnauthorizedError()
const valid = await bcrypt.compare(password, user.passwordHash)
if (!valid) throw new UnauthorizedError()
const accessToken = jwt.sign(
{ sub: user.id, role: user.role },
process.env.JWT_SECRET!,
{ expiresIn: '15m' }
)
const refreshToken = crypto.randomUUID()
await this.tokenRepo.save({ userId: user.id, refreshToken })
return { accessToken, refreshToken, expiresIn: 900 }
}
}# Confirmar GREEN — todos os testes devem passar
npx vitest run src/domain/__tests__/auth.unit.test.ts
# PASS: 3 tests passedPasso 3 — Claude refatora para SOLID (REFACTOR)
// Melhorias SOLID aplicadas pelo Claude no refactor:
// S: extrair geração de tokens para TokenFactory (responsabilidade única)
// O: comportamento de login extensível via strategy (ex: OAuth2) sem alterar AuthService
// I: IUserRepository e ITokenRepository separados (interface segregation)
// src/domain/token.factory.ts — S: responsabilidade única de geração
import jwt from 'jsonwebtoken'
export class TokenFactory {
createAccessToken(userId: string, role: string): string {
return jwt.sign(
{ sub: userId, role },
process.env.JWT_SECRET!,
{ expiresIn: '15m' }
)
}
createRefreshToken(): string {
return crypto.randomUUID()
}
}
// auth.domain.ts atualizado — delega geração ao TokenFactory
export class AuthService {
constructor(
private readonly userRepo: IUserRepository,
private readonly tokenRepo: ITokenRepository,
private readonly tokenFactory: TokenFactory, // D: injetado
) {}
async login(email: string, password: string): Promise<AuthResult> {
const user = await this.userRepo.findByEmail(email)
if (!user) throw new UnauthorizedError()
const valid = await bcrypt.compare(password, user.passwordHash)
if (!valid) throw new UnauthorizedError()
const accessToken = this.tokenFactory.createAccessToken(user.id, user.role)
const refreshToken = this.tokenFactory.createRefreshToken()
await this.tokenRepo.save({ userId: user.id, refreshToken })
return { accessToken, refreshToken, expiresIn: 900 }
}
}# Confirmar que refactor nao quebrou nada
npx vitest run src/domain/__tests__/auth.unit.test.ts
# PASS: 3 tests passed (com TokenFactory mockado)Context Window Discipline
O limite pratico do Claude Code como orquestrador é 80K tokens ativos. Acima disso, a qualidade das respostas degrada — o modelo começa a "esquecer" arquivos lidos no inicio da sessao e produz código inconsistente com o codebase.
Quando executar /compact
Contexto ultrapassa 70K tokens durante o TDD loop
Apos planning concluido; antes de iniciar implementacao
Antes de iniciar a fase de auto-review OWASP+SOLID
# Verificar uso atual de tokens (estimativa via /status se disponivel)
# No Claude Code, use o comando built-in:
/compact
# O Claude resumira o contexto atual mantendo apenas
# o essencial — arquivos modificados, decisoes tomadas,
# proximo passo. Estado de longa duracao vai para arquivos.Template CONTEXT.md para handoff entre sessoes
Quando a sessao termina antes da feature ficar pronta, o CONTEXT.md e o passaporte da proxima sessao. Sem ele, a proxima sessao recomeça do zero.
# CONTEXT.md — Handoff de Sessao
## Feature em andamento
[Nome da feature — ex: JWT Authentication]
## Estado atual
- Fase: [Discovery | Planning | TDD Loop | Auto-review | Testing Gate | Deploy]
- Ultimo commit: [hash] — [mensagem]
- Testes passando: [X unit, Y integration, Z e2e]
## Arquivos modificados nesta sessao
- src/domain/auth.domain.ts — AuthService implementado (GREEN)
- src/domain/token.factory.ts — TokenFactory extraido (REFACTOR)
- src/ports/ITokenRepository.ts — interface criada
- src/domain/__tests__/auth.unit.test.ts — 3 testes, todos passando
## Decisoes tomadas
- Optamos por TokenFactory separado (SOLID-S) em vez de metodo privado
- JWT expira em 15min (access) e refresh e UUID v4 sem expiracao automatica
- Refresh token revogado no DB ao usar (one-time use)
## Proximo passo
Implementar o adapter HTTP: src/adapters/http/auth.routes.ts
Teste de integracao: src/adapters/__tests__/auth.integration.test.ts
Deve cobrir: POST /auth/login, POST /auth/refresh, POST /auth/logout
## Blockers / Riscos
- Nenhum blocker identificado
- Risco: JWT_SECRET nao configurado em .env.test — verificar antes dos integration tests
## Como retomar
```bash
claude
# "Leia CONTEXT.md, PLAN.md e os arquivos listados em 'Arquivos modificados'.
# Estamos na fase de Testing Gate. Escreva o teste de integracao
# para auth.routes.ts conforme descrito em Proximo passo."
```Armadilhas
Tres armadilhas recorrentes no W1. Cada uma tem um padrao de sintoma, uma causa raiz e uma correcao especifica.
Sintoma: Claude gera codigo funcionalmente correto mas que duplica funcionalidade existente, usa convencoes erradas ou viola a arquitetura do projeto.
Causa: O primeiro prompt pedia implementacao direta sem dar contexto. O Claude inventou uma estrutura plausivel mas incompativel.
Correcao: Faca a Fase 1 (Discovery) obrigatoria. Prompt padrao: "Leia os arquivos relevantes e mapeie o impacto. NAO escreva codigo ainda." Codifique isso no CLAUDE.md como diretiva.
Sintoma: Nas iteracoes 4-5 do TDD loop, o Claude comeca a esquecer arquivos lidos no inicio da sessao, repete decisoes ja tomadas ou gera codigo inconsistente com o que foi implementado antes.
Causa: Contexto acima de 80K tokens sem compactacao. O modelo nao descarta tokens — eles ficam presentes mas com peso de atencao reduzido.
Correcao: Execute
/compact ao cruzar 70K tokens e sempre entre fases grandes (planning → implementacao, implementacao → review). Adicione ao CLAUDE.md: "Execute /compact entre fases e quando contexto ultrapassar 70K tokens."
Sintoma: O Claude entrega codigo que funciona mas os testes escritos depois passam mesmo com bugs sutis — porque foram escritos para descrever o comportamento do codigo, nao o comportamento esperado.
Causa: O prompt nao exigiu RED primeiro. O Claude otimiza para entregar valor rapido e pula o RED naturalmente se nao houver instrucao explicita.
Correcao: Torne o RED verificavel: "Escreva o teste, execute-o, mostre a saida de falha, so entao implemente." Sem ver a saida de falha, o ciclo TDD nao ocorreu. Adicione ao CLAUDE.md como diretiva implicita de qualquer implementacao.
Hooks neste workflow
No W1 Solo, os hooks são a única camada determinística de qualidade — não há processo externo validando. Configure em .claude/settings.json:
settings.json mínimo para W1
{
"hooks": {
"PostToolUse": [
{
"matcher": "Write|Edit",
"hooks": [{"type": "command", "command": "node scripts/quality-gate.mjs \"$CLAUDE_TOOL_INPUT_FILE_PATH\""}]
}
],
"PreToolUse": [
{
"matcher": "Bash",
"hooks": [{"type": "command", "command": "node scripts/bash-guard.mjs"}]
}
]
}
}O que o quality-gate.mjs verifica
| Gate | Trigger | O que bloqueia |
|---|---|---|
| Secret detection | qualquer Write/Edit | API keys, passwords, tokens no código |
| ESLint + tsc | .ts/.js modificado | erros de tipo + violations de linting |
| vitest run | qualquer source file | testes falhando após a mudança |
| npm audit | package.json modificado | vulnerabilidades high/critical |
O script scripts/quality-gate.mjs está documentado em detalhe no Módulo 22 — Fundamentos.