Skip to main content
Contracts are created and signed using approved Legal Identities. Contract proposals are XMPP messages sent through POST /Agent/Xmpp/SendXmlMessage; there is no POST /Agent/Legal/SendProposal server resource.

Lifecycle

Follow the lifecycle

  1. Create a contract from an approved template with Legal/CreateContract. Assign each approved Legal Identity to its exact role.
  2. Have the initiating party retrieve and review the returned contract, then sign its assigned role.
  3. Send a contractProposal stanza to the counterparty’s bare or full JID. A sent: true response confirms sending, not receipt or acceptance.
  4. Confirm the counterparty received the matching contractId and role, then retrieve the contract with Legal/GetContract.
  5. Show the counterparty the exact returned human-readable contract. Treat explicit user confirmation as the acceptance boundary.
  6. Sign the counterparty’s role with Legal/SignContract.
  7. Retrieve the contract again and verify the state required by the template. Confirm every required role signature instead of treating a successful HTTP response as completion.

Construct a contract signature

Use the algorithm metadata stored with keyId:
HTTP-Host must match the request header exactly, including a non-default port. Generate nonce from at least 32 random bytes, Base64-encode it, and never reuse it.