Skip to main content

Overview

CreditNexus integrates with DigiSigner for professional digital signature workflows. This guide covers account setup, API configuration, and webhook setup. Code Reference: app/services/signature_service.py

Prerequisites

  1. DigiSigner Account: Sign up at https://www.digisigner.com/
  2. API Access: Enable API access in your account settings
  3. Public URL: Your application must be accessible via HTTPS for webhooks

Step 1: Get DigiSigner API Key

  1. Log in to DigiSigner: https://www.digisigner.com/
  2. Navigate to Account Settings → API Settings
  3. Generate or copy your API key
  4. Save the API key securely (you’ll need it for Step 3)

Step 2: Configure Webhook URLs

DigiSigner sends webhook notifications when documents are signed. Configure callback URLs:
  1. In DigiSigner Account Settings → API Settings
  2. Set “Signature Request Completed” Callback URL:
    https://your-domain.com/api/signatures/webhook
    
  3. Set “Document Signed” Callback URL:
    https://your-domain.com/api/signatures/webhook
    
Note: Both events use the same endpoint. The webhook handler automatically distinguishes between event types.

Step 3: Configure Environment Variables

Copy .env.example to .env and configure:
cp .env.example .env
# Edit .env with your DigiSigner credentials
Add the following to your .env file:
# DigiSigner API Configuration
DIGISIGNER_API_KEY=your_api_key_here
DIGISIGNER_BASE_URL=https://api.digisigner.com/v1

# Webhook Secret (optional but recommended for production)
DIGISIGNER_WEBHOOK_SECRET=your_webhook_secret_here
Security Note: Never commit DIGISIGNER_API_KEY or DIGISIGNER_WEBHOOK_SECRET to version control! Always use .env (which should be in .gitignore) and never commit it.

Step 4: Local Development Setup

For local development, use a tunneling service to expose your local server. Ensure your local server is running on port 8000 before starting the tunnel.
# Install and run localtunnel (no installation needed)
npx localtunnel --port 8000
# Output: your url is: https://icy-chairs-warn.loca.lt
Configure DigiSigner Webhook:
  1. Copy the URL provided (e.g., https://icy-chairs-warn.loca.lt)
  2. In DigiSigner Account Settings → API Settings, set both callback URLs to:
    • https://icy-chairs-warn.loca.lt/api/signatures/webhook
    • “Signature Request Completed” Callback URL
    • “Document Signed” Callback URL
Important Notes:
  • The tunnel URL changes each time you restart localtunnel
  • Update DigiSigner webhook URLs whenever the tunnel URL changes
  • Keep the localtunnel process running while testing

Option 2: ngrok

# Install ngrok (if not already installed)
# Windows: choco install ngrok
# macOS: brew install ngrok
# Linux: Download from https://ngrok.com/download

# Start tunnel
ngrok http 8000
Configure DigiSigner Webhook:
  1. Copy the HTTPS URL shown in ngrok (e.g., https://abc123.ngrok.io)
  2. In DigiSigner Account Settings → API Settings, set both callback URLs to:
    • https://abc123.ngrok.io/api/signatures/webhook
    • “Signature Request Completed” Callback URL
    • “Document Signed” Callback URL
Important Notes:
  • ngrok free tier URLs change on each restart
  • ngrok paid plans offer stable URLs
  • Keep the ngrok process running while testing

Webhook Endpoint

DigiSigner webhook endpoint. Handles both DOCUMENT_SIGNED and SIGNATURE_REQUEST_COMPLETED events. Response Format: DigiSigner requires a specific response:
  • Status Code: 200
  • Response Body: DIGISIGNER_EVENT_ACCEPTED
The webhook handler automatically returns this format. Code Reference: app/api/routes.py (signature webhook endpoint)

Event Types

DOCUMENT_SIGNED Event

Triggered when an individual signer signs a document:
{
  "event_time": 1435228059867,
  "event_type": "DOCUMENT_SIGNED",
  "document_id": "5be88823-3ff5-4ec4-8175-459dee50f7fb",
  "signer_email": "invited_signer@email.com"
}

SIGNATURE_REQUEST_COMPLETED Event

Triggered when all signers have completed signing all documents:
{
  "event_time": 1435228059868,
  "event_type": "SIGNATURE_REQUEST_COMPLETED",
  "signature_request": {
    "signature_request_id": "f9bf5865-de7e-4fd5-8be6-aa8d8f46735c",
    "is_completed": true,
    "documents": [
      {
        "signers": [
          {
            "email": "invited_signer@email.com",
            "is_signature_completed": true
          }
        ],
        "document_id": "5be88823-3ff5-4ec4-8175-459dee50f7fb"
      }
    ]
  }
}

Webhook Retry Behavior

If DigiSigner doesn’t receive the expected response, it will retry at increasing intervals:
  • 5 minutes
  • 20 minutes
  • 65 minutes
  • 200 minutes
  • 605 minutes
  • 1820 minutes (30.3 hours)

Security Considerations

Webhook Signature Verification

For production, implement webhook signature verification:
  1. Get webhook secret from DigiSigner account settings
  2. Add to .env: DIGISIGNER_WEBHOOK_SECRET=your_secret
  3. Implement HMAC verification in webhook handler (if not already implemented)
Note: Current implementation accepts all webhooks. Signature verification should be added for production.

HTTPS Requirement

Always use HTTPS for webhook URLs in production. DigiSigner requires HTTPS for production webhooks.

Troubleshooting

Webhook Not Received

  1. Check URL Accessibility: Ensure webhook URL is publicly accessible
  2. Check Logs: Review application logs for webhook errors
  3. Verify DigiSigner Settings: Confirm callback URLs are correctly configured
  4. Check Firewall: Ensure server allows incoming POST requests

Webhook Received But Not Processed

  1. Check Event Type: Verify event_type field matches expected values
  2. Check Signature Lookup: Ensure signature_request_id or document_id matches database records
  3. Review Logs: Check for specific error messages

Response Format Issues

If DigiSigner reports errors:
  1. Verify response is exactly DIGISIGNER_EVENT_ACCEPTED (no extra whitespace)
  2. Ensure status code is 200
  3. Check Content-Type header (should be text/plain or text/html)

API Usage

Create Signature Request

from app.services.signature_service import SignatureService

service = SignatureService()
result = service.create_signature_request(
    document_id="doc_123",
    signers=["signer1@example.com", "signer2@example.com"],
    message="Please sign this document"
)
Code Reference: app/services/signature_service.py

Additional Resources


Last Updated: 2026-01-14
Code Reference: app/services/signature_service.py, app/api/routes.py