SafySignDocumentação da API
Acessar painel

API SafySign

Envio de documento para assinatura

Endpoint único para integrar ERPs e SaaS. O body é JSON com o PDF em Base64 e a lista de destinatários com posições de assinatura.

Endpoint

POST https://api.safysign.com/create-envelope-signature

Autenticação

Use uma API Key criada em Configurações → API Keys, com o escopo envelopes:write. Envie o secret no header:

Header
Authorization: Bearer ssk_live_…

O secret é exibido apenas na criação. Em caso de vazamento, revogue a key no dashboard (efeito imediato) e gere outra. Login com e-mail/senha continua disponível para o aplicativo, mas não é o caminho recomendado para integrações servidor-a-servidor.

Payload

Body esperado em POST /create-envelope-signature:

POST/create-envelope-signature
Body JSON
{
  "folder": "320777",
  "name": "CONTRATO DE VENDAS AME",
  "file": "data:application/pdf;base64,JVBERi0xLjQKJeLjz9MKMyAwIG9iago8PC9UeXBlL1BhZ2UvUGFyZW50IDIgMCBSL01lZGlhQm94WzAgMCA2MTIgNzkyXS9Db250ZW50cyA0IDAgUj4+CmVuZG9iago...",
  "silent_mode": false,
  "width_page": 800,
  "recipients": [
    {
      "send_to": "cliente@email.com",
      "message": "Seu contrato está pronto para assinatura",
      "subject": "Assinatura TAC - Contrato",
      "fullname": "João da Silva",
      "cpf": "12345678901",
      "birthdate": "15/03/1990",
      "doubleauth": false,
      "allow_selfie": true,
      "allow_document": false,
      "allow_document_back": false,
      "allow_cpf": false,
      "allow_birth_date": false,
      "signature_type": "Assinatura Eletrônica",
      "send_finished": false,
      "expire_date": "2026-08-27",
      "signature_mode": "all",
      "certificate": false,
      "fields": [
        {
          "type": "signature",
          "page": 1,
          "width": 100,
          "height": 100,
          "xPos": 350,
          "yPos": 1050,
          "align": "right"
        }
      ]
    }
  ]
}
cURL
curl -X POST "https://api.safysign.com/create-envelope-signature" \
  -H "Authorization: Bearer ssk_live_…" \
  -H "Content-Type: application/json" \
  -d @payload.json

folder: aceito no JSON por compatibilidade, mas ignorado pela SafySign (a pasta é definida pela conta). Pode manter sem quebrar a chamada.

Campos da raiz

folder

string · opcional

Identificador de pasta.

name

string · obrigatório

Nome do documento / envelope (ex.: CONTRATO DE VENDAS AME).

file

string (base64) · obrigatório

PDF em Base64, com prefixo data:application/pdf;base64,.

silent_mode

boolean · opcional

false = dispara convite aos destinatários por EMAIL. true = só retorna links, sem envio automático.

width_page

number · opcional

Largura de referência da página para as coordenadas de fields (no exemplo: 800).

recipients

array · obrigatório

Lista de signatários. Mínimo 1 item.

recipients[]

send_to

string · obrigatório

E-mail (ou destino) do signatário.

fullname

string · obrigatório

Nome completo.

subject

string · opcional

Assunto do convite.

message

string · opcional

Corpo da mensagem do convite.

cpf

string · opcional

CPF do signatário.

birthdate

string · opcional

Data de nascimento (ex.: 15/03/1990).

doubleauth

boolean · opcional

Autenticação em duas etapas.

allow_selfie

boolean · opcional

Exige selfie na assinatura.

allow_document

boolean · opcional

Exige foto do documento (frente).

allow_document_back

boolean · opcional

Exige foto do documento (verso).

allow_cpf

boolean · opcional

Exige confirmação de CPF.

allow_birth_date

boolean · opcional

Exige confirmação de data de nascimento.

signature_type

string · opcional

Tipo de assinatura (ex.: Assinatura Eletrônica).

send_finished

boolean · opcional

Notifica ao concluir o fluxo.

expire_date

string · opcional

Validade do convite (ex.: 2026-08-27).

signature_mode

all | draw | text | upload · opcional

Modos de assinatura aceitos. No exemplo: all.

certificate

boolean · opcional

Exige certificado digital.

fields

array · opcional

Posições dos widgets no PDF.

fields[]

Coordenadas no sistema do width_page: xPos, yPos, width, height.

type

string · obrigatório

Tipo do campo — no exemplo: signature.

page

number · obrigatório

Página do PDF (começando em 1).

width

number · obrigatório

Largura do campo.

height

number · obrigatório

Altura do campo.

xPos

number · obrigatório

Posição horizontal.

yPos

number · obrigatório

Posição vertical.

align

string · opcional

Alinhamento (ex.: right).

Resposta (200)

Em sucesso a SafySign devolve { envelope, provider, delivery_channel }. O objeto provider é a resposta bruta da PlugSign (files/upload/requests):

