Package Exports
- @looppause/mcp
Readme
@looppause/mcp
MCP server for LoopPause — pause AI agent execution and route approval requests to humans via Slack or email. The agent receives a cryptographically signed proof of the human's decision and resumes.
"The missing primitive so agents don't go rogue — or die waiting for approval."
What it does
Exposes a single MCP tool: pause_agent_action
When called, the tool:
- POSTs an approval request to the LoopPause API
- Delivers a Slack Block Kit card and/or an email to the specified recipient
- Blocks the agent (polls every 5 seconds) until the human responds
- Returns the full signed response payload — decision, comment, structured fields, HMAC signature
The agent can verify the signature with its LOOPPAUSE_SIGNING_SECRET before trusting the decision.
Installation
Recommended: npx (no install required)
npx @looppause/mcpGlobal install
npm install -g @looppause/mcp
looppause-mcpConfiguration
| Environment variable | Required | Description |
|---|---|---|
LOOPPAUSE_API_KEY |
✅ Yes | Your LoopPause API key (sk_live_…) |
LOOPPAUSE_API_URL |
No | Override the API base URL (default: https://api.looppause.com) |
Get your API key at looppause.com/dashboard.
Usage in Claude Code
Add to your .claude/settings.json (or ~/.claude/settings.json for global):
{
"mcpServers": {
"looppause": {
"command": "npx",
"args": ["-y", "@looppause/mcp"],
"env": {
"LOOPPAUSE_API_KEY": "sk_live_your_key_here"
}
}
}
}Claude Code will automatically discover and offer the pause_agent_action tool.
Usage in Cursor
Add to your Cursor MCP configuration:
{
"mcpServers": {
"looppause": {
"command": "npx",
"args": ["-y", "@looppause/mcp"],
"env": {
"LOOPPAUSE_API_KEY": "sk_live_your_key_here"
}
}
}
}Tool reference
pause_agent_action
pause_agent_action({
// Required
action_description: string, // What the agent is about to do (shown to human)
action_details: object, // Structured key-value context (amount, vendor, etc.)
// At least one recipient required
recipient_email?: string, // Email address
recipient_slack?: string, // Slack channel (#approvals) or user ID (U12345)
// Optional
timeout_hours?: number, // Default 24, max 168 (1 week)
})When both recipient_slack and recipient_email are provided, Slack is the
primary channel and email is the fallback.
Example
// In your agent — before an irreversible action
const result = await mcp.callTool("pause_agent_action", {
action_description: "Transfer £12,450 to Globex Corp for invoice INV-2341",
action_details: {
vendor: "Globex Corp",
amount: 12450,
currency: "GBP",
invoice_ref: "INV-2341",
},
recipient_slack: "#finance-approvals",
recipient_email: "sarah@company.com",
timeout_hours: 4,
});Response
On approval or rejection the tool returns a JSON string:
{
"pause_id": "pause_01jwxyz123",
"agent_id": "mcp-agent",
"status": "responded",
"created_at": "2026-05-24T10:00:00.000Z",
"expires_at": "2026-05-24T14:00:00.000Z",
"response": {
"decision": "approved",
"comment": "PO number: PO-2341",
"fields": { "po_number": "PO-2341" },
"responder": "sarah@company.com",
"responded_at": "2026-05-24T10:14:32.000Z",
"channel": "slack",
"nonce": "a8f3c2...",
"signature": "sha256=4d9f1a..."
}
}Verify the signature against your LOOPPAUSE_SIGNING_SECRET before proceeding:
import { createHmac, timingSafeEqual } from "node:crypto";
function verifyDecision(payload: string, receivedSig: string): boolean {
const body = JSON.parse(payload);
const { signature: _, ...unsigned } = body.response;
const canonical = JSON.stringify(
Object.fromEntries(Object.entries(unsigned).sort())
);
const expected = "sha256=" +
createHmac("sha256", process.env.LOOPPAUSE_SIGNING_SECRET!)
.update(canonical)
.digest("hex");
const a = Buffer.from(expected);
const b = Buffer.from(receivedSig);
return a.length === b.length && timingSafeEqual(a, b);
}Terminal states
| Return value | Meaning |
|---|---|
| JSON string | Human responded — check response.decision for "approved" or "rejected" |
"The approval request timed out…" |
No response within timeout_hours |
"The approval request was cancelled." |
Pause was manually expired |
Registry submissions
Smithery.ai
This package includes smithery.yaml for automatic configuration injection.
- Fork or publish
@looppause/mcpto npm - Submit at smithery.ai/new → enter
@looppause/mcp - Smithery will read
smithery.yamland present a UI for users to enter their API key
Anthropic MCP directory
- Ensure the package is published to npm as
@looppause/mcp - Submit via the Anthropic MCP directory form or the directory submission page when available
- List as:
@looppause/mcp— LoopPause human-in-the-loop approval tool
Local development
# From the monorepo root
cd packages/mcp
npm run build # tsc → dist/
npm run type-check # type-check only, no emit
npm run dev # tsx watch (no build step)License
MIT