Documentation

Data protection

Detection modes, the 60-detector library, entity detection and its selectable models, security scanning, the model notice, and retention.

Data protection runs on every request before dispatch. The default mode is tokenize: every detected value is swapped for a stable typed token like «EMAIL_1». Only tokens reach the provider, and the response is restored to the real values on its way back to you, streamed or not. The token map lives in memory for the life of the request and is never persisted.

# tokenize mode (the default): what you send
curl https://api.sluis.ai/v1/chat/completions \
  -H "Authorization: Bearer $SLUIS_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "model": "sluis/auto", "messages": [{ "role": "user",
        "content": "Mail j.devries@acme.nl that IBAN NL91ABNA0417164300 is active." }] }'

Other modes: mask rewrites detected values irreversibly, block refuses the request with 422, and allow_log passes it through while flagging the audit row.

60 built-in detectors ship out of the box: 28 for personal data, from the US Social Security number to a national-ID pack that checksum-validates 12 EU countries, and 32 for secrets and credentials. Each one can be toggled per organisation, and custom terms (plain or regex) cover anything specific to your business:

Personal data · 28EmailPhone numberIBANCredit cardIPv4 addressIPv6 addressMAC addressUS Social Security numberDutch BSNPortuguese NIFGerman Steuer-IDPolish PESELBelgian rijksregisternummerFrench NIR (INSEE)Spanish DNI/NIEItalian codice fiscaleSwedish personnummerDanish CPR numberFinnish henkilötunnusUK National Insurance numberEU VAT numberBIC/SWIFT codeDutch license plateDutch addressPassport numberDate of birthGPS coordinatesVehicle identification number
Secrets & credentials · 32API key (generic)AWS access keyAWS secret access keyPrivate key (PEM)GitHub tokenGitLab tokenSlack tokenSlack webhook URLDiscord webhook URLGoogle API keyGoogle OAuth refresh tokenStripe keyMollie API keyAnthropic API keyOpenAI API keySluis keyHugging Face tokennpm tokenSendGrid keyTwilio keyShopify tokenVault tokenDatabricks tokenDocker Hub tokenTelegram bot tokenJSON Web TokenCredentials in URL.env file dumpAzure storage key / SASPassword assignmentConfidentiality markerHigh-entropy token (generic)

Entity detection

Persons, organizations and locations are hard to catch by pattern alone. Sluis adds five opt-in layers: context heuristics (honorifics, salutations, signatures; persons only), email correlation (derives names from addresses in the same text), a tenant name directory, a shipped name dictionary, and NER: a recognition model operated by Sluis as a network-internal sidecar, so text never leaves the deployment perimeter to be scanned. NER finds persons, organizations and locations in plain prose.

The name dictionary is the deterministic counterpart to NER: given names and surnames compiled from government open data into a compiled dictionary that ships inside the gateway. It matches full names and honorific-anchored names with no added latency and nothing leaving your perimeter. Names that are also ordinary words are only matched with name-shaped context around them, so rare names remain the job of the directory or NER.

NER model options

Two tiers trade latency for catch rate: swift (spaCy xx_ent_wiki_sm) answers in single-digit milliseconds with basic multilingual coverage; deep (GLiNER2-PII on an mDeBERTa-v3 backbone, Apache-2.0) catches meaningfully more, at a higher latency per scanned segment. Choose per organisation in Policies → Data protection; a key may pick a different model via its option overrides, but can never switch the layer on when the organisation has it off.

ModelCoverageMeasured accuracyLatency
swift · spaCy xx_ent_wiki_smmultilingual, basicall-entity F1 0.58 · person F1 0.72 · recall ~0.53~7-14 ms
deep · GLiNER2-PII (mDeBERTa-v3, Apache-2.0)7 trained languages (EN, FR, ES, DE, IT, PT, NL) + multilingual backbone transferall-entity F1 0.61 · person F1 0.76 · recall ~0.70~150-250 ms per scanned segment

Measured 2026-08-12 on an internal benchmark: WikiANN test sentences in six languages (NL, EN, DE, FR, ES, IT; 150 per language), scored as micro-F1 over (label, text) pairs at text level with the production false-positive filter applied, on an Apple-silicon dev machine at FP32. WikiANN is Wikipedia-domain, silver-standard data and spaCy's home turf, so read the numbers as relative guidance between the tiers, not absolute field accuracy.