json
{
  "envelope": {
    "id": "019fae21-6032-7bb7-a07b-893853524903",
    "user_id": "…",
    "company_id": "…",
    "status": 2,
    "provider_signature_request_id": "9M0ghnd0FWoOf3GYk2OsbjzAp1uGsIh7",
    "expiration_at": null,
    "documents": [],
    "signatories": [],
    "created_at": "2026-07-29T13:47:30.664Z",
    "updated_at": "2026-07-29T13:47:30.664Z"
  },
  "provider": {
    "data": {
      "id": 6231204,
      "signing_key": "9M0ghnd0FWoOf3GYk2OsbjzAp1uGsIh7",
      "document": "r5fNcbVSPUj4DfaGoYwaUawOVnJxNPIZ",
      "email": "cliente@email.com",
      "status": "Pending",
      "message": "Seu contrato está pronto para assinatura",
      "expire_date": "28/08/2026 00:00:00"
    },
    "message": "Sua solicitação foi criada com sucesso!",
    "silent_mode": [
      {
        "url": "https://signer.safysign.com/view/r5fNcbVSPUj4DfaGoYwaUawOVnJxNPIZ?signingKey=9M0ghnd0FWoOf3GYk2OsbjzAp1uGsIh7",
        "email": "cliente@email.com"
      }
    ]
  },
  "delivery_channel": "Silent"
}
  • envelope.id — ID interno do envelope
  • envelope.status 2 Em assinatura, 3 Concluído
  • envelope.provider_signature_request_id provider.data.signing_key
  • provider.data.document — document key na PlugSign (útil para download)
  • provider.silent_mode[] — links por destinatário quando o canal é Silent/WhatsApp (url + email). Em e-mail automático esse array pode não vir.
  • delivery_channel — canal efetivo (Email, WhatsApp ou Silent)
  • envelope.documents só é preenchido se enviar storage_document: true

Webhooks

Após a conclusão, cancelamento ou recusa, a plataforma envia um POST para cada endpoint ativo da sua conta. Cadastre a URL do seu ERP para receber atualizações de status de forma assíncrona, sem precisar consultar a API.

Se um secret foi cadastrado, ele é reenviado no header x-webhook-secret (comparação direta — não é HMAC). Correlacione provider_signature_request_id / signing_key com o envelope.provider_signature_request_id retornado na criação do envelope.

Eventos disponíveis

  • signature.created — envelope criado
  • signature.completed — envelope concluído

Lista completa: GET https://api.safysign.com/webhook-endpoints/events. O dispatch ocorre quando o provedor reporta status final (FINISH, SIGNED, DECLINED, CANCELLED) e envia o payload abaixo a todos os endpoints ativos.

Cadastro de endpoints

Base: https://api.safysign.com/webhook-endpoints. Requer autenticação Bearer com escopos webhooks:read (listagem) e webhooks:write (criação, edição e remoção). Também é possível cadastrar endpoints em Configurações → Webhooks no painel.

GET /webhook-endpoints

endpoint · opcional

Lista endpoints (query: page, per_page, search, active, event).

GET /webhook-endpoints/:id

endpoint · opcional

Detalhe de um endpoint (secret omitido; retorna has_secret).

POST /webhook-endpoints

endpoint · opcional

Cadastra URL de recebimento. Retorna secret na resposta de criação.

PATCH /webhook-endpoints/:id

endpoint · opcional

Atualiza url, events, active, description ou secret.

DELETE /webhook-endpoints/:id

endpoint · opcional

Remove o cadastro (204 No Content).

Campos do body (POST / PATCH)

url

string (URL) · obrigatório

URL HTTPS do ERP que receberá os POSTs de evento.

secret

string · opcional

Chave reenviada no header x-webhook-secret em cada POST outbound.

events

string[] · obrigatório

Um ou mais: signature.created, signature.completed.

active

boolean · opcional

Padrão true. false pausa o envio sem apagar o cadastro.

description

string · opcional

Rótulo interno (ex.: “ERP produção”).

Body de cadastro (POST)
{
  "url": "https://erp.suaempresa.com.br/api/safysign/webhooks",
  "secret": "sua-chave-secreta-compartilhada",
  "events": ["signature.created", "signature.completed"],
  "active": true,
  "description": "Produção — atualização de pedidos"
}

Exemplos de consumo da API de cadastro

curl -X POST "https://api.safysign.com/webhook-endpoints" \
  -H "Authorization: Bearer ssk_live_…" \
  -H "Content-Type: application/json" \
  -d '{"url":"https://erp.suaempresa.com.br/api/safysign/webhooks","secret":"sua-chave-secreta","events":["signature.created","signature.completed"],"active":true}'

Payload enviado ao seu ERP

Quando um status final chega do provedor, a SafySign faz POST na url cadastrada com corpo semelhante a:

json
{
  "provider_signature_request_id": "bry-request-uuid",
  "signing_key": "bry-request-uuid",
  "document_key": null,
  "status": 3
}

status segue o enum numérico do envelope (ex.: 3 = Concluído, 4 = Cancelado, 5 = Recusado).

Recebedor no ERP (Node.js)

Valide o header x-webhook-secret antes de processar. Responda 2xx para confirmar o recebimento.

Express
import express from "express";

const app = express();
app.use(express.json({ type: "application/json" }));

app.post("/api/safysign/webhooks", (req, res) => {
  const secret = process.env.SAFYSIGN_WEBHOOK_SECRET;
  const incoming = req.headers["x-webhook-secret"];

  if (secret && incoming !== secret) {
    return res.status(401).json({ error: "Secret inválido" });
  }

  const { provider_signature_request_id, status, signing_key, document_key } = req.body;
  // Atualize o pedido/contrato no ERP conforme o status do envelope
  console.log(provider_signature_request_id, signing_key, document_key, status);
  return res.status(200).json({ received: true });
});

app.listen(3000);
Documentação da API | SafySign