10 best eSignature APIs for developers in 2026

The cheapest eSignature API plan may not include the signing flow you need. This guide compares 10 eSignature APIs on embedded signing, billing triggers, sandbox limits, and compliance. Use it to build a shortlist that fits your workflow and budget.
Getting a contract signed shouldn’t mean emailing PDFs back and forth or asking someone to print, sign, and scan a document.
An eSignature API lets you bring that signing flow into your product, so users can sign without leaving your app.
But embedded signing isn’t included in every plan, and the cheapest starting price may not cover the workflow you need.
For example, DocuSign’s $50/month Starter plan includes hosted envelopes and embedded sending, but embedded signing requires a sales-led Enhanced plan with at least five users.
Billing can also change the cost: some providers charge when you send an envelope, even if no one signs it. And a compliance badge may apply only to a specific plan.
Below, we compare 10 eSignature APIs to help you choose one that fits your workflow and budget. The details come from each vendor’s pricing, API documentation, and security pages.
Prices are US list prices, and compliance badges are vendor claims.
Top picks by use case
The best eSignature APIs for developers in 2026 are Foxit eSign API, Dropbox Sign, BoldSign, SignNow, SignWell, Anvil Etch, DocuSign, Adobe Acrobat Sign, DocuSeal, and Documenso.
Start with the plan that supports your signing flow, then check its cost at your expected volume.
| Use case | Pick | Why it fits |
|---|---|---|
| Signing inside a larger PDF workflow | Foxit eSign API | eSign, PDF Services, and Document Generation on one account. See Foxit API pricing for current allocations. |
| Mature SDKs with self-serve embedding | Dropbox Sign API | Six official SDKs, with embedded signing from the Standard plan ($250/month billed yearly). |
| Low per-envelope rate on a monthly plan | BoldSign API | $30/month with 40 envelopes, then $0.75 per envelope sent. |
| Per-signature API pricing with no monthly tier to pick | SignNow API | Full API access is gated behind the custom-quoted Site License plan, billed at $1.50 per signature invite. |
| Pure usage pricing with no monthly minimum | SignWell API | From $0.85 per API document, falling to $0.20 with volume. |
| Paying only for completed signatures | Anvil Etch | $1.50 per packet, billed only when every party signs, with embedding included on the free plan. |
| Government and FedRAMP requirements | DocuSign eSignature REST API | DocuSign Federal offers FedRAMP Moderate and provisional DoD IL4 authorization, separate from commercial Enhanced. |
| Teams already licensing Adobe | Adobe Acrobat Sign API | Free Developer Edition available. Production access and embedding go through Adobe sales. |
| Low per-document fee with an open-source core | DocuSeal | $0.20 per completed document plus a $20 Pro seat. AGPL-3.0 self-hosting available. |
| Open source with unlimited documents | Documenso | Teams plan at $40/month billed yearly includes embedded signing under a fair-use policy. |
Most of these APIs support several use cases, so compare their features and plan limits against your full workflow.
How we compared these eSignature APIs
Every entry below is scored against the same 8 criteria, in the same order:
API capabilities
Embedded signing
Webhook support
Sandbox access
Pricing
SDK availability
Rate limits
Security and compliance
The 10 eSignature APIs in detail
Start with the signing experience you need, then compare plan requirements and billing rules.
Foxit eSign API
Foxit’s eSign REST API embeds signing workflows directly into web applications, portals, and backend systems, so a product that generates, converts, and sends a document for signature runs under one Foxit developer relationship instead of two.
The API uses standard OAuth 2.0 authentication and returns an embeddedSessionURL that renders inside an <iframe> in your own application.
Foxit’s eSign API covers envelope creation, embedded signing, webhook events, and activity history.
Key features at a glance
| Feature | Details |
|---|---|
| Covers | Envelopes, templates, embedded signing and sending, envelope activity history. PDF Services and Document Generation available on the same account. Cloud only, storage region chosen at activation. |
| Embedded signing | Available on every plan, including the free Developer plan (trial). |
| Webhooks | Webhook channels for envelope status events. Status checks and webhooks consume no credits. |
| Sandbox | eSign trial on the free Developer plan. Envelopes are watermarked in TEST mode. |
| Pricing | eSign is billed per envelope created. eSign, PDF Services, and Document Generation draw from one shared credit pool. See Foxit API pricing and Credits Explained for current plan allocations and billing details. Billed annually and credits do not roll over. |
| SDKs | REST API with an official Postman collection and code samples. Confirm installable SDK availability with Foxit for the current unified API. The separate PDF SDK is not an eSign API SDK. |
| Rate limits | Per application, per minute, rolling 60-second window: 15 RPM in Sandbox mode, 100 RPM in Production. Free Developer plan allows up to 10 applications, paid plans up to 50. |
| Compliance claims | Foxit’s API security page lists ESIGN/UETA, AES/qualified electronic signature (QES), 21 CFR Part 11, and SOC 2 Type II. QES involves identity-validation services and a confirmed plan. |
Where it fits
Keeping eSign, PDF Services, and Document Generation on one account avoids separate keys and billing cycles.
The billing trigger is envelope creation, so cost appears before signing; status checks, webhooks, downloads, and session generation consume no credits.
Annual credits don’t roll over, so size usage before picking a plan.
Foxit uses one credit pool for eSign, PDF Services, and Document Generation.
Creating an eSign envelope uses credits; checking its status, downloading documents, and generating signing sessions do not.
Best for
Products that generate or convert PDFs then send them for signature.
Create a free developer account to activate the eSign trial. Then follow the eSign API reference to send your first envelope.
The eSign API developer portal, source of the Postman collection.
You can start with 500 free credits a year, with no credit card required.
Each application gets 15 requests per minute in the sandbox and 100 in production. The free plan allows up to 10 applications; paid plans allow up to 50.
Dropbox Sign API
Dropbox Sign (formerly HelloSign) ships six official SDKs and a published “endpoints by subscription plan” map showing which calls each plan unlocks, across signature requests, templates, bulk send, and embedded requesting and signing.
Dropbox Sign’s developer docs homepage, with the endpoints-by-plan and rate-limit references.
Key features at a glance
| Feature | Details |
|---|---|
| Covers | Signature requests, templates, bulk send, embedded requesting and signing. Hosted only. |
| Embedded signing | Standard ($250/month billed yearly) and Premium. Not available on Essentials. |
| Webhooks | Event callbacks. |
| Sandbox | Free test mode. Documents are watermarked and not legally binding. 10 requests/minute. |
| Pricing | Essentials $75/month billed yearly (50 signature requests/month), Standard $250/month (100 requests/month), Premium by quote. Billed per signature request. |
| SDKs | Python, Ruby, PHP, Java, Node.js, C#. |
| Rate limits | 100 requests/minute general; 25 requests/minute on heavier endpoints. Confirm current limits against the Dropbox Sign rate limits docs. |
| Compliance claims | SOC 2 Type II, ISO 27001, eIDAS, GDPR. QES available as a Premium add-on. See Dropbox Sign’s Trust Center for the full certification list. |
Where it fits
The endpoints-by-plan map shows restrictions before you build, since embedded signing requires Standard or above (Essentials returns HTTP 402), and full white-label branding needs the sales-led Premium plan.
Best for
Teams that want official SDKs and a self-serve Standard plan for in-app embedded signing. Start with the API docs and a free sandbox account.
Dropbox Sign allows 100 requests per minute for general calls and 25 for heavier endpoints.
BoldSign API
BoldSign’s API runs on a monthly plan with a low per-envelope rate and a free sandbox with full API access, covering signing, requesting, templates, and embedded flows on the Enterprise API plan, with US, EU, Canada, and Australia base URLs.
BoldSign’s Developer Hub, the starting point for the sandbox and docs.
Key features at a glance
| Feature | Details |
|---|---|
| Covers | Signing, requesting, templates, embedded signing and sending on the Enterprise API plan. Web plans are sandbox-only for API envelopes. Hosted, with US, EU, Canada, and Australia endpoints. |
| Embedded signing | Enterprise API plan only. |
| Webhooks | Enterprise API plan only. |
| Sandbox | Free, with full API access. Test documents are watermarked and deleted after 14 days. 50 requests/hour. |
| Pricing | $30/month including 40 envelopes, then $0.75 per envelope sent. Two users included. See BoldSign API pricing for current rates. |
| SDKs | .NET, Node.js, Java, Python, PHP. |
| Rate limits | 2,000 requests/hour in production. |
| Compliance claims | SOC 2 Type 2, HIPAA, GDPR, PCI DSS via Stripe’s processing, eIDAS. QES offered. See BoldSign’s data storage and security page for details. |
Where it fits
BoldSign’s cost is easy to estimate, since $30 includes 40 envelopes, then $0.75 each, so 100 envelopes a month costs $30 + (60 × $0.75) = $75. Embedded signing and webhooks are both self-serve. Envelopes bill on send, so a declined one still counts.
Best for
SaaS products embedding signing at modest volume that want a low per-envelope rate with no sales conversation. Start with the developer docs and the pricing page.
BoldSign’s $30 monthly plan includes 40 envelopes, with additional envelopes billed at $0.75 each.
BoldSign allows 50 requests per hour in the sandbox and 2,000 per hour in production.
SignNow API
SignNow’s per-user plans (Business, Business Premium, Enterprise) cover sending, branding, and workflow features, but full API access and embedded signing sit behind a separate, custom-quoted Site License plan rather than any of those self-serve tiers.
You can embed both signing and sending with SignNow’s API.
Key features at a glance
| Feature | Details |
|---|---|
| Covers | Embedded signing and sending, document generation from .docx templates, and webhooks, documented across the full REST API. Hosted. |
| Embedded signing | Full API access, including embedded signing, requires the Site License plan. Business, Business Premium, and Enterprise plans do not include it. |
| Webhooks | Documented event callbacks for signing status. |
| Sandbox | Free developer account with a Development mode application, up to 500 signature invites without an active trial or subscription. |
| Pricing | Business $8/month, Business Premium $15/month, Enterprise $30/month, billed annually per user with 100 invites/year included. Full API access needs the Site License plan, billed per signature invite from $1.50, custom-quoted through sales. See SignNow pricing for current rates. |
| SDKs | Node.js, C#, Java, Python, PHP. |
| Rate limits | Per application: 500 requests/hour in Development, 1,000 requests/hour by default in Live. |
| Compliance claims | SOC 2 Type II, ISO 27001, PCI DSS, CCPA, HIPAA via BAA, 21 CFR Part 11. AES and QES on Enterprise. See SignNow’s eSignature compliance page for details. |
Where it fits
SignNow’s branding and workflow features scale through ordinary per-user plans, but production API access, including embedded signing, is a sales-led Site License conversation.
Best for
Teams already planning to negotiate a volume-based API contract who want per-signature pricing rather than a flat monthly tier.
Review the API docs and pricing page to confirm current terms.
The per-user plans don’t include full API access. For that, you’ll need a separately quoted Site License.
SignWell API
SignWell takes a pure usage-pricing approach, charging per API document with no seats and no monthly minimum.
The rate drops with volume, so cost tracks actual usage rather than a fixed tier.
SignWell’s getting-started guide walks you through the API token setup and a first request.
Key features at a glance
| Feature | Details |
|---|---|
| Covers | Signing, requesting, and template editing through the API, with white-label embedding. Hosted. |
| Embedded signing | Available on the API usage plan, including embedded signing, requesting, and template editing. |
| Webhooks | Yes, with hash verification. |
| Sandbox | Unlimited test usage on free developer account. Production documents: 3/month free, 25/month once a card is added. Confirm eligibility before relying on the free allowance. |
| Pricing | From $0.85 per API document, falling to $0.20 and lower with volume. No seats or monthly minimum. See SignWell API pricing for current per-document rates and the volume calculator. |
| SDKs | Ruby, Node.js, Python, PHP, plus CLI and MCP server support. |
| Rate limits | Per token: 100 requests/minute general, 30 requests/minute for creation endpoints, 20 requests/minute for test endpoints. |
| Compliance claims | ESIGN, UETA, eIDAS, SOC 2 Type II, HIPAA with BAA. See SignWell’s security page for details. |
Where it fits
Per-document pricing means a product sending 10 documents one month and 200 the next pays only for actual usage.
The free allowance is inconsistent (25/month advertised, 3/month card-free), so confirm which applies.
Best for
Low or spiky document volumes with no minimum commitment. Review the developer docs and the pricing page.
SignWell advertises 25 free API documents a month once you add a card.
Anvil Etch E-Sign API
Anvil Etch charges $1.50 per packet only when every party has signed, so a stalled packet costs nothing.
With embedded signing on the free plan too, Anvil is the only API here where you pay only for flows that finish.
Anvil’s Etch E-Sign API documentation page.
Key features at a glance
| Feature | Details |
|---|---|
| Covers | E-signatures, PDF filling, document generation, and Workflows on the same platform. Hosted. |
| Embedded signing | Every plan, including Free. White-labeled signing pages from Product Pack ($425/month, or $340/month billed annually). |
| Webhooks | Yes, with optional payload encryption. |
| Sandbox | Unlimited free test mode with watermarked documents. |
| Pricing | $1.50 per packet, billed only when every party signs, with 25 starter packets once a card is added. See Anvil pricing for current rates and subscription options. |
| SDKs | Node.js, Python, .NET. Go is community-supported. REST plus GraphQL. |
| Rate limits | Production: 4 requests/second on Free or pay-as-you-go, 40 requests/second on subscriptions. Development: 4 requests/second on all plans. |
| Compliance claims | SOC 2 Type II, eIDAS, GDPR, UETA, ESIGN. HIPAA with a BAA on Enterprise. See Anvil Etch’s security and compliance page for details. |
Where it fits
At a 30% abandonment rate, send-based billing charges every envelope while Anvil charges only the 70% that complete.
Its 4-requests/second free-tier production cap is the tightest here; a subscription lifts it to 40/second but adds a monthly fee.
Best for
Products with high signing-flow abandonment, where paying only on completion changes the cost model. Review the API docs and the pricing page.
White-labeled signing starts with Anvil’s Product Pack at $425 per month on monthly billing.
DocuSign eSignature REST API
DocuSign is the largest eSignature platform by market presence and the one most likely to appear in enterprise procurement.
Its REST API covers hosted envelopes, templates, PowerForms, and bulk send; DocuSign Federal separately offers FedRAMP Moderate and provisional DoD IL4 authorization.

DocuSign lists Starter at $50/month, Intermediate at $300/month, and Advanced at $480/month.
Key features at a glance
| Feature | Details |
|---|---|
| Covers | Hosted envelopes and templates. PowerForms and API bulk send from Advanced. Government-cloud deployment is a separate sales discussion. |
| Embedded signing | Enhanced plans only (sales-led, five-user minimum). Embedded sending is available on every plan. |
| Webhooks | Account-, envelope-, and recipient-level Connect. Recipient-level access from Advanced. Retries extend across a 15-day span. |
| Sandbox | Free developer account with no expiry. Envelopes are not legally valid. Production requires a Go-Live review. |
| Pricing | Starter $50/month billed annually (from 40 envelopes/month), Intermediate $300/month, Advanced $480/month, Enhanced by quote. Billed per envelope sent. See DocuSign developer plans and pricing for current rates. |
| SDKs | C#, Java, Node.js, PHP, Python, Ruby, iOS, Android. |
| Rate limits | Account burst cap: 500 calls per 30 seconds, applied to both the developer/demo and production environments, within a 3,000-calls-per-hour baseline. One GET status check per envelope per 15 minutes. |
| Compliance claims | ISO 27001/27017/27018, PCI DSS, SOC 1/2 Type II. Enhanced lists AES/QES and sales-led HIPAA BAA/Part 11 options. Federal-cloud authorizations (FedRAMP Moderate, DoD IL4) are separate from commercial plans. See DocuSign’s compliance certifications page for the full list. |
Where it fits
The developer sandbox never expires, and its 8 official SDKs cover more platforms than any API here.
Embedded signing needs the Enhanced plan (five-user minimum); BoldSign, Dropbox Sign, Anvil, and Foxit offer it self-serve instead. GET endpoints allow only one status check per envelope every 15 minutes, making webhooks mandatory in practice.
Best for
Government buyers with procurement requirements that specify FedRAMP or DoD IL4 authorization.
Start with the plans and pricing page; the rate-limit figures above come from DocuSign’s own developer blog, linked in the key features table.

DocuSign’s default limit is 3,000 calls per hour, with a 500-call cap per 30 seconds. Status polling for the same envelope is limited to once every 15 minutes.
Adobe Acrobat Sign API
Adobe Acrobat Sign’s REST API v6 covers agreements, library templates, bulk sending via MegaSign, and webhooks, though production access and embedded signing go through Adobe sales rather than a self-serve tier.

Adobe’s REST API v6 lets you create agreements, retrieve signed documents, and set up webhooks.
Key features at a glance
| Feature | Details |
|---|---|
| Covers | Agreements, library templates, bulk sending (MegaSign), and webhooks through REST API v6. Hosted. |
| Embedded signing | Documented in the developer guide. Production embedding requires an Acrobat Sign Solutions or Embed (OEM) partner program agreement. |
| Webhooks | Yes, through the webhook APIs. |
| Sandbox | Free Developer Edition. Test documents carry a “test” label. |
| Pricing | Sales-led. Sent agreements consume transactions. Confirm allowances and terms in your contract. See Acrobat Sign Solutions for current options. |
| SDKs | Adobe labels its older SDKs obsolete. Use REST v6 and the current Postman samples. |
| Rate limits | Plan-dependent. GET polling capped at 3 requests/minute for Global, Enterprise, and Developer tiers, or 3 per 3 minutes for other tiers. Polling limits don’t establish total throughput. |
| Compliance claims | Adobe’s compliance list, filtered to Acrobat Sign Solutions for enterprise, lists SOC 2 Type 2, SOC 3, ISO 27001, ISO 27017, ISO 27018, HIPAA ready, FDA 21 CFR Part 11 ready, and PCI DSS 4.0. Deployment and contract scope vary by product tier. |
Where it fits
The API automates signing from CRMs for organizations already running Acrobat Sign, and MegaSign handles bulk sending to thousands of recipients.
Production access and embedded signing both require a sales-led Solutions license, and its 3-requests/minute GET polling limit is the tightest here.
Best for
Organizations that already license Acrobat Sign and want to automate existing workflows. Start with the developer guide and the free Developer Edition.

You can try Acrobat Sign’s API with a free Developer Edition before committing to a paid plan.

