local-pii

Security & Hashing

What each strategy leaks, why unkeyed hashing is forbidden, and how to handle the mapping.

The mapping is the secret

mapping (placeholder → original) is the only thing that can reverse anonymization. Keep it in memory. Do not log it, send it to analytics or crash reporters, or persist it unless you must — and if you must, use the platform keystore (expo-secure-store), never plain storage.

Also keep the raw text out of logs/analytics/crash reporters that run before anonymization.

What each strategy leaks to the provider

StrategyLeaks the value?Leaks equality?Leaks the type?
sequential()nowithin a sessionyes ([EMAIL_1])
hashed({ secret })noyes (stable)yes
token() (random)nonono
token({ secret })noyes (stable)no

"Leaks equality" = the provider can tell two mentions are the same entity. That's a feature for stable IDs, but it's more metadata than sequential within one session — which is why sequential stays the default.

Why unkeyed hashing is forbidden

A plain hash of a value (sha256(email)) as a placeholder is a privacy leak, worse than sequential numbering:

  • Placeholders are sent to the provider.
  • PII is low-entropy — names, phones and emails are guessable/enumerable.
  • So anyone holding the placeholder can confirm a guessed value offline by recomputing the hash (a rainbow/dictionary attack).

local-pii therefore only offers keyed hashing (hashed / token({ secret })) using a random ≥128-bit secret generated on device (getOrCreateDeviceSecret) that never leaves it. Without the key, a correct guess is not verifiable.

Tool calls are a disclosure destination

Rehydrating tool-call arguments hands your tool the real values — appropriate for your own code, a re-disclosure if the tool forwards data to a third party. See Tool Calls.

On this page