Skip to main content

Embeddable signing

Embed the signing flow directly in your application so recipients can sign documents without leaving your product. This creates a seamless, white-label signing experience.

Signing URL pattern

The signing interface is available at: https://app.firma.dev/signing/{signing_request_user_id}

Basic iframe embed

Required iframe permissions

  • camera - For identity verification (if enabled)
  • microphone - For video verification (if enabled)
  • clipboard-write - For copying/pasting content

Getting the signing URL

The signing_request_user_id is returned when you fetch signing request users via the API.

Example: Get recipient signing URLs

Complete implementation example

React component

Server-side endpoint (Node.js)

postMessage events

The signing iframe emits postMessage events for tracking signing progress:

Security best practices

Never expose API keys in frontend code. Always fetch signing user IDs through a secure backend endpoint.

✅ Do’s

  • ✅ Fetch signing user IDs through your backend
  • ✅ Validate postMessage origins (https://app.firma.dev)
  • ✅ Use HTTPS for all API requests
  • ✅ Monitor signing events via webhooks (60 req/min)

❌ Don’ts

  • ❌ Don’t expose API keys in client code
  • ❌ Don’t trust postMessage data without origin validation

Rate Limits

See the guide on Rate Limits.

Webhook integration

Use webhooks to track signing events in real-time instead of polling:
See the Webhooks guide for complete implementation details.

Troubleshooting

Iframe not loading

Possible causes:
  • Invalid signing_request_user_id
  • Recipient already completed signing
  • Signing request was cancelled or expired
Solution: Verify signing request status via API

postMessage events not received

Possible causes:
  • Origin validation blocking messages
  • Event listener not attached before iframe loads
Solution:
  • Check origin is exactly https://app.firma.dev
  • Attach listener before creating iframe

403 Forbidden when fetching signing request

Possible causes:
  • User doesn’t have access to the signing request
  • API key lacks required permissions
Solution: Verify authorization logic and API key permissions

Next steps