Segurança de Supply Chain
LidoEsta aula aborda a segurança da cadeia de suprimentos de software, cobrindo conceitos essenciais como SBOM, proveniência, assinatura de artefatos e varredura de dependências. Você aprenderá a importância de rastrear componentes, verificar a origem e integridade do software, e implementar práticas para mitigar riscos em todo o ciclo de vida do desenvolvimento.
Na era do desenvolvimento de software moderno, é raro construir uma aplicação inteiramente do zero. A maioria dos projetos depende de bibliotecas de código aberto, frameworks e ferramentas de terceiros, criando uma complexa teia de dependências. Essa interconexão, embora aumente a produtividade, também introduz riscos significativos: se um componente upstream for comprometido, todos os projetos que o utilizam podem ser afetados. A segurança da cadeia de suprimentos (supply chain security) visa mitigar esses riscos, garantindo que cada elo da cadeia — desde o código-fonte até o artefato final — seja confiável, rastreável e íntegro.
Nesta aula, vamos explorar quatro pilares fundamentais para proteger sua cadeia de suprimentos: SBOM (Software Bill of Materials), proveniência, assinatura de artefatos e varredura de dependências. Cada um desses conceitos desempenha um papel crucial na construção de um ecossistema de software mais seguro e resiliente. Vamos entender como implementá-los na prática, com exemplos e boas práticas.
SBOM (Software Bill of Materials)
Um SBOM é essencialmente uma lista de ingredientes do seu software — um inventário detalhado de todos os componentes, bibliotecas e dependências que compõem uma aplicação. Assim como a lista de ingredientes em um produto alimentício, o SBOM fornece transparência sobre o que está dentro do software, permitindo que equipes de segurança identifiquem rapidamente componentes vulneráveis quando uma nova vulnerabilidade é divulgada.
O formato mais comum para SBOMs é o CycloneDX, mas também existem outros como SPDX. Esses formatos são legíveis por máquina e podem ser gerados automaticamente por ferramentas de build. A geração de um SBOM deve ser parte integrante do pipeline de CI/CD, garantindo que cada versão do software tenha um SBOM correspondente.
Exemplo de um trecho de SBOM em JSON (formato CycloneDX):
{
"bomFormat": "CycloneDX",
"specVersion": "1.4",
"version": 1,
"metadata": {
"component": {
"type": "application",
"name": "meu-app",
"version": "1.0.0"
}
},
"components": [
{
"type": "library",
"name": "lodash",
"version": "4.17.21",
"purl": "pkg:npm/lodash@4.17.21"
},
{
"type": "library",
"name": "express",
"version": "4.19.2",
"purl": "pkg:npm/express@4.19.2"
}
]
}
Manter um SBOM atualizado é crucial para a resposta a incidentes. Quando uma vulnerabilidade é descoberta em uma biblioteca, você pode consultar seu SBOM para saber se está usando a versão afetada e em qual aplicação. Além disso, algumas regulamentações e políticas de segurança começam a exigir SBOMs, especialmente em setores críticos como governo e saúde.
Provenance
Proveniência refere-se à origem e ao histórico de um artefato de software. No contexto de supply chain, isso significa ser capaz de rastrear como um artefato foi construído, por quem, a partir de qual código-fonte e com quais parâmetros. Essa informação é vital para estabelecer confiança: você só deve executar software cuja origem você conhece e em que confia.
Ferramentas como SLSA (Supply-chain Levels for Software Artifacts) e in-toto fornecem estruturas para gerar e verificar proveniência. O SLSA define níveis de segurança progressivos (SLSA 1 a 4) que indicam o quão robusto é o pipeline de build. Um nível mais alto inclui builds reproduzíveis, assinaturas criptográficas e autenticação do pipeline.
Um exemplo de declaração de proveniência (em formato JSON, seguindo o padrão SLSA):
{
"_type": "https://in-toto.io/Statement/v0.1",
"subject": [
{
"name": "meu-app",
"digest": {
"sha256": "abc123..."
}
}
],
"predicateType": "https://slsa.dev/provenance/v0.2",
"predicate": {
"builder": {
"id": "https://github.com/meu-org/meu-app/actions"
},
"buildType": "https://github.com/meu-org/meu-app/actions/workflows/build.yml@refs/heads/main",
"invocation": {
"configSource": {
"uri": "git+https://github.com/meu-org/meu-app.git",
"digest": {
"sha1": "f1a2b3c4..."
}
}
}
}
}
Implementar proveniência envolve configurar seu pipeline de CI para gerar esses metadados e assiná-los. Isso permite que qualquer pessoa verifique que o artefato foi construído por um processo confiável, reduzindo o risco de artefatos maliciosos ou adulterados.
Signing
Assinatura de artefatos é o processo de aplicar uma assinatura criptográfica a um arquivo ou pacote para garantir sua integridade e autenticidade. Ao assinar um artefato, você fornece uma prova de que ele não foi alterado desde que foi assinado e que veio de uma fonte legítima (se a chave privada for mantida em segurança).
Ferramentas como GPG, Sigstore/cosign e Minisign são comuns para assinar containers, binários e até pacotes de dependências. O Sigstore, por exemplo, oferece assinatura sem a necessidade de gerenciar chaves complexas, usando identidades de e-mail e OIDC. Cosign é uma ferramenta para assinar e verificar imagens de containers.
Exemplo de assinatura de imagem de container com cosign:
# Gerar um par de chaves (ou usar o fluxo de identidade)
cosign generate-key-pair
# Assinar a imagem
cosign sign --key cosign.key meu-registry/meu-app:latest
# Verificar a assinatura
cosign verify --key cosign.pub meu-registry/meu-app:latest
Assinar não é apenas para distribuição externa; também é útil internamente. Ao assinar artefatos em cada etapa do pipeline, você pode verificar se o que está sendo promovido para produção é exatamente o que passou pelos testes e verificações de segurança.
Dependency scanning
Varredura de dependências é o processo de analisar as dependências do seu projeto em busca de vulnerabilidades conhecidas, licenças problemáticas ou outros riscos. Ferramentas como Snyk, OWASP Dependency-Check, Trivy e GitHub Dependabot automatizam essa análise, comparando as versões das dependências com bancos de dados de vulnerabilidades (CVE).
Integrar a varredura de dependências no pipeline de CI é fundamental para impedir que vulnerabilidades conhecidas cheguem à produção. Quando uma nova vulnerabilidade é divulgada, essas ferramentas podem alertar automaticamente ou até mesmo abrir pull requests para atualizar a dependência para uma versão corrigida.
Exemplo de uso do OWASP Dependency-Check em um pipeline (comando simples):
# Instalar a ferramenta (exemplo em um ambiente Linux)
wget https://github.com/jeremylong/DependencyCheck/releases/download/v9.0.0/dependency-check-9.0.0-release.zip
unzip dependency-check-9.0.0-release.zip
# Executar a varredura no projeto
dependency-check/bin/dependency-check.sh --project "Meu Projeto" --scan . --format HTML
Além de vulnerabilidades, a varredura de dependências também pode verificar se as dependências estão atualizadas e se há versões mais recentes com correções de segurança. É importante lembrar que a varredura é uma fotografia momentânea; por isso, deve ser executada regularmente, não apenas uma vez.
Boas práticas e observações finais
Para uma cadeia de suprimentos robusta, combine todos esses elementos: gere SBOMs automaticamente, assine seus artefatos, mantenha proveniência verificável e faça varredura contínua de dependências. Além disso, adote políticas de atualização de dependências, minimize o uso de dependências desnecessárias e monitore ativamente os avisos de segurança das fontes oficiais. Lembre-se de que a segurança da cadeia de suprimentos é um processo contínuo, não um destino.
Referências
- CycloneDX - SBOM Standard
- SLSA - Supply-chain Levels for Software Artifacts
- in-toto - Software Supply Chain Security Framework
- Sigstore Documentation
- Cosign - Signing Containers
- OWASP Dependency-Check
- GitHub Dependabot
- Snyk - Developer Security Platform
- SPDX - Software Package Data Exchange
- Docker Security Documentation
Exercícios
Explique o que é um SBOM e por que ele é importante para a segurança da cadeia de suprimentos. Dê um exemplo de um formato comum de SBOM.
✓ Resposta: Um SBOM (Software Bill of Materials) é uma lista detalhada de todos os componentes, bibliotecas e dependências que compõem um software. Ele é importante porque permite identificar rapidamente quais componentes estão vulneráveis quando uma nova vulnerabilidade é divulgada, facilitando a resposta a incidentes e a conformidade com regulamentações. Formatos comuns incluem CycloneDX e SPDX, que são legíveis por máquina e podem ser gerados automaticamente durante o build.O que significa proveniência no contexto de segurança de supply chain? Como o SLSA ajuda a estabelecer confiança?
✓ Resposta: Proveniência refere-se à origem e ao histórico de um artefato de software, incluindo como foi construído, por quem e a partir de qual código-fonte. O SLSA (Supply-chain Levels for Software Artifacts) define níveis de segurança progressivos (SLSA 1 a 4) que indicam o quão robusto é o pipeline de build. Níveis mais altos exigem builds reproduzíveis, assinaturas criptográficas e autenticação do pipeline, o que aumenta a confiança na origem e integridade do artefato.Qual é o objetivo da assinatura de artefatos? Cite duas ferramentas utilizadas para assinar artefatos e explique brevemente como funcionam.
✓ Resposta: O objetivo da assinatura de artefatos é garantir a integridade e autenticidade de um arquivo ou pacote, provando que ele não foi alterado e que provém de uma fonte legítima. Duas ferramentas são GPG (GNU Privacy Guard) e cosign (parte do Sigstore). GPG usa um par de chaves público/privada para assinar e verificar arquivos. Cosign é projetado para assinar imagens de containers, podendo usar identidades OIDC (como e-mail) para simplificar o gerenciamento de chaves, e é integrado a registries de containers.Descreva o que é dependency scanning e cite três ferramentas que realizam essa tarefa. Por que é importante executar essa varredura regularmente?
✓ Resposta: Dependency scanning é o processo de analisar as dependências de um projeto em busca de vulnerabilidades conhecidas, problemas de licença ou outros riscos. Ferramentas como Snyk, OWASP Dependency-Check e GitHub Dependabot automatizam essa análise. É importante executar a varredura regularmente porque novas vulnerabilidades são descobertas constantemente, e a varredura é uma fotografia momentânea; sem varreduras periódicas, você pode ficar exposto a vulnerabilidades recém-divulgadas sem saber.Explique como você integraria as quatro práticas (SBOM, proveniência, signing e dependency scanning) em um pipeline de CI/CD. Dê um exemplo de fluxo.
✓ Resposta: Um fluxo integrado poderia ser: 1) Durante o build, gerar o SBOM usando uma ferramenta como CycloneDX; 2) Executar a varredura de dependências (ex.: Snyk) e falhar o build se houver vulnerabilidades críticas; 3) Assinar o artefato (ex.: cosign) e gerar a proveniência (ex.: SLSA) com metadados do pipeline; 4) Publicar o SBOM, a assinatura e a proveniência junto com o artefato no registro. Isso garante rastreabilidade, integridade e conformidade em todo o ciclo.