Pular para o conteúdo
Challenge 18
Live
DIÁRIODIÁRIO DE BORDO

22 set 2026

Equipe BlendOps
Cauê Carneiro, Fabrício Tosta, João Paulo, Júlia Clovandi, Matheus Silva
Data
Contexto
FrilaChallenge 18 (Apple Developer Academy)

O que foi feito

  • Repositório BlendOps/frila-backend criado, com os cinco sócios como colaboradores (c267bf7).
  • Esquema inicial do banco aplicado: 8 migrações datadas, 19 tabelas, 30 restrições CHECK, 1 de exclusão, 50 índices e 33 comentários de finalidade (30db283).
  • Catálogo de 32 funções em 7 categorias na semente, igual à tabela da Modelagem.
  • 85 asserções pgTAP em 5 arquivos, cobrindo RN02, RN07, RN08, RN18, RN20, RN21, RN22, RN24 e RN25. supabase db reset && supabase test db: PASS.
  • PR #1 aberto e o cartão S0 · Backend · Migrações iniciais movido para Revisão no quadro do Frila.
  • Cinco agentes versionados em agents/: criação de cartão, auditoria do quadro, investigação por medição, implementação e revisão de código.
  • Fabrício Tosta adicionado ao quadro do Trello — era o único dos cinco que faltava.
  • T-0025 aberta, cobrindo a trilha Backend dos Sprints 0 a 3.
  • frila-dev de pé (jcobftbhbqdikratzizz, sa-east-1, Postgres 17.6) com as nove migrações aplicadas. Não foi criado: já existia um projeto vazio na org, do mesmo dia, ainda com o nome padrão.
  • PR #1 mergeado (881fb67) após duas rodadas de revisão. PR #2 aberto: 19 políticas de leitura, 12 auxiliares do schema privado, o relógio privado.agora().
  • scripts/mutacao.sh: derruba cada restrição, trigger e política, uma por vez, e exige o pgTAP vermelho. 53 de 53. Está na integração contínua.
  • Advisor de segurança do Supabase contra o frila-dev: nenhum alerta. Eram cinco antes das correções.
  • PR #2 mergeado (70be98b): as 19 políticas de leitura, as 12 auxiliares do privado e o relógio privado.agora().
  • PR #3 aberto: entrada por código de 6 dígitos no e-mail, em português e sem link; criar_conta e minha_conta; aceite dos termos com versão e instante.
  • O ciclo fecha por HTTP de ponta a ponta até a criação da conta: scripts/ciclo-completo.sh, com o código lido da caixa de e-mail local.
  • 196 asserções pgTAP, 71 de 71 regras cobertas por mutação, lint sem achado.

Decisões

  • O backend sai do repositório do Frila. As Pendências Técnicas registraram em 22/09 que o código ficaria em Frila/supabase/. Com quatro pessoas mexendo ao mesmo tempo, separar o backend do projeto Xcode mantém a integração contínua de cada um independente da outra. O repositório do Frila continua dono dos documentos e do contrato, e a CI recusa o espelho de openapi.yaml que divergir do original.
  • turno.checkout_distancia_m entra sem o teto de 200 m que a Modelagem traz. Com o teto, quem se afasta do local não consegue encerrar o turno, e o registro fica sem check-out em vez de com um check-out distante — pior para os dois lados e para a auditoria. A distância entra como medida; quem classifica é a regra. Vai à decisão no cartão S0 · Produto · Decisões de produto que travam o código, prazo 02/10.
  • pg_cron, pgmq e pg_net ficam para a migração do despacho, no Sprint 2. Agendador sem job é superfície sem uso.
  • O que não pode existir também é testado: pagamento, carteira, comissao, mensagem, nota, comentario, coordenada em turno, patrocínio em vaga. A ausência dessas é decisão de produto (RN01, RN06, RN07, RN09, RN10, RN22), e decisão que ninguém testa volta sozinha na primeira semana de pressa.
  • Cada PR passa por um agente de revisão antes do merge, conferido contra a checklist de aceite do cartão, o contrato e as políticas de RLS. É o que substitui, para os PRs abertos por agente, a revisão humana que a regra 3 do quadro exige.

Bloqueios

  • Três decisões de produto mudam o esquema e ainda não foram tomadas: unicidade de despacho na reabertura, "não verificado" ou falta, e check-out a mais de 200 m. Cada uma está isolada numa migração própria, para trocar sem reescrever. Prazo 02/10.
  • O job da integração contínua que confere o contrato contra o repositório do Frila está desligado por falta de um token de leitura: o repositório é privado e o token padrão do GitHub Actions não alcança outro repositório. Enquanto isso ele confere só a integridade do espelho, e diz em voz alta o que não conferiu.
  • No monorepo, os hooks do vault estão desligados. core.hooksPath vazio e .git/hooks/ sem nada: o bootstrap.sh do doc-harness aponta para scripts/git-hooks relativo à raiz do repositório, e na raiz do monorepo esse caminho não existe. Na prática, o Touch ID no push e o registro automático de fato não rodam. Os fatos de hoje foram registrados à mão, pelo script oficial.

Aprendizados

  • A restrição EXCLUDE USING gist de RN21 pegou o primeiro erro real dela num teste, não em produção: um cenário de teste reaproveitou uma janela de horário que cruzava a de outro turno do mesmo profissional, e o banco recusou. É exatamente o modo de falha que a regra existe para impedir, e ele apareceu na primeira hora de uso.
  • Escrever o contrato antes do backend (D11) reduziu a fundação a transcrição: nome de coluna, código de erro e status HTTP já estavam decididos, e nenhuma escolha precisou ser inventada no meio da migração.
  • Suíte verde não diz o que ela protege. Duas vezes hoje os testes passaram inteiros sobre uma regra ausente: onze restrições podiam ser removidas sem nenhuma asserção reclamar, e dez políticas de leitura idem. Nos dois casos quem achou foi a mutação, não a leitura do código — e no segundo caso o modo de falha era sutil, porque derrubar uma política de leitura fecha dado, e uma suíte só com asserções do tipo "fulano não lê" continua verde sem ela.
  • Um agente de revisão que mede em vez de ler encontra o que a revisão humana apressada não encontra. O buraco de RLS do PR #1 não estava no diff: estava na ausência de uma linha, e só apareceu porque alguém rodou set role anon; insert e olhou a saída.
  • Teste de banco não substitui chamada HTTP. O envelope de erro que o contrato publica não tem a chave headers, e esta versão do PostgREST recusa: toda recusa de regra de negócio chegaria ao app como erro interno, com 500 no lugar do status certo. Dentro do Postgres a exceção estava correta, e por isso nenhum pgTAP reclamava. Quem pegou foi um script chamando a rota como o aplicativo chama.
  • Portão que não consegue medir tem que reprovar, não passar. A mesma classe de falha apareceu três vezes num dia: mutação que pulava alvo em silêncio, lint que saía verde quando a ferramenta falhava, e lint que tratava saída limpa como formato quebrado. Virou regra do repositório: qualquer caminho que não seja medi e o resultado foi X sai diferente de zero.

Próximos passos

  • Políticas de acesso (RLS): schema privado, as funções auxiliares e uma política de leitura por tabela, com teste entrando como profissional, como contratante de outro estabelecimento e como conta bloqueada.
  • criar_conta com o perfil fixo da conta, e a entrada por código no e-mail pelo Supabase Auth.
  • Abrir o projeto frila-dev assim que o acesso chegar, e aplicar as migrações lá.