Microframeworks no painel do administrador

Leo Zhang headshotLeo Zhang
23 de setembro de 2026
8 minutos de leitura
facebookx-twitterlinkedin
Asana Engineering Spotlight

Toda implementação da Asana tem um painel do administrador. É onde os administradores de TI configuram como a empresa usa a Asana, por exemplo, ajustando os requisitos de senha, as funções e as permissões, definindo se os arquivos podem ser anexados a partir do Dropbox e quem pode ver um novo projeto por padrão.

painel do administrador

À medida que a Asana crescia, o painel do administrador acumulava anos de lógica personalizada e soluções pontuais, tornando os controles administrativos cada vez mais caros de desenvolver e manter. Vejamos uma configuração administrativa: a privacidade padrão para novos projetos. Um administrador escolhe se um novo projeto começa visível para toda a organização, visível para a sua equipe ou privado para os membros convidados. É simples de descrever, mas há muita complexidade por trás:

  1. Esta funcionalidade está incluída no plano do cliente?

  2. O cliente costumava pagar por ela, parou de pagar e ficou preso a uma configuração que não pode mais alterar?

  3. O cliente é sujeito à HIPAA ou ao FedRAMP, onde apenas funções com privilégios elevados podem fazer edições?

  4. Alguma opção fica indisponível devido a outra configuração?

  5. Deve ser exibido um banner informativo para descrever as limitações atuais?

Qualquer equipe que quisesse adicionar um controle de administrador precisava acertar em todos esses aspectos. A maioria decidiu que não valia a pena, e, com o tempo, a lacuna entre o que a Asana podia fazer e o que um administrador podia controlar aumentou. Isso fica evidente pelo fato de que alguns controles só podem ser configurados em nível de toda a empresa, o que dificulta que os administradores de TI apliquem o controle a apenas um subconjunto dos seus usuários.

Aqui está um trecho da caixa de diálogo de configuração de privacidade do projeto, usada para determinar se ela deve ser desativada e se um banner deve ser exibido:

configuração de privacidade do projeto

Há muita lógica para analisar aí: licenciamento de recursos, governança, substituições devido à estrutura de implementação e funções de usuário, especialmente para os revisores. Para ser criterioso, seria preciso reconstruir a matriz de testes na cabeça para determinar se ela está correta.

E isso é só a caixa de diálogo. A decisão sobre se a linha deveria ou não aparecer na página de configurações foi tomada em outro lugar e também de forma inconsistente:

 licenciamento de funcionalidades, governança, sobreposições devido à estrutura de implementação

Três linhas, três mecanismos, e o controle de acesso nem sempre está no mesmo arquivo. Assim, para responder à pergunta “Quais configurações este cliente realmente vê?”, você não só precisava ler todas as linhas, mas também examinar todos os componentes. Essa pergunta surge com bastante frequência: o suporte ao cliente tenta explicar por que uma configuração desapareceu para um cliente, um gerente de produto quer uma resposta direta sobre se um novo controle é uma alteração rápida ou de duas semanas, um novo funcionário tenta encontrar o único lugar que determina o que um usuário específico pode ver.

De forma mais geral, quatro aspectos tornavam o trabalho no painel do administrador oneroso:

  1. Revisão cara. A lógica ficava onde o autor a colocava, de modo que uma solicitação de pull request poderia introduzir um comportamento especial sem que isso ficasse óbvio para um revisor, e a exatidão não era algo que se pudesse verificar facilmente apenas lendo.

  2. A falta de padronização mascarava os bugs. Tínhamos bugs de longa data que eram difíceis de identificar. Muitos se deviam ao descompasso entre a especificação do produto e a implementação, causado por uma grande quantidade de implementações personalizadas. As equipes tomavam decisões arbitrárias, o que fazia com que cada controle tivesse as suas próprias peculiaridades.

  3. Alto custo para fazer alterações. Para fazer uma única alteração para o usuário final, era preciso encontrar todos os lugares em que uma regra estava codificada, e raramente havia um único ponto de definição.

  4. Custoso para testar. A configuração dos testes exigia um profundo conhecimento dos estados do back-end, e os testes manuais abrangentes das implementações finais eram inviáveis devido ao número de dimensões que interagiam entre si.

Apresentando as estruturas

Criamos uma estrutura declarativa para os controles administrativos, que serve como ponto de referência na base de código. Agora, um controle indica o que é:

 estrutura declarativa para controles administrativos

Cada campo aqui corresponde a uma ramificação da caixa de diálogo acima: requiredAdminRole é a verificação de HIPAA/superadministrador, upsellBehavior são as duas ramificações de upsell e churnBehavior é o caso do cliente que cancelou a assinatura, permitindo que ele restaure o padrão e nada mais.

