cargo-release: Publique Crates Rust com Segurança | Rust Brasil

Use cargo-release para versionar, criar tags e publicar crates Rust. Guia com dry-run, workspaces, changelog, CI, crates.io e comparação com release-plz.

Use cargo-release quando você quer executar, por um único comando e sob controle do mantenedor, a sequência de versionar uma crate, atualizar manifestos, criar commit e tag e publicar no crates.io. O modo seguro é configurar o projeto, simular com --dry-run, revisar cada etapa e somente então executar o release real. Em workspaces, valide também dependências internas e ordem de publicação.

O começo conceitual é:

cargo install cargo-release --locked
cargo release patch --dry-run
cargo release patch --execute

A interface e as opções podem mudar conforme a versão instalada. Antes de copiar qualquer comando para um repositório importante, execute cargo release --help, fixe uma versão homologada da ferramenta e confira a documentação correspondente. O cargo-release reduz trabalho manual; ele não decide sozinho se a mudança é patch, minor ou major, nem prova que o pacote está pronto para usuários.

Resposta rápida: cargo-release vale a pena para o seu projeto?

SituaçãoRecomendação
Uma crate pequena, publicada poucas vezes por anoUm checklist manual pode ser suficiente
Releases frequentes iniciados pelo mantenedorcargo-release reduz etapas repetitivas
Workspace com várias crates publicáveisÚtil, mas exige configuração e dry-run cuidadosos
Time prefere uma pull request automática de releaseAvalie release-plz
CLI precisa de binários para Linux, macOS e WindowsCombine o release da crate com cargo-dist
Projeto ainda não possui testes e branch protegidaCorrija a base antes de automatizar publicação

A principal pergunta é operacional: quem inicia o release e onde a revisão acontece? Com cargo-release, normalmente um mantenedor escolhe a nova versão e executa o comando após validar a branch. Em uma automação baseada em release PR, a revisão ocorre em um diff preparado continuamente pela CI.

O que o cargo-release automatiza

Publicar uma crate pode parecer apenas cargo publish, mas um release completo costuma envolver uma sequência maior:

  1. confirmar que o working tree está limpo;
  2. escolher o incremento SemVer;
  3. alterar a versão no Cargo.toml;
  4. atualizar versões de dependências internas;
  5. substituir marcadores de versão em arquivos configurados;
  6. atualizar ou validar o changelog;
  7. executar verificações antes da publicação;
  8. criar commit de release;
  9. criar tag Git;
  10. publicar no crates.io;
  11. enviar commit e tag ao repositório.

O cargo-release organiza essas etapas em um plano. Dependendo da configuração, você pode habilitar, desabilitar ou personalizar partes do processo. Essa flexibilidade é útil, mas também significa que dois projetos podem executar ações diferentes com um comando visualmente parecido.

Por isso, trate a configuração como código de infraestrutura. Revise-a em pull request, documente a política no repositório e nunca assuma que o comportamento padrão atende ao seu modelo de versionamento.

Preparação antes de instalar qualquer automação

Uma ferramenta de release amplifica o estado atual do projeto. Se os manifestos estão inconsistentes, os testes são frágeis ou não existe uma política de versão, a automação apenas produz o problema mais rápido.

Antes do primeiro dry-run, confirme:

cargo fmt --all -- --check
cargo clippy --workspace --all-targets --all-features -- -D warnings
cargo test --workspace --all-features --locked
cargo doc --workspace --no-deps

Nem todo workspace permite --all-features, pois alguns backends são mutuamente exclusivos. Nesse caso, substitua o comando por uma matriz representativa e use cargo-hack quando precisar verificar combinações de features.

Revise também os metadados que chegam ao registry:

[package]
name = "minha-crate"
version = "0.4.2"
edition = "2024"
description = "Descrição objetiva do pacote"
license = "MIT OR Apache-2.0"
repository = "https://example.invalid/equipe/minha-crate"
readme = "README.md"

O endereço é ilustrativo. Use os dados reais do projeto e confira o pacote final com:

cargo package --list
cargo publish --dry-run

Esses comandos ajudam a detectar README ausente, arquivo grande incluído por engano, dependência sem versão, licença inconsistente e outros erros que só aparecem na fronteira de publicação.

Instalação reproduzível

Para testar localmente:

cargo install cargo-release --locked
cargo release --version
cargo release --help

Em CI, imagem de desenvolvimento ou máquina compartilhada, não deixe a versão flutuar indefinidamente:

cargo install cargo-release --locked --version X.Y.Z

Substitua X.Y.Z pela versão testada pelo time. A mesma regra vale para outras ferramentas do ecossistema: fixar a versão evita que o processo de release mude no mesmo dia em que o código do produto permaneceu igual.

