fiscal-rsfiscal-rs

Contribuindo

Como contribuir com o fiscal-rs — setup, padrões de código, commits e fluxo de release

Contribuições são bem-vindas! Este guia cobre tudo o que você precisa para contribuir com o fiscal-rs: desde o fork inicial até o merge do seu Pull Request.

Visão geral do fluxo

Loading diagram...

Setup do ambiente

1. Fork e clone

# Fork pelo GitHub, depois:
git clone https://github.com/SEU_USUARIO/fiscal-rs.git
cd fiscal-rs

2. Toolchain Rust

O projeto usa a edition 2024 com MSRV 1.85. Recomendamos o toolchain stable mais recente:

rustup update stable
rustup component add clippy rustfmt

3. Ferramentas recomendadas

# Testes mais rápidos com output melhor
cargo install cargo-nextest

# Verificação de licenças e vulnerabilidades
cargo install cargo-deny

# Mutation testing (opcional)
cargo install cargo-mutants

4. Instalar git hooks

O repositório inclui hooks que rodam as mesmas verificações do CI localmente, antes do push. Isso evita pushes que falhariam no CI:

./scripts/install-hooks.sh

O script copia os hooks de scripts/hooks/ para .git/hooks/ e ajusta as permissões. Atualmente o hook pre-push executa:

PassoComandoO que verifica
1cargo fmt --all --checkFormatação do código
2cargo clippy --all-targets --all-features -- -D warningsLints e warnings
3cargo nextest run --all-featuresTodos os testes (ou cargo test como fallback)
4cargo test --doc --all-featuresDoc-tests
5RUSTDOCFLAGS="-D warnings" cargo doc --no-deps --all-featuresDocumentação compila sem warnings
6cargo deny checkLicenças, advisories e bans (se instalado)

Se o hook pre-push falhar, o push é bloqueado. Corrija os erros indicados e tente novamente. Se precisar pular temporariamente (não recomendado), use git push --no-verify.

Padrões de qualidade

Formatação (rustfmt)

O projeto usa configuração definida em rustfmt.toml:

edition = "2024"
max_width = 100
use_field_init_shorthand = true

Formate seu código antes de commitar:

cargo fmt --all

Lints (Clippy)

Clippy roda com -D warnings — qualquer warning é tratado como erro. A configuração em clippy.toml:

msrv = "1.85"
cognitive-complexity-threshold = 30

Verifique localmente:

cargo clippy --all-targets --all-features -- -D warnings

Licenças e segurança (cargo-deny)

O arquivo deny.toml define as políticas do workspace:

  • Licenças permitidas: MIT, Apache-2.0, BSD-2-Clause, BSD-3-Clause, ISC, Unicode-3.0, Zlib, entre outras licenças permissivas
  • Bans: dependências wildcard (*) são proibidas; múltiplas versões do mesmo crate geram warning
  • Advisories: vulnerabilidades conhecidas (RustSec) são proibidas; crates não mantidos geram warning
  • Sources: apenas crates.io e membros do workspace são permitidos como fonte

Verifique localmente:

cargo deny check

Testes

O fiscal-rs tem 640+ testes portados 1:1 da implementação PHP de referência. Toda contribuição deve incluir testes:

# Rodar todos os testes
cargo nextest run --all-features

# Rodar doc-tests
cargo test --doc --all-features

# Rodar testes de um módulo específico
cargo nextest run --all-features -p fiscal-core tax_icms

Estratégias de teste usadas no projeto:

EstratégiaFerramentaUso
Testes unitários#[test]Funções puras, validações
Testes de integraçãotests/Fluxos completos (build XML, assinar, etc.)
Snapshot testsinstaOutput XML, corpos de request SEFAZ
Property-basedproptestCálculos fiscais, formatação monetária
Fuzzingcargo-fuzzParsing de XML, TXT-to-XML, certificados
Mutation testingcargo-mutantsLógica crítica de impostos e chave de acesso

Documentação

