Personal Data Hooks

2 Aufrufe Markdown

The nine hooks over consent, exports, data requests and identity documents.

Overview

The four moments of personal data: a customer gives consent, exports their data, asks for it to go, and submits identity documents.

Two hooks deliberately withhold content: the document on export, the identity paper on submission. Listeners get only a summary, because spreading that data to a second place works against the point.

Reference

actionuser.gdpr_consent_changed
AccountPrivacy proof stamp

Runs when a customer gives or withdraws consent for data processing. It fires only on a real change: saving the same value again does not raise it.

Parameters 3
$uidintThe customer whose consent changed.
$statusintThe new state: one for given, zero for withdrawn. Since the hook fires only on a change, the previous state is always the opposite.
$given_atstringThe stamp written to the record. This is the time part of the consent proof: use this value rather than reading it back.
Return 1
voidThe return is ignored. The consent is already written; this cannot block it.
Listener
Hook::add('action:user.gdpr_consent_changed', 10, function ($uid, $status, $given_at) {
    // Take the proof stamp from here rather than reading it back.
    Acme::recordConsent($uid, (bool) $status, $given_at);
});

Following a data export

actionuser.gdpr_exported
AccountPrivacy summary only

Runs when a customer exports their own data.

Parameters 2
$uidintThe customer exporting.
$metaarrayA summary of the export: its format and size. The document content is withheld on purpose: passing it would hand every listener the customer’s personal data.
Return 1
voidThe return is ignored.
Listener
Hook::add('action:user.gdpr_exported', 10, function ($uid, $meta) {
    // The document content is deliberately withheld.
    Acme::auditExport($uid, (int) ($meta['size'] ?? 0));
});

Following a data request being opened

actionuser.gdpr_request_created
AccountPrivacy two kinds

Runs when a customer opens a deletion or anonymisation request.

Parameters 2
$uidintThe customer opening it.
$typestringThe kind: remove for deletion, anonymize for anonymisation.
Return 1
voidThe return is ignored.
Listener
Hook::add('action:user.gdpr_request_created', 10, function ($uid, $type) {
    Acme::openComplianceCase($uid, $type);
});

Following a data request being cancelled

actionuser.gdpr_request_cancelled
AccountPrivacy withdrawn

Runs when a customer withdraws a request they opened.

Parameters 2
$uidintThe owner of the request.
$request_idintThe id of the cancelled request.
Return 1
voidThe return is ignored.
Listener
Hook::add('action:user.gdpr_request_cancelled', 10, function ($uid, $request_id) {
    Acme::closeComplianceCase($request_id);
});

Following a data request being carried out

actionuser.gdpr_processed
AdminUsers cannot be undone

Runs after a data request is carried out. Deletion and anonymisation cannot be undone: by this point the data is already gone.

Parameters 3
$request_idintThe request id.
$user_idintThe customer concerned.
$actionstringWhat was carried out: removal, anonymisation, destruction or cancellation.
Return 1
voidThe return is ignored.
Listener
Hook::add('action:user.gdpr_processed', 10, function ($request_id, $user_id, $action) {
    // The data is gone: clear your own copy as well.
    if ($action !== 'cancelled') Acme::purgeMirror($user_id);
});

Following documents being submitted

actionuser.documents_submitted
AccountDocuments reference only

Runs when a customer submits identity documents.

Parameters 2
$uidintThe customer submitting. This flow is for the person themselves: a sub-user cannot submit on somebody else’s behalf.
$doc_metaarrayA summary of the submission. ? No document content is here, only references and metadata. It is deliberate, so identity documents are not handed to listeners.
Return 1
voidThe return is ignored. The records are already written; this cannot block the submission.
Listener
Hook::add('action:user.documents_submitted', 10, function ($uid, $doc_meta) {
    // No document content, only the reference.
    Acme::queueReview($uid);
});

Widening the document field types

filteruser.document_field_types
AdminUsers passed by link

Runs while the list of types offered when defining a document field is built. Add a field type of your own here.

Parameters 1
$typesarrayby linkType key against the visible label.
Return 1
voidThe return is ignored; you write over the data.
Listener
Hook::add('filter:user.document_field_types', 10, function (&$types) {
    $types['acme-iban'] = 'Acme IBAN check';
});

Changing a document field definition

filteruser.document_field_input
AdminUsers passed by link

Runs before a document field is saved. Fill in the settings of a type you added here.

Parameters 2
$valuesarrayby linkThe row to be written: status, type, labels, options, accepted extensions and size limit.
$typestringby linkThe field type. It is there so you can tell whether this is your type: check it first.
Return 1
voidThe return is ignored; you write over the data.
Listener
Hook::add('filter:user.document_field_input', 10, function (&$values, &$type) {
    // Check whether it is your type first.
    if ($type !== 'acme-iban') return;

    $values['max_size'] = 512;
});

Changing the document records view

filteruser.document_records_view
AdminUsers personal data

Runs when an administrator looks at a customer’s documents, before the records reach the screen.

Parameters 2
$recordsarrayby linkThe document records: field name, value, status. They carry identity details: this is where masking belongs.
$user_idintby linkThe customer being looked at; for reading only.
Return 1
voidThe return is ignored; you write over the data.
Listener
Hook::add('filter:user.document_records_view', 10, function (&$records, &$user_id) {
    // Hide the identity number from eyes without clearance.
    if (Acme::canSeeFullId()) return;

    foreach ($records as $i => $r) $records[$i]['field_value'] = Acme::mask($r['field_value'] ?? '');
});

Pitfalls

Content is withheld on purpose

The export hook does not carry the document, and the submission hook does not carry the identity paper; both give a summary only. That is design, not omission: handing the data to listeners works against the protection. If you need the content, read it through your own permitted path.

A processed request cannot be undone

By the time the removal or anonymisation hook runs the data is already gone. You must clear your own copy as well, or the customer's data lives on with you.

War das hilfreich?

Vielen Dank für Ihre Rückmeldung!

Brauchen Sie weitere Hilfe?

Unser Support-Team ist rund um die Uhr für Sie da, wenn Sie oben nicht fündig werden.