tree: b6b978e05139fa4d0171e4e367c7aa95cb2514c8
  1. src/
  2. tests/
  3. .gitignore
  4. pyproject.toml
  5. README.md
tools/privacy-llm/redactor/README.md

Table of Contents generated with DocToc

redactor

Stdlib-only Python project implementing the PII redactor for the Magpie privacy-llm tool. Three console scripts:

Console scriptPurpose
pii-redactReplace declared PII values in stdin with hash-prefixed identifiers; persist new mappings to the local file.
pii-revealReplace identifiers in stdin with stored real values from the local mapping.
pii-listPrint the current mapping for debugging (text or JSON).

The behavioural contract — which fields count as PII, the identifier format, the redact-then-reveal lifecycle — lives in ../pii.md. This README covers local-setup and day-to-day invocation.

Run

From the framework's root (this repository when running standalone; the snapshot path inside an adopting tracker repo):

# Redact: pass --field <type>:<value> for each PII value to swap.
# `name:` is for any natural-person name OTHER than the reporter
# and other than current <tracker> collaborators (see ../pii.md).
echo "I worked with Other Researcher (other@example.com) on this finding" | \
  uv run --project tools/privacy-llm/redactor pii-redact \
    --field name:"Other Researcher" \
    --field email:"other@example.com"
# →  I worked with N-<hex> (E-<hex>) on this finding

# Reveal: identifiers in stdin → real values from the local map.
echo "Reply mentions N-<hex>" | \
  uv run --project tools/privacy-llm/redactor pii-reveal
# →  Reply mentions Other Researcher

# List the current map (text or JSON):
uv run --project tools/privacy-llm/redactor pii-list
uv run --project tools/privacy-llm/redactor pii-list --format json

Skill files reference the same invocation via the <framework> placeholder so the path resolves in either context:

uv run --project <framework>/tools/privacy-llm/redactor pii-redact ...

<framework> substitutes to the snapshot path inside an adopting project (typically .apache-magpie/apache-magpie/) and to . when running standalone — see the placeholder convention in AGENTS.md.

Field types accepted by --field:

Friendly nameCodeUse for
nameNNatural-person name of a non-reporter, non-collaborator individual the reporter mentions.
emailEEmail address of the same.
phonePPhone number of the same.
ipIPIPv4 or IPv6 address self-disclosed by a third party.
handleHPersonal social handle (GitHub, Twitter, IRC nick, …) of the same.
addressAPostal / employer address of the same.

Mapping file

The mapping is stored at:

~/.config/apache-magpie/pii-mapping.json     (default)
$PII_MAPPING_PATH                             (env override)
--mapping-path <path>                         (per-call override)

The file is written with mode 0o600, atomically (tempfile + os.replace). It is per-machine, never committed. The identifier-from-value derivation is deterministic, so two developers redacting the same value get the same identifier without sharing the file.

Test

# Run the test suite:
uv run --project tools/privacy-llm/redactor --group dev pytest

# With coverage (if you add coverage.py to the dev group locally):
uv run --project tools/privacy-llm/redactor --group dev pytest --cov=redactor

Lint / type-check

uv run --project tools/privacy-llm/redactor --group dev ruff check src tests
uv run --project tools/privacy-llm/redactor --group dev ruff format --check src tests
uv run --project tools/privacy-llm/redactor --group dev mypy

Referenced by