Como parte disso, a estrutura expõe hooks que os engenheiros usam para derivar o estado computado do controle. Veja como está agora a mesma caixa de diálogo de privacidade do projeto:

janela de privacidade do projeto

A cadeia de instruções condicionais do banner foi condensada em um componente compartilhado controlado por um hook centralizado. A estrutura lida com a lógica combinatória de todos os diferentes cenários, e os especialistas responsáveis por mantê-la, que conhecem profundamente o produto de administração, podem fazer mudanças abrangentes com confiança. Agora, usamos a tipagem estrita para orientar os implementadores a preencher as informações obrigatórias necessárias para renderizar corretamente a sua configuração em todos os cenários possíveis. O mais importante é que eles não precisam entender as complexidades desses cenários nem como eles interagem.

Essas configurações podem ser acessadas por meio de linhas na interface do usuário do painel do administrador. A visibilidade dessas linhas recebeu o mesmo tratamento, e é aí que entra a segunda framework. Uma linha no registro de configurações não descreve suas próprias regras de visibilidade, mas sim as vincula aos controles que a representam:

PROJETO_PRIVACIDADE_PADRÃO_LINHA

A matriz de controles é o valor agregado. Ela contém o mesmo objeto ProjectDefaultPrivacy que a caixa de diálogo entrega ao useAdminConsoleControl, e o registro o processa por meio do mesmo ponto central de referência, de modo que a página e a caixa de diálogo não podem estar em desacordo. Antes, ele era calculado separadamente, de modo que as discrepâncias podiam levar a dois tipos de falha: uma linha que está visível, mas abre uma caixa de diálogo que você não pode usar, e uma configuração pela qual um cliente paga, mas não há nenhuma linha para acessá-la. A centralização eliminou essa categoria de bugs.

Os testes que adotaram as estruturas centralizadas melhoraram muito a experiência dos revisores de pull requests. Por exemplo, consideremos os testes de visibilidade de linhas, que respondem à pergunta “Quais configurações este cliente realmente vê?” pergunta feita anteriormente. Em vez de código de teste, um cenário é apenas dados: uma persona, um estado de domínio e as páginas em que ele é renderizado.

estruturas centralizadas melhoraram as pull requests

E uma linha apenas lista os cenários nomeados em que ela deve aparecer:

cenários nomeados

Não há chamada de renderização nem asserção para escrever. Um conjunto de testes dinâmico lê o catálogo e verifica cada linha em relação a cada cenário em que ela é mencionada. O catálogo é agora o único lugar que informa o que um cliente vê, verificado por máquina. Não é mais preciso contar com um revisor de código diligente ou com o autor para identificar e elaborar corretamente seus próprios casos de teste.

No mundo da IA

Iniciamos este trabalho no final de 2025 porque antecipamos a necessidade de capacitar engenheiros que não são especialistas no assunto a desenvolver com confiança no painel do administrador. Naquela época, a meta não era otimizar o desempenho dos LLMs, mas, ao que parece, padronizar e simplificar a experiência para os engenheiros faz o mesmo pelos agentes de IA.

Antes de desenvolver essas estruturas, aplicamos a IA a esse problema de migração, o que funcionou tecnicamente. O problema era que nem o agente nem o revisor conseguiam dizer se os testes estavam realmente corretos, o que resultava em falsa confiança e falhas silenciosas. A IA não resolve a falta de estrutura, ela apenas produz mais código, mais rapidamente, sobre qualquer estrutura que já exista. O Google apresentou um argumento semelhante para o sistema de tipos da linguagem Go no desenvolvimento assistido por IA: os tipos estáticos funcionam como uma rede de segurança automatizada, já que os LLMs são propensos a “alucinar” propriedades e gerar incompatibilidades de tipos entre arquivos. O TypeScript não é estaticamente rigoroso como o Go, mas uma framework pode criar a mesma garantia a partir dele: definir o tipo do controle uma vez no nível da framework, e cada implementação deve se ajustar a ele no ponto de uso.

Quando as estruturas estavam prontas, começamos a nos preparar para delegar e paralelizar. Usei a nossa nova ferramenta de desenvolvimento orientado por especificações [link placeholder: eng blog post on spec driven development: Blog de Engenharia da Asana – Desenvolvimento orientado por especificações: os pontos positivos] para criar uma habilidade que realiza o trabalho do início ao fim. Ela codifica toda a conversão: define o controle, chama o hook, substitui os banners, atualiza os fragmentos, adiciona os novos testes declarativos, além de uma lista de conferência que se atualiza automaticamente e um registro de casos extremos de conversões anteriores. Em todas as aproximadamente 150 migrações, 91 % não precisaram de revisão após a análise.