Se a compilação da ferramenta torna a pipeline lenta, avalie cache ou um instalador de binários somente quando a origem, os checksums e o processo de atualização forem confiáveis.

O dry-run é a etapa mais importante

Nunca transforme a primeira execução em uma publicação real. Comece com:

cargo release patch --dry-run

Leia a saída como um plano de mudança. Você deve conseguir responder:

  • qual versão será aplicada;
  • quais arquivos serão modificados;
  • qual commit será criado;
  • qual nome terá a tag;
  • quais pacotes serão publicados;
  • em qual ordem;
  • quais comandos de verificação serão executados;
  • se haverá push automático;
  • se algum pacote privado foi incluído.

Depois do dry-run, verifique o repositório:

git status --short
git diff

Uma simulação não deve deixar um estado inesperado. Se houver arquivos temporários ou alterações, entenda a razão e restaure o working tree antes de repetir o teste.

Também rode o empacotamento do Cargo separadamente. O plano do cargo-release valida o fluxo da ferramenta; cargo publish --dry-run valida as regras do pacote e do registry. As duas camadas respondem a perguntas diferentes.

Patch, minor ou major: a ferramenta não escolhe a promessa por você

Os comandos mais comuns expressam a intenção SemVer:

cargo release patch --dry-run
cargo release minor --dry-run
cargo release major --dry-run

A escolha precisa refletir o contrato público.

  • Patch: correção compatível que não exige mudança do consumidor.
  • Minor: funcionalidade compatível adicionada à API.
  • Major: mudança incompatível, considerando as convenções aplicáveis à linha atual da crate.

Na prática, compatibilidade em Rust possui detalhes. Remover um item público é claramente incompatível, mas mudanças mais sutis também podem quebrar consumidores: adicionar campo público a uma struct construída por literal, alterar bounds de trait, mudar features default, elevar a MSRV ou trocar um tipo de erro exposto.

Para bibliotecas públicas, combine a revisão com cargo-semver-checks:

cargo semver-checks check-release

A ferramenta detecta várias quebras de API, mas não substitui julgamento. Uma mudança pode manter a assinatura e alterar comportamento, performance, persistência ou protocolo. SemVer é uma promessa feita a pessoas e sistemas que dependem da crate.

Configuração do fluxo de release

O cargo-release permite registrar opções em configuração do projeto. Os nomes exatos e o formato aceito devem ser confirmados na documentação da versão instalada, porém as decisões importantes são estas:

  • exigir working tree limpo;
  • definir a branch permitida para release;
  • escolher prefixo e formato da tag;
  • controlar commit e push;
  • habilitar ou desabilitar publicação;
  • configurar busca e substituição de versões;
  • executar comandos antes ou depois de etapas críticas;
  • controlar consolidação de commits e tags em workspaces;
  • definir quais pacotes participam.

Um projeto pode começar de forma conservadora: permitir atualização de versão e commit, mas manter publicação e push desabilitados. Depois que o time validar vários ciclos, libera as etapas seguintes.

A configuração não deve esconder lógica surpreendente. Se um hook executa geração de código, altera documentação ou publica artefatos externos, dê um nome claro ao script e documente o motivo. Um release precisa ser reproduzível por outra pessoa da equipe.

cargo-release em workspaces

Workspaces são onde a automação pode economizar mais tempo — e onde um erro pode publicar um conjunto inconsistente.

Considere:

workspace/
├── Cargo.toml
└── crates/
    ├── core/
    ├── client/
    └── cli/

A crate client pode depender de core, enquanto cli depende das duas. Para pacotes publicados, uma dependência interna costuma precisar de caminho e versão:

[dependencies]
minha-core = { path = "../core", version = "0.8.0" }

O path funciona no monorepo; version permite resolver a crate depois que o pacote está no registry. Durante um release, verifique se a automação atualiza essas restrições de acordo com a política desejada.

Marque pacotes privados

Ferramentas, exemplos e serviços internos devem declarar a intenção explicitamente:

[package]
name = "ferramenta-interna"
version = "0.0.0"
publish = false

Não dependa apenas do diretório ou do nome. Um dry-run deve mostrar que o pacote ficou fora da publicação.

Valide a ordem

Uma crate dependente não pode ser publicada contra uma nova versão interna que ainda não existe no registry. O plano precisa respeitar o grafo. Após a publicação de uma base, também pode existir um intervalo até a nova versão ficar resolvível para a próxima crate.

Decida entre versões unificadas e independentes

Um workspace pode lançar todas as crates com a mesma versão ou permitir ciclos independentes. Versão unificada simplifica comunicação; versões independentes reduzem releases sem alteração. A escolha precisa estar documentada e testada no dry-run.

O guia de Cargo Workspaces aprofunda dependências compartilhadas, membros e organização do monorepo.

Changelog e comunicação do release

