Contract, Mandate and Signature
Find this scenario in our Bruno collection
Save time in your implementation by observing the sequence of calls and retrieving requests directly from Bruno.
The following documentation describes how to set up, via API, a direct debit mandate linked to a contact, how to display a sale's contract, and how to electronically sign these documents.
Glossary of key concepts
Before going any further, let's make sure we're using the same terminology.
Contact
This is the customer subscribing to the club. To avoid confusion with their potential status (prospect, customer, former customer ...), we will call them contact in this document.
Mandate
The mandate is an authorization to debit the contact's bank account. It links a club that wishes to collect payments to the bank account that will be debited.
Contract
If the sold product is associated with a contract model (
product.contractModelis set), a contract is automatically generated with the sale and must be signed.
Macro process and prerequisites
As mentioned earlier, you must know the two main parties involved:
- the club
- the contact
Depending on what needs to be signed, the process follows these steps:
- Add the mandate — only if a mandate must be created
- Display the contract to the user — only if a contract was generated with the sale
- Initiate the signature process via SMS
- Complete the signature process
Of course, the contact must have a valid mobile phone number to be eligible for electronic signature.
Add the Mandate
POST
/{clientToken}/mandates
WARNING
All fields are required
| parameter | description | example |
|---|---|---|
clubId | ID of the club in IRI format | /{clientToken}/clubs/1 |
contactId | ID of the contact targeted by the mandate. This is an IRI, not just a numeric ID | /{clientToken}/contacts/12345 |
contactFamilyName | Contact's last name | Doe |
contactGivenName | Contact's first name | John |
contactNumber | Contact's number | 423456 |
contactAddress[addressCountry] | Country | France |
contactAddress[addressCountryIso] | Pays | FR |
contactAddress[addressLocality] | City | La Madeleine |
contactAddress[postalCode] | Postal code | 59110 |
contactAddress[streetAddress] | Street address | 41 rue du Général de Gaulle |
holder | Account holder | John Doe |
iban | Bank account number | DE15843988385047239833 |
bic | Bank identifier | DEUTDEFF |
bank | Bank name | DEUTSCHE BANK AG |
validFrom | Start date of mandate validity | 2019-06-21 |
Example
POST /{clientToken}/mandates
Body
{
"clubId": "/{clientToken}/clubs/22",
"contactId": "/{clientToken}/contacts/1",
"contactFamilyName": "Doe",
"contactGivenName": "John",
"contactNumber": "1",
"contactAddress": {
"addressCountry": "France",
"addressCountryIso": "FR",
"addressLocality": "La Madeleine",
"postalCode": "59110",
"streetAddress": "41 Rue du Général de Gaulle"
},
"holder": "John Doe",
"iban": "DE15843988385047239833",
"bic": "DEUTDEFF",
"bank": "DEUTSCHE BANK AG",
"validFrom": "2019-06-21"
}Response 201 Created
{
"@context":"\/clientToken\/contexts\/Mandate",
"@id":"\/clientToken\/mandates\/373969", // <-- mandate ID
"@type":"Mandate",
// ...
}Display the Contract to the User
If the sold product is associated with a contract model (product.contractModel is set), a contract is automatically generated with the sale and must be signed.
To visually display the contract to the client, simply perform a GET /:clientToken/sales/:saleId/contract, which will return the raw PDF content to display.
curl --location 'https://.../demoapi/sales/12345/contract' \
--header 'authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJOdDmWEJwl2Zqc' \
--header 'x-user-club-id: /onfit/clubs/2325' \
--header 'x-user-network-node-id: /onfit/network_nodes/2229' \
--header 'x-gravitee-api-key: xxx-yyy-zzz'Note
You receive the raw PDF content, so you need to create an endpoint that serves this content with the correct HTTP headers.
Initiate the Signature Process via SMS
The electronic signature process involves sending an SMS to the contact. This SMS contains a code they must use to validate the signature in the next step.
This process is the same for contracts and mandates:
- If you have only a contract, provide the
saleId(/:clientToken/sales/:id) astargetId - If you have only a mandate, provide the
mandateId(/:clientToken/mandate/:id) astargetId - If you have both a contract and a mandate to sign, you can sign both in a single call by providing both IDs in a
targetIdsarray
POST /{clientToken}/signature_requests
| parameter | description | example |
|---|---|---|
contactId | Contact ID in IRI format | /{clientToken}/contacts/1 |
targetId | ID of the mandate to sign in IRI format | /{clientToken}/mandates/373969 |
targetIds | Array of IDs (in IRI format) of items to sign | /{clientToken}/mandates/373969 |
Example
POST /{clientToken}/signature_requests
Body
{
"contactId": "/{clientToken}/contacts/1",
// "targetId": "/{clientToken}/mandates/373969"
"targetIds": [
"/{clientToken}/mandates/373969",
"/{clientToken}/sales/936973"
]
}Response 201 Created
{
"@context":"\/clientToken\/contexts\/SignatureRequest",
"@id":"\/clientToken\/signature_requests\/3451", // <-- signature process ID
"@type":"SignatureRequest",
// ...
}Complete the Signature Process
Once the SMS is received, the application orchestrating the signature must collect the code from the targeted contact and complete the signature process by validating this code.
POST
/{clientToken}/signature_requests/{signatureRequestId}/transitions
| parameter | description | example |
|---|---|---|
signatureRequestId | ID of the previously created signature process | 3451 |
transition | Type of transition. Possible values are validate or cancel | validate |
code | Validation code received via SMS | 1234 |
Example
POST /{clientToken}/signature_requests/3451/transitions
Body
{
"transition": "validate",
"code": "94852"
}Response 201 Created