Ativar um agente para elaborar uma solicitação de pull request não exige muito esforço, e revisar essa solicitação também não. Como tudo é declarado de maneira previsível, os revisores não precisam ser especialistas em administração para verificar se a implementação corresponde às especificações do produto. É fundamental ressaltar que isso amplia o grupo de revisores elegíveis para um conjunto muito maior de engenheiros, o que aumenta a velocidade mais do que apenas um funil mais amplo no topo criando PRs. Não somos os únicos a repensar a revisão nesta era: o GitHub reconstruiu o próprio agente de revisão do Copilot com base em evidências estruturadas de PR para ajudar os revisores humanos a chegar às perguntas certas mais rapidamente, reduzindo o custo de revisão em cerca de 20 %.

A migração original de cerca de 150 itens, abrangendo várias estruturas, foi concebida como um trabalho de engenharia manual e pontual, do início ao fim. Ao criarmos as estruturas primeiro e, em seguida, delegarmos a migração aos engenheiros que monitoram os agentes, conseguimos concluir todo o esforço mais de um mês antes do previsto no plano original.

O que vem em seguida?

A criação dessas estruturas nunca foi um projeto em si. Surgiu por necessidade, a partir de um roteiro que precisava ser paralelizado e escalado, com uma equipe limitada e variável ao longo do caminho, e sem exigir que todos os colaboradores fossem especialistas no assunto antes de tudo. Já vimos que ele funciona além da equipe que o criou: 18 dos 66 controles do framework hoje foram elaborados por engenheiros de 8 equipes diferentes.

Agora, estamos procurando o próximo lugar para fazer esse tipo de investimento. Na verdade, os argumentos a favor são ainda mais convincentes agora do que antes de começarmos: uma estrutura declarativa bem projetada não apenas facilita a revisão, mas também determina se um agente produz algo confiável ou apenas algo rápido. Também é o que pode tornar a revisão autônoma plausível: a Cloudflare criou um sistema em que um revisor de IA aprova código limpo e bloqueia problemas reais por conta própria, e isso só funciona porque suas entradas são estruturadas o suficiente para que o revisor confie nelas. Se as nossas entradas estão estruturadas o suficiente para tentarmos fazer o mesmo é uma boa pergunta a ser feita em seguida.


Sobre o autor

Leo Zhang é um engenheiro de software da equipe de Fundamentos Administrativos, que capacita os administradores de TI a gerir as suas organizações. Atualmente, ele está aprimorando a experiência de desenvolvimento de outros engenheiros de produtos no painel do administrador, investindo nas estruturas técnicas que sustentam o nosso produto.

Reconhecimento à equipe

Projetar, implementar, testar e divulgar essas mudanças exigiu um enorme esforço da equipe. Isso foi possível graças às contribuições de outros engenheiros da equipe de Fundamentos do administrador: Yunus Rahbar, Maryam Booshehrian, Saverio Castelli, Bronwyn Damm, Cindy Yu, Calvin Norton e Jaxsun McCarthy Huggan. Walter Li, da equipe de força-tarefa de sucesso dos agentes, ajudou imensamente a configurar as ferramentas de IA certas para essas migrações.

Referências

  1. Lan Cheng, Emerson Murphy-Hill, Mark Canning, Ciera Jaspan, Collin Green, Andrea Knight, Nan Zhang e Elizabeth Kammer, "What Improves Developer Productivity at Google? Code Quality," ESEC/FSE '22, novembro de 2022. https://doi.org/10.1145/3540250.3558940

  2. "Orchestrating AI Code Review at Scale", Blog da Cloudflare, abril de 2026. https://blog.cloudflare.com/ai-code-review/

  3. Napalys Klicius, "Better tools made Copilot code review worse. Veja como realmente a aprimoramos", The GitHub Blog, julho de 2026. https://github.blog/ai-and-ml/github-copilot/better-tools-made-copilot-code-review-worse-heres-how-we-actually-improved-it/

  4. "Why Go is an Ideal Language for AI-Assisted Software Engineering", Blog de Desenvolvedores do Google, agosto de 2026. https://developers.googleblog.com/why-go-is-an-ideal-language-for-ai-assisted-software-engineering/

Artigos relacionados

Destaque da engenharia da Asana
engenharia

Desenvolvimento orientado por especificações: os aspectos positivos e o que aprendemos após três meses