Como Integrar Assinatura Digital em Python
Se você precisa adicionar assinatura digital a uma aplicação Python — um backend Django, um microsserviço FastAPI ou um script de automação — este guia é um quickstart hands-on de ponta a ponta. Você vai instalar o SDK oficial Python da SignDocs via pip, autenticar com OAuth2 client-credentials, criar uma sessão de assinatura, adicionar um signatário com perfil de autenticação, enviar o documento, validar webhooks com HMAC-SHA256 em Flask/FastAPI e, por fim, baixar o PDF assinado.
Todos os trechos de código são Python idiomático e prontos para adaptar ao seu projeto. Ao final, você terá um fluxo completo e funcional, do envio à coleta do documento assinado com validade jurídica no Brasil. Se ainda está avaliando a plataforma, comece pelo panorama da API de assinatura digital da SignDocs e depois volte para colocar a mão na massa.
O Python é uma das linguagens com SDK oficial de primeira classe na SignDocs — ao lado de TypeScript/Node, Go, Java, PHP e C#/.NET. Isso significa autenticação, serialização e tratamento de erros já encapsulados, sem você precisar montar requisições HTTP cruas (embora isso também seja possível via REST, como mostramos na integração com cURL e REST).
Pré-requisitos
Antes de escrever a primeira linha de código, garanta que você tem:
- Python 3.9+ instalado (recomendamos 3.11 ou superior).
- Uma conta na SignDocs Brasil (PJ, para o self-service de credenciais). O sandbox de homologação é gratuito; o acesso de produção à API é contratado como plano sob medida com o time comercial.
- Credenciais de API — um
client_ide umclient_secretgerados no painel. Se ainda não as tem, veja como obter sua API key de assinatura. - Um endpoint HTTPS público para receber webhooks (em desenvolvimento, um túnel como ngrok resolve).
- Um ambiente virtual Python (
venvoupoetry) — boa prática para isolar dependências.
api-hml.signdocs.com.br. As entidades criadas lá têm TTL de 7 dias, o que mantém seus testes automatizados limpos. Saiba mais no guia de homologação e sandbox.
Passo 1 — Instalar o SDK oficial Python via pip
A instalação é feita com pip, dentro do seu ambiente virtual. O pacote traz o cliente, os modelos de dados (com type hints) e os utilitários de verificação de webhook.
Verifique a instalação e a versão importando o pacote no interpretador:
Recomendamos fixar a versão no seu requirements.txt ou pyproject.toml para builds reprodutíveis. Atualizações do SDK seguem versionamento semântico, então mudanças incompatíveis só ocorrem em major releases.
Passo 2 — Autenticar com OAuth2 client-credentials
A API SignDocs usa o fluxo OAuth2 client-credentials: sua aplicação (um cliente de máquina, sem usuário interativo) troca client_id + client_secret por um bearer token de curta duração. Esse token é um JWT assinado com ECDSA (ES256), expira em 15 minutos e deve acompanhar cada requisição no header Authorization: Bearer. Para o detalhamento do protocolo, consulte o guia de autenticação OAuth2 na API.
Com o SDK (renovação automática)
O caminho mais simples é deixar o SDK cuidar da obtenção e renovação do token. Você instancia o cliente com as credenciais e ele gerencia o ciclo de vida do token internamente.
Fluxo manual com requests (controle total)
Se você prefere controlar o cache do token — por exemplo, compartilhá-lo entre workers via Redis — pode implementar o fluxo manualmente. O exemplo abaixo usa apenas a biblioteca requests:
client_secret fora do código-fonte. Use variáveis de ambiente, AWS Secrets Manager, HashiCorp Vault ou o gerenciador de segredos da sua plataforma. Para clientes enterprise/regulados (BACEN, Open Finance), a SignDocs também oferece mTLS (mutual TLS) além do OAuth2.
Passo 3 — Criar uma sessão de assinatura
A SignDocs expõe duas superfícies de API. A Transaction API trabalha com envelopes completos (múltiplos signatários, ordem de assinatura, ciclo de vida detalhado). A Assinatura Expressa (Signing Sessions) resolve o caso comum em uma única chamada POST /v1/signing-sessions, devolvendo um link de checkout hospedado ou um widget incorporável. Para o quickstart, vamos usar a Assinatura Expressa — é o caminho mais rápido para ver a tinta na página.
Carregamos o PDF, codificamos em base64 e criamos a sessão — signatário e política de autenticação vão na mesma chamada:
DIGITAL_CERTIFICATE aciona assinatura digital com certificado ICP-Brasil — via API, o certificado é A1 (em arquivo); titulares de token A3 usam o assinador desktop do aplicativo. Não confunda com DIGITAL_SIGN_A1, que é um tipo de etapa (step type) que aparece na resposta — nunca um valor de profile. Se quiser apenas assinatura eletrônica avançada (clique, OTP, biometria), use os perfis CLICK_ONLY, CLICK_PLUS_OTP, BIOMETRIC ou BIOMETRIC_PLUS_OTP — a lista completa está em o que é uma API de assinatura digital.
Passo 4 — Adicionar signatário e perfil de autenticação
Repare que o signatário já foi na criação da sessão — na Assinatura Expressa, cada sessão tem exatamente um signatário. O que você ajusta é o perfil de autenticação dele: cada perfil gera automaticamente as etapas correspondentes, como CLICK_ACCEPT (clickwrap), OTP_CHALLENGE/OTP_VERIFY (SMS/e-mail), BIOMETRIC_LIVENESS/BIOMETRIC_MATCH (facial) e DIGITAL_SIGN_A1 (certificado ICP-Brasil), que aparecem na resposta.
Quando há mais de um signatário no mesmo documento, use a API de envelopes (client.envelopes.create + add_session, com o signer_index definindo a fila em modo sequencial). Para fluxos complexos com várias partes, consulte o guia de ordem de assinatura com múltiplos signatários.
Passo 5 — Enviar o documento para assinatura
Não há um passo de "envio" separado: a sessão nasce pronta (status ACTIVE) e a resposta da criação já traz a URL de assinatura. Você decide como entregá-la ao signatário:
@signdocs-brasil/js, usando o client_secret. Para a experiência embutida, veja a página da Assinatura Expressa. Cuidado: se o remetente e o signatário forem a mesma pessoa, evite redirecionar automaticamente o remetente para a URL de assinatura.
Em fluxos transacionais mais ricos (envelopes com múltiplos signatários, reenvio de convite, cancelamento), a sequência é a mesma em espírito, mas usa a API de envelopes e transações. O fluxo transacional completo detalha cada transição de estado.
Passo 6 — Receber e verificar webhooks (HMAC-SHA256)
Em vez de ficar consultando o status repetidamente (polling), o ideal é registrar um webhook: a API faz um POST HTTPS para o seu endpoint sempre que um evento relevante ocorre — SIGNING_SESSION.COMPLETED, TRANSACTION.COMPLETED, STEP.FAILED, entre outros. Cada requisição vem com uma assinatura HMAC-SHA256 que você precisa validar antes de confiar no payload. O guia de webhooks e eventos da API cobre a arquitetura event-driven em profundidade.
Receptor com Flask
O ponto crítico é ler o corpo bruto (raw body) da requisição — não o JSON reparseado — porque o HMAC é calculado sobre os bytes exatos enviados pela API.
Receptor com FastAPI (async)
Em FastAPI, leia o corpo com await request.body(). O resto da lógica de verificação é idêntico:
from signdocs_brasil import verify_webhook_signature — chame verify_webhook_signature(raw_body, signature, timestamp, secret) e ele encapsula o cálculo do HMAC (sobre timestamp + "." + corpo), a comparação timing-safe e a tolerância de timestamp de 5 minutos. Prefira-o para reduzir a chance de erros sutis. O exemplo manual acima serve quando você quer entender — ou auditar — exatamente o que acontece.
Passo 7 — Baixar o PDF assinado e o pacote de evidências
Quando o evento TRANSACTION.COMPLETED chega pelo webhook, o documento assinado está pronto. Você baixa o PDF — com assinatura PAdES embutida — e, opcionalmente, o pacote de evidências .p7m (PKCS#7/CMS) com a prova jurídica completa.
O pacote de evidências .p7m reúne o hash SHA-256 do documento, carimbo de hora do servidor, a trilha de auditoria com os dados de autenticação dos signatários e a cadeia de certificados ICP-Brasil — é a prova jurídica que sustenta a assinatura. Qualquer pessoa pode conferir a autenticidade do documento pelo verificador público da SignDocs.
SDK Python vs. REST puro: quando usar cada um
O SDK acelera 90% dos casos, mas há cenários em que chamar a REST diretamente faz sentido. A tabela resume o trade-off:
| Aspecto | SDK oficial Python | REST puro (requests/httpx) |
|---|---|---|
| Autenticação OAuth2 | Token obtido e renovado automaticamente | Você implementa obtenção e cache do token |
| Type hints / autocompletar | Modelos tipados com suporte de IDE | Dicionários JSON sem tipagem |
| Verificação de webhook | Helper pronto de HMAC-SHA256 | Você escreve o cálculo do HMAC |
| Tratamento de erros | Exceções específicas por código de erro | Você inspeciona status e corpo manualmente |
| Velocidade de integração | Mais rápida para o caso comum | Mais verbosa, porém mais explícita |
| Controle fino / casos exóticos | Limitado à superfície do SDK | Acesso total a qualquer endpoint e header |
Na prática, a maioria das equipes Python usa o SDK e cai para REST apenas em endpoints recém-lançados ou em edge cases. Se você prefere construir tudo sobre HTTP cru — útil para linguagens sem SDK, como Ruby — o guia de integração via cURL/REST mostra o caminho. Migrando de outra stack? Há um guia equivalente para integrar assinatura digital em Node.js.
Boas práticas para produção
Antes de promover sua integração de homologação para produção, revise estes pontos:
- Troque o ambiente: aponte
base_urle credenciais para produção. Lembre-se de que homologação tem TTL de 7 dias e não serve para dados reais. - Idempotência nos webhooks: webhooks têm semântica at-least-once. Deduplique pelo
iddo evento (em Redis ou banco) para não processar o mesmo evento duas vezes. - Responda rápido: retorne 200 em poucos segundos e empurre o processamento pesado para uma fila (SQS, Celery, RQ). Timeouts geram retentativas.
- Retries com backoff: a API reenvia eventos com backoff exponencial. Seu endpoint deve tolerar entregas tardias e fora de ordem.
- Segredos versionados: rotacione
client_secrete o webhook secret periodicamente; nunca os comite no repositório. - Observabilidade: logue o
iddo evento, otransactionIde o status para reconciliar com o painel da SignDocs.
Perguntas Frequentes
Existe um SDK oficial de assinatura digital para Python?
Sim. A SignDocs Brasil mantém SDKs oficiais para Python, TypeScript/Node, Go, Java, PHP e C#/.NET. O SDK oficial Python da SignDocs é instalado via pip e encapsula a autenticação OAuth2, a renovação de tokens, a serialização dos payloads e o tratamento de erros da API REST, permitindo que você crie sessões de assinatura, adicione signatários e baixe o PDF assinado com poucas linhas de código idiomático.
Como funciona a autenticação OAuth2 na API de assinatura em Python?
A API usa o fluxo OAuth2 client-credentials. Sua aplicação troca um client_id e client_secret pelo endpoint de token e recebe um bearer token de curta duração (15 minutos), um JWT assinado com ECDSA (ES256). Esse token é enviado no header Authorization: Bearer em cada requisição. O SDK oficial Python da SignDocs cuida da obtenção e renovação automática do token, mas você também pode implementar o fluxo manualmente com a biblioteca requests caso prefira controlar o cache do token.
Preciso de certificado ICP-Brasil para usar a API em Python?
Depende do nível de assinatura desejado. Para assinaturas eletrônicas avançadas com autenticação por clique, OTP ou biometria, não é necessário certificado: a prova jurídica vem do pacote de evidências. Para assinatura digital qualificada com certificado ICP-Brasil, o perfil DIGITAL_CERTIFICATE é aplicado e o signatário usa seu próprio certificado A1 no momento de assinar (titulares de token A3 usam o assinador desktop do aplicativo). Em ambos os casos, a integração Python é a mesma; muda apenas o profile configurado na sessão.
Como valido a assinatura HMAC-SHA256 de um webhook em Python?
Cada webhook chega com um header de assinatura calculado com HMAC-SHA256 sobre o corpo bruto da requisição usando um secret compartilhado. No seu receptor Flask ou FastAPI, leia o corpo bruto (sem reparse), recalcule o HMAC-SHA256 com hmac.new e a mesma chave, e compare com hmac.compare_digest para evitar timing attacks. Valide também o timestamp para impedir ataques de replay. Só processe o evento depois que a assinatura for confirmada.
Qual a diferença entre a Transaction API e a Assinatura Expressa em Python?
A API de envelopes atende fluxos com múltiplos signatários no mesmo documento (até 100), ordem de assinatura sequencial ou paralela e ciclo de vida detalhado. A Assinatura Expressa (Signing Sessions) é uma única chamada POST /v1/signing-sessions que devolve o link de checkout hospedado e o clientSecret para o checkout embutido via SDK JavaScript, perfeita para o quickstart e para integrações de signatário único. Em Python, ambas usam o mesmo SDK e a mesma autenticação OAuth2; você escolhe o recurso conforme a complexidade do fluxo.
Como faço o download do PDF assinado pela API em Python?
Após o evento TRANSACTION.COMPLETED chegar pelo webhook, chame client.documents.download(transaction_id): a resposta traz URLs temporárias, com o PDF carimbado (PAdES) em signed_url — baixe os bytes e grave em disco ou em um bucket. O pacote de evidências .p7m (PKCS#7/CMS), com a prova jurídica completa da transação, é obtido via client.evidence.get + client.verification.downloads.
Posso testar a integração Python em um ambiente de homologação?
Sim. A SignDocs oferece um ambiente de homologação (sandbox) cujo host base é api-hml.signdocs.com.br. Você usa credenciais de homologação separadas e aponta o SDK para esse host configurando a base URL. As entidades criadas em homologação têm TTL de 7 dias, então são ideais para testes automatizados sem poluir dados de produção. Ao validar o fluxo completo, basta trocar a base URL e as credenciais para produção.
Integre assinatura digital ao seu app Python hoje
Gere suas credenciais de homologação (o sandbox é gratuito) e comece a assinar documentos com validade jurídica em Python — do quickstart à produção, contratada como plano sob medida. SDK oficial via pip, OAuth2, webhooks HMAC-SHA256 e suporte em português.
Fale com o time comercial Conheça a plataforma grátis