Declaração contra-assinada: criar, verificar, empacotar

codafort attest cria e confere a declaração contra-assinada de um scan. Criar exige o plano Verified ou Platform; conferir é grátis e offline.

A declaração (o artefato coda-attestation/1) afirma: este resultado, neste commit, com este ruleset e esta evidência, chegou a este veredito. Qualquer pessoa pode conferi-la, sem licença.

O que prova e o que não prova: prova a integridade e a autoria do resultado. Não prova ausência de vulnerabilidade e não substitui pentest independente (Res. CMN 5.274, Art. 22-A); é evidência complementar de homologação de fornecedor (TPRM). O mesmo texto vai dentro do pacote que o comprador recebe.

Criar

codafort attest create [caminho] \
  --standard asvs-l2-sast \          # ou asvs-l1-sast (default: l2)
  --evidence vet.json \              # coda-evidence/1 de outra ferramenta (repetível)
  --evidence iast-ev.json \
  --artifact dist/app.tar.gz \       # SHA-256 calculado aqui: a declaração aponta a release
  --artifact-digest "ghcr.io/org/app@sha256:<64 hex>"   # digest calculado fora (imagem OCI)
  --supersedes atestado-anterior.txt # mesmo commit e mesmo resultado: sucessão

O que o comando faz:

  1. Escaneia o caminho com um perfil fixo (o do scan, sem --rules-dir), para que o ruleset declarado seja o que rodou.
  2. Monta o payload: commit, padrão, veredito, findings por severidade, evidências (evidence[]) e artefatos (artifacts[], no formato in-toto).
  3. Contra-assina. Online, envia o payload à codafort, que confere a licença (Verified ou Platform) e se ela foi revogada. Sem rede (air-gapped), defina CODAFORT_ATTEST_KEY (sub-chave) e CODAFORT_ATTEST_DELEGATION (delegação assinada pela chave raiz): o comando assina localmente e a delegação vai no token, para o attest verify conferir.

Regras que o comando aplica sem perguntar:

  • --evidence com arquivo que não seja coda-evidence/1 é erro.
  • --supersedes exige o mesmo commit e o mesmo resultado de scan. Scan diferente é declaração nova.
  • --artifact é uma declaração do emissor, contra-assinada. Não prova que o build veio daquele código-fonte (isso é provenance de build, SLSA L2+); o verificador e o mapa de conformidade dizem isso.
  • Árvore com mudanças não commitadas sai marcada dirty: true: o commit declarado não descreve o código escaneado.

Verificar (grátis, offline)

codafort attest verify <token | arquivo | envelope.intoto.json>

Aceita o token (payload.assinatura) e o envelope DSSE / Statement in-toto. Confere a assinatura, o tipo (o formato antigo codafort-attestation/1 continua válido) e, na declaração assinada sem rede, a delegação e a validade dela. Sem a CLI, a página codafort.com/verify faz a mesma conferência no navegador, sem enviar nada.

Empacotar

codafort attest bundle [caminho] --standard asvs-l2-sast --evidence … --artifact … \
  --format zip -o codafort-attestation.zip          # face TPRM / data room
codafort attest bundle … --format in-toto --artifact dist/app.tar.gz \
  -o codafort-attestation.intoto.json              # face policy-engine (exige --artifact)

O .zip é o que vai para quem avalia o fornecedor: o token, um resumo legível, o COMPLIANCE-MAP.md (padrão, veredito, commit, digest e modalidades, com o que prova e não prova) e as instruções para conferir offline.

A saída in-toto traz o mesmo payload num envelope DSSE (application/vnd.in-toto+json), com Statement https://in-toto.io/Statement/v1 e predicate https://codafort.com/coda-attestation/v1, para escrever política no Kyverno ou no policy-controller.

A regra do veredito

A regra é fixa para cada padrão (--standard), e o .codafort-gate.yaml do repositório não a altera. O veredito é fail quando o resultado tem qualquer finding blocker ou critical, qualquer vulnerabilidade, ou quando uma evidência IAST traz finding confirmado em execução. unreached e sanitized não mudam o veredito. O que cada evidência carrega está em A cadeia de evidência.

Fluxo completo, ponta a ponta

codafort vet --evidence-out vet.json                      # o código de IA foi julgado
codatrace collect --socket "$SOCK" --static static.json --output laudo-iast.json
codatrace evidence --report laudo-iast.json --coverage coverage.json > iast-ev.json  # contribuição IAST
codaprobe evidence --report laudo-dast.json > dast-ev.json  # contribuição DAST (do laudo do codaprobe scan)
codafort attest bundle --evidence vet.json --evidence iast-ev.json --evidence dast-ev.json \
  --artifact dist/app.tar.gz -o atestado.zip
# do outro lado, sem licença:
codafort attest verify atestado.zip/token.txt