Skip to main content

SHIM Guard

SHIM Guard is a local pre-submit prompt guard for hook-capable coding-agent CLIs. It scans a submitted prompt in the client hook process and either stays silent, replaces the model-facing prompt with a typed redaction, or stops the client and saves a typed redaction for easy resubmission.

It is an alpha. Treat the compatibility and release gates below as part of the product boundary.

Install

Use one package manager:

uv tool install shim-guard
# or
pipx install shim-guard

The command is shim:

shim
shim --version
shim help
shim update
shim demo codex
shim demo claude
shim demo copilot
shim config
shim install codex --dry-run
shim install codex
shim doctor codex
shim install claude
shim doctor claude
shim install copilot
shim doctor copilot
shim status codex
shim status claude
shim status copilot
shim revert codex
shim revert claude
shim revert copilot

shim update delegates to the package manager used during installation: uv tool upgrade shim-guard or pipx upgrade shim-guard.

Marketplace plugins

Install the CLI before installing the SHIM Guard plugin from a Claude Code or Codex marketplace:

uv tool install shim-guard
shim help

The plugin registers the prompt hook and calls the installed shim-guard-hook executable. Keep the uv tool bin directory on PATH, then restart the client after installation. The marketplace plugin and shim install codex or shim install claude are alternative hook installation methods; do not use both for the same client.

Install the public Codex marketplace and plugin with:

codex plugin marketplace add GetSHIM/shim-guard
codex plugin add shim-guard@shim-guard

In Claude Code, run:

/plugin marketplace add GetSHIM/shim-guard
/plugin install shim-guard@shim-guard

For local marketplace testing from a repository checkout:

codex plugin marketplace add .
codex plugin add shim-guard@shim-guard

In Claude Code, run:

/plugin marketplace add .
/plugin install shim-guard@shim-guard

For direct local inspection, pipe text instead of placing it in shell history or a process list:

printf '%s' 'Contact me at alice@example.com' | shim scan
printf '%s' 'Contact me at alice@example.com' | shim redact

scan and redact read stdin. Do not pass real prompts as command-line arguments. redact --json reports only status and counts; use the default output when piping typed text. Redirected output preserves surrounding text, while an interactive terminal escapes non-printing control characters.

What the prompt hook does

Codex and Claude Code integrations use each client's native UserPromptSubmit command-hook event. GitHub Copilot CLI uses userPromptTransformed, which can replace the model-facing prompt directly.

submitted prompt
  -> supported client invokes its local SHIM hook
  -> bounded offline detector evaluates the prompt in memory
  -> safe: exit 0 with empty stdout and stderr
  -> finding: Copilot receives the typed redaction directly
            | Codex/Claude write a private temporary redaction and return its path
  -> handled guard error: native client fail-closed response

The hook does not require a SHIM account, API key, network request, daemon, telemetry, prompt log, finding log, or replacement map. For Copilot, SHIM replaces the model-facing prompt with its typed redaction and creates no temporary redaction file. For Codex and Claude Code, it creates one 0600 redacted text file in the operating system's temporary directory and puts a ready-to-copy Read this file and use its contents as my prompt: <absolute path> instruction in the block response. Paste that whole line as the next prompt so the agent can read the redaction. Detected raw values are not included in SHIM's hook messages or redaction output. Redactions are typed and ordinal, for example <EMAIL_1>.

The initial public entity allowlist is:

EMAIL, PHONE, CREDIT_CARD, IBAN, IP_ADDRESS, MAC_ADDRESS, US_SSN, TR_NATIONAL_ID, TR_VKN, SECRET, and DB_URI.

The default preset enables every supported entity. shim config shows an explicit ON or OFF state for each entity. Changes are previewed before they are saved:

shim config --only EMAIL --only SECRET
shim config --disable IP_ADDRESS --disable MAC_ADDRESS
shim config --enable PHONE
shim config --reset

The repeatable options can be combined except that --only and --reset are standalone modes. scan, redact, and the installed hook use the selection; the synthetic demo always checks its built-in fixture. Settings are stored in $XDG_CONFIG_HOME/shim-guard/config.toml, or ~/.config/shim-guard/config.toml when XDG is unset. Malformed contents block inspection safely and can be replaced with shim config --reset --yes. Unsafe paths remain untouched for manual review. Selecting no entities is allowed but shown as a warning.

guard-v1-metrics.json reports 100% synthetic case-category precision and recall across its 27 fixtures, with a positive and targeted safe negative for each category. That narrow fixture-bound result is not a real-world statistical guarantee.

Privacy and limits

SHIM only covers a prompt after a supported client invokes a trusted, enabled hook that starts and completes. It is not whole-machine DLP and cannot promise detection of every sensitive value.

  • The host client receives the raw prompt before the hook can decide. Other matching hooks start concurrently and can receive it too.
  • Copilot's timeline can display the original prompt even though SHIM replaces the model-facing content and the value stored in session history.
  • The host client or another tool may keep transcripts, logs, telemetry, caches, or history outside SHIM's control.
  • A disabled, untrusted, missing, crashed, or timed-out hook is client controlled and can fail open. Some clients require changed hooks to be reviewed and trusted again.
  • Users can intentionally disable individual entity detectors, including all of them. shim config shows the active policy.
  • A redacted suggestion can still contain content the detector missed. Review the temporary file before sending it, then delete it when it is no longer needed. Otherwise it remains until the user or operating system cleans the temporary directory.
  • SHIM does not claim secure memory erasure in Python and does not inspect files, tool output, transcript content, images, audio, clipboard history, or unsupported client events.

