Compose And Send Contract

Compose and send a contract in one step

Publishes the template, builds a signing workflow from the given signers
(optionally gated so a stage only proceeds after a transaction succeeds),
and sends the contract request — atomically; by default the workflow is
ad-hoc (not saved as a reusable Contract Flow) unless save_as_flow is
true. Returns 404 if the template, project, or transaction is not found.
Returns 400 if signers don't cover every template signer role exactly
once (or duplicate a role), or if payment_gate.after_role doesn't match
a signer. Returns 422 if any signer uses your client signing profile and
none is configured.

Recent Requests
Log in to see full request history
TimeStatusUser Agent
Retrieving recent requests…
LoadingLoading…

Compose and send a contract in a single call. The endpoint builds a contract flow from the template and the signers you supply (optionally inserting a payment gate that holds signing until a linked transaction succeeds) and creates the contract request that delivers the contract to the signers. There is no separate publish step: the template and the new contract flow are usable as soon as they exist. All of these steps run in one transaction: if any step fails the whole operation is rolled back, so no orphaned contract flow is left behind. On success it returns the created contract request, including its participants and their signing status.

Authentication & access

  • Requires a client API token: Authorization: Bearer <token>.
  • API credentials need the contracts.requests.write permission. Dashboard users need the OWNER or OPERATIONS role, or a custom role that includes this permission.
  • Contract signing must be enabled for the client. If it is disabled the request returns 403.

Request body

FieldTypeNotes
template_version_idstring, requiredID of the contract template version to send.
signersarray, required (min 1)Ordered list of signers. Each entry's role must match a template signer role, and together the signers must cover every template signer role exactly once.
payment_gateobject, optionalWhen set, signing is held until a linked transaction succeeds. payment_gate.after_role (1-255 characters) must match one of the signers' roles.
save_as_flowboolean, default falsePersist the ad-hoc setup as a reusable contract flow instead of an internal ad-hoc one.
flow_namestring, optional (max 255)Name for the saved contract flow when save_as_flow is true. Defaults to an auto-generated Ad-hoc: <template name> label.
project_idstring, optionalID of the project this contract belongs to. Must belong to your client and must not be archived.
transaction_idstring, optionalID of a payment transaction to link to this contract. One payment funds one live contract: a transaction already linked to another contract request is refused unless that request ended canceled, declined or expired.
variablesobject, optionalTemplate variable values applied to this contract.
email_notificationsobject, optionalPer-event email notification and attachment toggles, extra completion recipients and view-only (CC) recipients for the contract flow created by this send. See below.

Each signer (signers[])

FieldTypeNotes
rolestring, required (1-255)Signer role name as defined in the template.
sourceenum, requiredWho fills this signer. One of: client_signing_profile (auto-sign), user, business_customer, or external.
user_idstringRequired when source is user.
business_customer_idstringRequired when source is business_customer.
externalobjectRequired when source is external; provides the external signer's name (1-255 characters) and email.
field_valuesobject, optionalPre-filled template field values for this signer.
expire_after_hoursinteger, optional (1-2160)Hours this signer has to sign once it is their turn. Omit or null for no expiration. Not allowed on client_signing_profile signers.
parallel_with_previousboolean, default falseSign at the same time as the previous signer instead of waiting for them. Signers that sign together must all carry the same expire_after_hours. Ignored on the first signer.

