Agents can't skip steps: an MCP server that runs gated, API-only stepfiles on the client's own model.
- ✓Open-source license (Apache-2.0)
- ✓Actively maintained (<30d)
- ✓Clear description
- ✓Topics declared
- ✓Documented (README)
claude mcp add stepgate -- npx -y stepgate{
"mcpServers": {
"stepgate": {
"command": "npx",
"args": ["-y", "stepgate"]
}
}
}Resumen de MCP Servers
# Stepgate
[](https://github.com/Chaarangan/stepgate/actions/workflows/ci.yml)
[](https://www.npmjs.com/package/stepgate)
[](LICENSE)
**Agents can't skip steps.** Write an agent's procedure once, as a YAML stepfile, and every step is gated: the agent moves on only when a mechanical check passes, never on its own word.
**One file runs anywhere.** A stepfile has no packages, no versions to pin and no code to deploy, so it moves as a single file to any MCP client, such as Claude Code, Cursor or an agent you wrote, and runs on the model that client already uses.
A **stepfile** declares its inputs, the remote APIs and MCP servers it may call, and an ordered list of steps. Each step says what output it must produce and which **gates** check that output. The file names no model and no framework.
**Stepgate** runs stepfiles. It is an MCP server that offers each stepfile as a tool. When a client's agent calls it, Stepgate shows the agent one step at a time, makes every API call the step needs, and moves on only when the step's gates pass.
## Make the procedure you already wrote enforceable
A skill or runbook written as markdown tells an agent what to do, and the agent decides how much of it to follow. Here is one:
```markdown
---
name: package-notes
description: Writes an upgrade note for each npm package, with versions taken from the registry.
---
1. Look up each package's latest version on the npm registry.
2. Write a one-line upgrade note for each. Never state a version the registry did not return.
```
`stepgate_outline` turns it into a skeleton, and the finished stepfile makes both lines binding. Stepgate does the lookup itself, so the agent never fetches or copies a version. The agent only writes the notes, and a gate rejects any note whose version differs from what the registry returned, naming the rows that broke it:
```yaml
stepgate: "1"
id: package-notes
description: Writes an upgrade note for each npm package, with versions taken from the registry.
inputs:
type: object
required: [packages]
properties:
packages: { type: array, minItems: 1, maxItems: 20, items: { type: string, pattern: "^[a-z0-9][a-z0-9._-]*$" } }
tools:
npm:
openapi:
server: https://registry.npmjs.org
document:
openapi: 3.1.0
info: { title: npm registry, version: "1" }
paths:
/{name}/latest:
get:
operationId: getLatest
parameters: [{ name: name, in: path, required: true, schema: { type: string } }]
exposes: [getLatest]
steps:
- id: look-up
do:
calls:
- id: latest
operation: getLatest
each: { var: inputs.packages }
arguments: { name: { var: item } }
output:
packages: { map: [{ var: responses.latest }, { object: [[name, { var: name }], [latest, { var: version }]] }] }
produces:
type: object
required: [packages]
properties: { packages: { type: array } }
- id: notes
instructions: |
Write a one-line upgrade note for each of these packages, saying what
its latest version is and whether that is a new major version:
{{steps.look-up.packages}}
produces:
type: object
required: [notes]
properties:
notes:
type: array
items:
type: object
required: [name, latest, note]
properties: { name: { type: string }, latest: { type: string }, note: { type: string } }
gates:
- id: versions-from-registry
message: Every note must give the version the registry returned for its package.
predicate:
none:
- join: [{ var: output.notes }, { var: steps.look-up.packages }, name, name]
- or: [{ "==": [{ var: right }, null] }, { "!=": [{ var: left.latest }, { var: right.latest }] }]
retries: 2
```
## Why
When an agent is handed a plan as text, it decides how much of the plan to follow, a step counts as done when the agent says so, and nothing records afterwards what actually ran. A stepfile moves those decisions out of the model:
- **Steps run in order, one at a time.** The agent is shown only the current step's instructions and operations, never a later step, so it cannot skip ahead. Earlier steps stay in its own conversation.
- **Gates decide, not the model.** A step passes only when its output satisfies JSON Schema, JSONLogic or an HTTP verifier, and gates can check that output against what the APIs actually returned, so a fabricated value fails. A failed gate's diagnosis goes back to the model for a bounded number of retries.
- **The model judges, the server computes.** A mechanical step makes its API calls and builds its output from a template, with no model involved, and a derived field fills in a count or a lookup after the model submits. The model is left the work that needs judgement.
- **Writes wait for a person.** An approve gate asks a person to confirm a step's output through an MCP elicitation before a later mechanical step writes it, so what reaches Jira is what the person saw ([which clients show the form](docs/connect.md#approvals)).
- **The model never holds a key.** The server makes every tool call and attaches credentials itself, and it refuses requests to hosts the stepfile does not declare.
- **Every run leaves a record.** A hash-chained ledger lists each step, tool call, gate verdict and retry, and editing it afterwards breaks the chain, which `stepgate --verify` detects.
- **Nothing to install on the client side.** Stepfiles call remote APIs only, and the client adds one MCP server to its configuration. Stepgate needs no model key: the client's own model does the reasoning, and the same file gives the same path through its steps whichever model that is.
## Quick start
Add the server to your MCP client's configuration, naming one or more stepfiles from the [catalog](stepfiles/), or giving absolute paths to your own `.stepfile.yaml` files ([details](docs/connect.md#your-own-stepfiles)):
```json
{
"mcpServers": {
"stepgate": {
"command": "npx",
"args": ["-y", "stepgate", "market-research"],
"env": { "TAVILY_API_KEY": "tvly-..." }
}
}
}
```
The client sees a `market-research` tool. Ask your agent to run it for `{ "brand": "Oatly", "market": "UK plant-based milk" }` and it works through four steps (search, filter, analyse, report) with `stepgate_call` and `stepgate_submit`, ending with every step's output. [docs/connect.md](docs/connect.md) has the configuration for Claude Code, Claude Desktop, Cursor, VS Code and other clients.
Every server also offers tools for writing stepfiles: ask your agent to write one for your use case, and it can read the format, inspect the APIs, validate its draft and try it through Stepgate ([details](docs/connect.md#writing-stepfiles-with-an-agent)).
To serve over HTTP instead of stdio, run `npx -y stepgate --http 3100 market-research` and connect to `http://127.0.0.1:3100/mcp`. `npx -y stepgate --list` shows the catalog, and `--help` lists every option, including these:
- `--watch` reloads your stepfiles when you save them, while you write one.
- `--test <stepfile>` checks its gates offline against recorded cases, and `--record-cases <dir>` records those cases from a real run.
- `--auth <stepfile> <credential>` signs in to an MCP server that uses MCP authorization and prints the variables to set ([details](docs/connect.md#mcp-servers-that-use-mcp-authorization)).
- `--verify <ledger>` checks a run's ledger for edits.
## A stepfile
```yaml
stepgate: "1"
id: market-research
inputs:
type: object
required: [brand, market]
properties:
brand: { type: string }
market: { type: string }
credentials:
tavily:
kind: bearer
hosts: [mcp.tavily.com]
description: Web search, used only by the search step.
tools:
tavily:
mcp: { url: "https://mcp.tavily.com/mcp/" }
credential: tavily
exposes: [{ name: tavily_search, effect: read }]
steps:
- id: search
tools: [tavily_search]
instructions: |
Run at least six searches about {{inputs.brand}} in {{inputs.market}}.
Submit every result as a source with an id of the form S-01.
produces:
type: object
required: [sources]
properties:
sources: { type: array }
gates:
- id: enough-sources
schema: { properties: { sources: { minItems: 12 } } }
- id: domain-breadth
message: Sources must span at least six distinct domains.
predicate:
">=":
- { length: { unique: { map: [{ var: output.sources }, { host: { var: url } }] } } }
- 6
retries: 2
# ... filter, analyse and report steps
```
Credentials say what is needed, never where it lives: the server reads `tavily` from `TAVILY_API_KEY`. `effect: read` marks the search as safe to retry. The complete file is [stepfiles/marketing/market-research](stepfiles/marketing/market-research/), and editors that support `yaml-language-server` validate against [server/schema/stepfile.schema.json](server/schema/stepfile.schema.json), which the npm package also ships.
## Catalog
[stepfiles/](stepfiles/) is a community catalog of stepfiles, reviewed and shipped with the npm package, so each one runs by name. Built something repeatable? Adding it is one folder and one pull request: see [stepfiles/README.md](stepfiles/README.md), or [suggest an idea](https://github.com/Chaarangan/stepgate/issues/new?template=stepfile_idea.yml).
## Documentation
- [docs/stepfile.md](docs/stepfile.md): how to write a stepfile: fields, tools, credentials, steps and gates.
- [docs/connect.md](docs/connect.md): connecting Claude Code, Claude Desktop and other MCP clients.
- [docs/how-it-works.md](docs/how-it-works.md):Lo que la gente pregunta sobre stepgate
¿Qué es Chaarangan/stepgate?
+
Chaarangan/stepgate es mcp servers para el ecosistema de Claude AI. Agents can't skip steps: an MCP server that runs gated, API-only stepfiles on the client's own model. Tiene 1 estrellas en GitHub y su última actualización registrada es del 2026-09-28.
¿Cómo se instala stepgate?
+
Puedes instalar stepgate clonando el repositorio (https://github.com/Chaarangan/stepgate) o siguiendo las instrucciones del README en GitHub. ClaudeWave también te ofrece bloques de instalación rápida en esta misma página.
¿Es seguro usar Chaarangan/stepgate?
+
Nuestro agente de seguridad ha analizado Chaarangan/stepgate y le ha asignado un Trust Score de 95/100 (tier: Verified). Revisa el desglose completo de comprobaciones superadas y flags en esta página.
¿Quién mantiene Chaarangan/stepgate?
+
Chaarangan/stepgate es mantenido por Chaarangan. La última actividad registrada en GitHub es del 2026-09-28, con 11 issues abiertos.
¿Hay alternativas a stepgate?
+
Sí. En ClaudeWave puedes explorar mcp servers similares en /categories/mcp, ordenados por popularidad o actividad reciente.
Despliega stepgate en tu cloud
Lleva este repo a producción en minutos. Cada plataforma genera su propio entorno con variables de entorno editables.
¿Mantienes este repo? Añade un badge a tu README
Pega el badge en tu README de GitHub para mostrar que está auditado por ClaudeWave. Cada badge enlaza de vuelta a esta página y muestra el Trust Score actual.
[](https://claudewave.com/repo/chaarangan-stepgate)<a href="https://claudewave.com/repo/chaarangan-stepgate"><img src="https://claudewave.com/api/badge/chaarangan-stepgate" alt="Featured on ClaudeWave: Chaarangan/stepgate" width="320" height="64" /></a>Más MCP Servers
Fair-code workflow automation platform with native AI capabilities. Combine visual building with custom code, self-host or cloud, 400+ integrations.
User-friendly AI Interface (Supports Ollama, OpenAI API, ...)
An open-source AI agent that brings the power of Gemini directly into your terminal.
Real-time global intelligence dashboard. AI-powered news aggregation, geopolitical monitoring, and infrastructure tracking in a unified situational awareness interface
🕷️ An adaptive Web Scraping framework that handles everything from a single request to a full-scale crawl! Don't be shy, join here: https://discord.gg/EMgGbDceNQ and follow here for daily tips and tricks: https://x.com/Scrapling_dev
The fastest path to AI-powered full stack observability, even for lean teams.