Pi Coding Agent App Security Checklist
Harden Pi Coding Agent: standard MCP paths, host discovery controls, tool scoping, and diff-aware CI for AI-built apps.

On this page
- 1. Use standard MCP paths and lock precedence
- 2. Keep host config discovery off unless you explicitly adopt
- 3. Scope MCP authority: disable, directTools, and least-privilege env
- 4. Treat packages, extensions, and skills as code with version pinning
- 5. Build diff-aware CI: four modes need four gates
- FAQ
- Q: Where does Pi store MCP config and which file wins?
- Q: Should I enable hostConfigDiscovery?
- Q: How do I add LyraShield MCP to Pi?
- Q: How do I disable a server without deleting config?
- Why pair Pi Coding Agent with LyraShield
- CTA
Pi Coding Agent from pi.dev is a minimal, extensible agent harness with packages, skills, and a strict MCP adapter. This checklist turns those primitives into a shippable guardrail for AI-built apps. Start with the vibe coding security guide for the shared baseline, then apply the Pi controls below.
1. Use standard MCP paths and lock precedence
Pi’s pi-mcp-adapter auto-reads standard MCP files. Verified precedence low-to-high:
~/.config/mcp/mcp.json(user-global shared preferred)~/.agents/mcp.json~/.agents/mcp/mcp.json~/.pi/agent/mcp.jsonor$PI_CODING_AGENT_DIR/mcp.json(Pi global override, write target for imports).mcp.json(project shared preferred).pi/mcp.json(Pi project override, highest precedence, write target for/mcp disable)
Security implication: a .pi/mcp.json in your repo can override every global definition. Commit it, require PR approval, and keep global files minimal. Prefer .mcp.json for shared project config when you want the same setup to work across hosts; use .pi/mcp.json only when you need Pi-specific overrides like directTools.
If you already have .mcp.json or ~/.config/mcp/mcp.json, Pi uses it immediately. First /mcp open shows a heads-up explaining detection and that Pi only writes adapter-specific overrides to its own files, a sensible isolation pattern.
2. Keep host config discovery off unless you explicitly adopt
Pi detects host-specific configs (Cursor, Claude Code, Codex, etc.) but does not load them automatically. /mcp setup and pi-mcp-adapter init show exactly what was found, let you pick imports, and preview file diffs before writing. To opt-in to fallback loading, set settings.hostConfigDiscovery to on; prompt only reports; default is off.
Leave it off. Automatic adoption of host configs would let a Cursor MCP server with broad filesystem access become a Pi server without review.
The hostConfigDiscovery gate also prevents transitive trust creep. When Pi discovers a Cursor ~/.cursor/mcp.json entry pointing at npx -y @modelcontextprotocol/server-filesystem /, Pi surfaces the source path and target scope but does not load it until you run /mcp setup and confirm import. This explicit step matters because host configs often include broad filesystem or shell tools and env vars copied from another agent session. Keeping discovery off ensures that a compromised or overbroad host config cannot silently become a Pi verifier. When you do import, limit the imported server to the project root, set idleTimeout low so the stdio process recycles, and pin the package version in lockfile to avoid floating @latest resolves that change resolution behavior between pi-mcp-adapter and pi-mcp-extension.
Additionally, treat extension pinning as a security control, not just stability. Pi can load both pi-mcp-adapter and pi-mcp-extension with overlapping responsibilities for standard path resolution. Version drift between them changes which file wins as highest precedence and whether ~/.agents/mcp.json is read at all. Commit your chosen adapter version, test upgrades in a branch, and capture /mcp tools output as a build artifact so reviewers can compare tool surface before and after. Explicit import is the security control: it copies nothing sensitive and never writes to external host files per adapter docs. Discovery reports source paths, provenance, and same-name conflicts, read that output in PR review when you adopt.
This maps to supply chain control and is analogous to Amp’s workspace approval gate covered in amp-app-security-checklist.
3. Scope MCP authority: disable, directTools, and least-privilege env
Pi supports per-server disabled, global idleTimeout (default 10min), requestTimeoutMs (default 30s), toolPrefix, showStatusIcon, autoAuth, and directTools controls. /mcp disable <name> and /mcp enable <name> persist only disabled in .pi/mcp.json, the source file is never rewritten and credentials never copied. Run /reload after toggling.
Fastest path: run npx lyrashield init, which detects Pi and writes its MCP config. Verify with npx lyrashield doctor, then npx lyrashield login to store credentials in ~/.lyrashield/credentials.json (nothing committed). The manual config below is what the CLI writes.
LyraShield config, canonical at picode integration guide:
Project-shared .mcp.json (works across hosts):
{
"mcpServers": {
"lyrashield": {
"command": "npx",
"args": ["-y", "@lyrashield/mcp"],
"env": {
"LYRASHIELD_API_KEY": "${LYRASHIELD_API_KEY}"
}
}
}
}
Remote Streamable HTTP (centralized revocation):
{
"mcpServers": {
"lyrashield": {
"url": "https://app.lyrashieldai.com/api/mcp",
"transport": "streamable-http",
"headers": {
"Authorization": "Bearer ${LYRASHIELD_API_KEY}"
}
}
}
}
Pi-specific override with direct tools:
{
"settings": {
"toolPrefix": "mcp",
"requestTimeoutMs": 30000,
"directTools": false
},
"mcpServers": {
"lyrashield": {
"command": "npx",
"args": ["-y", "@lyrashield/mcp"],
"directTools": true
}
}
}
Hardening:
- Use
${NAME}env var interpolation, not literal keys. Pi resolves env vars in config values per spec. - Keep
directTools: falseglobally, enable per-server only for vetted verifiers like LyraShield to reduce tool surface. - Set
requestTimeoutMslow for networked verifiers to fail closed.
4. Treat packages, extensions, and skills as code with version pinning
Pi’s extensibility via packages/extensions/skills is its USP, and a supply chain boundary. An extension that adds MCP support bridges tools into the LLM.
Checklist:
- Pin extension versions.
pi-mcp-extensionvspi-mcp-adapterversion drift changes resolution behavior (shared vs Pi-owned paths). - Inventory
settings.importsif you use compatibility imports for OpenCode. Theopencodeimport reads V1mcpentries from~/.config/opencode/opencode.jsonand projectopencode.json, explicit-import only. - Review any extension that registers filesystem MCP at
/. Standard Pi filesystem examplenpx -y @modelcontextprotocol/server-filesystem /workspacescoped to/workspaceis appropriate;/is not. - Version skills that drive context engineering. Skills shape what context enters the model window, a skill that injects untrusted URLs expands prompt-injection surface.
This aligns with OWASP LLM05 Insecure Output Handling and LLM06 Excessive Agency: a skill that can call MCP tools with unvalidated output gets broad authority.
5. Build diff-aware CI: four modes need four gates
Pi’s four modes (plan, act, etc. per architecture) benefit from mode-aware approval. Do not allow auto-transition from plan to execution that writes auth logic without human sign-off.
Target CI:
- Mode-based CODEOWNERS: changes to
src/auth/**require human review regardless of Pi mode that generated them. - Diff-aware lockfile review: if Pi adds a dependency, require SCA and secrets scan on diff, not full scan.
- SARIF upload: Pi-generated PRs should emit SARIF from any scanner, not just pretty logs. The LyraShield GitHub Action, SCA + secrets + agentic pentest with SARIF, is intended for this slot, enabling
retestafter fix rather than trusting first-pass generation. /mcpstatus in CI logs. Running/mcp toolsand capturing tool list in a build artifact gives auditors a snapshot of what verifiers were available when the PR was built.
| # | Control | File/Command | If Skipped |
|---|---|---|---|
| 1 | Commit .mcp.json + .pi/mcp.json in git |
.mcp.json, .pi/mcp.json, PR review |
Global override silently changes verifier list |
| 2 | Keep hostConfigDiscovery: off |
settings.hostConfigDiscovery |
Cursor/Codex server with broad FS access auto-loads |
| 3 | Use ${VAR} not literals |
env, headers interpolation |
lsk_ key committed to repo |
| 4 | /mcp disable writes only flag to .pi/ override |
/mcp disable lyrashield, /reload |
Disabling in shared file breaks other hosts |
| 5 | Pin extension versions, audit skills | package.json, *.extension, skills dir |
Malicious extension bridges exfil tool |
| 6 | Diff-aware SARIF gate | .github/workflows/*, SARIF upload |
AI auth bypass merges because CI only linted |
FAQ
Q: Where does Pi store MCP config and which file wins?
Standard shared: ~/.config/mcp/mcp.json global, .mcp.json project. Pi overrides: ~/.pi/agent/mcp.json global, .pi/mcp.json project highest. Full precedence is ~/.config/mcp/mcp.json < ~/.agents/mcp.json < ~/.agents/mcp/mcp.json < Pi global < .mcp.json < .pi/mcp.json. Commit project files.
Q: Should I enable hostConfigDiscovery?
No. Default off is the secure default. It prevents automatic loading of Cursor/Claude Code/Codex configs. Use /mcp setup to preview and explicitly adopt if needed, discovery never writes external host files.
Q: How do I add LyraShield MCP to Pi?
In .mcp.json or .pi/mcp.json under mcpServers: local command: npx, args: ["-y","@lyrashield/mcp"] with ${LYRASHIELD_API_KEY} env, or remote url: https://app.lyrashieldai.com/api/mcp with transport: streamable-http and Authorization: Bearer ${LYRASHIELD_API_KEY}. See picode integration guide.
Q: How do I disable a server without deleting config?
Run /mcp disable <name> in Pi, it writes disabled: true only in .pi/mcp.json project override, which is highest precedence. Run /reload so tool surfaces refresh. Manual equivalent is "disabled": true in any MCP config. Re-enable with /mcp enable <name>.
Primary references: OWASP Top 10 for injection and misconfiguration, CWE-20 for validation gaps when pi.dev extensions load untrusted context, MCP spec for the standard .mcp.json shape Pi adopts, GitHub Actions security for diff-aware gates, and OSV for lockfile scanning after Pi adds dependencies.
Why pair Pi Coding Agent with LyraShield
Pi gives you a minimal, composable harness with explicit standard paths and safe defaults like hostConfigDiscovery: off. That minimalism maps well to verification: you add only what you need, and Pi shows provenance. LyraShield fits that slot as release assurance for AI-built apps, a narrow MCP surface for target, review, evidence, fix, retest, report plus SCA and secrets, emitting SARIF for existing code-scanning. LyraShield separates detection from proof: every finding produces an immutable assurance record, and fix proposals are approval-gated, PR execution is blocked until a server-generated patch is bound to the exact approval.
Configure LyraShield once in .mcp.json or .pi/mcp.json using npx -y @lyrashield/mcp locally or https://app.lyrashieldai.com/api/mcp remotely per the PiCode integration guide. Pi owns generation and orchestration; LyraShield owns verification evidence that survives mode transitions. The platform is live in open beta, and scans, findings and evidence, approval-gated fix proposals, retests, and reports are implemented. Automatic server-generated Fix PR execution is not enabled.
Before you merge, run the AI app security checklist to verify auth, secrets, and dependencies one more time.
CTA
Create an account at lyrashieldai.com for Pi integration snippets, extension pinning guide, and access to diff-aware verification.
Frequently asked
Where does Pi store MCP config?
Shared: ~/.config/mcp/mcp.json and .mcp.json. Pi overrides: ~/.pi/agent/mcp.json global and .pi/mcp.json project. Precedence is project Pi override highest.
What is hostConfigDiscovery?
Controls whether Pi loads Cursor/Claude Code/Codex host configs as fallback. Default off. Discovery never writes external host files.
How do I add LyraShield to Pi?
In .mcp.json or .pi/mcp.json: mcpServers.lyrashield with command npx -y @lyrashield/mcp or url https://app.lyrashieldai.com/api/mcp with Authorization header.
How do I disable an MCP server in Pi?
/mcp disable <name> writes disabled:true to .pi/mcp.json project override. Manual equivalent is disabled:true in any MCP config.
Related posts
- Amp App Security Checklist
Practical checklist for Amp: scope orbs, MCP servers, skills, and CI gates before shipping AI-built code to production.
- Amp MCP security workflow for evidence-state agent scans
Set up LyraShield AI with Amp via MCP to scan changed code, verify findings, and enforce a diff aware GitHub Action gate with SARIF.
- Claude Code MCP Agent Rules Security Setup
Configure LyraShield MCP with Claude Code agent rules to catch OWASP risks secrets and dependency issues across local and remote MCP