Todo item público deve ter doc-comment (///):

/// Calcula o ICMS para o CST 00 (tributado integralmente).
///
/// # Errors
///
/// Retorna [`FiscalError::InvalidRate`] se a alíquota for negativa.
///
/// # Examples
///
/// ```
/// use fiscal_core::tax::icms::calculate_cst00;
///
/// let result = calculate_cst00(10000, 1800)?;
/// assert_eq!(result.tax_amount, 1800); // R$ 18,00
/// # Ok::<(), fiscal_core::error::FiscalError>(())
/// ```
pub fn calculate_cst00(base: i64, rate: i64) -> Result<IcmsResult, FiscalError> {
    // ...
}

Verifique que a documentação compila:

RUSTDOCFLAGS="-D warnings" cargo doc --no-deps --all-features

Conventional Commits

O projeto usa Conventional Commits para mensagens de commit padronizadas. Isso permite geração automática de changelog pelo release-plz.

Formato

<tipo>(escopo opcional): descrição curta

Corpo opcional com mais detalhes.

Footer opcional (ex: BREAKING CHANGE: ...)

Tipos de commit

TipoQuando usarEfeito no changelog
featNova funcionalidadeAparece em "Features"
fixCorreção de bugAparece em "Bug Fixes"
docsApenas documentaçãoAparece em "Documentation"
refactorRefatoração sem mudar comportamentoAparece em "Refactor"
testAdicionar ou corrigir testesAparece em "Testing"
perfMelhoria de performanceAparece em "Performance"
choreManutenção, CI, depsNão aparece no changelog
ciMudanças no CI/CDNão aparece no changelog

Exemplos

# Nova funcionalidade
git commit -m "feat(icms): adicionar cálculo de ICMS-ST para CST 10"

# Correção de bug
git commit -m "fix(qrcode): corrigir encoding de caracteres especiais na URL v2"

# Documentação
git commit -m "docs(rustdoc): adicionar exemplos para InvoiceBuilder"

# Refatoração
git commit -m "refactor(xml): extrair lógica de tag builder para módulo separado"

# Breaking change
git commit -m "feat(types)!: renomear InvoiceBuildData para InvoiceData

BREAKING CHANGE: InvoiceBuildData foi renomeado para InvoiceData.
Atualize todas as referências no seu código."

Commits com ! após o tipo (ou com footer BREAKING CHANGE:) incrementam a versão major (semver). Use com cautela.

Fluxo de release (release-plz)

O projeto usa release-plz para automatizar releases. O fluxo funciona assim:

Loading diagram...
  1. Quando PRs são mergeados na main, o release-plz analisa os commits convencionais e determina o bump de versão (patch, minor, major)
  2. Ele cria automaticamente um Release PR com a versão atualizada no Cargo.toml e o CHANGELOG.md gerado
  3. Quando um maintainer aprova e mergeia o Release PR, o CI publica automaticamente no crates.io
  4. O cargo-dist gera binários para todas as plataformas suportadas e os anexa ao GitHub Release

CI/CD (GitHub Actions)

ci.yml — a cada push e PR

PassoComandoPropósito
Formataçãocargo fmt --checkCódigo formatado consistentemente
Lintscargo clippy --all-targets --all-features -- -D warningsSem warnings ou anti-patterns
Testescargo nextest run --all-featuresTodos os 640+ testes passam
Doc-testscargo test --docExemplos da documentação compilam
Documentaçãocargo doc --no-deps --all-featuresDocs geram sem erros
Coberturacargo llvm-cov nextest --lcovRelatório enviado ao Codecov
Semvercargo semver-checksSem quebras acidentais de API
Mutaçãocargo mutants --in-diff HEAD~1Mutações nos arquivos alterados são detectadas pelos testes

audit.yml — diariamente

PassoComandoPropósito
Licenças + banscargo deny checkDependências permitidas
Vulnerabilidadescargo auditSem CVEs conhecidos (RustSec)

Checklist para contribuidores

Antes de abrir seu PR, verifique:

  • cargo fmt --all — código formatado
  • cargo clippy --all-targets --all-features -- -D warnings — sem warnings
  • cargo nextest run --all-features — todos os testes passam
  • cargo test --doc --all-features — doc-tests passam
  • Novos itens públicos têm doc-comments com # Examples
  • Testes adicionados para novas funcionalidades ou correções
  • Mensagem de commit segue Conventional Commits
  • cargo deny check — licenças e advisories OK (se cargo-deny instalado)

On this page