To embed Acrobat Sign in a production app, you’ll need to arrange access through Adobe sales.
DocuSeal
DocuSeal is open source under AGPL-3.0, with a Pro tier adding embedding, white labeling, and a per-document fee.
The core API and webhooks are open-source, but embedded signing and the React, Vue, Angular, and JavaScript embed components require Pro, even when self-hosted.

DocuSeal uses submission endpoints to send documents and retrieve signed PDFs.
Key features at a glance
| Feature | Details |
|---|---|
| Covers | Signing and form building. AGPL-3.0 core with mandatory UI attribution terms. Embedded signing on Pro. Hosted and self-hosted options. |
| Embedded signing | Pro tier, with React, Vue, Angular, and JavaScript components. |
| Webhooks | Form, submission, and template events (available under the OSS license). |
| Sandbox | Free, unlimited API and embedding sandbox. |
| Pricing | Pro: $20/user/month plus $0.20 per completed document. Same fee structure applies on Pro self-hosted. See DocuSeal pricing for current rates. Volume discounts are available. |
| SDKs | Front-end embed components (React, Vue, Angular, JavaScript). Confirm server SDK availability before planning your integration. |
| Rate limits | Not published as of 7 Oct 2026. |
| Compliance claims | Cloud: SOC 2 Type II and ISO 27001. HIPAA requires a BAA and activation in the HIPAA-compliant cloud tier. See DocuSeal’s security page for details. |
Where it fits
The $0.20 per-document fee, combined with the $20 Pro seat, is the lowest-cost model here for moderate user counts and high volume.
AGPL-3.0 requires releasing modifications under the same license if you distribute one, so proprietary products should review terms with legal (a commercial license is available).
Best for
Teams that want a low per-document fee now, with the option to self-host later. Review the API docs and pricing.

DocuSeal Pro combines a $20 monthly seat fee with a $0.20 charge per completed document.
Documenso
Documenso is open source under AGPL-3.0, with a REST API, an official TypeScript/Node.js SDK, and a self-hosted option.
Embedded signing is a Teams-plan feature; removing Documenso’s own branding needs the higher Platform tier.

Documenso’s v2 REST API is moving from separate documents and templates to a unified envelopes model.
Key features at a glance
| Feature | Details |
|---|---|
| Covers | Documents, templates, recipients, fields, and webhooks through the v2 REST API (being consolidated into a unified “envelopes” model). Hosted and self-hosted options. |
| Embedded signing | Teams plan and above, through the EmbedDirectTemplate component or signing tokens for documents created via the API. White-label embedding (no Documenso branding) requires the Platform plan. |
| Webhooks | Document, recipient, and template lifecycle events, with signature verification. |
| Sandbox | Separate staging environment that mirrors production; requires its own account and a test card to try paid-plan features. |
| Pricing | Teams: $40/month billed yearly (5 users included, additional users $8/month), with API access and embedded signing. Platform: $250/month billed yearly, with unlimited API access and white-label embedding. See Documenso pricing for current rates and the Fair Use Policy. |
| SDKs | Official TypeScript/Node.js SDK (@documenso/sdk-typescript) plus a React embed package. The REST API itself is language-agnostic. |
| Rate limits | 1,000 requests/minute per IP across /api/v1, /api/v2, and /api/v2-beta; organization-level limits can apply below that. Responses include X-RateLimit-* headers and a Retry-After value on 429s. |
| Compliance claims | SOC 2: compliant. 21 CFR Part 11 and HIPAA: compliant, but gated behind the Enterprise license. ISO 27001: planned, not yet certified. See Documenso’s compliance documentation for details. |
Where it fits
The AGPL-3.0 core keeps a self-hosted path open if you outgrow the hosted tiers; a commercial license removes the modification-disclosure terms.
Compliance is split by plan, since SOC 2 applies broadly, but 21 CFR Part 11 and HIPAA require the Enterprise license, not the self-serve Teams or Platform tiers.
Best for
Teams that want an open-source, self-hostable alternative to a closed-source API, and can self-serve on Teams or Platform rather than needing Enterprise-tier compliance from day one. Review the developer docs and pricing.

The official TypeScript/Node.js SDK’s GitHub repository (MIT-licensed, separate from the AGPL-3.0 server).

Documenso’s Teams plan includes embedded signing at $40/month; white-label embedding requires Platform at $250/month. Both prices are billed yearly.
Check which plan includes embedded signing
Every API here can technically embed a signing experience; the plan decides whether you can ship it to real users.
DocuSign gates it behind Enhanced (sales-led, 5-user minimum), Dropbox Sign requires Standard at $250/month, DocuSeal requires a Pro seat at $20/user/month, Documenso requires Teams at $40/month, and SignNow requires the quoted Site License.
Foxit eSign API includes it on every plan, including the free Developer plan. White-label branding often sits behind a still-higher plan, such as Dropbox Sign’s Premium, Anvil’s $425/month Product Pack, or Documenso’s $250/month Platform tier.
How billing triggers change your cost model
Vendors here bill at 4 points in the envelope lifecycle.
Foxit charges per envelope created, so cost accrues whether the signer completes, declines, or never opens it.
DocuSign, Adobe Acrobat Sign, BoldSign, and SignWell charge when it’s sent; SignNow’s Site License bills per signature invite similarly.
Dropbox Sign charges per signature request, close to send-based; Anvil and DocuSeal charge only when signing is completed; Documenso’s flat subscription doesn’t move with volume.
A 30% abandonment rate under send-based billing means paying for envelopes that generate no signed document. See Credits Explained, BoldSign’s API page, and Anvil pricing for the respective billing models.
Sandbox caps and rate limits you will hit first
Sandboxes aren’t identical here. BoldSign deletes sandbox documents after 14 days, so re-create test envelopes each run; DocuSign’s developer account never expires; Documenso tests through a separate staging environment.
| Vendor | Published limit |
|---|---|
| Dropbox Sign | 10 requests/minute in test mode |
| SignNow | 500 requests/hour per application in Development, 1,000 requests/hour by default in Live |
| SignWell | 100 requests/minute for general requests, 30/minute for document or template creation, and 20/minute in test mode |
| Adobe Acrobat Sign | 3 identical GET requests/minute on Global, Enterprise, and Developer tiers; 3 per 3 minutes on other tiers |
| DocuSign | Do not poll the same envelope or API object more than once every 15 minutes |
| Documenso | 1,000 requests/minute per IP, plus organization-level windows |
Dropbox Sign’s cap will slow fast-firing test suites. DocuSign’s rule matters most, since checking status after each signer action would violate it, so use webhooks wherever supported.
Confirm any unpublished limit before sizing your integration.
Match the API to your compliance requirements
A compliance badge doesn’t tell you whether an API’s default signing flow meets your requirements.
Work with legal to identify the signature level needed, including whether QES applies, and how the API captures consent and preserves the signing record.
For Foxit eSign API, the security and compliance documentation covers signature standards, consent capture, and audit trails. QES requires identity-validation services, so confirm the applicable plan with Foxit.
Best eSignature APIs FAQs
How do I choose the best eSignature API for my app?
Start with the constraint that will block you in production, not the feature list. Check which plan includes embedded signing, what triggers billing, and whether compliance claims cover your plan tier. Then compare sandbox access, SDKs, and rate limits against your expected volume.
Which eSignature APIs include embedded signing on a free plan?
Foxit eSign API includes embedded signing on every plan, including the free Developer plan, so you can build and test in-app signing before you pay. Anvil Etch also includes embedding on its free plan. Most other vendors gate embedded signing behind a paid or sales-led plan, so check plan details before you build.
Do eSignature APIs charge for envelopes that never get signed?
It depends on the billing trigger. Some vendors bill when you create or send an envelope, so declined or abandoned envelopes still count. Others bill only when every party signs, so estimate your costs at your expected completion rate.
Does a SOC 2 or HIPAA badge mean every plan is compliant?
Not always. Several vendors limit HIPAA, 21 CFR Part 11, or QES to specific plans or enterprise licenses. Confirm which plan meets your requirement, and work with legal to check how the API captures consent and preserves the signing record.
Choosing the right eSignature API
Start from the constraint that will actually block you in production, not the feature list.
A free or low-cost embedded-signing requirement rules out DocuSign and SignNow, narrowing the field to Foxit, BoldSign, Dropbox Sign, Anvil, and the two open-source options.
High abandonment rates favor Anvil’s completion-based billing or DocuSeal’s per-document model, since neither charges for a signature that never happens.
A regulated workflow needing 21 CFR Part 11 or HIPAA should check whether that’s included at its plan tier or gated behind an enterprise license, since several vendors here split that exact line.
For a product that already generates or converts PDFs and needs to send the result for signature, Foxit eSign API keeps eSign, PDF Services, and Document Generation on one developer account and one billing relationship, with embedded signing available from the free Developer plan. Create a free developer account to try it, or start with whichever API above matches your billing model, compliance requirements, and embedding needs.
Adobe Sign API alternatives: 5 simpler options for embedded signing

The Adobe Sign API supports embedded signing, but getting it to real users means going through a partner program and a sales conversation. This roundup compares five alternatives on authentication, iframe embedding, SDK coverage, and pricing. Find the right fit for your use case and start testing in a free sandbox today.
Embedded signing has a clear technical shape. An iframe loads a document, captures the signature, and fires a webhook when it’s done. Adobe Sign’s API handles that, but the path from credentials to a production embed is longer than the feature requires.
This roundup covers five alternatives evaluated on authentication setup, envelope creation, iframe embedding, and webhook handling. Each entry is specific enough to shortlist and act on today.
What Adobe Sign’s API gives you for embedded signing
Adobe’s Acrobat Sign API follows a standard OAuth2 flow. Your application exchanges credentials for a bearer token, posts to the /agreements endpoint to create an agreement, then calls /agreements/{agreementId}/views with a SIGN view type to receive a signing URL. The embedded experience loads from that URL.
The integration itself is well-documented. The production delta for teams building in-app signing surfaces at the shipping stage. Adobe does offer a free Acrobat Sign Developer Edition for testing, but shipping the embedded experience to real users goes through Acrobat Sign Embed, an OEM partner program that requires onboarding, provisioning, and app certification. Adobe’s own documentation directs developers to contact Adobe to become an Embed partner. Pricing for the API and the embed path is unpublished and requires direct contact. Teams that need an iframe signing session inside their product often find that the full onboarding cycle exceeds what the use case demands.
This article sets Acrobat Sign as the benchmark, covers what its production embed path actually involves, and then presents five alternatives that reach production faster.
Adobe’s own Acrobat Sign Embed docs, confirming the OEM partner program requires contacting Adobe directly rather than a self-serve signup.
What “simpler” means for an embedded signing API
Every alternative in this roundup is evaluated on four criteria.
- Steps from credentials to first embedded session. Fewer authentication steps and self-serve signup mean faster iteration.
- True iframe embed vs. redirect-only. A genuine iframe keeps signers inside your product. A redirect breaks the in-app experience.
- SDK language coverage. Real, installable packages on public registries (npm, PyPI, Maven, RubyGems) vs. sample code.
- Pricing model. Self-serve tiers with published rates vs. sales-gated access and custom quotes.
5 alternatives worth shortlisting
The comparison table below summarizes all 5 alternatives across these criteria.
| Provider | Embed Approach | SDK Coverage | Compliance | Pricing Model | Free Tier |
|---|---|---|---|---|---|
| Dropbox Sign | iframe (hellosign-embedded) | 6 official SDKs (Python, Node, PHP, .NET, Ruby, Java) | ESIGN, UETA, GDPR | Self-serve | Yes (test mode) |
| SignWell | iframe | 4 official SDKs (Ruby, Node, Python, PHP) | ESIGN, UETA | Self-serve, published pricing | Yes |
| BoldSign | iframe | REST + official SDKs | ESIGN, UETA, GDPR | Self-serve | Yes (free sandbox) |
| Documenso | iframe (embed SDKs for React, Vue, Svelte, Angular, Solid, Preact) | 6 framework-specific embed SDKs | ESIGN, UETA, GDPR | Self-serve / self-host | Free (self-host) |
| Foxit eSign API | iframe (embeddedSessionURL) | Sample code in cURL, PHP, C#, Java; Postman collection | eIDAS (AES, QES), ESIGN, UETA, 21 CFR Part 11, HIPAA, GDPR, CCPA | Self-serve trial, then pricing at developer-api.foxit.com | 30-day TEST mode trial |
Dropbox Sign
Dropbox Sign delivers one of the cleaner developer experiences in this space. The hellosign-embedded library wraps the iframe lifecycle, handling the parent window’s domain verification and the post-signing event messages. Official SDKs exist on PyPI, npm, Packagist, NuGet, RubyGems, and Maven. Two gates apply before you hit live traffic, as embedded apps need App Approval before leaving test mode, and the iframe verifies the parent window’s domain, so your production domain must be registered. Best for teams where polished DX and iframe UX are the top priorities.
Dropbox Sign’s API features comparison, confirming the 6-language SDK coverage and embedded-signing feature.
Dropbox Sign’s embedded signing documentation, naming the App Approval and domain-matching requirements before production traffic.
SignWell
SignWell publishes its pricing transparently on its pricing page and exposes a clean REST API that returns a signing URL you embed directly. SignWell also ships four official SDKs, covering Ruby, Node, Python, and PHP, so integration does not have to stay at the raw HTTP layer. The predictable pricing structure makes SignWell a reasonable fit for teams with variable signing volume that need cost certainty before committing.
SignWell’s pricing page, showing published self-serve rates rather than a sales-gated quote.
SignWell’s “Getting Started” docs page, listing the four official SDKs alongside the OpenAPI file.
BoldSign
BoldSign offers a free API sandbox that covers the full build-and-test cycle for embedded send-and-sign before you go anywhere near production. The path from sandbox credentials to a working iframe is short. Check BoldSign’s pricing page for current plan details. Best for teams optimizing for the fastest route to a working production embed.
BoldSign’s developer hub, showing the free sandbox signup and the Embedded Send & Sign feature. (BoldSign’s own pricing page geo-blocks automated requests from this connection, so it isn’t pictured here; the URL above is live and correct.)
Documenso
Documenso is open-source and self-hostable, which changes the data-control equation entirely. The project ships official embed SDKs for React, Vue, Svelte, Angular, Solid, and Preact, plus a web-component package. Teams that need their signed documents to stay on their own infrastructure can self-host for free. On Documenso Cloud, embedded signing starts at the Teams plan. Best for teams with strict data residency requirements or open-source mandates.
Documenso’s pricing page, confirming Embedded Signing is included from the Teams plan up, with self-hosting as the free alternative.
Documenso’s embedding docs, listing the framework-specific SDK packages.
Foxit eSign API for embedded signing
Foxit eSign API covers the complete embedded signing stack, including authentication, envelope creation, iframe signing sessions, embedded sending sessions, webhooks, and branding controls, all served from a cloud-hosted REST API.
Credentials and regional setup
Foxit separates its API products at the credential level. The Developer Portal at developer-api.foxit.com issues keys for PDF Services and Document Generation. eSign uses a separate account and dashboard. Create your account at the Foxit eSign Portal (login.foxitesign.foxit.com), then activate API access from the API tab in your account settings. Your Client ID and Client Secret appear there once API access is active.
The Foxit eSign Portal sign-in page, the separate account referenced above (distinct from the main Developer Portal login).
Before your first API call, pick your regional host. Foxit supports four regions, and your credentials are scoped to the region where they were issued.
- US:
na1.foxitesign.foxit.com - EU:
eu1.foxitesign.foxit.com - Canada:
na2.foxitesign.foxit.com - Australia:
au1.foxitesign.foxit.com
Authentication
Foxit eSign uses the OAuth2 client_credentials grant. POST your credentials form-encoded (a JSON body returns HTTP 415) to /api/oauth2/access_token.
POST https://na1.foxitesign.foxit.com/api/oauth2/access_token
Content-Type: application/x-www-form-urlencoded
grant_type=client_credentials
&client_id=YOUR_CLIENT_ID
&client_secret=YOUR_CLIENT_SECRET
&scope=read-write The response contains an access_token. Pass it as Authorization: Bearer <token> on every subsequent request.
Envelope creation and the embedded session URL
To launch an embedded signing session, create the envelope with the embedded session flag set. The API returns an embeddedSessionURL for each recipient. Use the complete URL the API returns, because assembling it manually produces failures when session hosts and tokens vary by region.
The signing experience loads into a standard iframe.
<div style="height: 800px; width: 100%; overflow: hidden;">
<iframe
id="esignIframe"
src="EMBED_SESSION_URL"
title="Foxit eSign signing session"
style="width: 100%; height: 100%; border: 0;"
></iframe>
</div> Include the esignGeniePostMessageParent.js script on the parent page to receive post-message events from the signing session. After signing or declining, Foxit eSign redirects to your specified URL and appends folderId and event as query parameters (signing_success or signing_declined).
A real embeddedSessionURL opened directly (the same page an iframe would load), created live with createEmbeddedSigningSession, showing the Text Tag field rendered as an interactive input and the “Required Fields Left” counter this article’s flow produces.
To give preparers an embedded document-preparation experience, set createEmbeddedSendingSession to true in the Create Envelope request. Foxit returns a second embeddedSessionURL for the sending view, which you embed the same way.
Document preparation
Two paths exist for placing signature fields.
- Text Tags in the PDF: embed tag syntax directly in the PDF content, then set
processTextTags: truein the envelope creation call. Foxit converts the tags into fields without removing the text. Match the tag font color to the document background to hide the raw tag text from signers. - Direct API field placement: if your application already holds the page coordinates and field dimensions, POST the field definitions directly and skip Text Tags entirely.
Webhooks
Webhooks deliver real-time envelope status changes without polling. Configure webhook channels to receive events when an envelope reaches EXECUTED status, which lets your application trigger downstream steps (such as uploading the signed document to a CRM or generating follow-up forms) the moment signing completes.
Code samples and integration path
Foxit’s eSign developer guide ships sample code in cURL, PHP cURL, C#, and Java. Foxit also publishes an eSign Postman collection on GitHub, which covers the full request sequence from authentication through envelope retrieval. The API overview page lists .NET, Java, PHP, Python, Ruby, and TypeScript as SDK languages, but no packages under those names appear on PyPI, npm, RubyGems, Packagist, or Maven. eSign integration is a direct REST integration with sample code in four languages, with no six-language installable SDK suite available.
Compliance coverage
Foxit eSign covers a broad compliance floor, documented at foxit.com/esign-pdf/maintain-industry-compliance/, including eIDAS conformance at the Advanced Electronic Signature (AES) and Qualified Electronic Signature (QES) levels, ESIGN, UETA, 21 CFR Part 11, HIPAA, GDPR, and CCPA. Audit trails include identity verification, tamper-evident logs, and certificates of completion. Regional hosting across four jurisdictions keeps signed documents within a chosen geographic boundary without requiring you to build compliance infrastructure from scratch.
Trial mode
Activating eSign provisions a 30-day trial in TEST mode. Completed envelopes in TEST mode carry a watermark. Check developer-api.foxit.com for current pricing and plan details before moving to production.
How to pick the right provider
Match your primary requirement to the provider built for it.
- Regulated industries requiring eIDAS at AES or QES level, HIPAA, or 21 CFR Part 11 coverage: Foxit eSign API.
- Transparent self-serve pricing and predictable per-document costs: SignWell.
- Fastest path to a working production embed with minimal friction: BoldSign.
- Self-hosted or open-source data control requirements: Documenso.
- Cleanest developer experience with a polished iframe UX library: Dropbox Sign.
Identify the scenario that matches your requirements and open that provider’s free tier or sandbox today. Every option above gives you something to test without a sales call.
Adobe Sign API FAQ
What is an embedded signing API?
An embedded signing API is a REST API that returns a session URL a developer loads inside their own application, typically via iframe, so signers complete the entire signing process without leaving the host product. The API handles session creation, field rendering, signature capture, and status callbacks on the server side.
Why do developers look for Adobe Sign API alternatives?
The most common reasons are the enterprise-tier access requirements that gate the production embedded signing path, pricing that is unpublished for self-serve on the API or Embed OEM program, and an integration scope that exceeds what a dedicated embedded signing use case needs. Teams building a single in-app signing flow often want a REST API, a sandbox, and published pricing, and several alternatives deliver exactly that.
Does Foxit eSign API support iframe-based embedded signing?
Yes. The Create Envelope endpoint returns an embeddedSessionURL that loads directly into an iframe on your page. Include the esignGeniePostMessageParent.js script on the parent page to receive post-message events from the signing session, and configure a redirect URL to capture the signing_success or signing_declined outcome.
How do I choose an e-signature API for embedded signing?
Apply four criteria, counting the steps from credentials to your first embedded session, confirming the API returns a true iframe URL rather than a redirect, checking whether the provider’s SDKs are real installable packages on public registries, and verifying that pricing is published at a self-serve tier your team can access without a sales conversation. The comparison table above maps all five providers across these dimensions.
What compliance standards do embedded signing APIs typically cover?
Most providers cover ESIGN and UETA, which establish legal validity for electronic signatures in the US. GDPR coverage is common among providers with EU hosting. Foxit eSign API extends further to eIDAS at AES and QES levels, HIPAA, 21 CFR Part 11, and CCPA, making it the strongest option for regulated industries.
Can I test an embedded signing API before committing to a paid plan?
Yes. Every provider in this roundup offers a free tier or sandbox. Dropbox Sign provides a test mode, BoldSign offers a free sandbox covering the full build-and-test cycle, SignWell has a free plan, Documenso is free to self-host, and Foxit eSign API provisions a 30-day TEST mode trial on account activation.
What is the difference between a true iframe embed and a redirect-based signing flow?
A true iframe embed loads the signing session inside your application’s page, so the signer never leaves your product. A redirect-based flow sends the signer to an external URL, breaking the in-app experience and handing off visual control to the signing provider. For products where brand consistency and user retention matter, a true iframe embed is the correct choice.
Getting started with Foxit eSign API
Create a free Foxit account at app.developer-api.foxit.com/sign-up, activate eSign from your account settings, and collect your Client ID and Client Secret from the Foxit eSign Portal. Those eSign credentials are issued separately from your PDF Services and Document Generation keys, so look in the eSign Portal’s API tab specifically. From there, authenticate with the client_credentials grant, create an envelope, and load the returned embeddedSessionURL into an iframe. The full flow is testable in 30-day TEST mode with no commitment required.
6 Best PandaDoc API alternatives for developers in 2026

