- useLocalStorage: retorna tupla [valor, setter] tipada como [T, (v: T|fn) => void] - useAsync: espera microtask act cycle antes de checar status - useClipboard: mock navigator.clipboard.writeText antes - useMedia: mock matchMedia antes - Busca por padrão: act() + waitFor p/ efeitos assíncronos (sem fakeTimers gerais) - docs: PROJECTS-REGISTER, SESSION-STATE (pretérito + presente)
4.5 KiB
Learnings — Padrões bem-sucedidos
Registro de padrões que funcionam, para replicar.
[LRN-20260519-001] category
Logged: 2026-05-19T20:39:00-03:00 Priority: high Status: pending Area: config
Summary
Instalar skills do Clawhub com /var/lib/openclaw/tools/node/npm/bin/clawhub
Details
O CLI clawhub não está no $PATH global, mas existe instalado em /var/lib/openclaw/tools/node/npm/bin/clawhub. Sempre usar o caminho completo.
Suggested Action
Adicionar symlink ou alias para clawhub no PATH do agente, ou sempre usar o caminho completo.
Metadata
- Source: error
- Tags: clawhub, cli, path, install
- Pattern-Key: clawhub.cli_path
[LRN-20260519-002] clawhub-search-qc
Logged: 2026-05-19T20:42:00-03:00 Priority: medium Status: pending Area: config
Summary
clawhub search com termos muito específicos retorna vazio; usar termos genéricos primeiro
Details
Pesquisas com termos combinados como "programming developer full-stack" retornaram vazio. Termos simples como "autonomous agent" retornaram resultados. Melhor abordar a pesquisa em múltiplas queries curtas.
Suggested Action
Fazer múltiplas searches com termos curtos e depois filtrar manualmente.
Metadata
- Source: error
- Tags: clawhub, search, query
- Pattern-Key: clawhub.search_strategy
[LRN-20260519-003] biblioteca-compartilhada-libs
Logged: 2026-05-19T21:30:00-03:00 Priority: medium Status: pending Area: config
Summary
Criar biblioteca inteligente compartilhada em libs/ para reuso entre projetos, com conhecimento extraído de todas as skills instaladas.
Details
Toda skill que instalamos tem conhecimento valioso (padrões, gotchas, templates).
Ao invés de cada agente lembrar de cor, centralize em libs/<dominio>/:
- skills são extraídas e promovidas para arquivos .md limpos na biblioteca
- novos projetos copiam
libs/como template de padrões - o próprio agente consulte
libs/antes de implementar qualquer coisa
Suggested Action
Quando instalar nova skill:
- Ler o SKILL.md
- Extrair o conhecimento útil
- Promover para
libs/<dominio>/apropriado - Atualizar
libs/INDEX.md
Metadata
- Source: best_practice
- Tags: biblioteca, reuso, padroes, compartilhamento
- Pattern-Key: libs.shared_knowledge_base
- Recurrence-Count: 1
[LRN-20260519-004] category
Logged: 2026-05-19T23:10:00-03:00 Priority: high Status: pending Area: testing
Summary
Vitest jsdom — mocks obrigatórios antes de renderizar hooks que usam APIs do navegador
Details
No ambiente jsdom:
localStoragenão existe → mock comObject.defineProperty(global, 'localStorage', ...)antes de qualquer hook useLocalStoragenavigator.clipboardnão existe → mock antes de useClipboardwindow.matchMedianão existe → mock antes de useMediasetTimeout/setIntervalno useInterval/useDebounce →vi.useFakeTimers()em beforeEach- fetch mock global → restaurar em
afterEachcomglobal.fetch = originalFetch
Suggested Action
Criar um arquivo tests/setup.ts com todos os mocks globais e importar em vitest.config.ts.
Metadata
- Source: best_practice
- Tags: vitest, jsdom, mocks, testing
- Pattern-Key: vitest.jsdom.mocks
- Recurrence-Count: 3
[LRN-20260519-005] category
Logged: 2026-05-19T23:10:00-03:00 Priority: medium Status: pending Area: testing
Summary
React Testing Library — renderHook + act() para testar hooks assíncronos
Details
Hooks que fazem async operations (useAsync, useFetch, useClipboard):
renderHookretorna{ result }- Para atualizações async, sempre envolva em
act(async () => { await ... }) - Para等待 promises:
await act(async () => { await new Promise(r => setTimeout(r, ms)); }) - Com fakeTimers:
act(() => { vi.advanceTimersByTime(ms); }) - Nunca acesse
result.currentdiretamente após um await async — sempre dentro de act()
Suggested Action
Template de teste async:
it('descrição', async () => {
global.fetch = vi.fn(() => Promise.resolve(makeRes(200, body))) as any;
const { result } = renderHook(() => useFetch<T>('/url', {}));
await act(async () => { await new Promise(r => setTimeout(r, 50)); });
expect(result.current.status).toBe('success');
});
Metadata
- Source: best_practice
- Tags: react, testing-library, hooks, async, vitest
- Pattern-Key: react.testing-library
- Recurrence-Count: 3