For the exact trust boundary and current client evidence, see Privacy and Compatibility.

Client installation ownership

shim install codex --dry-run shows the target and exact owned fragment. It uses $CODEX_HOME/hooks.json when CODEX_HOME is set and otherwise ~/.codex/hooks.json. When that file is absent, SHIM creates it. When it is a valid existing hook document, SHIM preserves every existing hook, tells the user that the document is shared, and appends SHIM's exact matcher group last. The dry run shows only SHIM's fragment, never the whole settings-file diff.

SHIM leaves inline hooks in Codex's config.toml untouched. Codex may load both representations and warn that they coexist. Malformed or ambiguous hook documents, unsafe hook-file paths or permissions, and concurrently changed files require reviewed manual setup. SHIM does not create a full-file backup or read credential stores.

Repeated install and revert are safe no-ops. shim revert codex removes only SHIM's exact matcher group, preserves every other hook, and retains the hook document even when it becomes empty.

shim install claude --dry-run follows the same ownership rules for $CLAUDE_CONFIG_DIR/settings.json when CLAUDE_CONFIG_DIR is set and ~/.claude/settings.json otherwise. Claude Code stores hooks alongside other user settings, so SHIM preserves every unrelated key and hook, appends its exact group last, and uses the client's shell-free command plus args form. Its block response asks Claude Code not to repeat the original prompt in the block message. shim revert claude removes only that exact group and retains the settings file.

shim install copilot --dry-run targets SHIM's dedicated user hook file at $COPILOT_HOME/hooks/shim-guard.json, or ~/.copilot/hooks/shim-guard.json when COPILOT_HOME is unset. SHIM creates missing private parent directories and refuses to overwrite unexpected content at that path. The hook uses userPromptTransformed and returns modifiedTransformedPrompt. shim revert copilot removes the exact hook while retaining an empty versioned hook document.

Compatibility and release gates

The implementation target is CPython 3.13 on macOS and Linux. Codex CLI 0.149.0, Claude Code 2.1.210, and GitHub Copilot CLI 1.0.80 were locally inspected. Codex reported its hook feature as stable and enabled; Claude Code accepted SHIM's generated user settings through its native doctor command. All three native hook contracts have repository fixtures. This is not a claim that a live interactive session, every authentication mode, trust review, or timeout behavior has been verified. Each additional client still requires a native adapter and compatibility evidence. SHIM Protect remains deferred.

Before a public release, maintainers must record real-client compatibility, trusted-hook activation, the supported authentication routes, corpus results, and fresh-process latency. Publication is gated on those facts; placeholders are deliberately not metrics. See Compatibility.

Development

uv sync --locked
uv run --locked ruff check .
uv run --locked ruff format --check .
uv run --locked ty check
uv run --locked pytest
uv build --no-build-isolation
git diff --check

See Architecture, Contributing, and Security.

License

Apache-2.0. See LICENSE.

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

shim_guard-0.1.2.tar.gz (33.4 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

shim_guard-0.1.2-py3-none-any.whl (47.9 kB view details)

Uploaded Python 3

File details

Details for the file shim_guard-0.1.2.tar.gz.

File metadata

  • Download URL: shim_guard-0.1.2.tar.gz
  • Upload date:
  • Size: 33.4 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for shim_guard-0.1.2.tar.gz
Algorithm Hash digest
SHA256 7d32ac4795a5bbeab4ca627a1d6fe53bddffe497099d917f90031f503ca998b1
MD5 ff5f61cf0fba78206ab37dc23d214a13
BLAKE2b-256 05d6f9064d48bd4bf69e2244c1783708070e27de26b365c1d448a4565eadfeb5

See more details on using hashes here.

Provenance

The following attestation bundles were made for shim_guard-0.1.2.tar.gz:

Publisher: release.yml on GetSHIM/shim-guard

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file shim_guard-0.1.2-py3-none-any.whl.

File metadata

  • Download URL: shim_guard-0.1.2-py3-none-any.whl
  • Upload date:
  • Size: 47.9 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for shim_guard-0.1.2-py3-none-any.whl
Algorithm Hash digest
SHA256 d96525e59a194c27b5885421659e6caf50a4bed64895b4758a369df9a450656b
MD5 b1b83b28db59fa87afcfc0e2ac844ff7
BLAKE2b-256 a04ffc05c436cf18e6bd9e9335acf922318020f355f81862cff08b83defb5b0b

See more details on using hashes here.

Provenance

The following attestation bundles were made for shim_guard-0.1.2-py3-none-any.whl:

Publisher: release.yml on GetSHIM/shim-guard

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Release history Release notifications | RSS feed

0.1.3

2 files

This release

0.1.2 This release

2 files

0.1.1

2 files

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page