Skip to content
Quarters Developers
esc
  • Type an endpoint, an object or a word from a guide.

Agreements

Report an external agreement

PUT /api/v1/reservations/{id}/agreement

Your whole current view of the envelope. The same externalId as the current agreement updates it in place; a different one, or the first, creates a new version and supersedes a live one, exactly as a re-issue from the dashboard would.

Signers are matched by role and never removed. A report about one party says nothing about the others, so you may send only the party that changed.

Path parameters

ParameterInTypeDescription
id requiredpathstringThe reservation id.

Request body

application/json, shaped as AgreementInput.

FieldTypeDescription
externalId string | nullYour stable id for the envelope (a DocuSeal submission id, say). Required unless status is failed: a failure before any envelope exists, missing fields or an API outage, annotates the current agreement instead.
status requiredenum "sent""completed""declined""failed""voided"
sentAt timestamp | nullDefaults to now the first time the status is reached, and is kept afterwards. ISO 8601
completedAt timestamp | nullAs sentAt. ISO 8601
declinedAt timestamp | nullAs sentAt. ISO 8601
voidedAt timestamp | nullAs sentAt. ISO 8601
error string | nullWhy it failed, for staff to read on the booking. Only kept while status is failed. max 2000 chars
documentUrl url | nullWhere the provider hosts the executed document. Shown to staff as a link. max 2000 charshttps only
signers SignerInput[]Up to ten. Matched by role; a party you leave out is left as it was. max 10default []

Response

201 { agreement: Agreement }

Agreement fields
FieldTypeDescription
id string
version integerCounts up on every re-issue. Superseded versions are not listed.
provider enumquarters for an envelope Quarters issued itself, external for one written through this API. "quarters""external"
externalId string | nullYour stable id for the envelope, as you reported it.
status enum "sent""completed""declined""failed""superseded""voided"
templateName string | nullThe Quarters template used; null for an external envelope.
sentAt timestamp | null ISO 8601
completedAt timestamp | null ISO 8601
declinedAt timestamp | null ISO 8601
voidedAt timestamp | null ISO 8601
error string | nullWhy it failed. Only kept while status is failed.
documentUrl string | nullThe provider-hosted copy of the executed document, as reported.
document object | nullSet once the executed PDF has been archived: by Quarters for its own envelopes, by you through the document endpoint for yours.
signers Signer[]
createdAt timestamp ISO 8601
updatedAt timestamp ISO 8601

Errors

Every failure is { error, message }; see Errors. A missing or expired bearer is a 401 on every endpoint but the token exchange.

StatuserrorWhen
400invalid_requestA bad field, named in the message; a missing externalId on a non-failed status; or a role listed twice.
404not_foundUnknown reservation.
409conflictThe organisation signs its contracts in Quarters (switch the provider under Settings › Contracts first), or a failure without an externalId arrived while a sent or completed envelope is current. Report it against that envelope’s id instead.

Notes

  • 201 when the call created a new version, 200 when it updated the current one in place.
  • The moment status becomes completed, a booking that is reserved becomes confirmed, the same consequence a signature in Quarters has. You do not have to change the booking status yourself, and you receive a reservation.updated webhook for it.
  • declined, voided and failed are recorded and shown to staff; none of them changes the booking. Quarters sends no email on any of these: your system already talked to the parties.
  • Reporting sent with a new externalId while a sent agreement is current marks the old one superseded. A completed one is kept in the history untouched.
  • A report whose externalId belongs to a superseded version lands on that historical row: it records what happened, but changes nothing about the current agreement or the booking. Finishing an old envelope after staff re-issued never confirms anything.

Request

curl -X PUT "https://go.quarters.live/api/v1/reservations/7c02…/agreement" \
  -H "Authorization: Bearer $ACCESS_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "externalId": "docuseal:1849213",
    "status": "sent",
    "signers": [
      {
        "role": "lessor",
        "name": "City Retreat B.V.",
        "email": "bookings@cityretreat.com",
        "status": "completed"
      },
      {
        "role": "lessee",
        "name": "Sofia Rossi",
        "email": "sofia@example.com",
        "status": "pending",
        "signingUrl": "https://docuseal.com/s/…"
      }
    ]
  }'

Response · 201

{
  "agreement": {
    "id": "9a41…",
    "version": 1,
    "provider": "external",
    "externalId": "docuseal:1849213",
    "status": "sent",
    "templateName": null,
    "sentAt": "2026-09-08T10:02:11.000Z",
    "completedAt": null,
    "declinedAt": null,
    "voidedAt": null,
    "error": null,
    "documentUrl": null,
    "document": null,
    "signers": [
      {
        "role": "lessor",
        "name": "City Retreat B.V.",
        "email": "bookings@cityretreat.com",
        "status": "completed",
        "signingUrl": null,
        "viewedAt": null,
        "completedAt": "2026-09-08T10:02:11.000Z",
        "declinedAt": null,
        "declineReason": null
      },
      {
        "role": "lessee",
        "name": "Sofia Rossi",
        "email": "sofia@example.com",
        "status": "pending",
        "signingUrl": "https://docuseal.com/s/…",
        "viewedAt": null,
        "completedAt": null,
        "declinedAt": null,
        "declineReason": null
      }
    ],
    "createdAt": "2026-09-08T10:02:11.000Z",
    "updatedAt": "2026-09-08T10:02:11.000Z"
  }
}