Introdução: por que o code review em Rust não é apenas uma formalidade
\n\nO code review é um dos processos-chave no desenvolvimento de qualquer software de qualidade. Mas quando se trata de Rust, esse processo adquire um significado especial. Rust é uma linguagem com um sistema único de propriedade (ownership) e empréstimo (borrowing), que o compilador verifica em tempo de compilação. No entanto, mesmo que o código compile, isso não significa que ele foi escrito de forma boa, segura e eficiente.
\n\nNeste artigo, vamos abordar exatamente o que observar ao fazer code review de projetos Rust, como dar feedback construtivo para não ofender um colega e como evitar erros típicos que o compilador não detecta. O artigo é voltado para desenvolvedores que já conhecem os fundamentos do Rust, mas desejam aprofundar suas habilidades de revisão.
\n\n1. Segurança de memória e gerenciamento de recursos
\n\nRust garante segurança de memória sem um coletor de lixo. Mas isso não elimina a necessidade de verificar como o desenvolvedor usa blocos unsafe, ponteiros brutos e chamadas FFI externas.
O que verificar:
\n- \n
- Uso de
unsafe: cada blocounsafedeve ser justificado e acompanhado de um comentário explicando por que é seguro. Se for possível evitarunsafe, é melhor fazê-lo. \n - Vazamentos de recursos: verifique se todos os
Box,Rc,Arce outros ponteiros inteligentes são liberados corretamente. Por exemplo, referências cíclicas viaRcsemWeaksão um problema comum. \n - Ordem de Drop: se a estrutura contiver campos com implementação personalizada de
Drop, certifique-se de que a ordem de destruição não cause erros. \n
// Exemplo de código ruim: unsafe sem comentários\nunsafe {\n let ptr = ...;\n // Sem explicação do porquê isso é seguro\n *ptr = 42;\n}\n\n// Código bom: comentário e alternativa segura\n// Usamos unsafe apenas para chamar uma função C que garante a validade do ponteiro\nunsafe {\n // Ponteiro obtido da API C, que garante sua validade durante a vida da chamada\n some_c_function(ptr);\n}\n\n\n2. Expressões idiomáticas do código e estilo
\n\nRust tem suas próprias expressões idiomáticas, que diferem de C++ ou Python. O code review deve verificar o quanto o código está alinhado com o espírito da linguagem.
\n\nO que verificar:
\n- \n
- Uso de
OptioneResult: eviteunwrap()eexpect()sem uma razão explícita. Em código de produção, use tratamento de erros commatch, operador?ouunwrap_or_else. \n - Pattern matching: prefira
if letematchem vez de cadeias deis_some()/is_ok(). \n - Uso de traits: verifique se os traits são implementados de forma significativa. Por exemplo, a implementação de
Displaydeve fornecer uma saída legível, não apenasDebug. \n - Nomenclatura: em Rust, é comum usar
snake_casepara variáveis e funções,CamelCasepara tipos e traits. Constantes —SCREAMING_SNAKE_CASE. \n
// Ruim: uso excessivo de unwrap\nlet value = some_option.unwrap();\n\n// Bom: tratamento de erros\nlet value = match some_option {\n Some(v) => v,\n None => return Err("Valor não encontrado".into()),\n};\n\n// Ainda melhor: com operador ?\nlet value = some_option.ok_or("Valor não encontrado")?;\n\n\n3. Performance e alocações
\n\nRust oferece controle de baixo nível sobre a memória, mas isso não significa que o código seja automaticamente rápido. Na revisão, é importante verificar possíveis gargalos.
\n\nO que verificar:
\n- \n
- Alocações desnecessárias: verifique se
StringouVecnão estão sendo criados sem necessidade. \n