End-user identifier (end_user)
Every question sent to /v1/ask must carry end_user: an opaque identifier of the person who asked in your system. Datafala uses this value only to count active users per month, which is the basis of the band-based monthly fee.
What to send
A value derived from the person's internal ID, never the personal data itself. Do not send a name, email, CPF or the ID in plain text.
- Format: 16 to 128 characters made of letters, numbers,
_and-. SHA-256/HMAC hexadecimal (64 characters), base64url and UUID are accepted. Emails, names, spaces and short IDs (such as42) are rejected with422 invalid_end_user. - Stable: the same person always generates the same value, in every question and in every month.
- Individual: never use the same value for two people (a service account or a generic
adminuser). A shared value counts as one person only and shows up in audit signals. - Fixed secret: generate the value with a secret that stays only on your server (
DATAFALA_END_USER_SECRET).
After a change, each person starts generating another value and is counted again in the month of the change, which changes the band on the invoice.
Examples
Python:
import hashlib
import hmac
import os
SECRET = os.environ["DATAFALA_END_USER_SECRET"].encode()
def datafala_end_user(user_id: int | str) -> str:
return hmac.new(SECRET, str(user_id).encode(), hashlib.sha256).hexdigest()
Node.js:
import { createHmac } from "node:crypto";
export function datafalaEndUser(userId) {
return createHmac("sha256", process.env.DATAFALA_END_USER_SECRET)
.update(String(userId))
.digest("hex");
}
PHP:
function datafala_end_user(string|int $userId): string {
return hash_hmac('sha256', (string) $userId, getenv('DATAFALA_END_USER_SECRET'));
}
A public, stable UUID of the user also works, as long as it does not change over time.
To generate the secret once:
python3 -c "import secrets; print(secrets.token_hex(32))"
Requirement and limit
- If your tenant requires the field and the question comes without it, the response is
400 end_user_required. New customers already start requiring it. - Each
end_usercan make 10 questions per minute. Above that,429 rate_limitedwithdetails.scope = "end_user". - Requests refused with
429do not count as an active user. Questions that fail during generation (sql_rejected,no_answer,llm_error) do count, because the person used the system.
Privacy
The value received does not go into logs, responses, history or metrics. It is stored only as HMAC-SHA256 with a salt specific to your tenant, never linked to a question, and the counting records are deleted after 13 months.