@decionis/mcp 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/LICENSE ADDED
@@ -0,0 +1,13 @@
1
+ Copyright version 2.0 (c) 2026 Decionis, Inc.
2
+
3
+ Licensed under the Apache License, Version 2.0 (the "License");
4
+ you may not use this file except in compliance with the License.
5
+ You may obtain a copy of the License at
6
+
7
+ http://www.apache.org/licenses/LICENSE-2.0
8
+
9
+ Unless required by applicable law or agreed to in writing, software
10
+ distributed under the License is distributed on an "AS IS" BASIS,
11
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ See the License for the specific language governing permissions and
13
+ limitations under the License.
package/README.md ADDED
@@ -0,0 +1,233 @@
1
+ # @decionis/mcp — agent policy tools and execution hooks
2
+
3
+ A stdio [Model Context Protocol](https://modelcontextprotocol.io) server that lets AI coding
4
+ agents (Claude Code, Cursor, Codex, OpenHands, …) read a repository's `DECIONIS_POLICY.md`
5
+ and evaluate candidate actions **before** they commit, deploy, or migrate anything.
6
+
7
+ It is not a re-implementation: `decionis_evaluate` boots the real `@decionis/protocol`
8
+ service in-process with an in-memory store, publishes the repo policy through the
9
+ protocol's own schema-validated bundle ingestion, and evaluates through
10
+ `POST /v1/protocol/evaluate-decision` via fastify `inject()`. The verdict an agent sees
11
+ locally is the verdict the platform would produce — with **zero network, zero database,
12
+ zero credentials, and nothing recorded**.
13
+
14
+ (The protocol service separately exposes a _remote_, authenticated MCP surface for
15
+ org-connected agents; this package is the local, offline complement for repo checkouts.)
16
+
17
+ The package now exposes two complementary surfaces:
18
+
19
+ - **MCP tools** let the model read policy, evaluate an intended action, and understand the
20
+ verdict vocabulary.
21
+ - **Native `PreToolUse` hooks** intercept every supported tool call outside the model's
22
+ discretion. Codex, GitHub Copilot, and Claude Code all normalize into one
23
+ `AgentToolCall` contract and one `AgentGateEvaluator` interface.
24
+
25
+ MCP is the discovery and explanation surface. The native hook is the binding enforcement
26
+ surface.
27
+
28
+ ## Tools
29
+
30
+ | Tool | Purpose |
31
+ | ----------------------- | ---------------------------------------------------------------------------------------------------------------------- |
32
+ | `decionis_read_policy` | Path, sha256, and compiled rules (or compile errors) of the repo's `DECIONIS_POLICY.md`. |
33
+ | `decionis_evaluate` | Evaluate a candidate action payload against the policy through the real evaluator; returns the verdict + matched rule. |
34
+ | `decionis_verdict_help` | The verdict vocabulary, rules-block grammar, and how an agent should behave on each verdict. |
35
+
36
+ The policy file resolves from the tool's `path` argument, then `$DECIONIS_POLICY_PATH`,
37
+ then `./DECIONIS_POLICY.md` in the working directory.
38
+
39
+ ## Install
40
+
41
+ ```bash
42
+ npm install -g @decionis/mcp
43
+ ```
44
+
45
+ Or skip the install entirely — every client config below can launch the server
46
+ through `npx -y @decionis/mcp`.
47
+
48
+ ## Wire it up
49
+
50
+ **Claude Code** — `.mcp.json` at the repo root:
51
+
52
+ ```json
53
+ {
54
+ "mcpServers": {
55
+ "decionis": {
56
+ "command": "npx",
57
+ "args": ["-y", "@decionis/mcp"]
58
+ }
59
+ }
60
+ }
61
+ ```
62
+
63
+ **Codex** — add the stdio server to `~/.codex/config.toml` or a trusted project's
64
+ `.codex/config.toml`:
65
+
66
+ ```toml
67
+ [mcp_servers.decionis]
68
+ command = "npx"
69
+ args = ["-y", "@decionis/mcp"]
70
+ required = true
71
+ ```
72
+
73
+ **Cursor** — use the Claude server block in `.cursor/mcp.json`. During development,
74
+ `"command": "pnpm", "args": ["--filter", "@decionis/mcp", "dev"]` also works.
75
+
76
+ **Source checkout** — build once (`pnpm --filter @decionis/mcp build`) and point the
77
+ client at the bin directly: `"command": "node", "args": ["<repo>/apps/mcp/dist/index.js"]`.
78
+
79
+ ## Native execution gate
80
+
81
+ Install the package globally so `decionis-agent-hook` (and the other bins) land on the
82
+ host's `PATH`:
83
+
84
+ ```bash
85
+ npm install -g @decionis/mcp
86
+ ```
87
+
88
+ Copy the provider template to its native repository location:
89
+
90
+ | Host | Template | Native location |
91
+ | -------------------------------------- | ------------------------------- | ----------------------------- |
92
+ | Codex | `templates/CodexHooks.json` | `.codex/hooks.json` |
93
+ | Claude Code | `templates/ClaudeSettings.json` | `.claude/settings.json` |
94
+ | GitHub Copilot CLI/cloud agent/VS Code | `templates/CopilotHooks.json` | `.github/hooks/Decionis.json` |
95
+
96
+ For a source checkout, replace the template's `decionis-agent-hook …` command with:
97
+
98
+ ```text
99
+ node "$(git rev-parse --show-toplevel)/apps/mcp/dist/AgentHookCli.js" <provider>
100
+ ```
101
+
102
+ where `<provider>` is `codex`, `copilot`, or `claude`.
103
+
104
+ ### Evaluation modes
105
+
106
+ The hook defaults to **local mode**. It loads `DECIONIS_POLICY.md`, publishes it into the
107
+ real in-process protocol evaluator, and enforces the result without network access or
108
+ credentials.
109
+
110
+ Set these variables to use the enterprise policy graph and signed decision pipeline:
111
+
112
+ ```bash
113
+ DECIONIS_AGENT_GATE_MODE=remote
114
+ DECIONIS_AGENT_GATE_URL=https://protocol.decionis.com/v1/protocol/evaluate-decision
115
+ DECIONIS_API_KEY=<org-scoped-key>
116
+ DECIONIS_ORG_ID=<org-uuid>
117
+ ```
118
+
119
+ `DECIONIS_AGENT_GATE_TIMEOUT_MS` optionally changes the remote request timeout (default:
120
+ 4 seconds). Partial remote configuration is rejected; network errors, invalid hook input,
121
+ missing policy, and evaluator failures all produce a native deny response.
122
+
123
+ An `APPROVE` result returns no permission override, so the host's normal sandbox and user
124
+ approval flow still applies. `REJECT`, `REVIEW`, and `ESCALATE` all stop the tool call;
125
+ the latter two remain blocked until a human resolves them through the policy workflow.
126
+
127
+ ### Reusable interface
128
+
129
+ Other runtimes can import the same contracts and orchestration layer:
130
+
131
+ ```ts
132
+ import {
133
+ AgentHookRunner,
134
+ type AgentGateEvaluator,
135
+ type AgentHostAdapter,
136
+ type AgentToolCall,
137
+ } from "@decionis/mcp/agent";
138
+ ```
139
+
140
+ A new provider implements only `AgentHostAdapter`; a new decision backend implements only
141
+ `AgentGateEvaluator`. Neither needs to understand the other provider formats.
142
+
143
+ For pre-prompt enforcement, `@decionis/sdk-node` exposes the complementary
144
+ `DecionisAgentTaskGateway` interface. It reserves the model budget before an OpenAI or
145
+ Anthropic proxy call, verifies sandbox egress, consumes the same bound grant at the proxy,
146
+ and reconciles provider usage. Copilot embeddings use the same reserve/egress/reconcile
147
+ contract when model transport itself is not replaceable.
148
+
149
+ See
150
+ [`docs/integrations/agents/AgentBoundaryGateway.md`](../../docs/integrations/agents/AgentBoundaryGateway.md)
151
+ for the provider SDK configuration and four-boundary deployment model.
152
+
153
+ ### Managed distribution
154
+
155
+ Device-management templates are under `templates/managed`:
156
+
157
+ - `CodexRequirements.toml` pins the managed `PreToolUse` hook in
158
+ `requirements.toml`.
159
+ - `CopilotPolicyHooks.json` is the root-owned Copilot CLI policy hook; cloud agent
160
+ continues to use the repository template.
161
+ - `ClaudeManagedSettings.json` is the organization-controlled Claude Code settings
162
+ fragment.
163
+ - `AgentPolicyBundle.json` is a fail-closed, source-dated policy-graph skeleton. It
164
+ contains explicit official list-price cards retrieved on 2026-07-27. Negotiated rates
165
+ are stored separately under the organization policy's
166
+ `agentExecution.providerContracts`; a contract overrides the public baseline only while
167
+ it is effective and independently maker-checker approved.
168
+ - `AgentGateConfig.example.json` documents the protected, org-scoped runtime
169
+ configuration. The package never embeds its API key.
170
+
171
+ Build the deterministic deployment ZIP with:
172
+
173
+ ```bash
174
+ pnpm --filter @decionis/mcp package:managed
175
+ ```
176
+
177
+ The ZIP contains Linux, macOS, and Windows payload trees, the bundled managed runner,
178
+ native policy files, the organization policy template, an install manifest, and
179
+ `SHA256SUMS`. Codex executes the runner from its declared managed hook directory. Render
180
+ the example runtime configuration at the manifest destination, protect it with
181
+ administrator-only permissions, and distribute the matching payload through the
182
+ organization's package or device-management system.
183
+
184
+ ### Host boundaries
185
+
186
+ - `PreToolUse` happens after the host has already spent tokens choosing a tool. It prevents
187
+ the side effect, but it cannot prevent the model cost incurred before that point. Put the
188
+ Decionis API/network gateway in front of model traffic when pre-prompt token and cost
189
+ reservation is required.
190
+ - Codex hooks cover shell commands, `apply_patch`, MCP calls, and supported local
191
+ function tools. Hosted tools that do not traverse the local hook path need a separate
192
+ gateway boundary.
193
+ - Copilot command-hook timeouts are fail-open at the host level. Keep the Decionis
194
+ request timeout below the hook timeout (the defaults are 4 seconds and 10 seconds)
195
+ and deploy the executable inside the cloud-agent image.
196
+ - Copilot cloud agent requires the Decionis endpoint to be permitted by its network
197
+ firewall when remote mode is used.
198
+ - VS Code agent hooks are currently a preview surface. VS Code reads the same
199
+ `.github/hooks/*.json` template, emits the PascalCase-compatible snake-case payload,
200
+ and receives the nested native denial shape from the adapter.
201
+ - Copilot's `userPromptSubmitted` event is observational and cannot block prompt
202
+ processing. Copilot pre-prompt spend enforcement therefore belongs at the enterprise
203
+ proxy/API boundary, not in a repository hook.
204
+ - Hook inputs may contain secrets inside commands or tool arguments. The gate evaluates
205
+ them in memory and does not log them.
206
+
207
+ ## Development
208
+
209
+ ```bash
210
+ pnpm --filter @decionis/mcp test # vitest (includes the real evaluator)
211
+ pnpm --filter @decionis/mcp typecheck
212
+ pnpm --filter @decionis/mcp build # self-contained dist/index.js (shebang bin)
213
+ pnpm --filter @decionis/mcp package:managed
214
+ ```
215
+
216
+ Smoke test over stdio:
217
+
218
+ ```bash
219
+ printf '%s\n' \
220
+ '{"jsonrpc":"2.0","id":1,"method":"initialize","params":{"protocolVersion":"2025-06-18"}}' \
221
+ '{"jsonrpc":"2.0","id":2,"method":"tools/call","params":{"name":"decionis_evaluate","arguments":{"payload":{"action":"production-deploy","change_freeze":true}}}}' \
222
+ | node dist/index.js
223
+ ```
224
+
225
+ ## Notes
226
+
227
+ - The rules-block compiler here mirrors
228
+ `apps/api/src/services/policyEncoding/decionisRulesBlock.ts` and must stay in lockstep
229
+ (local difference: JSON-only block bodies; the platform also accepts YAML).
230
+ - Rules without `"domain": "*"` are filtered by the platform's decision-domain match —
231
+ the evaluate tool detects this and tells the agent how to fix the policy.
232
+ - Local evaluations mint no signed Decision Dossier; CI runs through
233
+ [`decionis/govern`](https://github.com/decionis/govern) produce the verifiable record.
@@ -0,0 +1,2 @@
1
+
2
+ export { }
@@ -0,0 +1,17 @@
1
+ #!/usr/bin/env node
2
+ import {
3
+ AgentHookCommand
4
+ } from "./chunk-UN67W5FH.js";
5
+ import "./chunk-QSCP7MRQ.js";
6
+
7
+ // src/AgentHookCli.ts
8
+ void AgentHookCommand.run(process.argv.slice(2)).then((exitCode) => {
9
+ process.exitCode = exitCode;
10
+ }).catch((error) => {
11
+ process.stderr.write(
12
+ `decionis-agent-hook: ${error instanceof Error ? error.message : error}
13
+ `
14
+ );
15
+ process.exitCode = 2;
16
+ });
17
+ //# sourceMappingURL=AgentHookCli.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/AgentHookCli.ts"],"sourcesContent":["import { AgentHookCommand } from \"./agent/AgentHookCommand.js\";\n\nvoid AgentHookCommand.run(process.argv.slice(2))\n .then((exitCode) => {\n process.exitCode = exitCode;\n })\n .catch((error) => {\n process.stderr.write(\n `decionis-agent-hook: ${error instanceof Error ? error.message : error}\\n`,\n );\n process.exitCode = 2;\n });\n"],"mappings":";;;;;;;AAEA,KAAK,iBAAiB,IAAI,QAAQ,KAAK,MAAM,CAAC,CAAC,EAC5C,KAAK,CAAC,aAAa;AAClB,UAAQ,WAAW;AACrB,CAAC,EACA,MAAM,CAAC,UAAU;AAChB,UAAQ,OAAO;AAAA,IACb,wBAAwB,iBAAiB,QAAQ,MAAM,UAAU,KAAK;AAAA;AAAA,EACxE;AACA,UAAQ,WAAW;AACrB,CAAC;","names":[]}
@@ -0,0 +1,2 @@
1
+
2
+ export { }