Enregistrer un consentement hors ligne
Toutes les personnes concernées n'ont pas de clé d'accès. Une personne âgée qui signe un formulaire sur papier, ou qui répond au téléphone, ne passera jamais par le flux d'approbation par demande de consentement. Pour ces cas, l'organisation consigne elle-même le consentement, par l'une de deux voies :
- Sur papier : portée
attest, paliermanual, assurancecompany_attested. La preuve est une feuille signée à la main, dont l'empreinte est consignée. - Par téléphone : portée
attest_verbal, palierverbal, assurancecompany_documented. La preuve est la parole de l'organisation : il n'y a aucun document.
Les deux autorisent à /v1/check exactement comme un consentement signé par le
citoyen; seuls tier et assurance diffèrent, et c'est votre système qui décide
de ce que chaque palier débloque. La portée attest_verbal n'est jamais cochée par
défaut sur une clé : elle doit être un choix délibéré.
Choisir la version du document
Chaque consentement hors ligne se rattache à la version publiée exacte d'un
document de consentement, son documentVersionId. Lisez-la avec
GET /v1/consent-documents, ou avec GET /v1/catalog?documentCode=..., qui renvoie
du même coup les cellules à présenter.
La personne doit recevoir le texte de cette version. Le document d'information se télécharge en PDF, à imprimer avec la feuille ou seul :
curl -sS "https://api.agreely.ca/v1/consent-documents/versions/$VERSION_ID/pdf?locale=fr" \
-H "Authorization: Bearer $AGREELY_API_KEY" -o document-information.pdf
Télécharger ce PDF ne consigne rien : ce n'est pas une preuve que la personne a été informée.
Sur papier
Il vous faut une clé à portée attest.
Imprimer la feuille de signature
POST /v1/customers/{customerRef}/consent-sheets produit la feuille de signature
d'une version pour un client que l'organisation connaît : une paire Oui/Non par
demande de consentement, les finalités d'information sans case, la signature et une
référence imprimée. Le même appel émet le lien de réclamation dont cette
référence est le second facteur.
curl -sS https://api.agreely.ca/v1/customers/cust_8812/consent-sheets \
-H "Authorization: Bearer $AGREELY_API_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: feuille-cust_8812-2026-10-09" \
-d '{"documentVersionId":"e4d41dc3-c8a5-44b1-96c5-be740c45cc6d","locale":"fr"}'
# { "signatureSheet": { "pdf": "<base64>", ... }, "printedReference": "ABCD-EFGH", "claim": { "claimUrl": "...", ... } }
La référence et le lien ne sont renvoyés qu'une fois : conservez-les au moment de l'appel. Une nouvelle feuille pour le même client retire le lien précédent.
Deux règles avec une feuille de signature
N'envoyez jamais le lien de réclamation dans la même enveloppe que la feuille, ni dans le même message. La référence imprimée ne protège qu'un lien qui voyage séparément.
N'envoyez jamais l'empreinte de la feuille vierge comme evidence.pdfSha256. La preuve est la feuille signée, numérisée à son retour : c'est son empreinte qu'on consigne à l'étape suivante.
Consigner la feuille signée
Vous partez de la feuille signée, numérisée en PDF, et de la version publiée
sous laquelle la personne a consenti. Le SDK hache le PDF localement (SHA-256);
par défaut, seul le pdfSha256 quitte votre machine. Les octets bruts ne
partent qu'avec une mise sous séquestre explicite.
const m = await agreely.manualConsents.record({
customerId: "cust_8812",
documentVersionId: "doc_v3", // the PUBLISHED disclosure version signed under
effectiveDate: "2026-01-01",
validUntil: "2031-01-01",
items: [{ category: "Phone number", purpose: "Billing" }],
evidence: {
pdfSha256: Agreely.hashPdf(bytes), // "0x"+sha256, hashed LOCALLY, required
// pdf: base64Pdf, // optional: only with an explicit upload
},
});
m.assurance; // "company_attested"
m.consentRefs; // one 0x ref per cell; m.anchored is false at record time$m = $agreely->manualConsents()->record([
'customerId' => 'cust_8812',
'documentVersionId' => 'doc_v3',
'effectiveDate' => '2026-01-01',
'validUntil' => '2031-01-01',
'items' => [['category' => 'Phone number', 'purpose' => 'Billing']],
'evidence' => [
'pdfSha256' => Agreely::hashPdf($bytes), // "0x"+sha256, LOCAL, required
// 'pdf' => $base64Pdf, // optional opt-in upload
],
]);
$m->assurance; // "company_attested"
$m->consentRefs; // one 0x ref per cellagreely manual-consent create \
--customer cust_8812 --document-version doc_v3 \
--effective-date 2026-01-01 --valid-until 2031-01-01 \
--item "Phone number:Billing" \
--pdf ./signed-consent.pdf --json
# the hash alone is sent; add --upload to also escrow the raw bytescurl -sS https://api.agreely.ca/v1/manual-consents \
-H "Authorization: Bearer $AGREELY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"customerId": "cust_8812",
"documentVersionId": "doc_v3",
"effectiveDate": "2026-01-01",
"validUntil": "2031-01-01",
"items": [{"category":"Phone number","purpose":"Billing"}],
"evidence": {"pdfSha256":"0x…"}
}'La réponse porte consentId, merkleRoot, un consentRefs (un 0x-hex par
cellule), assurance: "company_attested" et anchored: false (l'ancrage se produit
ensuite, de façon asynchrone). Agreely.hashPdf est statique et n'appelle aucun
réseau; elle produit exactement la forme attendue par evidence.pdfSha256.
Quelques règles à connaître :
itemsnomme les demandes cochées « Oui ». Il peut être vide si chaque demande a reçu un « Non ». Les lignes que le document donne à titre d'information sont ajoutées par le serveur comme reconnues, jamais comme des consentements; la réponse les liste dansacknowledged.effectiveDateest la date de la signature, jamais dans le futur.- Une finalité sensible fondée sur le consentement exige
"sensitiveExpressAttested": true: l'organisation atteste que le consentement a été donné expressément. Agreely consigne cette attestation, il ne la vérifie pas. - Une feuille signée avant la publication de la version choisie exige
"versionAttested": true: l'organisation atteste que la feuille demandait le consentement pour les mêmes finalités, avec la même information. - Passez un en-tête
Idempotency-Key: une nouvelle tentative avec le même corps rejoue la première réponse et ne consigne rien de neuf. - Chaque refus porte une
reasonstable (predates_withdrawal,relationship_ended,sensitive_express_required, ...). Comparez-la, jamais lemessage. La liste complète est dans la référence de l'API, à la section « Consigner un consentement sur papier ».
Il s'applique à l'identique
Un consentement attesté par l'entreprise et un consentement signé par le citoyen
autorisent de façon identique à /v1/check. Seul le palier diffère : une
vérification renverra assurance: "company_attested" et
tier: "manual" au lieu de "citizen_signed" et "full". Le code qui protège une
fonctionnalité n'a rien à changer.
Lier plus tard le consentement au citoyen
La personne peut, plus tard, rattacher ce consentement hors ligne à son propre identifiant décentralisé grâce à un lien de réclamation à usage unique. La feuille de signature en émet déjà un; pour un consentement consigné sans feuille produite par l'API, émettez-le à part :
const link = await agreely.manualConsents.createClaimLink({
customerId: "cust_8812",
reference: "order-4471", // optional
});
// { claimUrl, token, expiresAt } - single-use
À la CLI : agreely manual-consent claim-link --customer cust_8812 --reference order-4471.
Par téléphone
Il vous faut une clé à portée attest_verbal.
Le script à lire
Le script à lire à la personne se trouve dans l'application Web d'Agreely : dans la fiche du client, à la page Consentement verbal, choisissez le document puis affichez le script. Il reprend l'information de la version, chaque demande une à une, et la relecture des réponses.
Par l'API, il n'y a pas de script à télécharger. Deux champs relient l'appel à ce qui a été lu :
documentVersionIdlie le consentement à la version exacte du document lue au téléphone;scriptVersionest le libellé que votre organisation donne au script qu'elle a lu (par exempleaccueil-v3). Agreely le consigne tel quel dans le reçu.
Consigner le consentement verbal
Chaque demande posée reçoit une réponse explicite, "yes" ou "no" : il n'existe
aucun raccourci qui consignerait une liste de finalités comme acceptées.
curl -sS https://api.agreely.ca/v1/verbal-consents \
-H "Authorization: Bearer $AGREELY_API_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: appel-client-7-2026-10-08" \
-d '{
"customerId": "client-7",
"documentVersionId": "e4d41dc3-c8a5-44b1-96c5-be740c45cc6d",
"answers": [
{"category": "Photo", "purpose": "Publication", "answer": "yes"},
{"category": "Adresse", "purpose": "Livraison de repas", "answer": "no"}
],
"obtainedAt": "2026-10-08T14:05:00-04:00",
"obtainedBy": "Luc Gagnon",
"scriptVersion": "accueil-v3",
"respondent": {"consentedBy": "self"},
"validUntil": "2027-10-31",
"paperExpected": true
}'
# { "consentId": "...", "tier": "verbal", "assurance": "company_documented", "consentRefs": ["0x..."], ... }
obtainedAt est l'instant de l'appel, la date du consentement : au plus 7 jours dans
le passé et jamais dans le futur, pas même d'une seconde
(obtained_at_in_future). Un consentement plus fort déjà en vigueur pour une
finalité, sur papier ou par clé d'accès, n'est jamais remplacé par un appel
(stronger_consent_active), sauf dans la fenêtre de renouvellement décrite plus
bas. Pour une personne mineure de moins de 14 ans, le répondant doit être le
titulaire de l'autorité parentale ou le tuteur.
Recevoir la feuille signée qui confirme l'appel
Avec paperExpected: true, l'organisation envoie à la personne une feuille qui
reprend les demandes. Quand elle revient signée, consignez-la avec une clé à portée
attest :
curl -sS https://api.agreely.ca/v1/verbal-consents/$CONSENT_ID/paper \
-H "Authorization: Bearer $AGREELY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"signedAt": "2026-10-20T10:30:00-04:00",
"answers": [{"category": "Photo", "purpose": "Publication", "answer": "yes"}],
"evidence": {"pdfSha256": "0x..."}
}'
Le consentement verbal n'est jamais réécrit : chaque finalité cochée passe dans un
nouveau consentement manual, que la vérification suit dès lors. Le
consentement date toujours de l'appel; la signature est sa date de preuve. Une
case laissée sans « Oui » sur la feuille est consignée comme un retrait daté de la
signature. Si la feuille ne revient jamais, le consentement reste verbal : Agreely
ne le fait pas expirer pour autant. GET /v1/verbal-consents/{consentId} donne
l'historique complet de l'appel et de la feuille.
Renouveler par téléphone une feuille qui arrive à échéance
Un consentement signé sur papier dont la fin tombe dans les 30 jours civils peut
être renouvelé par téléphone. Ces 30 jours sont une règle de produit d'Agreely, pas
un délai prévu par la loi. La requête est un POST /v1/verbal-consents ordinaire :
- c'est un nouveau consentement; la feuille n'est jamais réécrite et reste consignée telle quelle;
/v1/checkrépond aussitôttier: "verbal"avec le nouveauvalidUntil, puismanualquand la nouvelle feuille signée revient. Si votre système exigemanualpour un usage, il verraverbalentre l'appel et le retour de la feuille;- le renouvellement ne peut pas prendre fin avant la feuille
(
renewal_ends_before_current) ni être daté avant sa signature (renewal_predates_current); - un « Non » au renouvellement ne retire rien : la feuille reste en vigueur jusqu'à sa propre fin.
Hors de la fenêtre, l'appel est refusé comme d'habitude. Un consentement signé par clé d'accès ne se renouvelle jamais par téléphone : renouvelez-le par une nouvelle demande en ligne.
Retirer un consentement hors ligne
Deux routes, selon ce que vous retirez :
POST /v1/manual-consents/{consentRef}/revoke(portéeattest, ouattest_verbalpour un consentement verbal) retire un consentement que l'organisation a consigné. Sa réponse dit dansgatece que/v1/checkrépond désormais pour la finalité.POST /v1/customers/{customerRef}/consents/{consentRef}/withdrawal(portéewithdraw) consigne le retrait demandé par la personne sur n'importe quel consentement, y compris celui qu'elle a signé en ligne avec sa clé d'accès. Cette route reste ouverte pendant un défaut de paiement.
Dans les deux cas, un retrait s'attache à la finalité : retirer par n'importe
quelle référence de la chaîne (un renouvellement et la feuille qu'il renouvelle, un
appel et la feuille qui l'a confirmé) retire le consentement en cours. Une feuille ou
un appel daté avant un retrait consigné ne le rouvre jamais
(predates_withdrawal).
La limite honnête
Un consentement consigné par l'organisation ne prouve pas qu'un humain a consenti
Un consentement company_attested documente que l'organisation a attesté détenir une feuille signée dont l'empreinte correspond à ce qui a été consigné. Il ne prouve pas qu'un humain a bel et bien signé, ni qui a signé : il n'y a pas d'assertion par clé d'accès de la personne concernée. Un consentement company_documented est plus faible encore : il consigne que l'organisation a déclaré, à l'instant consigné (l'empreinte du reçu est ensuite ancrée), que la personne a consenti par téléphone à ces finalités sous ce script; il ne prouve pas que l'appel a eu lieu. Ce sont des voies légitimes pour les cas sans clé d'accès, et c'est pourquoi assurance et tier les nomment explicitement partout.
Ensuite
- Référence de l'API : chaque route, ses corps, ses réponses et ses raisons de refus.
- Demandes de consentement : la voie signée par le citoyen, et le contexte côté entreprise du consentement hors ligne.
- Portail citoyen : ce que voit la personne concernée lorsqu'elle réclame et confirme son consentement.
- Vérifier un reçu : un reçu
company_attestedse vérifie entièrement hors ligne.