Attribution and audit events
Public customer, end-customer, beneficiary and fiat/crypto withdrawal responses include an attribution object. The same object is included at data.attribution in customer-created, onboarding case/status, beneficiary and withdrawal webhooks. Account-provisioning notifications such as customer.account_ready describe a different resource and are outside this contract.
Webhook attribution is enabled separately after the emitting services have been upgraded. During rollout, and when replaying older saved events, data.attribution may be absent. Treat absence as unknown; do not infer an actor from another field.
{
"attribution": {
"status": "captured",
"source": "dashboard",
"user": { "id": "00000000-0000-4000-8000-000000000001", "email": "operator@example.com" },
"api_key": null,
"initiated_at": "2026-09-22T09:15:00Z"
}
}
source is dashboard, admin, api, system or unknown. user identifies the authenticated user when present. For API-key actions it is null, and api_key contains the authenticating key's id, name and safe prefix. No secret is returned. An API key's creator is not necessarily the person behind a particular API call, so the key's creator is never substituted for the acting user.
These values are captured when the resource is created. User email and key name are snapshots: later renaming a key or changing an email does not rewrite history. Completion webhooks and later reads preserve the original initiator, including when a background worker completes the operation.
Beneficiaries created from queued batches and withdrawals created from approved payout batches retain the batch maker's captured identity and initiation time. The later executor and approver do not replace the maker. A batch created before capture was enabled produces unknown initiation metadata.
Records without a captured initiation return status: "unknown", source: "unknown", and null user, key and time. Historical records are not attributed from their owner, their latest approver or approximate timestamp matches. reconstructed is reserved for explicitly reviewed historical reconstruction; this feature does not automatically reconstruct or backfill existing records.
Retrieve recorded activity
GET /api/v1/partner/customers/{customerId}/audit-events
X-Api-Key: your API key
The key needs the audit:read scope and permission to access the specified customer. Existing scopes do not automatically grant access to the audit feed. Resource read scopes already expose the original initiator on their corresponding records. The feed includes that customer's activity and its currently owned end customers; it does not expose other customers sharing the tenant.
| Parameter | Meaning |
|---|---|
from |
Inclusive UTC event time, optional |
to |
Exclusive UTC event time, optional; must be later than from |
resource_type |
Optional: customer, beneficiary, fiat_withdrawal, crypto_withdrawal, beneficiary_batch, payout_batch |
resource_id |
Optional resource UUID |
limit |
1–200, default 100 |
cursor |
next_cursor from the previous response, with the same filters |
The response's data contains events, has_more, next_cursor and as_of. Each event contains a stable id, customer_id, resource_type, resource_id, action, occurred_at, actor and resource_status. Actions are created, updated, deleted, approved, rejected or retired. The event's actor describes that action; the resource's attribution continues to describe its original creation.
Results use ascending event time and event ID. The cursor pins the upper event-time bound and is bound to the key, customer and filters. A changed, corrupted or mismatched cursor returns 400 cursor_invalid; an inaccessible customer returns 404. Ownership is checked again on every page.
For ongoing polling, use overlapping time windows and deduplicate by event id. as_of is an event-time bound, not a database transaction snapshot: an operation already in progress can commit later. Do not rely on a page number or webhook delivery ID as an activity cursor.
Coverage
The feed records committed changes made through the application's tracked persistence path to the supported customer, beneficiary, withdrawal and batch records after this feature is enabled. It also records staff beneficiary retirement during correction and recovery. Rolled-back changes do not leave events. Historical activity, direct SQL changes and other bulk persistence operations (including background bank-registration outcomes and lease bookkeeping) are not reconstructed. It is a resource activity feed, not a list of every HTTP request, login or provider callback.
An initiating identity and an approving identity are distinct. These fields do not implement or certify two-person withdrawal approval.