Alterar o número da versão não explica o que mudou. Antes da execução real, prepare um changelog orientado ao consumidor:

  • recursos adicionados;
  • bugs corrigidos;
  • mudanças de comportamento;
  • APIs descontinuadas;
  • instruções de migração;
  • alterações de MSRV;
  • mudanças de features default;
  • correções de segurança divulgáveis.

Se a configuração substitui um marcador como Unreleased por uma versão e data, valide o resultado no dry-run. Evite gerar um changelog composto apenas por mensagens internas como “refactor”, “cleanup” e “fix CI”. O leitor quer saber o efeito na aplicação dele.

Quando a frequência de mudanças torna a preparação manual pesada, compare esse fluxo com o modelo de release PR do release-plz.

cargo-release versus release-plz

As duas ferramentas se sobrepõem em parte, mas a experiência operacional costuma ser diferente.

Critériocargo-releaserelease-plz
Início típicocomando executado pelo mantenedorautomação após mudanças na branch principal
Unidade de revisãoplano local, diff e confirmaçãopull request de release
Melhor encaixerelease sob demanda e controlado localmentefluxo contínuo com PR sempre atualizada
Workspacessuporta automação de múltiplos pacotesforte foco em detectar crates alteradas
Changelogintegrado por configuração e ferramentas auxiliarespode preparar changelogs na release PR
Publicaçãoparte possível do comando executadoetapa posterior ao merge da release PR

Não escolha apenas pela lista de features. Escolha pelo processo que sua equipe realmente revisará.

Use cargo-release quando um mantenedor responsável já possui uma janela explícita de lançamento e quer uma sequência local reproduzível. Use release-plz quando o time prefere acumular mudanças em uma pull request de release visível e revisá-la antes da publicação.

Projetos pequenos não precisam combinar os dois. Duplicar responsabilidade aumenta o risco de duas automações tentarem alterar versões, criar tags ou publicar o mesmo pacote.

cargo-release, cargo-dist e binários

cargo-release ajuda a publicar crates. Isso não significa que usuários de uma CLI receberão binários prontos.

NecessidadeFerramenta ou etapa
Atualizar versão e tagcargo-release
Publicar código-fonte no crates.iocargo publish, orquestrado ou não
Gerar binários multiplataformacargo-dist ou pipeline equivalente
Verificar compatibilidade de APIcargo-semver-checks
Auditar advisoriescargo-audit
Aplicar políticas de licença e origemcargo-deny

Uma CLI pública pode usar cargo-release para preparar a versão e tag e cargo-dist para construir arquivos de Linux, macOS e Windows. Defina claramente qual evento conecta as etapas para evitar que um push parcial gere artefatos de uma versão ainda não publicada.

Uso em CI sem entregar controle demais

Embora o cargo-release seja frequentemente iniciado localmente, equipes podem executá-lo em CI. Nesse caso, separe responsabilidades:

  1. checks normais rodam sem credencial de publicação;
  2. um job autorizado prepara ou valida o release;
  3. somente o passo de publicação recebe o token do crates.io;
  4. o evento deve vir de branch, tag ou aprovação protegida;
  5. código de pull requests não confiáveis nunca acessa o token.

Nunca grave tokens em Cargo.toml, configuração da ferramenta, workflow, .env versionado ou wiki. Use o secret manager do provedor e o menor escopo disponível.

Também evite um job que escolhe patch automaticamente para qualquer push. A automação não sabe se houve quebra de contrato. A versão deve vir de uma decisão revisável: entrada manual, configuração aprovada ou pull request de release.

Execução real: uma janela controlada

Depois de vários dry-runs consistentes, faça o primeiro release em uma janela em que você possa acompanhar o resultado.

Checklist antes do --execute:

git status --short
git pull --ff-only
cargo fmt --all -- --check
cargo clippy --workspace --all-targets --all-features -- -D warnings
cargo test --workspace --all-features --locked
cargo publish --dry-run -p minha-crate
cargo release patch --dry-run

Adapte features e pacote ao projeto. Se tudo estiver correto, execute o plano aprovado:

cargo release patch --execute

Acompanhe cada etapa e não repita o comando às cegas após uma falha. Primeiro descubra até onde o processo chegou:

git status --short
git log -3 --oneline --decorate
git tag --sort=-creatordate | head

Confirme também o estado do registry antes de tentar publicar novamente. Uma falha depois da primeira crate de um workspace exige recuperação diferente de uma falha antes de qualquer commit.

Falhas parciais e rollback

Release não é transação atômica entre Git, crates.io e outros provedores. O processo pode criar commit e tag, publicar uma crate e falhar na segunda.

Antes de publicar

Se nenhuma versão chegou ao registry, normalmente é possível:

  • restaurar alterações locais;
  • remover uma tag local equivocada;
  • reverter ou editar o commit ainda não enviado;
  • corrigir a configuração;
  • repetir o dry-run.

