mirage
strukto-ai
The World's First Unified Virtual Filesystem For AI Agents
PerryLink/dsh-mask
PII masking middleware for DeepSeek Harness: anonymize names, phones, emails, ID cards, bank cards, keys, and addresses to placeholders before they reach the model, restore them at the display layer, keep the restore table only in memory and a controlled storage domain, never log plaintext, and expose /mask and the mask_test tool
PROJECT TOPICS
INSTALL REFERENCE
dsh plugin --profile web add github:PerryLink/dsh-mask
该命令指向仓库当前默认分支;尚无绑定当前 commit 的完整验证结果。
PROJECT README
PII masking middleware for DeepSeek Harness — anonymize personal data before it reaches the model, restore it at the display layer.
Phones, emails, ID cards, bank cards, keys, and more become placeholders at the model boundary; the plaintext never enters your session log.
| Surface | Status |
|---|---|
| Harness | DeepSeek Harness 0.1.0-rc.6 |
| Node | ^22.19.0 \|\| >=24.0.0 |
| Platforms | Anywhere DSH runs (pure host, zero-dependency regex; no browser half) |
| Model | Text models fully supported; no extra model capability required |
dsh-mask anonymizes personal data at the model boundary — before a message reaches the model — and keeps a restore table so placeholders can be mapped back to the originals at the display layer:
agent/pre-step messages are rewritten so phones, emails, ID cards, bank cards, keys, and IPs (each opt-in) become <PHONE_1>-style placeholders. The masked text is what gets logged and sent to the model.placeholder → original map lives only in memory and a controlled storage domain (dsh_mask); the plaintext never enters the session log.mask/applied session event records only "replaced N values + type distribution", never the original text or the mapping./mask command — status (counts + distribution), on/off (runtime toggle), restore <text> (unmap placeholders), help.mask_test tool — run a snippet through the detector and see the placeholder result; it never reveals the original values.user message ──agent/pre-step──▶ placeholders ──model──▶ placeholders ──restore──▶ display
▲ │
└──────── restore table (memory + dsh_mask) ────────┘
# 1. install the bundle into your profile
dsh plugin --profile web add "github:PerryLink/dsh-mask#main"
# or from npm (published releases)
dsh plugin --profile web add dsh-mask
# 2. verify the row mounts
dsh --profile web --dump-config | grep -A2 'id: mask'
Then tailor the entity list in your profile patch:
- insert:
- id: mask
name: dsh-mask
config:
entities: [phone, email, id-card, bank-card, key]
> /mask status
> /mask restore <PHONE_1>
main): dsh plugin --profile web add "github:PerryLink/dsh-mask#main" (equivalent to installing from git+https://github.com/PerryLink/dsh-mask.git). No build step — index.mjs and lib/ are the shipped artifacts.dsh plugin --profile web add dsh-mask.pnpm pack in this repo, then dsh plugin --profile web add ./dsh-mask-<version>.tgz.dsh plugin --profile web remove dsh-mask (or remove the row from the profile patch).All tunables are Schemastery Config fields (changeable from cordis.yml). An id-targeted override replaces the whole row — restate every key you need. cordis.patch.yml documents each key inline.
| Key | Default | Meaning |
|---|---|---|
enabled |
true |
Master switch; false unregisters the listener, the /mask command, and the mask_test tool |
mode |
regex |
Detection mode; only regex is implemented (regex+ner for name/address recognition is reserved and fails loud) |
entities |
[phone, email, id-card, bank-card, key] |
Which PII types to mask; ip is also regex-capable (opt-in), person/address require NER |
scope |
messages |
Masking surface; only messages (agent messages) is implemented (tools argument masking is reserved) |
registerCommand |
true |
Register the /mask command |
registerTools |
true |
Register the mask_test tool when the tools service is present |
persistRestoreTable |
true |
Persist the restore table to the controlled dsh_mask storage domain (false = memory only) |
maxRestoreEntriesPerSession |
500 |
Per-session restore entry cap (oldest evicted first) |
maxSessions |
1000 |
In-memory session cap (least-recently-used evicted, mapping reloaded on demand) |
Example override in your profile patch:
- insert:
- id: mask
name: dsh-mask
config:
entities: [phone, email, id-card, bank-card, key, ip]
persistRestoreTable: false
registerCommand: true
| Surface | Reveals plaintext | Notes |
|---|---|---|
agent/pre-step masking |
never | Rewrites messages to placeholders before they are logged or sent to the model |
/mask status |
never | Enabled state, total replaced, type distribution |
/mask on / /mask off |
never | Runtime toggle (resets to config.enabled on restart) |
/mask restore <text> |
yes (explicit) | Unmaps placeholders back to the values stored for this session |
mask_test |
never | Masks a snippet and reports the placeholder result + counts |
dsh-mask performs no network requests and stores no credentials; it only reads the session at the agent/pre-step boundary and writes its own dsh_mask storage domain. The dshWorkshop manifest declares network:none and credentials:none.placeholder → original restore table lives in memory and, when persistRestoreTable: true, in the controlled dsh_mask storage domain — this is the only place plaintext PII is stored, and it is never written to the session log.mask/applied is declared in types.d.ts and appended only when the host records the type (see Known limitations). Its payload is counts + type distribution only.lib/sanitize.mjs redacts PII, secrets, and URL credentials before any text reaches the model or the log; mask_test and /mask status never echo originals./mask restore is the single explicit reveal surface, and it only reads the mapping for the active session.mode (regex+ner), scope (tools), NER-only entities, and out-of-bounds numbers all fail loudly at load.person) and address (address) recognition needs an external NER recognizer, which the pure-host zero-dependency form does not bundle; mode: regex+ner and those entities fail loudly at load. The PII types covered out of the box are phone, email, ID card, bank card, key, and (opt-in) IP.restore() are the complete host-side seam a client plugin would consume, and /mask restore covers interactive needs today.0.1.0-rc.6. The harness does not yet record mask/* event types, so on rc.6 the session-log audit appends are skipped (sessions keep loading); the plugin enables them automatically once a host records the types or supports the ignorable envelope.pnpm install # node ^22.19 || >=24
pnpm run typecheck && pnpm run typecheck:ci # tsc --checkJs against the published rc.6 peers
pnpm test # node --test
pnpm run verify:self-contained # dependency specs resolve from the registry
pnpm run verify:artifacts # shipped files present + index.mjs importable
pnpm run check:readmes # five-language README consistency
pnpm pack # the published tarball
There is no build step: pure ESM, index.mjs and lib/ are the shipped artifacts.
dsh, dsh-plugin, deepseek-harness, deepseek, cordis, pii, mask, privacy, anonymization, security
agent/pre-step masking seam, the restore table, the /mask command and mask_test tool, and the five-language docs.This project is one of the DeepSeek Harness plugins maintained by PerryLink. If this one helps you, the others likely will too:
| Plugin | One-liner |
|---|---|
| dsh-mask | PII masking middleware: anonymize at the model boundary, restore at the display layer |
| dsh-mcp-panel | Read-only MCP runtime panel: /mcp command + Settings tab with status, tools and errors |
| dsh-doublecheck | Engineering-discipline guard: requirements grill, test gates, adversary review |
| dsh-background-agents | Durable background child agents with a Web UI sidebar, messaging and interrupt |
| dsh-lsp-actions | LSP diagnostics, formatting, completion, code actions and rename over language servers |
| dsh-output-styles | Claude Code outputStyles-equivalent runtime style switching |
| dsh-checkpoint-rewind | Claude Code /rewind-equivalent: snapshots, session forks, one-shot restore |
| dsh-permission-rules | Claude Code-style declarative allow/deny/ask permission rules with audit |
| dsh-auto-review | Second-model auto-review on the approval chain, fail-closed by default |
| dsh-memento | Approval-gated cross-session memory: ctx.memory seam + SQLite + memory tool |
| dsh-skill-pack-security | Security-audit skill pack: secret scan, dependency and supply-chain review |
| dsh-session-pin | Pin sessions in the Web sidebar with durable ordering |
| dsh-composer-history | Terminal-style input history for the web composer: arrows, Ctrl+R search |
| dsh-github | GitHub PR/issues integration for DSH, every write gated by approval |
| dsh-plugin-guide | Plugin-development knowledge base as an on-demand agent skill |
| dsh-claude-move | Migrate Claude Code sessions, memory, skills and CLAUDE.md into DSH |
LICENSE (Apache License 2.0) © 2026 dsh-mask contributors
CLASSIFICATION EVIDENCE
系统优先读取 GitHub Topics,再与站内分类词典和词根规则比对。当前命中: privacy、security。