Security scanning

Opt-in prompt-injection and jailbreak detection at the gate, scanned before dispatch. Three modes: off | log | block. log records hits in the audit trail without touching traffic; block refuses the request with a sealed 403 permission_error ("request refused: prompt-injection scan flagged this request"). The firing threshold is configurable per organisation, and the scan fails open: a scanner outage never takes down traffic.

The scan adds about 20 ms on a short prompt and about 620 ms on a long one (1500 characters), measured on an internal benchmark; the worst case is bounded, because the scanner caps how many 512-token windows it scores per request. It runs concurrently with the NER scan, so the combined added latency is close to the larger of the two, not the sum. Detection is a classifier, not a proof: benign instruction-like text can score as injection, a known reality across the field, which is why log is the recommended starting mode.

Every hit is disclosed in the audit trail as sec:injection:<score>, so review needs no extra tooling. Per-key deviations ride the same option overrides as data protection.

Built with Llama. The scan model is Llama Prompt Guard 2 86M (multilingual), used under the Llama 4 Community License.

Separately, opt-in key-behaviour anomaly detection runs as a background job with zero request latency: per-key baselines from robust statistics with hour-of-week seasonality, plus a multivariate isolation-forest layer. Alerts are explainable, never a bare score, and land in the console Security tab, optionally by email.

Model notice

When tokenization rewrote a request, Sluis injects a leading system message telling the model the «…» tokens are opaque placeholders it must keep intact; that is what keeps the restore reliable. On by default; customise or disable it per organisation.

Retention & audit fidelity

Content retention (request and response bodies for the audit log) is on by default and encrypted at rest; audit fidelity chooses whether retained content stores the tokens or the original values. Turn retention off for a metadata-only ledger; that also disables the response caches.

Document anonymization

Send a docx, pdf, image, or text file to POST /v1/documents/anonymize and the same document comes back with PII and secrets replaced by merge tags like «PERSON_NAME_1» in text, and blurred out of images and PDF pages. Processing is local to the gateway, OCR included; the operation is sealed in the audit chain and metered per page/image. The token mapping is returned only when you ask for it and never stored. Redacted PDFs keep an invisible searchable text layer built from the anonymized text. For large documents, enqueue an async job and collect the result later via a time-limited signed URL.

The same protection works in transit: with the dlp_documents policy on, files uploaded through /v1/files and inline OCR documents are anonymized before they leave toward a provider, refused under block, and scanned under allow_log.

# enqueue a large document (202 + job id; Idempotency-Key honoured)
curl https://api.sluis.ai/v1/documents/anonymize/jobs \
  -H "Authorization: Bearer $SLUIS_KEY" \
  -F file=@archive.pdf

# poll until succeeded; the signed download_url then needs no API key
curl https://api.sluis.ai/v1/documents/anonymize/jobs/9c31… \
  -H "Authorization: Bearer $SLUIS_KEY"

Embeddings

Pseudonymized tokens are stable within one request, not across requests, so embeddings of tokenized text may not match between calls. The dlp_embeddings policy setting controls whether the scan covers /v1/embeddings: it is on by default, and setting it to off sends embedding inputs to the provider unscanned. Every exempted call is recorded in the audit trail.

Per-key option overrides

Per-request header overrides are gone: deviations are standing, governed key configuration. An owner or admin sets sparse option_overrides on a key, in the Console's API keys view or via POST/PUT /admin/keys: the data-protection mode (including off), the NER model, and the prompt-injection scan mode. Anything unset inherits organisation policy, and a key can never switch a layer on that the organisation keeps off.

# per-key option overrides are standing key config, set by an owner or admin
curl -X PUT https://api.sluis.ai/admin/keys/{key_id} \
  -H "Authorization: Bearer $SLUIS_ADMIN_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{ "option_overrides": {
        "dlp": { "mode": "off" },
        "ner_model": "deep",
        "security": { "prompt_injection": { "mode": "block" } } } }'
# sparse: absent fields inherit org policy; every deviation is sealed in the audit trail

The x-sluis-dlp request header has been removed. A request that still carries it, any value, is refused with 400 and a pointer to the key's option overrides. Every deviation in effect is disclosed on the sealed audit row, so the trail always shows which configuration actually ran.