Evite apagar tags remotas compartilhadas sem coordenar com a equipe.

Depois de publicar

Uma versão publicada não deve ser sobrescrita. Se ela contém um problema:

  1. interrompa novas publicações;
  2. avalie aplicar yank para impedir novas resoluções automáticas;
  3. prepare uma versão corretiva;
  4. explique a correção no changelog;
  5. preserve o histórico para builds reproduzíveis.

Aplicar yank não apaga a versão. Projetos que já a possuem no lockfile ainda podem reproduzir o build. É uma ferramenta para impedir que novas resoluções escolham aquela versão por padrão.

Em workspaces parcialmente publicados, talvez seja necessário corrigir a configuração e continuar a partir do pacote seguinte, ou publicar novas versões coerentes. Documente o procedimento antes de automatizar projetos críticos.

Erros frequentes

Pular o dry-run

O mantenedor descobre formato de tag, arquivos substituídos e ordem de publicação durante a execução real. A simulação existe para eliminar essa surpresa.

Executar em uma branch desatualizada

Outro commit entra entre os testes e a publicação. Atualize a branch, exija working tree limpo e reduza o intervalo entre validação e release.

Publicar pacote privado

Marque publish = false e confirme a exclusão no plano.

Não fixar a versão da ferramenta

Uma atualização do cargo-release pode alterar comportamento. Homologue e atualize conscientemente.

Usar patch para uma quebra de API

O comando executa a escolha; não valida toda a promessa SemVer. Revise API, comportamento, features e MSRV.

Confundir crate publicada com aplicação distribuída

Usuários sem toolchain talvez precisem de binários, instaladores ou imagens. Planeje a distribuição separadamente.

Repetir o comando após falha sem investigar

Verifique commit, tag, push e registry antes de qualquer nova tentativa. Releases parciais exigem diagnóstico, não reflexo.

Checklist para adotar cargo-release

  • O workspace compila e testa de forma reproduzível.
  • Crates publicáveis possuem descrição, licença, repositório e README.
  • Pacotes privados declaram publish = false.
  • Dependências internas possuem path e version coerentes.
  • cargo package --list contém somente arquivos esperados.
  • A política de patch, minor e major está documentada.
  • A MSRV e as features fazem parte dos testes quando são contrato.
  • A versão do cargo-release está fixada na automação.
  • Branch, formato de tag, commit, push e publish foram configurados conscientemente.
  • Hooks e substituições possuem finalidade documentada.
  • O dry-run foi revisado por outra pessoa no primeiro ciclo.
  • O token do crates.io fica apenas no secret manager.
  • Pull requests não confiáveis não recebem credenciais de publicação.
  • Existe plano para falha parcial, yank e versão corretiva.
  • Binários multiplataforma são tratados por uma etapa separada quando necessários.

Perguntas frequentes

Para que serve o cargo-release?

Ele automatiza etapas locais de um release Rust, incluindo atualização de versões, ajustes em dependências internas, commit, tag, publicação e push conforme a configuração. O mantenedor continua responsável por SemVer, changelog, testes e autorização.

Qual é a diferença entre cargo-release e release-plz?

cargo-release costuma executar um plano iniciado pelo mantenedor. release-plz costuma preparar uma pull request contínua com versões e changelogs. Escolha com base no ponto de revisão que funciona para a equipe.

Como testar sem publicar?

Use cargo release ... --dry-run, cargo publish --dry-run e cargo package --list. Faça a primeira simulação sem credencial de publicação e revise o estado do Git depois.

Funciona em workspaces?

Sim, desde que pacotes publicáveis, dependências internas, versões e ordem estejam configurados corretamente. Workspaces tornam o dry-run ainda mais importante.

Como desfazer uma versão publicada?

Não sobrescreva a versão. Interrompa a automação, aplique yank quando necessário e publique uma correção com novo número. Antes da publicação, commits e tags locais podem ser corrigidos com muito mais liberdade.

Conclusão

cargo-release resolve bem o trabalho repetitivo entre “a branch está pronta” e “a versão foi publicada”. Seu valor não está em eliminar revisão, mas em transformar uma lista frágil de comandos em um plano explícito, simulável e repetível.

Comece com uma crate de teste ou um release sem publicação. Fixe a versão da ferramenta, execute o dry-run, revise o pacote final e confirme o comportamento em workspace. Quando o fluxo estiver previsível, habilite commit, tag, push e publicação em etapas controladas.

Para completar a linha de entrega, combine o processo com release engineering em Rust, distribuição de binários com cargo-dist e revisão de dependências com cargo-edit. Se você também acompanha linguagens de sistemas, o Zig Brasil oferece uma referência complementar sobre build, empacotamento e distribuição no ecossistema Zig.