PandaDoc’s API works well for sales documents, but Enterprise-only access and per-seat pricing get in the way of signing embedded in your product. This roundup compares six alternatives, including Foxit eSign, DocuSign, and BoldSign, across seven criteria that decide how well an eSign API fits your app. Use the side-by-side table to shortlist the right option before you commit.
PandaDoc built its API around document workflows (proposals, quotes, contracts with approval chains). The API is capable, but two frictions surface quickly when you try to embed signing inside a product you’re building. API access sits on the quote-based Enterprise tier, so a developer who wants programmatic control can’t pick a published plan and start. The self-serve plans are priced per seat, tracking headcount rather than envelope volume, which misaligns cost with the way product-embedded signing actually scales.
If your use case is pure signing or in-app embedded flows, you’ll likely outgrow PandaDoc’s API shape before you outgrow the need. This roundup covers six PandaDoc API alternatives (Foxit eSign, DocuSign, Adobe Acrobat Sign, Dropbox Sign, SignNow, and BoldSign), measured across seven criteria that determine how well an e-signature API fits a product integration. Every claim below was checked against the vendor’s own live pages in September 2026, and the Foxit behaviour was checked against the live sandbox.
What to look for in an e-signature API
The best e-signature API for a product integration keeps signers inside your application, authenticates server-side without interrupting the flow, and prices by usage rather than headcount. Every entry in this roundup is assessed against the same seven criteria, each of which maps to a row in the comparison table below.
In-app embedding mechanism. Three patterns exist in the market. The first returns a raw iframe URL directly from the API that you drop into an <iframe>. The second provides a vendor JavaScript library or web component that manages the session for you. The third redirects the signer to the vendor’s own domain and returns them afterward. The table names the mechanism and says whether the signer stays inside your application.
Auth approach. The grant type and how credentials reach the token endpoint. Client-credentials grants suit server-side integrations best, since no human login step interrupts the flow.
Webhook granularity. Which lifecycle events fire (viewed, signed, declined, expired) and whether payloads carry a signed HMAC you can verify before trusting them.
Client-library coverage. Official language SDKs versus a documented REST API with request samples. Both work, but the delta in integration time is real, and a published SDK that the vendor itself marks as out of date is worth less than a clean REST reference.
Named compliance certifications. Listed by name, not tier label. Certifications gated behind a plan upgrade, a signed agreement, or a qualified third-party provider are marked as such, because the conditions matter in a procurement conversation.
Pricing model structure. Described as per-seat, per-envelope, volume-based, or consumption and credit-based.
Free developer tier. Whether one exists, whether a credit card is required, and whether it carries production traffic or test-mode traffic only. Those three facts determine whether you can validate your integration before committing.
PandaDoc API at a glance
PandaDoc offers a free tier that includes 60 documents per year with no credit card, two self-serve per-seat monthly tiers at $19 and $49 per seat, and a quote-based Enterprise tier where API access lives.
PandaDoc’s published plans. Note that API sits in the Enterprise column, under “Let’s talk” pricing, while Starter and Business are metered per seat.
At the API level, PandaDoc supports document creation from a PDF or a pre-built template, recipient groups, and field placement through its field tags reference. Field tags use bracket notation and cover eight types, including textfield (short form t), checkbox (c), signature (s), date (d), initials (i), dropdown (dd), radio (r), and stamp (st). Radio and stamp each carry their own documented limitations, so a radio block has to sit on one page with unique option values, and a stamp field is square with its height derived from its width. The API changelog documents ongoing updates to this surface.
The Supported field types table, with radio and stamp as the two types most roundups miss, each followed by its own limitations section.
For in-app embedding, PandaDoc ships a separate pandadoc.js JavaScript library alongside four official client SDKs covering Python, Node, Java, and PHP. Webhooks fire on document lifecycle events. Branding control is restricted on the lower self-serve tiers.
PandaDoc fits well where the workflow is sales-heavy, covering proposals with approval routing, quotes that require CRM sync, and contracts that evolve through negotiation. That’s a different job than product-embedded signing, which is where the mismatch above comes from.
6 PandaDoc API alternatives
Each of the 6 is scored against the same 7 criteria above, starting with the option built specifically for product-embedded signing.
Foxit eSign API
Foxit eSign’s API is built for the product-embedded use case. Authentication runs over the OAuth 2.0 client-credentials flow against a POST-only, form-encoded token endpoint at POST https://na1.foxitesign.foxit.com/api/oauth2/access_token, and a JSON body to that endpoint returns HTTP 415 because it accepts only application/x-www-form-urlencoded. The regional hosts, per the Foxit eSign developers guide, are na1.foxitesign.foxit.com (US), eu1.foxitesign.foxit.com (EU), na2.foxitesign.foxit.com (CA, not ca1), and au1.foxitesign.foxit.com (AU).
Embedded signing runs through createEmbeddedSigningSession, and the parameter does not work on its own. Setting it to true with nothing else returns {"result": "error", "error_description": "email id of embedded signer(s) not submitted"} and no folder at all, which is the single most common way to lose an afternoon here. You have to pair it with either embeddedSignersEmailIds, an array naming the signers who get a session, or createEmbeddedSigningSessionForAllParties set to true, which covers every party on the envelope. Either pairing returns result: success and a top-level embeddedSigningSessions array whose entries carry emailIdOfSigner, embeddedToken, and embeddedSessionURL, the last of which is what you load in your own iframe. Setting createEmbeddedSigningSessionForAllParties alone, without createEmbeddedSigningSession, is silently ignored, returning success with folderStatus: DRAFT and no sessions.
{
"folderName": "Customer agreement",
"inputType": "base64",
"base64FileString": ["<base64 of your PDF>"],
"fileNames": ["agreement.pdf"],
"processTextTags": true,
"sendNow": false,
"parties": [
{
"firstName": "Jane",
"lastName": "Smith",
"emailId": "[email protected]",
"permission": "FILL_FIELDS_AND_SIGN",
"sequence": 1
}
],
"createEmbeddedSigningSession": true,
"embeddedSignersEmailIds": ["[email protected]"]
} The body above is the minimum that produces a working session. The one behaviour worth planning around is that folderStatus comes back as SHARED rather than DRAFT even with sendNow: false, because the envelope has to be live for the session URL to open. No email goes out either way, so sendNow: false still means the signer only reaches the document through the URL you hand them.
The embeddedSessionURL opened in a browser. The “Required Fields Left” counter in the header confirms the Text Tags were parsed into interactive fields rather than left as literal text.
Branding is handled by the themeColor parameter, four redirect parameters (signSuccessUrl, signDeclineUrl, signLaterUrl, signErrorUrl), and a long list of visibility toggles that goes well beyond the three most roundups mention. Alongside hideSenderName, hideFolderName, and hideDocumentsName, the developers guide documents hideSignerSelectOption, hideSignerActions, hideAddMeButton, hideAddNewButton, hideAddGroupButton, hideDeclineToSign, hideMoreAction, and hideNextRequiredFieldBtn, among others. Notification emails carry their own path through emailTemplateId, which applies an account-level template with custom content, logo, button colour, and footer. What the guide does not document anywhere is full white-label customization, and there is nothing in it about suppressing Foxit’s own mail delivery in favour of your SMTP server.
The client-library position is a documented REST API with request samples in cURL, PHP cURL, .NET, and Java, plus the official Foxit eSign Postman collection. No language-specific SDK exists. The collection imports cleanly, but two of its request bodies need their JSON repaired before they will run. “Create Envelope from URL” carries "inputType": "{"inputType": "url"}" with unescaped nested quotes, and sending it verbatim against the live sandbox returns HTTP 400 with Unexpected character ('i' (code 105)): was expecting comma to separate OBJECT entries. “Create Envelope from Base64” holds a bare unquoted base64 token inside an array and sets inputType to base64FileString, where the value the API actually accepts is base64. Both are quick fixes, but budget for them rather than assuming the collection runs as downloaded.
Compliance splits across two sources. The Foxit eSign compliance page documents conformance with eIDAS AES and QES (QES applies when used with a qualified trust service provider), ESIGN, UETA, HIPAA, GDPR, 21 CFR Part 11, and CCPA. The Foxit trust center is the source for SOC 2 Type 2 attested operations and for the Business Associate Agreement, which it frames as available where applicable rather than as a blanket offer.
Pricing is consumption and credit-based across the whole Foxit API Platform, which consolidates eSign alongside PDF Services, Document Generation, and PDF Embed on one account and one credit pool. The free Developer plan carries 500 shared credits per year, eSign is metered at 5 credits per envelope, and no credit card is required to open the account. That works out to roughly 100 envelopes on the free tier. Activating eSign provisions a 30-day Business trial in TEST mode, where completed envelopes are watermarked, so plan the production cutover separately from the integration work.
Best fit for teams building compliance-regulated products that need regional data residency, a granular compliance certification list, and an embedding mechanism that keeps signers inside the host application.
DocuSign eSignature API
DocuSign’s eSignature API is the most mature option on this list, with the broadest ecosystem of third-party integrations. Authentication supports OAuth2 authorization code and JWT grants, and the JWT path suits server-side integrations.
Embedded signing uses a recipient view URL returned by the API. The embedded signing guide is explicit that iframes work but come with conditions, stating that they “are not supported with all types of authentication options or SBS pen types” and that “Only full-screen iframes are supported for signers on mobile devices.” The newer focused view only works inside an iframe, and DocuSign’s own JavaScript library builds that iframe in the DOM for you. Client SDKs cover eight platforms, namely C#, Java, Node.js, PHP, Python, Ruby, iOS, and Android. Webhooks fire on a detailed event set including envelope and recipient lifecycle states, and payloads can be verified against a shared HMAC key.
The eight tabs on DocuSign’s SDK page. The two mobile SDKs are easy to miss because the page opens on C# by default.
Compliance certifications include SOC 2 Type 2, ISO 27001, HIPAA (via BAA, plan-dependent), eIDAS, ESIGN, and UETA. FedRAMP Moderate authorization covers eSignature and CLM on a Government Community Cloud deployment, which DocuSign describes as running on “special servers that only house government data.” That is a separate environment from the commercial cloud, so treat it as a distinct procurement path rather than a property of the standard product. See DocuSign eSignature plans for the current plan structure. Pricing is per-seat and per-envelope depending on plan tier.
A free developer account is available with “No obligation, no credit card required.” It runs against the demo environment rather than production, so promoting an integration means a separate go-live review.
The developer account form. The no-credit-card condition sits directly under the submit button, and the account it creates is a demo environment.
Best fit for enterprises with existing DocuSign contracts, teams that need FedRAMP coverage on the government cloud, or projects where the size of the SDK ecosystem reduces integration risk.
Adobe Acrobat Sign API
Adobe Acrobat Sign’s REST API, documented at the Acrobat Sign developer guide, offers OAuth2 authorization code and refresh token flows. Embedded signing redirects the signer to Adobe’s domain by default, though the API does support returning a signing URL you can iframe, and the configuration is less straightforward than dedicated embedded-first APIs.
Adobe does publish SDKs, and the SDK Downloads page names C#, JAVA, JavaScript, OpenAPI, and REST, each with a readme, docs, and a repo download. The more decision-relevant fact is printed on that same page, where Adobe states that “The SDKs are obsolete and haven’t been in sync with REST v6 APIs for a while” and directs developers to the API endpoints and the Postman workspace instead. Treat the SDK list as historical and plan on raw REST calls.
Adobe ships five SDKs and marks them obsolete on the same page. The blue callout is the sentence that should drive your integration plan.
Adobe integrates natively with Microsoft 365, Creative Cloud, and Acrobat. Webhooks fire on the AGREEMENT, WIDGET, and MEGASIGN resource types, scoped at ACCOUNT, GROUP, USER, or RESOURCE level, so bulk-send events are covered alongside agreements and web forms.
Compliance includes SOC 2 Type 2, ISO 27001, FedRAMP Moderate on the Acrobat Sign for Government offering, HIPAA (via BAA, plan-dependent), eIDAS, ESIGN, and UETA. Adobe publishes no standalone Acrobat Sign pricing page reachable through standard navigation, and plan structure varies by Adobe agreement type, so pricing is generally per-seat and negotiated. A free Acrobat Sign Developer Edition account does exist, and the developer guide states that it includes access to the Acrobat Sign API plus testing for document exchange and execution.
Best fit for organizations already running the Adobe enterprise stack, or where native Acrobat and Creative Cloud integration reduces friction for document authors.
Dropbox Sign API
Dropbox Sign (formerly HelloSign) is API-first by design. The SDK overview lists SDKs generated from an OpenAPI spec covering C#, Java, PHP, Python, Ruby, and Node.js. Authentication uses OAuth2 authorization code for user-facing flows and an API key for server-to-server calls.
Embedded signing returns a URL from the API that you load in an <iframe>, and the vendor’s hellosign-embedded JavaScript package manages the iframe lifecycle. Webhooks carry HMAC-SHA256 signatures for payload verification and fire on a full set of signature request lifecycle events.
Compliance covers SOC 2 Type 2, HIPAA (via BAA, plan-dependent), eIDAS, ESIGN, and UETA. Pricing on the Dropbox Sign API product page is volume-based rather than per-seat, with monthly subscription tiers keyed to signature-request count. Essentials starts at $75 per month and 50 requests, Standard at $250 per month and 100 requests, and Premium is custom, with volumes over 500 requests per month routed through sales. The API itself is free in test mode, which is how you validate an integration before committing to a tier.
Dropbox Sign meters the API by signature request volume. No seat count appears anywhere on the API product page.
Best fit for teams that want broad official SDK coverage and a developer-first embedded signing path, particularly where a Dropbox ecosystem connection is already present.
SignNow API
SignNow’s API treats white-labeling as a documented, first-class capability. The white-labeled signing guide covers brand containers created with POST /v2/brands, logo upload through POST /v2/brands/{brand_id}/resources/logo, background and button colour control through PUT /v2/brands/{brand_id}/resources/general, and per-element visibility in the signing editor through PUT /v2/brands/{brand_id}/resources/editor. The same guide tells you not to use SignNow’s default email delivery and to “trigger your own emails using your SMTP server” instead, which is the piece that makes full brand suppression achievable. Authentication is OAuth2 authorization code and password grant, and the SignNow API docs document the full flow.
The brand container and logo endpoints, with the request bodies inline. This is the page that carries the detail, not the white-labeling index.
Embedded signing is iframe-based, generated via POST /v2/documents/{document_id}/embedded-invites. Official SDKs cover PHP, Python, Java, .NET, and JavaScript. Webhooks support document lifecycle events. Compliance includes SOC 2 Type 2, HIPAA, eIDAS, ESIGN, UETA, and GDPR.
Pricing is volume-based, not per-seat. Every tier on the SignNow plans page is marked “Unlimited users” under the headline “Free unlimited users with plans that scale,” with Business at $8 per month, Business Premium at $15, and Enterprise at $30, each including 100 signature invites per year. Full API access sits on the Site License tier, which is priced at $1.50 per signature invite with volume discounts.
Every SignNow tier carries an “Unlimited users” badge. The Site License column, where full API access lives, is metered per signature invite.
Best fit for SaaS products where the requirement is full brand suppression of the signing vendor, including email notifications and signing UI chrome.
BoldSign API
BoldSign is API-first, developer-first. The BoldSign developer docs document iframe-based embedded signing through a Get Embedded Signing Link API that returns a URL you drop into an <iframe>. Official client libraries cover .NET (C#), PHP, Python, Java, and Node.js. Authentication supports both API key and OAuth2 access token patterns. Webhooks notify on document events.
BoldSign’s client libraries page. All five are vendor-maintained, with GitHub links per language.
Compliance documentation covers SOC 2 Type 2, eIDAS, ESIGN, UETA, HIPAA, and GDPR, plus data residency in the US, EU, Canada, and Australia. HIPAA is the one certification that is plan-gated, appearing first on the Business plan and carried upward from there, including on the Enterprise API plan. Everything else in that list is present on every tier.
The compliance block of BoldSign’s plan comparison. HIPAA is the only row with dashes, and they sit on the two cheapest tiers.
The API product is priced per envelope rather than per seat. That distinction matters because BoldSign’s web app tiers are seat-based and the two get conflated. The Enterprise API plan is $0.75 per envelope, starting at $30 per month with 40 envelopes included. A free sandbox gives full API access with no credit card required, with signed documents watermarked and deleted automatically 14 days after creation.
BoldSign’s API tier is metered per envelope. The free sandbox card on the right states the no-credit-card condition.
Best fit for teams that want a modern, lower-overhead alternative to DocuSign with a documented embedded signing path and a no-credit-card sandbox to validate before committing.
Shortlisting your options
| Criterion | Foxit eSign | DocuSign | Adobe Acrobat Sign | Dropbox Sign | SignNow | BoldSign |
|---|---|---|---|---|---|---|
| In-app embedding | Signer stays in your app. iframe URL from createEmbeddedSigningSession plus embeddedSignersEmailIds or createEmbeddedSigningSessionForAllParties | Signer stays in your app. Recipient view URL in an iframe, with auth-method and mobile full-screen caveats | Redirect to Adobe’s domain by default. Signing URL can be iframed, with more configuration | Signer stays in your app. URL from the API, with hellosign-embedded managing the iframe | Signer stays in your app. iframe URL via the embedded-invites endpoint | Signer stays in your app. iframe URL from the Get Embedded Signing Link API |
| Auth approach | OAuth2 client-credentials, POST-only form-encoded endpoint | OAuth2 authorization code and JWT grant | OAuth2 authorization code and refresh token | OAuth2 authorization code, with API key for server-to-server | OAuth2 authorization code and password grant | API key or OAuth2 access token |
| Webhook granularity | Envelope lifecycle events with HMAC secret-key verification | Full envelope and recipient lifecycle with HMAC verification | AGREEMENT, WIDGET, and MEGASIGN resource types, scoped at account, group, user, or resource level | Full signature request lifecycle with HMAC-SHA256 signature | Document lifecycle events | Document lifecycle events |
| Client libraries | REST API with cURL, PHP cURL, .NET, and Java samples, plus a Postman collection whose two envelope-creation bodies need JSON repair. No language SDK | C#, Java, Node.js, PHP, Python, Ruby, iOS, Android | C#, Java, JavaScript, OpenAPI, REST, all marked obsolete by Adobe and out of sync with REST v6 | C#, Java, PHP, Python, Ruby, Node.js (OpenAPI-generated) | PHP, Python, Java, .NET, JavaScript | .NET, Java, Node.js, PHP, Python |
| Compliance certifications | eIDAS AES and QES (QES requires qualified trust service provider), ESIGN, UETA, HIPAA, GDPR, 21 CFR Part 11, CCPA (compliance page), SOC 2 Type 2 and conditional BAA (trust center) | SOC 2 Type 2, ISO 27001, eIDAS, ESIGN, UETA, HIPAA via BAA (plan-dependent), FedRAMP Moderate on the Government Community Cloud | SOC 2 Type 2, ISO 27001, eIDAS, ESIGN, UETA, HIPAA via BAA (plan-dependent), FedRAMP Moderate on Acrobat Sign for Government | SOC 2 Type 2, eIDAS, ESIGN, UETA, HIPAA via BAA (plan-dependent) | SOC 2 Type 2, eIDAS, ESIGN, UETA, HIPAA, GDPR | SOC 2 Type 2, eIDAS, ESIGN, UETA, GDPR, data residency in US, EU, CA, AU. HIPAA from the Business plan upward |
| Pricing model | Consumption and credit-based, shared across eSign, PDF Services, DocGen, and Embed, at 5 credits per envelope | Per-seat and per-envelope (tier-dependent) | Per-seat, negotiated. No standalone Acrobat Sign pricing page is published | Volume-based monthly tiers keyed to signature-request count | Volume-based. Unlimited users on every tier, with full API access on Site License at $1.50 per signature invite | Per-envelope for the API product at $0.75, from $30 per month with 40 envelopes. Web app tiers are per-seat |
| Free developer tier | Yes. Free Developer plan, no credit card, 500 shared credits per year at 5 credits per envelope, roughly 100 envelopes. eSign activation runs 30 days in TEST mode with watermarked envelopes | Yes. Free developer account, no credit card, demo environment rather than production | Yes. Acrobat Sign Developer Edition, free, with API access for testing document exchange and execution | Yes. The API is free in test mode, with paid tiers required for production traffic | Yes. Free trial on the self-serve tiers, with full API access gated to the Site License tier | Yes. Free sandbox, no credit card, full API access. Signed documents are watermarked and deleted after 14 days |
Decision path for compliance-regulated apps. Foxit eSign’s two-source compliance posture covers eIDAS AES and QES, HIPAA, GDPR, 21 CFR Part 11, and CCPA on the compliance page, with SOC 2 Type 2 and the conditional BAA on the trust center, giving regulated teams a verifiable certification list alongside regional host selection across US, EU, CA, and AU. If FedRAMP Moderate is a hard requirement, both DocuSign and Adobe carry it on dedicated government cloud offerings, which is a separate procurement path from their commercial products.
Decision path for lowest-friction embedding. Foxit eSign, Dropbox Sign, and BoldSign all return an embeddable URL from the API with minimal configuration. Foxit eSign and BoldSign let you start with no credit card. Dropbox Sign’s hellosign-embedded library handles iframe lifecycle management if you’d rather not manage that directly.
Decision path for teams already on DocuSign. Stay on DocuSign. The JWT grant, the government cloud coverage, and the existing SDK investment represent switching costs that rarely pay back unless a specific compliance delta or pricing model change forces the move.
Decision path for full white-label. SignNow is the documented choice. Its white-labeled signing guide covers brand containers, logo and colour control, per-element visibility in the signing editor, and the instruction to send signing links from your own SMTP server, a surface no other vendor on this list documents to the same depth.
PandaDoc API alternatives FAQ
Which of these e-signature APIs support HIPAA compliance?
For Foxit eSign, HIPAA is documented on the Foxit eSign compliance page, and the Foxit trust center states that Foxit is prepared to enter into a Business Associate Agreement where applicable, so the BAA is conditional rather than blanket. BoldSign gates HIPAA to its Business plan and above, which its own plan comparison shows explicitly. Across the market, HIPAA support is usually tied to a specific plan tier and a signed BAA rather than being a platform-wide property, so read the plan table rather than the marketing page.
Does Foxit eSign offer a free developer plan?
Yes, through the developer-API sign-up form. No credit card is required, and the account-level pool of 500 shared credits per year (5 per eSign envelope) covers roughly 100 envelopes across the full signing lifecycle before the 30-day TEST-mode trial needs a production decision.
Can I test an e-signature API integration without a credit card?
All six alternatives let you start without one, but what the free environment can do varies. DocuSign’s is a demo environment rather than production, BoldSign watermarks and auto-deletes sandbox documents after 14 days, and SignNow reserves full API access for its Site License tier. Check the free-tier row in the table above for each vendor’s specific conditions.
What auth grant type should a server-side product integration use?
Client-credentials or JWT, since neither requires a human login step at token time. Foxit eSign uses client-credentials; DocuSign supports JWT alongside authorization code. Authorization code grants suit user-facing flows instead.
Conclusion
Choosing among PandaDoc API alternatives comes down to the same seven questions every time, namely whether the signer stays in your app, how the API authenticates, what the webhooks tell you, whether an official client library exists and is current, which certifications are named rather than implied, whether the meter counts seats or envelopes, and how far you can get before a credit card is required. Those answers move. Adobe’s SDKs were current once and are now marked obsolete on Adobe’s own page, SignNow has dropped its seat meter entirely, and a Postman collection can ship with JSON that does not parse. Check the vendor’s live pages rather than a roundup from last year, including this one.
If you want to test a full signing flow today, the Foxit eSign developer account is free, needs no credit card, and gives you 500 shared credits per year across eSign and the rest of the Foxit API platform, which is about 100 envelopes to build against before you decide anything.
6 Best DocuSign API Alternatives for Developers in 2026

Comparing a DocuSign API alternative can eat hours of research time. This guide breaks down six eSign APIs, including Dropbox Sign, Adobe Acrobat Sign, PandaDoc, SignNow, BoldSign, and Foxit eSign, against the six criteria that matter most for integration speed and long-term maintenance.
DocuSign’s API works, but redirecting signers to an external DocuSign-hosted page puts a seam in your user experience you can’t fully control, pricing tiers require a sales call to decode, and per-envelope costs escalate unpredictably at scale. If you’ve already decided DocuSign isn’t the right fit, this roundup gives you a structured way to narrow the field fast.
Six alternatives are covered here (Dropbox Sign, Adobe Acrobat Sign, PandaDoc, SignNow, BoldSign, and Foxit eSign), evaluated against six criteria that directly affect integration time and long-term maintainability. Each tool is broken down the same way, so you can compare like against like rather than marketing page against marketing page.
What to evaluate in an eSign API
The six criteria below separate APIs worth building on from ones that will cost you significant refactoring time later. Pin them down before you compare options.
Embedded signing depth. An iframe-based session keeps signers inside your application, while a redirect-based session hands them off to a third-party URL. The delta between “supports embedded signing” and “delivers a fully iframe-native experience” is significant.
Auth model. OAuth2 client credentials gives your backend a machine-to-machine token with no user interaction required. API key auth is simpler but typically coarser in permission scope and harder to rotate safely at scale.
Webhook event granularity. A single “document completed” event isn’t enough if your workflow needs to react to individual signer events, field changes, or expiration triggers. Check what event names are actually documented, not listed on a marketing page.
SDK language coverage. Confirm whether the vendor ships official SDKs for Python, Java, Node.js, and Go. If raw REST calls are your only option, factor in the maintenance overhead for your team.
Compliance certifications. eIDAS, ESIGN, UETA, HIPAA, GDPR, and 21 CFR Part 11 have different requirements. Confirm which certifications are documented and current, not featured in a hero banner.
Pricing model transparency. Envelope-based, seat-based, and consumption-based pricing each carry different risk profiles at scale. If you can’t read the pricing page without talking to sales, add that friction to your evaluation score.
The six alternatives at a glance
The table summarizes where each tool lands on the criteria above. Treat it as a shortlist filter, then read the section for any tool that survives. Compliance and pricing move often, so the linked pages are the source of truth, not this table.
| Tool | Auth | Embedded signing | Webhooks | Official SDKs | Pricing model |
|---|---|---|---|---|---|
| Dropbox Sign | OAuth2 + API key | Iframe via sign_url | Signer-level events | Python, Node, Java, Ruby, PHP | API tier, published |
| Adobe Acrobat Sign | OAuth2 | Transient docs + widgets | Extensive | Java, plus REST | Enterprise, sales-led |
| PandaDoc | OAuth2 + API key | Iframe (send + sign) | Document lifecycle | Node, Python, plus REST | Document/seat-based |
| SignNow | OAuth2 + API key | Embedded session URLs | Functional, coarser | Fewer official SDKs | Per-envelope, published |
| BoldSign | OAuth2 + API key | Iframe embedded | Documented events | .NET, Java, Node, Python | Tiered, transparent |
| Foxit eSign | OAuth2 client credentials | Iframe / web view, no redirect | 9 events incl. folder_executed, HMAC-signed | REST, examples in Python | Tiered, published |
Dropbox Sign
Dropbox Sign (formerly HelloSign) runs a clean REST API with solid embedded signing and documentation that developers consistently rate as approachable. If you’re already in the Dropbox ecosystem and don’t need heavy customization, it provides a reliable, well-documented API. But it does have thinner webhook payloads and narrower embedded-UX control than purpose-built full-control APIs.
- Auth model. OAuth2 for multi-account apps, plus straightforward API key auth for single-account integrations.
- Embedded signing. Embedded requests return a
sign_urlyou load directly into an iframe, keeping signers in your app. - Webhook granularity. Events fire at each signer-level state change, though payloads are less granular than the top-tier options.
- SDKs. Official SDKs for Python, Node.js, Java, Ruby, and PHP.
- Compliance. Positioned for general business use; confirm the current certification list in their docs before relying on a specific standard.
- Pricing model. API pricing is published as its own tier, separate from the end-user product.
See the developer docs and API pricing.
Dropbox Sign’s developer documentation. The organized reference and SDK list are the reason it scores well on the docs-quality criterion.
Adobe Acrobat Sign
Adobe Acrobat Sign brings enterprise-scale infrastructure and a deep compliance footprint to its REST API, at the cost of a larger, more complex surface area. It’s a reasonable fit for large enterprises already standardized on Adobe Document Cloud with compliance needs that benefit from Adobe’s footprint. On the other side, it also has the largest integration overhead on this list and pricing that is not self-serve.
- Auth model. OAuth2, integrated with Adobe’s broader identity and Document Cloud platform.
- Embedded signing. Supported via Transient Documents and widget-based flows rather than a single drop-in iframe call.
- Webhook granularity. Extensive event coverage, appropriate for large multi-step enterprise workflows.
- SDKs. An official Java SDK plus a broad REST surface; other languages typically integrate at the REST level.
- Compliance. Strong certification footprint aimed at healthcare, finance, and government; verify the specifics for your regulatory context.
- Pricing model. Enterprise-tier and sales-led; expect a conversation rather than a public per-call rate.
See the developer guide and Adobe’s Acrobat business pricing page.
The Acrobat Sign API overview. The breadth here is the point, and also the integration-overhead warning.
PandaDoc
PandaDoc’s API sits closer to document-creation-plus-signing than pure eSignature, which is a strength if you need both from one integration. It works well for building quote-to-sign or proposal-to-signature workflows where generation and signing happen through one API. The tradeoffs are document-based pricing that adds up at volume, and thinner signing-order controls than purpose-built eSign APIs.
- Auth model. OAuth2 and API key options.
- Embedded signing. Embedded sending and signing via iframe, alongside template-driven document generation.
- Webhook granularity. Document-lifecycle events covering creation, sending, and completion.
- SDKs. Official Node.js and Python SDKs, plus a documented REST API.
- Compliance. Business-grade; confirm the current list against your requirements in their docs.
- Pricing model. Document-centric and can climb at high envelope volumes, so model your cost at target scale.
See the developer documentation and pricing.
PandaDoc’s developer hub. Document generation sitting next to signing is what distinguishes it from pure eSign APIs.
SignNow
SignNow offers a capable REST API that is frequently competitive on per-envelope cost at volume, which makes it a common pick for high-throughput, straightforward signing. It’s a cost-sensitive option that can handle high-volume, straightforward signing if you don’t have any complex embedded-UX requirements. However, its coarser webhooks and narrower SDK coverage will push you toward raw REST.
- Auth model. API key and OAuth2 authentication.
- Embedded signing. Embedded session URL generation for in-app signing.
- Webhook granularity. Functional, but event types are coarser than the top-tier options.
- SDKs. Narrower official SDK coverage, so expect more raw REST work outside the main supported languages.
- Compliance. Business and industry compliance is advertised; verify the current certifications in their docs.
- Pricing model. Per-envelope pricing that is published and tends to reward volume.
See the API documentation and pricing.
SignNow’s REST API documentation. Envelope creation, signer routing, and embedded session URLs are all covered here.
BoldSign
BoldSign is a developer-first eSign API with a clean REST interface and pricing that is more transparent than most enterprise alternatives at the lower tiers. This option offers a modern, well-documented API with straightforward pricing, outside the most heavily regulated industries. Worth noting is a smaller compliance footprint than the established players.
- Auth model. OAuth2 and API key options.
- Embedded signing. Solid iframe-based embedded signing built for developer integration.
- Webhook granularity. Documented event types suitable for most integration workflows.
- SDKs. Official SDKs including .NET, Java, Node.js, and Python.
- Compliance. A newer entrant with a smaller certification footprint than established players, so verify current standards before committing in a regulated industry.
- Pricing model. Tiered and transparent, published without a mandatory sales call at the lower tiers.
See the developer portal and pricing.
The BoldSign Developer Hub. Transparent pricing and a self-serve sandbox are its main developer-experience draws.
Foxit eSign
Foxit eSign gives developers full control over the signing experience, with no redirect to an external Foxit-hosted page at any point. This is the tool covered in the most technical depth here, and the getting-started section below runs against its live API.
- Auth model. OAuth2 client credentials. Your backend gets a machine-to-machine Bearer token with no user login in the loop.
- Embedded signing. Signing sessions load inside an iframe or web view within your own application. You control the header, sidebars, and the exact page signers land on after finishing.
- Webhook granularity. Nine event types, including
folder_executed, and every callback is signed with an HMAC-SHA-256 digest of the raw body so you can verify authenticity. - SDKs. A documented REST API with worked examples; the getting-started code below is Python.
- Compliance. eIDAS at the AES and QES levels (QES requires pairing with a qualified trust service provider), plus the ESIGN Act, UETA, HIPAA, GDPR, 21 CFR Part 11, CCPA, FINRA, FERPA, and SOC 2 Type II infrastructure.
- Pricing model. Tiered and published, with a free developer account to build against.
The Foxit eSign embedded signing session, loaded in-app. Text tags in the source PDF are parsed into the interactive Full name, initial, date, and signature fields shown here, with no redirect to an external page.
Signing order control
Setting signInSequence to false on a folder request puts all recipients into parallel mode, while leaving it true enforces the sequence you define. Hybrid flows mix both, so some signers proceed in parallel while others wait on prior steps.
Compliance coverage
Full details live at the Foxit compliance page and the Foxit Trust Center.
Best for development teams that need full embedded-signing control, flexible signer routing, and broad compliance coverage from a single integration, especially in regulated industries.
Watch out for planning your regional endpoint (the instance_url returned at auth) into your configuration rather than hardcoding one.
Getting started with the Foxit eSign API
Three steps take you from zero to your first signed document. The code below runs end to end against the live API.
The Foxit eSign dashboard you land on after signing in. The API you are about to call drives the same envelopes shown here.
Step 1. Activate the API tab. Log into your Foxit eSign account, navigate to Settings, and open the API tab. Fill out the form to receive your client_id and client_secret.
The API Consumer Credentials screen. Foxit masks the client id, secret, and access token by default and requires a one-time passcode to reveal them, which is the credential-handling behavior worth knowing before you build.
Step 2. Obtain a Bearer token. POST to the regional OAuth2 endpoint with a form-encoded body (sending a JSON body returns HTTP 415 Unsupported Media Type). The response includes access_token, token_type, expires_in, and instance_url.
Step 3. Create an envelope and register a webhook. Use the Bearer token in the Authorization header to create an envelope (Foxit calls it a folder) from a source document, then register a webhook targeting the folder_executed (EXECUTED) event to be notified once every party has signed and the document is executed.
The code reads credentials from environment variables. It exchanges credentials for a token, then creates a draft envelope from a sample PDF without emailing anyone.
import os
import requests
# The token endpoint requires a form-encoded body
# (application/x-www-form-urlencoded). Sending a JSON body returns
# HTTP 415 Unsupported Media Type.
TOKEN_URL = "https://na1.foxitesign.foxit.com/api/oauth2/access_token"
# Step 1: Exchange credentials for a Bearer token.
token_response = requests.post(
TOKEN_URL,
data={ # use data= (form-encoded), NOT json=
"grant_type": "client_credentials",
"client_id": os.environ["FOXIT_ESIGN_CLIENT_ID"],
"client_secret": os.environ["FOXIT_ESIGN_CLIENT_SECRET"],
"scope": "read-write",
},
)
token_response.raise_for_status()
token_data = token_response.json()
access_token = token_data["access_token"] # Bearer token
instance_url = token_data["instance_url"] # already a full URL, e.g. https://na1.foxitesign.foxit.com/
base = instance_url.rstrip("/") # trim trailing slash; do NOT re-add https://
# Step 2: Create an envelope (folder) from a document.
# sendNow=False creates a DRAFT and emails no one.
headers = {
"Authorization": f"Bearer {access_token}",
"Content-Type": "application/json",
}
payload = {
"folderName": "Service Agreement",
"fileUrls": ["https://your-app.example.com/agreement.pdf"],
"fileNames": ["agreement.pdf"],
"sendNow": False, # DRAFT; set True to dispatch to signers
# signInSequence True = signers proceed in the sequence you define
# signInSequence False = all signers receive the document in parallel
"signInSequence": True,
"parties": [
{
"firstName": "Jane",
"lastName": "Doe",
"emailId": "[email protected]",
"sequence": 1,
}
],
}
resp = requests.post(f"{base}/api/folders/createfolder", headers=headers, json=payload)
resp.raise_for_status()
folder_id = resp.json()["folder"]["folderId"] # the id nests under "folder"
print("Envelope created:", folder_id) The code above reads your client id and secret from the environment, POSTs them form-encoded to the regional token endpoint, and reads the access_token and instance_url from the response. Because instance_url is already a complete URL, you strip its trailing slash and use it directly rather than prepending a scheme. You then POST to /api/folders/createfolder with the source document, the signing parties, and sendNow set to false so the envelope is created as a draft without notifying anyone, and read the new folder’s id from folder.folderId in the response.
Registering the executed webhook
You register webhooks once in the eSign portal’s API settings, not through the token flow above. Add your endpoint URL and a webhook secret, then enable the events you care about. The screenshot below shows the real configuration screen with folder_executed selected.
The Configure Webhooks page. Note the nine event checkboxes, folder_executed selected, and the field note confirming each request is signed with a Base64 HMAC-SHA-256 digest of the raw body.
folder_executed fires when all parties have signed and the document reaches the EXECUTED state, which is the point at which the completed, legally binding PDF is ready to archive. Foxit delivers each event as an HTTP POST with the signature appended as a query parameter (?signature=...), where the signature is the Base64-encoded HMAC-SHA-256 of the raw request body keyed with your webhook secret. Recompute that digest on receipt and compare it before you act on the callback.
import base64, hashlib, hmac
def verify_webhook(raw_body: bytes, signature: str, secret: str) -> bool:
"""Return True only if the callback's signature matches the raw body."""
expected = base64.b64encode(
hmac.new(secret.encode(), raw_body, hashlib.sha256).digest()
).decode()
return hmac.compare_digest(expected, signature) The full API reference is at developersguide.foxitesign.foxit.com.
Docusign API FAQ
What is an eSignature API?
An eSignature API lets your application send, track, and complete legally binding signature requests without building a separate signing portal. Your app calls the endpoints to create the workflow, route the document to signers, capture their signatures, and pull the completed, audit-ready record, all without anyone leaving your product.
What are the best DocuSign API alternatives for developers in 2026?
Six strong alternatives worth evaluating are Dropbox Sign (well-documented, fits the Dropbox ecosystem), Adobe Acrobat Sign (enterprise compliance depth), PandaDoc (proposal-to-signature workflows), SignNow (cost-effective at volume), BoldSign (developer-first, clean REST interface), and Foxit eSign (full embedded control and multi-standard compliance across eIDAS, ESIGN, UETA, HIPAA, GDPR, and 21 CFR Part 11).
Does the Foxit eSign API support embedded signing?
Yes. Signing sessions load inside an iframe or web view within your own application, with no redirect to an external Foxit page. You can customize headers and sidebars, and configure where signers land after completing the document. The experience stays inside your product throughout.
What compliance standards does the Foxit eSign API meet?
Foxit eSign meets eIDAS at the AES (Advanced Electronic Signature) and QES (Qualified Electronic Signature) levels (QES requires pairing with a qualified trust service provider). Additional certifications include the ESIGN Act, UETA, HIPAA, GDPR, 21 CFR Part 11, CCPA, FINRA, FERPA, and SOC 2 Type II infrastructure. Full details are at the Foxit compliance page.
How do I get started with the Foxit eSign API?
Create an account at developer-api.foxit.com, activate the API tab in your eSign account settings to receive your client_id and client_secret, then POST to https://na1.foxitesign.foxit.com/api/oauth2/access_token with a form-encoded body to obtain a Bearer token. Use that token in the Authorization header to make your first envelope call.
How does OAuth2 client credentials auth work in the Foxit eSign API?
Your backend POSTs a form-encoded request to the regional token endpoint using your client_id and client_secret. The response returns a Bearer token with a defined expiry and a region-specific instance_url. Every subsequent API call passes that token in the Authorization header, with no session-level user login required at any point.
What webhook events does the Foxit eSign API support?
You register webhooks through the eSign API Settings page and configure them to fire on specific event types, nine in total, spanning sent, viewed, signed, cancelled, executed, deleted, completed, assigned, and access-code-failure. The folder_executed event fires when all parties have completed signing. Foxit signs each webhook POST with an HMAC-SHA-256 digest of the raw body, giving you a verifiable authenticity signal on every inbound notification.
How does Foxit eSign handle parallel and sequential signing flows?
Setting signInSequence to false on a folder request sends the document to all recipients simultaneously. Setting it to true enforces the order you define in the sequence field on each party. Hybrid flows combine both modes, so some signers proceed in parallel while others wait on prior steps, all from a single API call.
Which eSign API is best for regulated industries?
Foxit eSign covers the broadest compliance footprint across eIDAS (AES and QES), HIPAA, GDPR, 21 CFR Part 11, FINRA, FERPA, CCPA, and SOC 2 Type II. Adobe Acrobat Sign also carries strong enterprise certifications relevant to healthcare and finance. Teams in regulated industries should verify current certification status directly with each vendor before committing.
What is the difference between envelope-based and consumption-based eSign pricing?
Envelope-based pricing charges a fixed fee per document sent for signature, which makes costs predictable at low volumes but expensive at scale. Consumption-based pricing ties costs to actual usage metrics (API calls, active users, or data volume), which can reduce spend at high volume but introduces budget variability. Seat-based pricing charges per licensed user regardless of volume, which suits teams with consistent, predictable signing activity.
Picking the right eSign API
The six criteria (embedded signing depth, auth model, webhook event granularity, SDK language coverage, compliance certifications, and pricing transparency) cut the field quickly when you apply them consistently.
Dropbox Sign fits teams in the Dropbox ecosystem who want reliable coverage without high complexity. Adobe Acrobat Sign suits large enterprises with existing Adobe infrastructure and deep compliance footprints. PandaDoc is the right call for proposal-to-signature workflows. SignNow works for cost-sensitive, high-volume signing at scale. BoldSign offers a clean developer experience outside the most heavily regulated industries.
If you need full embedded-signing control, flexible signer routing, and compliance coverage across eIDAS, HIPAA, GDPR, and 21 CFR Part 11 bundled without piecing those certifications together from add-ons, Foxit eSign is worth a close look. Once a folder reaches the EXECUTED state, the completed document carries a full audit trail and signer certificate, which is what you archive as the legal record.
An executed Foxit eSign agreement. The EXECUTED state is the archival point the folder_executed webhook announces.
Visit developer-api.foxit.com to create a free developer account and try the full signature flow with no commitment.
eSignature API: A Developer’s Guide to Adding Signing to Your App

Adding a signing step to your app involves more than it first appears. Authentication, document preparation, session handling, and completion tracking all need to work together. This guide walks through a full esignature API integration with Foxit eSign, from your first authenticated request to a signed, webhook-confirmed document.
Adding a signing step to an existing app sounds straightforward until you try to implement it. Getting a document signed is a simple idea, but the actual API surface, how authentication works, how you mark up a PDF, and how you learn that signing finished all take longer to figure out than they should. This guide walks a complete Foxit eSign API integration from the first authenticated request through to a webhook-confirmed, digitally signed document. Comfort with REST APIs and bearer tokens is enough to follow along.
What an eSignature API is and how signing workflows work
An eSignature API is a REST interface that owns the document-signing lifecycle, covering preparation, delivery, the signing session, and the audit trail. You supply the document and the signers, and the API handles field rendering, identity capture, signature application, and tamper-evident recordkeeping, so none of that infrastructure is yours to build.
The distinction that matters most for app developers is redirect-based versus embedded signing. Redirect-based signing sends the user to a hosted URL to sign and returns them afterwards, which means they leave your product mid-task. Embedded signing renders the session inside your own application, typically in an iframe, so the user never changes context. If signing sits in the middle of an onboarding or checkout flow, embedded keeps that flow intact.
Foxit eSign supports both. The lifecycle you implement runs through five stages, starting with OAuth 2.0 authentication, then PDF preparation with Text Tags, a POST to /esign/api/v1/folders/createfolder that defines signers and mints a session, the signer completing the embedded session, and a folder_executed webhook confirming the document is final.
The five stages this guide implements in order. Each one maps to a section below.
Prerequisites
Signing up for eSign API access is self-serve on the Foxit API Platform — no sales ticket and no waiting for an administrator. The platform provisions a trial eSign account for you and manages its credentials, so the whole setup is a short walkthrough:
- Create and sign in to your Foxit API Platform account. You need an active Foxit API plan and a complete CAS profile — first name, last name, email address, and company name (a company address is required for eSign provisioning). Your eSign account is provisioned from those profile details, so complete them before you start.
- Open the Dashboard and select Get started with eSign in the Dashboard header. That takes you to the eSign activation page.
- Choose your document-storage region. The activation card preselects United States, with European Union and Canada as alternatives. Select Activate with [region] storage. Confirm the region before activating: once the remote account exists, the region is locked, and changing it later means submitting a case with Foxit Support.
- Wait for provisioning to complete. You may see “Creating your eSign account” and then “Confirming your eSign account” — the second is a reliability check that reconciles ambiguous creation results, so let it finish instead of retrying activation.
- Confirm eSign is ready. A successful activation displays “eSign is ready”, your eSign company number, and the selected region. The platform manages the API account and its credentials, and the same unified
client_id/client_secretyou use for PDF Services also authenticate eSign API, Document Generation, and Embed API — there is no separate eSign key pair to generate. If credential retrieval is still pending or failed, use Resume credentials or Retry credentials on the page; the first-call button stays disabled until credentials are ready. - (Optional but worth it) Run the sample request on the activation page. It uses your profile’s name and email as the first signing party, sends a Base64-encoded one-page contract, adds Signer Name, Today’s Date, Signature, and Date Signed fields, creates a draft with sending disabled, and returns an embedded sending session URL — a quick end-to-end check that everything is wired up. The button switches to Running and then reports “Sample draft created. The embedded sending session is ready.”
Two things to know before you build: your provisioned account is an eSign Business trial that lasts 30 days and starts in TEST mode, so every envelope carries a watermark. Moving the account to Production mode is a Sales/Operations step performed in Foxit Monitor, not something the API can do.
Beyond the account, the rest of the prerequisites are lightweight:
- Python 3.8+ with pip and a venv, for the webhook handler later in this guide.
- Flask and requests for the sample code.
- curl for the token exchange, and ngrok or any tunnel that gives your local webhook endpoint a public HTTPS URL.
- A code editor, VS Code with the Python extension being a reasonable default alongside PyCharm.
- A tagged sample PDF, so you do not have to author one. This guide uses agreement-signable.pdf, which already carries Text Tags for a single signer.
Scaffold the workspace in one shot:
mkdir foxit-esign && cd foxit-esign
python3 -m venv .venv && source .venv/bin/activate
pip install flask requests
export ESIGN_HOST="https://na1.foxitesign.foxit.com"export ESIGN_CLIENT_ID="your_api_key"
export ESIGN_CLIENT_SECRET="your_api_secret"
export WEBHOOK_SECRET="your_webhook_secret" Step 1: Authenticate with the Foxit eSign API
The platform provisions your eSign account and manages its credentials, and that single pair is shared across eSign API, PDF Services, Document Generation, and Embed API. No bearer token, no client_credentials grant, no expires_in to watch.
The quickest way to prove a credential pair works is a minimal folder creation — the same /esign/api/v1/folders/createfolder endpoint Step 3 explains field by field:
curl -X POST "$ESIGN_HOST/esign/api/v1/folders/createfolder" \
-H "client_id: $ESIGN_CLIENT_ID" \
-H "client_secret: $ESIGN_CLIENT_SECRET" \
-H "Content-Type: application/json" \
-d '{
"folderName": "Auth check",
"inputType": "url",
"fileUrls": ["https://github.com/lucienchemaly/foxit-demo-templates/raw/main/esign/agreement-signable.pdf"],
"fileNames": ["agreement.pdf"],
"parties": [
{
"firstName": "Jane",
"lastName": "Smith",
"emailId": "[email protected]",
"permission": "FILL_FIELDS_AND_SIGN",
"sequence": 1
}
],
"processTextTags": false,
"processAcroFields": false,
"createEmbeddedSigningSession": false,
"createEmbeddedSendingSession": true,
"sendNow": false
}' A valid credential pair returns JSON with a folder object carrying folderId and folderStatus (DRAFT here, since sendNow is false), so the response doubles as your auth check — a rejected pair comes back as an error before any folder exists. Send the same two headers on every subsequent request. There is nothing to mint or refresh like an OAuth token; if the platform ever flags the stored credentials as stale, refresh them from the activation page with Resume credentials or Retry credentials. And because eSign shares the PDF Services credential pair, the two integrations are interchangeable — one pair of credentials covers both.
Step 2: Prepare a document and define signature fields with Text Tags
Foxit eSign reads field definitions out of the PDF itself at upload time. You embed them as Text Tags, plain-text strings placed where each field belongs, and the API converts them into interactive fields on ingest.
The syntax is ${fieldtype:party_number:required:field_name:width}, where y marks a field required and n marks it optional, the party number maps to a signer’s sequence, and width is expressed as underscores.
${signfield:1:y:____} # required signature, party 1
${datefield:1:y::____} # required date, party 1
${i:1:______} # initials field, party 1
${t:1:y:Full_Name:__________} # required text field, party 1, named "Full_Name"
${signfield:2:y:____} # required signature, party 2 Each tag names a type, either in full or by its short alias. The supported set covers signfield (s), initialfield (i), datefield (d), textfield (t), textboxfield (tb), checkboxfield (c), radiobuttonfield (rb), securedfield (sc), attachmentfield (a), imagefield (img), accept (ab), decline (db), payfield (pf), and formulafield (ff). Author them in lowercase to match the documented syntax.
Express width as underscores and never as a literal space, because a space stops the tag from being recognized. A tag written ${s:1: } renders in the signing UI as plain ${s:1: } text with no field attached, while ${signfield:1:y:____} becomes a real signature field. That failure is silent, so the create call still succeeds and you only notice when a signer has nothing to sign.
Two preparation details save support tickets later. Foxit eSign converts tags to fields but does not delete the tag text, so set the tag’s text color to match the page background if you do not want signers reading raw ${...} strings. And paste tags through a plain-text editor first, because smart-quote autocorrect in Word or Google Docs silently swaps straight ASCII characters for typographic ones and tag parsing then fails without an error.
If you would rather not tag a document by hand for a first run, agreement-signable.pdf is already prepared and hosted at a public URL you can pass straight to the next step.
Step 3: Send the document and mint an embedded session
One call to /esign/api/v1/folders/createfolder submits the document, defines the signers, and, when you ask for it, returns a ready-to-render signing URL. Foxit calls the signing container a folder rather than an envelope.
{
"folderName": "Customer Agreement - Acme Corp",
"fileUrls": ["https://github.com/lucienchemaly/foxit-demo-templates/raw/main/esign/agreement-signable.pdf"],
"fileNames": ["agreement.pdf"],
"parties": [
{
"firstName": "Jane",
"lastName": "Smith",
"emailId": "[email protected]",
"permission": "FILL_FIELDS_AND_SIGN",
"sequence": 1
}
],
"processTextTags": true,
"createEmbeddedSigningSession": true,
"embeddedSignersEmailIds": ["[email protected]"],
"sendNow": false
} In this body you point the API at the tagged PDF with fileUrls and give it a display name through fileNames, define the single signer in parties with firstName, lastName, emailId, the FILL_FIELDS_AND_SIGN permission and a signing sequence, then set processTextTags to true so the embedded tags become real fields. Asking for createEmbeddedSigningSession and naming the signer in embeddedSignersEmailIds returns a session URL in the same response, and sendNow set to false keeps Foxit from emailing an invitation, which is what you want while testing.
One nuance to expect here. sendNow: false on its own produces a DRAFT folder, but pairing it with createEmbeddedSigningSession returns folderStatus of SHARED, since the folder has to be live for the session URL to open. No email goes out either way, so the flag still suppresses the invitation, and the status you see just reflects that the document is now signable. To attach the file as bytes instead of a URL, send base64FileString as an array together with inputType set to "base64".
The response nests the folder identifier at folder.folderId and carries an embeddedSigningSessions array. Each entry holds emailIdOfSigner, the raw embeddedToken, and the renderable embeddedSessionURL, which follows this shape:
https://{HOST_NAME}/embedded/embeddedsign?eetid={URL-ENCODED-EMBEDDED-TOKEN}
Three behaviors are worth designing around before you ship. Omitting embeddedSignersEmailIds returns email id of embedded signer(s) not submitted, so always list embedded signers explicitly. Every party number used in a Text Tag needs a matching entry in parties, because a sendNow: true create still reports success while silently dropping the fields of a party that is not listed, which means a mandatory signature is never routed. And for a multi-party document where everyone signs in your app, createEmbeddedSigningSessionForAllParties set to true covers all recipients rather than naming them one by one.
To dispatch a draft later, POST to /api/folders/sendDraftFolder.
Folder state moves through DRAFT, SHARED, COMPLETED, and finally EXECUTED once the digital signature is applied. A run of this guide’s single-signer flow produced exactly that path, with the activity log labelling the creation event CREATED and then recording Envelope viewed, Jane Smith signed this folder at COMPLETED, and Document(s) successfully executed at EXECUTED. PARTIALLY SIGNED appears only when a folder has more than one party and some but not all of them have signed, so you will not see it on a single-signer document.
Step 4: Render the signing session in your app
Load the embeddedSessionURL in an iframe. The sandbox attribute needs a specific minimum set of permissions, and trimming it is a common way to break the signing UI with no visible error.
<iframe
id="signing-session"
src="PASTE_EMBEDDED_SESSION_URL_HERE"
width="100%"
height="780px"
style="border: none;"
sandbox="allow-scripts allow-same-origin allow-forms allow-popups allow-top-navigation"
></iframe> In this markup the src receives the embeddedSessionURL from the createfolder response, and the five sandbox permissions are the minimum the signing UI needs. Removing allow-popups or allow-top-navigation breaks the flow in ways that surface no obvious error, so keep all five unless you have tested a reduced set end to end. Session URLs are short-lived, so generate one when the user is ready to sign rather than caching it, and request a fresh one per signer through /esign/api/v1/embedded/regenerateEmbeddedSigningSession when a session goes stale.
To check the flow before wiring it into your own UI, download the ready-to-run iFrame test page, open it in a browser, paste your embeddedSessionURL into the input, and load it. A correctly tagged document renders with active signing controls.
A real session opened from the embeddedSessionURL this guide’s request returns. All four tags in the sample became required fields, which is what the counter is reporting. The raw tag text still shows through each box, which is exactly why you color it to match the page background before shipping.
Step 5: Confirm completion with webhooks
Polling for completion wastes requests and adds latency. Register a webhook instead and Foxit eSign posts to your endpoint as each signing event happens.
Registration lives on the eSign portal’s API settings page at /consumer/consumerdetails, under Configure Webhooks, where you set the callback URL, a webhook secret, and the events you want. That page is visible only to the account owner, so an admin-level user will not find it. Your endpoint has to be reachable over public HTTPS.
The owner-only webhook settings. The event checkboxes control which callbacks reach your endpoint.
The events available are folder_sent, folder_viewed, folder_signed, folder_cancelled, folder_executed, folder_deleted, folder_completed, folder_assigned, and folder_access_code_failure. In practice folder_viewed, folder_signed, folder_completed, and folder_executed are the ones that fire on an API-dispatched folder.
The event to build on is folder_executed. folder_completed fires once every party has signed, but folder_executed fires after Foxit applies the digital signature and locks the audit trail, so it is the point at which a download gives you the final document.
Foxit signs every callback. It delivers the POST as <your-url>?signature=<base64>, where the signature is the base64 of an HMAC-SHA-256 over the raw request body keyed with your webhook secret. Verify it against the unparsed bytes, since re-serializing the JSON changes whitespace or key order and breaks the comparison.
import base64
import hashlib
import hmac
import os
from flask import Flask, request, jsonify
app = Flask(__name__)
WEBHOOK_SECRET = os.environ["WEBHOOK_SECRET"]
def verify_signature(raw_body: bytes, signature: str) -> bool:
expected = base64.b64encode(
hmac.new(WEBHOOK_SECRET.encode(), raw_body, hashlib.sha256).digest()
).decode()
return hmac.compare_digest(expected, signature)
@app.route("/webhooks/esign", methods=["POST"])
def handle_esign_event():
raw_body = request.get_data()
if not verify_signature(raw_body, request.args.get("signature", "")):
return jsonify({"error": "invalid signature"}), 403
payload = request.get_json(silent=True) or {}
event_name = payload.get("event_name")
folder = payload.get("data", {}).get("folder", {})
if event_name == "folder_executed":
# The document is final here. Archive it, update your record, notify the user.
app.logger.info("Signing finished for folder %s", folder.get("folderId"))
return jsonify({"status": "received"}), 200 In this handler you read the unparsed body first, recompute the HMAC over those exact bytes with your webhook secret, and compare it against the signature query parameter using hmac.compare_digest so the check is not timing-dependent. A mismatch returns 403 before any business logic runs, which stops a spoofed POST to your public URL from triggging an archive. Only after the signature passes do you parse the JSON, read event_name, and branch on folder_executed to run downstream work, returning 200 so Foxit records the delivery as successful. A ready-to-run version of this receiver lives at webhook_receiver.py in the demo repo.
Test the whole path against a draft. Create the folder with sendNow set to false, dispatch it, sign in the embedded session, and watch the events arrive. Once the signer finishes, the session redirects to a result URL carrying event=signing_success, and the document reaches EXECUTED within a few seconds.
The session once every field is filled. The counter reads zero and Finish activates, which is the state that produces folder_completed and then folder_executed.
Step 6: Retrieve the executed document and its audit trail
With folder_executed in hand, pull the final PDF. The download takes the folder id as a query parameter.
curl -o executed.pdf \
"$ESIGN_HOST/api/folders/download?folderId=35117696" \
-H "Authorization: Bearer $ACCESS_TOKEN" The response streams the executed PDF, which arrives with a content type of application/octet-stream rather than application/pdf, so write the bytes to a file rather than sniffing the header. The returned document carries the filled field values and the signature certificate, so a text extraction of it contains the signer’s typed name, the date, and the per-signer Signer ID recorded on the certificate page.
For the audit trail itself, GET /api/folders/viewActivityHistory?folderId={id} returns a details object holding the folder metadata plus an activities array, where each entry carries an activity description and the folderStatus at that moment. That endpoint is GET-only and only returns data once the folder has been shared, so a pure DRAFT folder reports nothing useful.
The signature certificate attached to a document once folder_executed has fired. Each signer’s adopted signature sits beside the identity record Foxit captured, which is the tamper-evident audit trail you are archiving alongside the PDF.
Common mistakes
- Dropping the
/api/prefix : every eSign path sits under/api/, so it is/api/folders/createfolder, not/folders/createfolder. - snake_case request fields : the body is camelCase.
folderName,fileUrls,emailId, andsendNowwork, whilefolder_name,document_url,email, andsend_nowdo not. - Omitting
processTextTags: without it the tags stay inert text, the signer sees raw${...}strings, and they can finish without signing anything. - A tag party with no matching
partiesentry : the create returns success and that party’s fields disappear silently, so their signature is never collected. - Skipping signature verification : a public webhook URL that acts on any POST is a spoofing target. Verify the HMAC before you touch the payload.
- Archiving on
folder_completed: that fires before the digital signature is applied. Wait forfolder_executed. - Caching an
embeddedSessionURL: sessions expire. Mint one when the signer is ready, and regenerate when needed. - Trimming the iframe
sandboxlist : removingallow-popupsorallow-top-navigationbreaks signing with no error message. - Smart quotes or a space inside a tag : both stop tag recognition. Use straight ASCII and underscores.
- Reusing PDF Services credentials : eSign has its own portal, host, and key pair.
eSignature API FAQ
What is an eSignature API?
A REST interface that handles the document-signing lifecycle, covering preparation, delivery, the signing session, and the audit trail, so your app makes calls rather than building signing infrastructure.
What is embedded signing and why does it improve the user experience?
Embedded signing renders the session inside your own application instead of redirecting to a hosted page, so the signer finishes without leaving your product. That matters most when signing sits inside a flow you do not want to interrupt, like onboarding or checkout.
How do Text Tags relate to the parties in the API call?
The party number in a tag maps to a signer’s sequence in the parties array, so ${s:1: } is signed by the party with sequence: 1. Keeping those aligned is the difference between fields routing correctly and vanishing silently.
What is the difference between folder_completed and folder_executed?
folder_completed fires when all parties have signed. folder_executed fires after Foxit applies the digital signature and locks the audit trail, which is why downstream archiving should trigger on folder_executed.
How do I verify a webhook actually came from Foxit?
Recompute a base64 HMAC-SHA-256 of the raw request body using your webhook secret and compare it with the signature query parameter. Verify against raw bytes, never re-serialized JSON.
Can one folder hold several documents?
Yes. Pass additional entries in fileUrls with matching fileNames. Each document carries its own Text Tags, and party assignments stay consistent across the folder.
Do I need a paid plan to build this?
No. The free tier gives you credentials and lets you run the full flow, and no credit card is required to create the account.
Can I review a document before it reaches signers?
Yes. Create it with sendNow set to false for a DRAFT folder, inspect it in the eSign dashboard, then dispatch with /api/folders/sendDraftFolder.
Wrapping up
That is the full path for an eSignature API integration. Authenticate with the client_credentials grant, prepare a PDF with Text Tags, create the folder with processTextTags and an embedded session, render the returned embeddedSessionURL in an iframe, and act on a signature-verified folder_executed webhook.
The same shape extends to multi-signer approval chains, CRM-triggered signing when a deal closes, and template-based documents where fields arrive pre-filled from your own data. Those build on the pieces already in place rather than replacing them.
Ready to build? Create a free account (no credit card required) at account.foxit.com/site/sign-up, generate your API Key and Secret from the API tab, and run the token call above against agreement-signable.pdf to see a session URL come back.
Build a CRM-Triggered PDF Generation and eSign Workflow in Power Automate with Foxit’s REST APIs