Signers sign in the order given, except where parallel_with_previous groups them. A client_signing_profile signer is signed automatically (auto-sign); every other signer gets a signing link. When payment_gate is set, the gate is placed right after the signer named in after_role (after that signer's whole group when signing in parallel), and the signers after it wait until a linked transaction has succeeded.

Email notifications (email_notifications)

FieldTypeNotes
invitationboolean, default trueSend the signing invitation email when a link signer's turn starts.
completedboolean, default trueNotify participants when the contract is fully signed.
declinedboolean, default trueNotify participants when a signer declines.
expiredboolean, default trueNotify participants when the contract expires before completion.
completed_attach_documentboolean, default trueAttach the signed PDF to the completion email.
completed_attach_audit_logboolean, default falseAttach the signing audit log to the completion email.
completed_extra_emailsarray of emails, optional (max 10)Extra addresses that also receive the completion notification.
cc_emailsarray of emails, optional (max 10)View-only (CC) recipients. Each gets a read-only link to the contract when it is sent, plus the completed, declined and expired notifications per the toggles above. They cannot sign. Addresses that match a signer are skipped.
cc_view_link_daysinteger, default 30 (1-365)Days the CC view links keep working after the contract is completed, declined or expired. While signing is in progress they always work; canceling the contract closes them at once.

Signer preconditions

  • If any signer uses the client_signing_profile source (auto-sign), a signing profile must already be configured for the client. If none exists the request returns 422. The profile must also be able to sign for that role (a signature image when the role has a signature field, and values for the role's required fields); otherwise the request returns 400 listing what is missing.
  • Each user signer must reference a user under your client, and each business_customer signer must reference a business customer under your client. Verification status is not checked here: a subject in any kyc_status/kyb_status (or external attestation status) can be a signer.
  • Every signer needs a valid email address. A business_customer signer without a contact email, or a stored signer email that is not a valid address, returns 400.

Template preconditions

The referenced template version must be provisioned for signing, must not be archived, and must have at least one signer role and at least one fillable field; otherwise the request returns 400. Signers are matched against the template's roles as last stored, so after adding roles in the document builder call Refresh Contract Template before sending.

Response

Returns 200 with the created contract request. The payload includes the request id, the workflow_id and template_version_id that were used, overall status, the current_stage_index and current_participant_key, any linked transaction_id and project_id, applied variables and metadata, completion_extra_emails, cc_recipients (each with email, view_url and view_expires_at), and the full list of participants with each one's signing status. A signer's signer_url (and active_signing_url) is returned only while it is that signer's turn to sign. completed_document_url and audit_log_url are always null in this response.

If the signing service returns an error after the contract has been created (for example while auto-signing the first stage), the request is kept and returned in its current state instead of being rolled back. It moves on when the next signing event arrives; if nothing is pending (for example a failed auto-sign), call Reconcile Contract Request to retry.

Error responses

StatusWhen
400Duplicate signer role assignment; signers do not cover every template signer role exactly once; payment_gate.after_role does not match any signer; template is archived or not provisioned for signing; template has no signer roles or no fillable fields; expire_after_hours set on an auto-sign signer; signers signing in parallel have different expire_after_hours; the signing profile cannot auto-sign a role; a signer has no valid email address; project is archived; the transaction is already linked to another live or completed contract request
403Contract signing is disabled for the client
404Template version, signer user, signer business customer, project, or linked transaction not found under this client
422Request body failed validation (e.g. signer source/subject mismatch, missing required external signer details, expire_after_hours out of range); auto-sign requested without a configured signing profile
502The signing service returned an error or an invalid response
503The signing service is temporarily unavailable or not configured

Standard 401 (authentication), 403 (insufficient permission or role), and 429 (rate limit) responses apply to every endpoint and are documented in the Error reference.

Body Params
string
required

ID of the contract template version to send

signers
array of objects
required
length ≥ 1

Ordered list of signers for this contract

Signers*
string
required
length between 1 and 255

Signer role name as defined in the template

string
enum
required

Who fills this signer: client, user, business, or external

Allowed:
ExternalSignerInfo | null

Details for an external signer; required when source is external

ID of the registered user signing; required when source is user

ID of the business customer signing; required when source is business

field_values
object

Pre-filled template field values for this signer

1 to 2160

Hours this signer has to sign once it is their turn; null means no expiration. Not allowed on auto-signing signers.

boolean
Defaults to false

Sign at the same time as the previous signer instead of waiting for them. Signers that sign together must all carry the same expire_after_hours. Ignored on the first signer, who always starts the first group.

ComposeAndSendPaymentGate | null

Hold signing until a linked transaction succeeds

boolean
Defaults to false

Persist this ad-hoc setup as a reusable workflow

length ≤ 255

Name for the saved workflow when save_as_flow is true

ID of the project this contract belongs to

ID of a payment transaction to link to this contract

variables
object

Template variable values for this contract

email_notifications
object

Email notification + attachment config for the workflow created by this send

Responses

Language
Credentials
Bearer
LoadingLoading…
Response
Click Try It! to start a request and see the response here! Or choose an example:
application/json