This guide shows how to trigger a Word-to-PDF contract from a closed CRM deal, route it for signature through Foxit’s eSign API, and archive the signed copy automatically, using nothing but HTTP actions and a webhook.
Most Power Automate document tutorials stop at a SharePoint file move or an AI Builder extraction, and the ones that touch signatures assume a native connector that does not exist for a headless, API-first pipeline. The gap is the full chain, where a CRM deal closes, a contract is generated from a Word template, the PDF is routed for signature, and the signed copy is archived, with no manual export and no polling. This article builds that pipeline in Power Automate using the HTTP action to call Foxit’s REST endpoints directly, which is the same pattern that carries over to n8n, Zapier, or any orchestrator that can make an HTTP request.
Foxit exposes two REST APIs that chain cleanly for this. The Document Generation API takes a base64-encoded Word template plus a JSON payload and returns a base64 PDF, and the eSign API handles the signing lifecycle behind an OAuth2 token. The base64 PDF from generation drops straight into the eSign upload call, so the handoff stays inside one flow with no SDK to install and no desktop agent. This Power Automate Foxit API integration walks the two hosts and their two auth models, the document generation call, the send-for-signature call with embedded signature fields, and a second flow that receives Foxit’s webhook and archives the executed document.
Prerequisites
Power Automate runs in the browser, so there is no local runtime to install. What you need are the right accounts and one sample file.
A Power Automate account with the HTTP action : the HTTP action is a premium connector, so you need a per-user or per-flow premium license. This is the one paid dependency in the tutorial. On the free Microsoft 365 tier you will hit a wall at the first HTTP action, so confirm the plan before you start.
A Foxit Developer account : create one at account.foxit.com/site/sign-up and activate the free Developer plan, which includes 500 credits per year with no credit card. From the APIs Dashboard, copy the Document Generation Client ID and Secret, and separately the eSign Client ID and Secret. These are two different credential pairs for two different APIs.
A CRM that can trigger a flow : this article uses the Salesforce connector as the example. Any CRM with a Power Automate connector, or any system that can POST to a webhook URL, works the same way.
The sample contract template : download contract_signing.docx so you do not have to author one. It already carries both Document Generation merge tags and eSign signature tags, which is what makes the two-API handoff work.
A REST client : Postman or curl, to test each Foxit call in isolation before wiring it into a flow.
Store both Foxit credential pairs in the Power Automate secure store or as environment variables in your solution, never pasted as literals into an action, so they do not travel in exported flow definitions.
The APIs Dashboard is where you retrieve the Client ID and Secret. Document Generation and eSign each have their own pair.
How the Power Automate Foxit API Integration Works: Two APIs, Two Hosts, Two Flows
The pipeline has four stages. A CRM Closed Won event triggers document generation, the generated PDF is sent for signature, and the executed document is archived once every party has signed.
Salesforce: Opportunity → Closed Won
│
▼
HTTP: POST GenerateDocumentBase64 (na1.fusion.foxit.com) → base64 PDF
│
▼
HTTP: POST createfolder (na1.foxitesign.foxit.com) → folderId, email sent
│
… signer signs (async) …
▼
Flow 2: When a HTTP request is received <- Foxit webhook (folder_executed)
│
▼
HTTP: GET download → OneDrive: Create file
Power Automate owns orchestration and control flow. Foxit owns document rendering and the signature lifecycle. The single most common mistake in this integration is treating the two Foxit products as one, so keep them separate from the start. Document Generation runs on https://na1.fusion.foxit.com and authenticates with lowercase client_id and client_secret request headers. eSign runs on https://na1.foxitesign.foxit.com and authenticates with an OAuth 2.0 bearer token obtained from its own credential pair. They do not share credentials or a portal.
The work also splits into two flows for a reason. Generation and sending are synchronous, so they belong in one flow that runs when the deal closes. Signing completes minutes or days later, so a second flow triggered by Foxit’s webhook handles the archive step. That separation is what removes any polling from the design.
Here is the main flow built in the Power Automate designer, with the four HTTP actions chained after the trigger.
The four HTTP actions in order. This build uses a manual trigger so the flow runs on demand while you test; in production the Salesforce trigger from Step 1 takes its place as the entry point, and nothing downstream changes.
Step 1: CRM Trigger, Firing the Flow on a Closed Deal
Create an automated cloud flow and choose the Salesforce trigger for a created or modified record, pointing it at the Opportunity object. Add a condition so the flow only proceeds when the Stage equals Closed Won, which keeps every mid-pipeline edit from generating a contract.
Map the CRM fields the contract needs. For the sample template, that is the client name, the contract date, the deal value, and the signer’s name and email. Read them from the trigger output with expressions like triggerOutputs()?['body/Account_Name'] and store each in a variable or reference it inline, so the next two steps can assemble their payloads cleanly.
This step is swappable. Any CRM with a Power Automate connector, or any system that can POST JSON to a Power Automate HTTP-request trigger, drops in here without touching the Foxit calls that follow. If you use HubSpot or Dynamics 365, only the trigger and field paths change, so the rest of this tutorial stays identical.
Step 2: Generate the Contract PDF with GenerateDocumentBase64
The contract_signing.docx template drives this step. It contains Document Generation merge tags for the scalar fields and a table loop for line items, using Foxit’s {{ }} syntax:
{{clientName}}
{{contractDate \@ MM/dd/yyyy}}
{{dealValue \# "$#,##0.00"}}
{{TableStart:lineItems}} {{description}} {{amount}} {{TableEnd:lineItems}} The \@ switch formats a date and the \# switch formats a currency value, so you can pass a raw ISO date and a plain number and let the template render them. The {{TableStart:lineItems}} and {{TableEnd:lineItems}} tokens sit in a single Word table row and repeat that row for each object in the lineItems array.
Before the flow can send the template, it needs the file as a base64 string. The build here gets it with an HTTP GET action named Get template, pointed at the raw contract_signing.docx URL, and base64-encodes the response with the base64() expression. For a template you maintain yourself, store it in OneDrive or SharePoint and use a Get file content action instead of the GET. Then add a second HTTP action named Generate PDF, set to POST https://na1.fusion.foxit.com/document-generation/api/GenerateDocumentBase64 with client_id and client_secret headers and this JSON body:
{
"base64FileString": "@{base64(body('Get_template'))}",
"documentValues": {
"clientName": "@{variables('clientName')}",
"contractDate": "2026-07-17",
"dealValue": 48500,
"lineItems": [
{ "description": "Platform license (annual)", "amount": "$36,000.00" },
{ "description": "Onboarding and training", "amount": "$12,500.00" }
]
},
"outputFormat": "pdf"
} In this code, you send the base64-encoded template as base64FileString, pass the CRM-sourced fields as documentValues whose keys match the template tags exactly, and request a PDF with outputFormat set to the lowercase "pdf". The keys clientName, dealValue, and the lineItems array with its description and amount fields have to match the tag names in the Word file, since a mismatch leaves the tag unrendered rather than raising an error. The call is synchronous and returns HTTP 200 with a JSON response containing message, fileExtension, and base64FileString, where base64FileString is the rendered PDF as a base64 string.
The call is synchronous, so there is no task to poll and no status to check, and the generated contract is available immediately. Reference the rendered PDF in the next step directly with the expression body('Generate_PDF')?['base64FileString'], or add a Parse JSON action first if you prefer typed outputs. When you need the raw bytes rather than the string, for archiving or a file action, convert with the base64ToBinary() expression, one of the Workflow Definition Language conversion functions.
One limit to plan for is the upload size. Document Generation rejects .docx payloads larger than 4 MB after base64 encoding, which is roughly a 3 MB raw file, and the limit is not surfaced in a friendly error. If you hit it, compress images through Word’s Picture Format tools, drop embedded fonts and OLE objects, and split oversized templates. The sample here is about 37 KB, so first runs stay well clear of the cap. For template authoring detail and common payload errors, Foxit’s Document Generation API quickstart is the reference.
The generated contract. The signature and date fields at the bottom come from the eSign Text Tags embedded in the same template, ready for Step 3.
Step 3: Send for Signature with OAuth2 and createfolder
The eSign API needs a bearer token first. Add an HTTP action that POSTs to https://na1.foxitesign.foxit.com/api/oauth2/access_token with content type application/x-www-form-urlencoded and this body:
grant_type=client_credentials&client_id=YOUR_ESIGN_CLIENT_ID&client_secret=YOUR_ESIGN_CLIENT_SECRET&scope=read-write Name this action Get eSign token. Its JSON response carries access_token, token_type set to bearer, expires_in, and instance_url, and you reference the token in the next call as body('Get_eSign_token')?['access_token']. This is the client-credentials grant, which fits a server-to-server flow where no human is present to log in.
The signature fields are already defined in the template. contract_signing.docx carries two eSign Text Tags, ${signfield:1:y} and ${datefield:1:y}, which follow the ${fieldtype:party:mandatory} syntax. Here both are mandatory fields assigned to party 1, the client who signs. Because the tags live in the Word file, the PDF that Document Generation produced in Step 2 already has a signature and date field in place, so there is no manual field placement after generation. Keep two rules in mind when you author your own tags. Replace any space inside a tag with an underscore, since a literal space breaks tag recognition, and set the tag text color to match the document background so the tokens do not show in the final PDF.
Now add the send action, an HTTP action named Create signing folder, set to POST https://na1.foxitesign.foxit.com/api/folders/createfolder with an Authorization: Bearer @{body('Get_eSign_token')?['access_token']} header and this body:
{
"folderName": "Acme Corp Contract",
"inputType": "base64",
"base64FileString": ["@{body('Generate_PDF')?['base64FileString']}"],
"fileNames": ["contract_signing.pdf"],
"parties": [
{
"firstName": "Jordan",
"lastName": "Lee",
"emailId": "[email protected]",
"permission": "FILL_FIELDS_AND_SIGN",
"sequence": 1
}
],
"processTextTags": true,
"sendNow": true
} In this code, you attach the Step 2 PDF by passing it as the single element of the base64FileString array together with inputType set to "base64", which is the pairing the API requires for base64 uploads. The parties array names the signer with firstName, lastName, emailId, and a permission of FILL_FIELDS_AND_SIGN, and its sequence of 1 matches the party number in the ${signfield:1:y} tag. Setting processTextTags to true is what converts those embedded tags into real, interactive fields, and sendNow set to true dispatches the signing invitation immediately. The response returns result as success and nests the identifier at folder.folderId, which you store for the archive flow. Foxit calls this container a folder rather than an envelope.
The Create signing folder action. The access_token and base64FileString chips are dynamic references to the two prior HTTP actions, so the eSign token and the generated PDF flow straight into this call with no copy-paste.
Two behaviors are worth handling before you ship. Every party number referenced by a Text Tag must have a matching entry in the parties array, because if a tag points at a party that is not listed, a sendNow: true create still returns success but silently drops that party’s fields, so their signature is never routed. If you need a human to approve the contract before it leaves, set sendNow to false to create a draft without emailing anyone, then dispatch it later with POST https://na1.foxitesign.foxit.com/api/folders/sendDraftFolder.
What the recipient sees after createfolder sends the invitation. The signature field is the one defined by the ${signfield:1:y} tag.
Step 4: Receive the Webhook and Archive the Signed Document
Create a second automated flow using the When a HTTP request is received trigger. Saving the flow generates a callback URL. Register that URL as the webhook endpoint on the eSign portal’s API settings page, which is owner-only, and select the signing events you want delivered.
Archive on the right event. The folder status moves through DRAFT, then SHARED, then PARTIALLY SIGNED, then COMPLETED, then EXECUTED. Trigger the archive on folder_executed, not folder_completed. The folder_completed event fires when all signatures are in but before the digital signature has been applied to the PDF, whereas folder_executed guarantees the file you download is the final, digitally signed document.
Verify each callback before acting on it. Foxit delivers every webhook as POST <your-url>?signature=<base64>, where the signature is the base64 of an HMAC-SHA-256 of the raw request body keyed with your webhook secret. Power Automate’s expression language has no native HMAC function, so there are two practical paths. The stronger one calls a small Azure Function or an Office Script that recomputes the HMAC over the raw body and returns a match boolean, which the flow checks in a Condition. The lighter one restricts the trigger to your tenant and treats the webhook secret as a shared value checked in a Condition, which is simpler but weaker. Choose based on how exposed the endpoint is.
Once a callback is verified and the event is folder_executed, parse folderId from the payload and download the signed file. Add an HTTP action with the bearer token set to GET https://na1.foxitesign.foxit.com/api/folders/download?folderId=@{triggerBody()?['folderId']}, which returns the executed PDF as application/pdf. Pass the response body to the OneDrive for Business Create file action, naming the destination folder by deal name or date so contracts stay retrievable.
The owner-only webhook settings, where you paste the Power Automate callback URL and pick the events to receive.
If you cannot expose a public endpoint, poll instead. GET https://na1.foxitesign.foxit.com/api/folders/viewActivityHistory?folderId={id} returns the audit trail, with actions such as Created, Invitation Sent, Opened, Viewed, Signed, and Folder Executed. This endpoint is GET-only and only returns data once the folder has been shared or sent, so run it on a schedule from a separate flow.
Common Mistakes
Most failures in this pipeline come from a small set of recurring errors. Check these first when something does not work.
- Using one credential pair or one token for both APIs : Document Generation uses
client_idandclient_secretheaders onna1.fusion.foxit.com, while eSign uses a bearer token onna1.foxitesign.foxit.com. They are separate. - Sending the eSign PDF without
inputType: the base64 upload needsinputTypeset to"base64"alongside thebase64FileStringarray, or the API returnsfileUrls or base64FileString cannot be empty. - Omitting
processTextTags: withoutprocessTextTagsset totrue, the tags stay as inert text and the signer can finish without signing. - A tag party number with no matching party : if
${signfield:2:y}appears but thepartiesarray has no party 2, the send succeeds and that party’s fields vanish silently. - Missing a party email field : each party needs
emailId, notemail. The wrong key returnsemail id of party cannot be empty. - Archiving on
folder_completed: download onfolder_executedinstead, or you may pull a PDF before the digital signature is applied. - A stray space or smart quote in a tag : a literal space inside
${...}or a curly quote from Word autocorrect breaks tag recognition. Use straight quotes and underscores.
API Workflow Automation FAQ
Does this work with n8n or Zapier instead of Power Automate?
Yes. Any platform that can make HTTP requests and receive a webhook works, since the Foxit calls are identical. Only the orchestration layer changes.
Do I need a paid plan to test the Foxit side?
No. The free Developer plan gives 500 credits per year with instant activation and no credit card. The paid dependency here is the Power Automate premium license for the HTTP action.
Are Document Generation and eSign on the same credentials?
No. Each API has its own Client ID and Secret, so store two credential pairs and use each on its own host.
Can I skip generation and send an existing PDF to eSign?
Yes. The createfolder call accepts a base64 PDF directly, or a public file URL through fileUrls and fileNames, so the generation step is optional if you already have the document.
How do I add a second signer?
Add party-2 Text Tags to the template, such as ${signfield:2:y}, and a matching party-2 entry to the parties array. Keep the party numbers in the tags and the array aligned.
Next Step
The fastest way to confirm the pieces before building the flow is to run one call by hand. Create your free Foxit Developer account, pull your Document Generation and eSign Client IDs and Secrets from the APIs Dashboard, and run a single GenerateDocumentBase64 call against contract_signing.docx in a REST client. Once it returns a base64 PDF, you know the credentials and payload are right, and the rest of the Power Automate Foxit API integration is just wiring the same calls into actions. Create your free account to get started.
Embedded Signing with the Foxit eSign API: From Envelope Creation to In-App iFrame in One Session

This guide walks through the Foxit eSign API end to end: authenticate, create a folder, generate an embedded session URL, and render the signing experience in an iFrame your users never leave.
Most embedded signing tutorials hand you a three-step abstraction: get a token, create an envelope, open a recipient view. The implementation details live somewhere else, usually mapped to a different API’s object model that doesn’t quite match what you’re working with.
This tutorial covers the Foxit eSign API embedded signing mechanics from start to finish. Authenticate once, create a “folder” (Foxit’s term for what other platforms call an envelope), receive an embedded session URL in that same response, and render it in an iFrame your users never leave. No separate field-placement API call, no client-side SDK to install.
What You’ll Build
By the end of this guide, you’ll have a working embedded signing session: a PDF loaded into your app via iFrame, signature fields defined by Text Tags, a webhook handler that verifies completion events, and a post-signing redirect that keeps users inside your product. Every step runs against the Foxit eSign sandbox with credentials you can generate in under five minutes.
1. Prerequisites and Auth Setup
Before any code runs, make sure you have the following installed and configured:
venv for project isolation
The requests library
A code editor: VS Code with the Python extension is a solid choice. PyCharm, Sublime Text, and JetBrains Fleet work equally well.
A Foxit eSign developer account, available at account.foxit.com/site/sign-up with no credit card required
Set up your workspace:
mkdir foxit-esign-tutorial && cd foxit-esign-tutorial
python3 -m venv .venv && source .venv/bin/activate
pip install requests The Foxit eSign API Is a Separate Portal from PDF Services
Developers who already use Foxit tools hit this wall first: the Foxit eSign API runs at its own base host, with its own API Key and API Secret. These credentials don’t work with the client_id and client_secret from the PDF Services developer portal at developer-api.foxit.com. The eSign documentation lives at developersguide.foxitesign.foxit.com, separate from docs.developer-api.foxit.com. The API Playground handles PDF Services sandbox testing; eSign sandbox calls go to the eSign portal directly.
The NA environment base host is https://na1.foxitesign.foxit.com. All subsequent code samples reference this as {HOST_NAME}.
Generating an OAuth 2.0 Access Token
Set your credentials as environment variables before running anything:
export FOXIT_ESIGN_CLIENT_ID="your_api_key"
export FOXIT_ESIGN_CLIENT_SECRET="your_api_secret"
Then generate a Bearer token via the OAuth 2.0 client credentials flow:
curl -X POST "https://na1.foxitesign.foxit.com/api/oauth2/access_token" \
-d "client_id=$FOXIT_ESIGN_CLIENT_ID" \
-d "client_secret=$FOXIT_ESIGN_CLIENT_SECRET" \
-d "grant_type=client_credentials" \
-d "scope=read-write" The response carries an access_token field. Pass it as Authorization: Bearer {token} on every subsequent call, and store it server-side so your credentials never travel to the browser.
2. Creating an Envelope Programmatically with /api/folders/createfolder
Foxit eSign calls what other platforms call an “envelope” a folder. If you’re coming from DocuSign or PandaDoc, that naming difference will catch you on the first read of the docs. The endpoint is POST {HOST_NAME}/api/folders/createfolder. A template-based variant also exists at POST {HOST_NAME}/api/templates/createFolder (note the camelCase) for assembling envelopes from saved templates. This tutorial focuses on the direct document-upload flow.
Defining Signature Fields with Text Tags
Foxit eSign reads signature field definitions from the PDF itself at upload time. You embed them as Text Tags directly in the document, and the API parses the tags on ingest and converts them to interactive fields. The tag syntax follows this structure: ${fieldtype:party_number:required:field_name:width}. Here, y marks a field as required and n marks it as optional. The party number maps to the signing sequence for that recipient. Width is expressed as underscores.
A minimal set covering the four field types required for a real signing flow:
${s:1: } # signature field, party 1
${i:1:______} # initials field, party 1
${d:1:n::____} # optional date field, party 1
${t:1:y:Full_Name:__________} # required text field, party 1, named "Full_Name" The full set of supported tag types includes signfield (or s), initialfield (or i), datefield (or d), textfield (or t), textboxfield (or tb), checkboxfield (or c), radiobuttonfield (or rb), securedfield (or sc), attachmentfield (or a), imagefield (or img), accept (or ab), decline (or db), payfield (or pf), and formulafield (or ff).
To hide tags in production, set the tag font color to match the page background color. Foxit eSign converts the tags to fields but does not strip them from the rendered document.
Use this sample PDF with Text Tags pre-embedded to follow along. It includes a signature field, initials, a date field, and a text input, all mapped to party 1.
Submitting the createfolder Request
You can supply the PDF two ways against the same endpoint. In URL mode you pass a fileUrls array of publicly reachable PDF links alongside a matching fileNames array. In base64 mode you set "inputType": "base64" and pass a base64FileString array of base64-encoded PDF bytes, again with a matching fileNames array. The API rejects a request that supplies neither, returning fileUrls or base64FileString cannot be empty.
One parameter is easy to miss and breaks the whole flow when omitted. Set processTextTags to true so the API parses the Text Tags embedded in the PDF and converts them into interactive fields. Leave it out and the folder still gets created successfully, but the tags stay inert literal text on the page, the signing UI reports zero required fields, and a signer can reach Finish without ever signing. If your source PDF carries native AcroForm fields instead of Text Tags, the companion processAcroFields flag handles those.
URL-based submission via cURL, pointing at the hosted sample PDF:
curl -X POST "https://na1.foxitesign.foxit.com/api/folders/createfolder" \
-H "Authorization: Bearer $FOXIT_ESIGN_ACCESS_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"folderName": "Service Agreement",
"sendNow": false,
"processTextTags": true,
"createEmbeddedSigningSession": true,
"embeddedSignersEmailIds": ["[email protected]"],
"fileUrls": ["https://github.com/lucienchemaly/foxit-demo-templates/raw/main/esign/sample-text-tags.pdf"],
"fileNames": ["sample-text-tags.pdf"],
"parties": [
{
"firstName": "Alex",
"lastName": "Rivera",
"emailId": "[email protected]",
"permission": "FILL_FIELDS_AND_SIGN",
"sequence": 1
}
]
}'
In this request you ask Foxit eSign to fetch the tagged PDF from its public URL, hold the folder as a draft instead of emailing it by setting sendNow to false, and mint an embedded signing session for the party identified in embeddedSignersEmailIds. The single signer is defined in the parties array with a name, email, the FILL_FIELDS_AND_SIGN permission, and a signing sequence.
Base64 upload via Python, which avoids needing a public URL by sending the file bytes inline:
import os
import base64
import requests
HOST = "https://na1.foxitesign.foxit.com"
TOKEN = os.environ["FOXIT_ESIGN_ACCESS_TOKEN"]
with open("sample-text-tags.pdf", "rb") as pdf:
encoded = base64.b64encode(pdf.read()).decode()
payload = {
"folderName": "Service Agreement",
"sendNow": False,
"processTextTags": True,
"inputType": "base64",
"base64FileString": [encoded],
"fileNames": ["sample-text-tags.pdf"],
"createEmbeddedSigningSession": True,
"embeddedSignersEmailIds": ["[email protected]"],
# Recipient defined in the body overrides any tag-defined party
"parties": [
{
"firstName": "Alex",
"lastName": "Rivera",
"emailId": "[email protected]",
"permission": "FILL_FIELDS_AND_SIGN",
"sequence": 1,
}
],
}
response = requests.post(
f"{HOST}/api/folders/createfolder",
headers={"Authorization": f"Bearer {TOKEN}"},
json=payload,
)
print(response.json())
In this code, you read the local PDF, base64-encode its bytes, and place the result inside the base64FileString array with inputType set to base64 so the API knows to decode it rather than fetch a URL. The rest of the payload mirrors the cURL example, sending the folder as a draft and requesting an embedded session for the listed signer, after which you print the JSON response to read back the folder.folderId and the session URL. When both the PDF’s Text Tags and the API body define recipient parties, the body values take precedence, so you can reuse a tagged PDF template and swap in different signers at request time without touching the document.
3. Generating the Embedded Signing Session and Rendering the iFrame
Setting createEmbeddedSigningSession: true in the createfolder body, paired with an embeddedSignersEmailIds array naming which parties sign in your app, gives you a signed session URL in the same response. No second API call, no separate “recipient view” endpoint. The response carries an embeddedSigningSessions array, and each entry holds the signer email in emailIdOfSigner, the raw token in embeddedToken, and the ready-to-render link in embeddedSessionURL. That URL follows this format, where eetid is the URL-encoded embedded token:
https://{HOST_NAME}/embedded/embeddedsign?eetid={URL-ENCODED-EMBEDDED-TOKEN}
If you omit embeddedSignersEmailIds, the API returns email id of embedded signer(s) not submitted, so always list the embedded signers explicitly. For multi-party workflows you can set createEmbeddedSigningSessionForAllParties: true so every recipient signs in an embedded session rather than over email. When you need each signer’s live URL, request it per signer through the regenerate endpoint described below.
The full lifecycle runs from token request through webhook delivery:
Injecting the Session URL into an iFrame
The signing UI renders entirely inside the iFrame with no additional JavaScript library required.
function launchSigningSession(embeddedSessionURL) {
const iframe = document.createElement("iframe");
// These five sandbox permissions are the minimum required for the signing UI
iframe.setAttribute(
"sandbox",
"allow-scripts allow-same-origin allow-forms allow-popups allow-top-navigation",
);
iframe.src = embeddedSessionURL;
iframe.style.width = "100%";
iframe.style.height = "700px";
iframe.style.border = "none";
iframe.onload = function () {
console.log("Signing session ready");
};
document.getElementById("signing-container").appendChild(iframe);
} The sandbox attribute matters here. Remove allow-popups or allow-top-navigation and the signing UI breaks in ways that produce no obvious error. The five attributes above are the minimum viable set. Don’t strip them without testing the complete signing flow.
To verify the flow without wiring this into your app first, download the ready-to-run iFrame test page from the demo repo, open it in a browser, paste the embeddedSessionURL from your createfolder response into the input box, and click Load. It applies the same five sandbox permissions shown above. A correctly tagged document renders with the signing controls active, as shown below.
The sample document loaded in the iFrame with processTextTags enabled. The header shows “Required Fields Left: 2” and a “Next Required Field” button, confirming the Text Tags became interactive fields. If that counter reads zero or the page shows the raw ${...} tag text with no input boxes, recheck that processTextTags was set to true on the createfolder request.
Session URLs are short-lived. Generate the URL at request time and pass it directly to the client. Don’t cache it. If a user returns to an incomplete workflow after the session expires, call POST {HOST_NAME}/api/embedded/regenerateEmbeddedSigningSession with the folder ID and the signer email to get a fresh URL. The response mirrors a single embedded session entry, returning emailIdOfSigner, embeddedToken, and the new embeddedSessionURL.
4. White-Labeling the Signing Experience
Foxit eSign exposes branding control at several levels. You can apply a custom logo to the signing UI and outgoing notification emails, set application colors to match your product’s visual design, and configure a personalized sender name so recipients see your company name rather than a generic Foxit sender identity.
For logo and color configuration, manage these settings through the eSign Portal’s branding section. The portal publishes canonical limits on file size and supported formats. Check the branding settings in your account for current specifications rather than relying on numbers printed here that may have changed.
Configuring Post-Signing Redirect URLs
Custom redirect URLs keep users inside your application after they sign, decline, defer, or hit an error. Pass them as parameters in the createfolder body:
payload = {
"folderName": "Service Agreement",
"sendNow": False,
"processTextTags": True,
"createEmbeddedSigningSession": True,
"embeddedSignersEmailIds": ["[email protected]"],
# Return the user to your confirmation page after a successful signature
"signSuccessUrl": "https://app.example.com/contracts/signed",
# Return to a dedicated page when the signer declines
"signDeclineUrl": "https://app.example.com/contracts/declined",
# Return here when the signer chooses to finish later
"signLaterUrl": "https://app.example.com/contracts/later",
# Return here if the signing session errors out
"signErrorUrl": "https://app.example.com/contracts/error",
"parties": [ ... ],
"fileUrls": [ ... ],
"fileNames": [ ... ],
} Foxit eSign appends two query parameters to your success URL when it redirects, namely folderId for the folder that was signed and event, whose value is signing_success on a completed signature or signing_declined when the signer declines. Without these URLs, signers land on Foxit’s default confirmation page. With them, your application controls the entire post-signing navigation experience.
Tailoring Signer Instructions for Regulated Industries
Regulated workflows often need specific disclosure language in front of signers, which matters for ESIGN Act or eIDAS compliance scenarios where your legal team controls the wording. The createfolder body accepts a signerInstructionId and a confirmationInstructionId that reference instruction templates configured in your account, and you can drop explicit accept and decline button fields into the document itself using the accept (or ab) and decline (or db) Text Tag types. The eSign Developers Guide at developersguide.foxitesign.foxit.com documents these parameters.
5. Handling Webhook Callbacks for Completion Events
Foxit eSign fires HTTP POST requests to your registered endpoint when these lifecycle events occur: folder_sent, folder_viewed, folder_signed, folder_cancelled, folder_completed, folder_executed, and folder_deleted. Register your callback URL in the eSign Portal under API Settings. Make sure the endpoint is publicly reachable over HTTPS before you start testing with the sandbox.
Verifying the Webhook Signature
Every webhook POST includes a signature query parameter. It’s a base64-encoded HMAC-SHA-256 digest of the raw request body, computed using your webhook secret. Recompute the same digest server-side and compare before doing any processing. An unverified webhook is an open door.
import os
import hmac
import hashlib
import base64
from flask import Flask, request, abort
app = Flask(__name__)
WEBHOOK_SECRET = os.environ["FOXIT_ESIGN_WEBHOOK_SECRET"].encode()
@app.route("/webhook/foxit", methods=["POST"])
def foxit_webhook():
# Step 1: Pull the signature from the query string
received_sig = request.args.get("signature", "")
# Step 2: Recompute HMAC-SHA-256 over the raw request body
raw_body = request.get_data()
computed_sig = base64.b64encode(
hmac.new(WEBHOOK_SECRET, raw_body, hashlib.sha256).digest()
).decode()
# Step 3: Constant-time comparison guards against timing attacks
if not hmac.compare_digest(received_sig, computed_sig):
abort(403)
payload = request.json
event_name = payload.get("event_name")
folder_id = payload.get("data", {}).get("folder", {}).get("folderId")
if event_name in ("folder_completed", "folder_executed"):
handle_completion(folder_id)
elif event_name == "folder_cancelled":
handle_cancellation(folder_id)
# A non-2xx response triggers Foxit's automatic retry logic.
# Return 200 once verification and basic parsing succeed.
return "", 200
The payload structure is consistent across all events, carrying a top-level event_name, an event_date timestamp, and a data object whose folder field holds the full folder record. The folder identifier lives at data.folder.folderId, alongside the rest of the envelope-level metadata such as folderName and folderStatus.
Downstream Actions Triggered from folder_completed
When folder_completed or folder_executed fires, two actions cover the majority of production workflows. Fetch the signed document via the documents endpoint using the folder ID and store the result in your document storage layer. For contracts that require sequential agreements (a master services agreement followed by a statement of work, for example), fire the next createfolder call as part of the completion handler.
Audit history is available programmatically via GET {HOST_NAME}/api/folders/viewActivityHistory?folderId={FOLDER_ID}, which returns the full signing log once a folder has been shared or sent. This is a GET-only endpoint, and a folder still in DRAFT returns logs of a non-shared folder can not be viewed.
6. Common Mistakes and Troubleshooting
Text Tag Syntax Breaks on Copy-Paste
Smart-quote autocorrect in Word, Google Docs, and many other editors replaces straight ASCII brackets and quote characters with typographic equivalents. Tag parsing fails silently when this happens. Always paste tags into a plain-text editor first and verify the bracket characters are straight ASCII. The eSign Developers Guide writes every field-type notation in lowercase, such as signfield or s and textfield or t, so author your tags in lowercase to match the documented syntax rather than experimenting with capitalized variants.
Visible Text Tags Reaching Production
Foxit eSign converts embedded tags to fields but does not remove them from the document. If you ship a PDF without setting the tag text color to match the page background, signers see the raw ${...} strings on the page. Build the color-hide step into your PDF preparation pipeline before it becomes a support ticket.
Body-Level parties Overriding Tag-Defined Recipients
Tags define field layout and recipient assignment and must be embedded in the PDF itself, while recipient definitions in the API request body override tag-defined recipient metadata. If you’re seeing the wrong signer name or email appear, check whether a body-level parties definition is overriding the tag.
Expired Session URLs
Embedded session URLs are short-lived. Caching one and reusing it on the next page load will fail. Call POST {HOST_NAME}/api/embedded/regenerateEmbeddedSigningSession with the folder ID and signer email each time a returning user needs access to an incomplete session.
Over-Restrictive sandbox on the iFrame
The five required sandbox permissions are allow-scripts, allow-same-origin, allow-forms, allow-popups, and allow-top-navigation. If the UI loads but behaves unexpectedly, check your sandbox attributes first.
Credential Confusion Between eSign and PDF Services
The API Key and API Secret from the eSign Portal are specific to the eSign API, and the OAuth 2.0 flows also differ between the two. Using PDF Services credentials against the eSign /api/oauth2/access_token endpoint returns an authentication error. Keep the two credential sets separate and named clearly in your environment configuration.
Skipping Webhook Signature Verification
Always verify the signature query parameter before processing any payload. Return a 200-class status code once verification and basic parsing succeed, because a non-2xx response causes Foxit to retry delivery, which can create duplicate processing if your handler is not idempotent.
Embedded Signing FAQ
Can I regenerate an expired embedded signing session?
Yes. Call POST {HOST_NAME}/api/embedded/regenerateEmbeddedSigningSession with the folder ID and signer email. Foxit eSign returns a fresh embeddedSessionURL for the same envelope without resetting the signing state.
Do I need a separate Foxit account if I’m already using Foxit PDF Services?
Yes. The Foxit eSign API operates from a separate portal at na1.foxitesign.foxit.com with its own credentials. The two portals don’t share API keys, secrets, or authentication tokens.
Can I use an existing template instead of uploading a PDF?
Yes. Use POST {HOST_NAME}/api/templates/createFolder to assemble the envelope from a saved template rather than a raw document upload.
Does the embedded signing session work on mobile browsers?
Yes. The iFrame renders responsively on modern mobile browsers without additional configuration.
Is the audit trail accessible programmatically?
Yes. GET {HOST_NAME}/api/folders/viewActivityHistory?folderId={FOLDER_ID} returns the full signing activity log for any shared or sent envelope, including timestamps for each event. A folder still in DRAFT has no shared history to return.
What is the difference between folder_completed and folder_executed?
Both events signal that the folder has been completed with all required parties’ signatures, and the eSign Developers Guide describes them in the same terms, each delivering the folder record in data.folder. Listen for either to trigger downstream retrieval of the signed document, and make your handler idempotent so receiving both for the same folder does not double-process it.
Next Step
Activate your free Foxit eSign developer account at account.foxit.com/site/sign-up, no credit card required. Generate your OAuth token, fire a POST /api/folders/createfolder request with createEmbeddedSigningSession: true against the sandbox, and verify the returned URL loads in a local iFrame. From account creation to a working embedded signing session takes under 30 minutes.
Embed Secure eSignatures into Your App with Foxit API

Foxit eSign makes electronic signatures easy, but developers can take it further by automating the process. This tutorial shows how to use the Foxit eSign API to embed secure eSignatures in your apps. With Python code examples, you’ll learn to send documents for signing, dispatch reminders, and check the signing status programmatically.
Foxit eSign is an electronic signature solution that lets individuals and businesses sign, send, and manage documents online. Users can create legally binding eSignatures, prepare forms, and track document status in real time. Reusable templates, automated workflows, and audit trails reduce manual paperwork and keep signing processes moving.
At the simplest level, a user can log into the eSign dashboard and handle 100% of their signing needs. For example, they can upload a Microsoft Word template and drag and drop fields for the signing process. I did this with a simple Word document, and after uploading, the editor let me place fields exactly where I needed them:
That screenshot shows three fields added to my document: a date field, a signer name field, and the actual signature spot. Each field has many configuration options, and your own documents could have far more or far fewer. You can design these forms to meet whatever need you have. You can also do all of this directly within Word. The docs explain how to add fields directly into Word that become active during the signing process.
Once you’ve set up your template, you can initiate the signing process right from the app. The dashboard gives you a full history and audit trail covering whether someone has signed, when they signed, and who signed. As a developer, you’re probably wondering whether this process can be automated. It can.
If you’d rather watch an introduction first, the API introduction video walks through the same material.
eSign Via API
Before digging into the APIs, take a quick look at the API Reference. The signing process itself can get complex. Two, three, or more people may need to sign a document in a specific order, and the template field setup can be done entirely in Word. The focus here is a simple signing example, but nothing stops you from building more advanced, flexible workflows.
The full signing flow this article walks through, end to end:

The first step in any API usage is authentication. When you have an eSign account with API access, you receive a client_id and client_secret value, both of which you exchange for an access token at the appropriate endpoint. You’ll find the client_id and client_secret under the API tab in your Foxit eSign account settings once you’ve activated API access. A simple Python implementation looks like this:
CLIENT_ID = os.environ.get("CLIENT_ID")
CLIENT_SECRET = os.environ.get("CLIENT_SECRET")
def getAccessToken(id, secret):
url = "https://na1.foxitesign.foxit.com/api/oauth2/access_token"
payload=f"client_id={id}&client_secret={secret}&grant_type=client_credentials&scope=read-write"
headers = {
'Content-Type': 'application/x-www-form-urlencoded'
}
response = requests.request("POST", url, headers=headers, data=payload)
token = (response.json())["access_token"]
return token
access_token = getAccessToken(CLIENT_ID, CLIENT_SECRET) In this code, you pull the client_id and client_secret from environment variables, post them as application/x-www-form-urlencoded to na1.foxitesign.foxit.com/api/oauth2/access_token with the client_credentials grant and read-write scope, and read access_token off the JSON response. Every subsequent call in this article reuses that token in the Authorization: Bearer ... header.
The example uses the US region host (na1.foxitesign.foxit.com). If your account is in another region, swap in the appropriate host: eu1.foxitesign.foxit.com for EU, na2.foxitesign.foxit.com for Canada, or au1.foxitesign.foxit.com for Australia.
All remaining demos use this method, and at the end of this post you’ll find GitHub links for the full source.
Kicking Off the Signing API Process
With authentication handled, the code can drive the full signing process. The first thing to add is a signing flow using the template shown above. From the dashboard I noted the template ID, 392230, though APIs for working with templates let you retrieve that via code as well.
The Create Envelope from Template endpoint starts the signing process. An envelope is a set of documents a user must sign. For this demo it’s one document, but you can include multiple. The API reference example shows a large input body because the electronic signing process can be complex. For this simple demo, you only need the signer’s name and email address. This Python utility handles that:
def sendForSigning(template_id, first_name, last_name, email, token):
url = "https://na1.foxitesign.foxit.com/api/templates/createFolder"
body = {
"folderName":"Sending for Signing",
"templateIds":[template_id],
"parties":[
{
"permission":"FILL_FIELDS_AND_SIGN",
"firstName":first_name,
"lastName":last_name,
"emailId":email,
"sequence":1
}
]
}
headers = {
'Authorization': f'Bearer {token}',
}
response = requests.request("POST", url, headers=headers, json=body)
return response.json() The code above builds the create-envelope payload, with the folder name, the template ID list, and a single-element parties array carrying the signer’s name, email, and FILL_FIELDS_AND_SIGN permission, then POSTs it to /api/templates/createFolder with the bearer token and returns the parsed JSON. parties is an array because real signing flows often need multiple signers, and permission is required on each entry because it defines the role that party plays.
Passing in the template ID and signer details works like this:
# Hard coded template id
tid = "392230"
sendForSigningResponse = sendForSigning(tid, "Alex", "Rivera", "[email protected]", access_token) The call returns a large set of data. For now, pull out just the envelope ID:
envelopeId = sendForSigningResponse['folder']['folderId']
print(f"ID of the envelope created: {envelopeId}") Note: You’ll see ‘folder’ referenced in the API endpoints and results, but the eSign API is migrating to the ‘envelope’ term. Both terms are used interchangeably in the current API.
A few seconds after running this code, the signing email appeared in my account:
Sending out Electronic Reminders
To nudge signers who haven’t acted yet, use the Send Signature Reminder endpoint. It takes the envelope ID created earlier (and again, see the note above about envelope vs folder):
def sendReminder(envelope_id, token):
url = "https://na1.foxitesign.foxit.com/api/folders/signaturereminder"
body = {
"folderId":envelope_id
}
headers = {
'Authorization': f'Bearer {token}',
}
response = requests.request("POST", url, headers=headers, json=body)
result = response.json()
return result In this code, you build a one-key body containing the envelope ID, attach the bearer token, POST to /api/folders/signaturereminder, and return the parsed JSON. The endpoint is fire-and-forget from the client’s perspective, so a 2xx response means Foxit has queued the reminder email to the outstanding signer.
With the access token and envelope ID in hand, triggering a reminder takes a single call:
access_token = getAccessToken(CLIENT_ID, CLIENT_SECRET)
result = sendReminder(envelope_id, access_token) Running this sends an email reminder to the signer:
Ok, But Did They Sign Their Document Yet??
To check whether the signer has completed the process, use the Get Envelope Details endpoint. It takes the envelope ID from before. Here’s a Python wrapper for that API:
def getStatus(envelope_id, token):
url = f"https://na1.foxitesign.foxit.com/api/folders/myfolder?folderId={envelope_id}"
headers = {
'Authorization': f'Bearer {token}',
}
response = requests.request("GET", url, headers=headers)
result = response.json()
return result The code above issues a GET to /api/folders/myfolder with the envelope ID as a query-string parameter, sends the bearer token in the Authorization header, and returns the parsed JSON. The full response body carries every audit-trail field the dashboard surfaces (parties, timestamps, folder status), and the next snippet pulls just folderStatus out for a quick yes/no.
Checking status against the envelope ID:
result = getStatus(envelope_id, access_token)
print(f"Envelope status: {result['folder']['folderStatus']}") The endpoint returns a lot of information, but printing just the status gives you a high-level view of where the process currently stands.
With the example shown above, the envelope status is SHARED. Clicking the link in the signing email opens the signing view:
The date is already filled to today’s date, and the name is pre-filled because eSign knows who the document was sent to. Clicking to sign is all that remains. Once the signer does that, the same status call returns EXECUTED.
Next Steps
If you’re new to eSign, the main homepage gives you a solid introduction, and the Foxit eSign YouTube channel has video content covering the service in depth.
Beyond the basics covered here, the API has significantly more to offer. Webhooks deliver automatic notifications when envelope events fire, so you don’t need to poll for status. The API also supports embedded signing sessions for keeping signers inside your own application, SSO authentication for signers, and multi-party workflows with sequential or parallel signing order. The API Reference covers all of these in full.
All three code examples from this post are available in the GitHub repo. The eSign API is also part of the broader Foxit developer platform, which includes APIs for PDF processing, document generation, and embedded PDF viewing. Bring your questions to the developer forums.
Ready to wire signing into your own product? Create a free developer account directly at account.foxit.com/site/sign-up (no credit card required). The direct URL skips the pricing-page redirect from the developer portal and drops you on the account form, with API credentials waiting in the API Keys section once you’re in.
eSign API FAQ
How do I embed e-signatures in my app with the Foxit eSign API?
You authenticate with OAuth2 to get an access token, then call Create Envelope from Template to send a document for signature. In this article’s flow, the signer completes signing through an emailed link. For a fully in-app experience where signers never leave your interface, the Foxit eSign API also supports embedded signing sessions, which you load directly inside your app and pair with webhooks to capture completion events.
What is an embedded signature?
An embedded signature is one a signer applies inside your own application’s interface rather than on a separate hosted signing page. Instead of redirecting the signer to an external Foxit eSign page, your app presents the signing experience in context, keeping users in your product end to end. With the Foxit eSign API, this is delivered through embedded signing sessions rather than the standard email-based envelope flow.
What is an embedded signing API?
An embedded signing API generates a secure signing session you load inside your own app — typically in an iframe or web view — so signers complete documents without leaving your interface. The Foxit eSign API provides this through embedded signing sessions, alongside the email-based flow demonstrated in this article (create an envelope, signer signs via an emailed link). Webhooks then notify your app the moment an envelope reaches EXECUTED status.
How do I authenticate with the Foxit eSign API?
Authentication uses the OAuth2 client-credentials grant. You exchange your client_id and client_secret — found under the API tab in your Foxit eSign account settings — for an access token by POSTing to the regional OAuth2 endpoint (for example, na1.foxitesign.foxit.com for the US, or eu1 for the EU). Send that token as a Bearer header on every subsequent call; the same token is reused across envelope creation, reminders, and status checks.
How do I check whether a signer has completed a document?
Call the Get Envelope Details endpoint with your envelope ID, passing the Bearer token in the Authorization header. The response carries the full audit trail — parties, timestamps, and status. Reading folderStatus gives a quick state: SHARED while the document is out for signature, and EXECUTED once the signer finishes. For real-time updates instead of polling, the Foxit eSign API offers webhooks that fire on envelope events.
Why does the Foxit eSign API use both "folder" and "envelope"?
They refer to the same thing. An envelope is the set of documents a signer must complete. The Foxit eSign API is migrating from the older term “folder” to “envelope,” so you’ll still see folder in endpoint paths and response fields — for example, createFolder, folderId, and folderStatus — while the documentation increasingly uses envelope. Both terms are interchangeable in the current API.