Skip to content

Repository files navigation

arrest

npm version CI Coverage Status

An OpenAPI 3.1 REST framework for Node.js. You describe resources and operations; arrest serves them, validates them against JSON Schema, authorizes them, documents them as an OpenAPI document — and, if you want, exposes them to AI agents as MCP tools, with the same validation and the same authorization as the REST endpoints.

Features

  • OpenAPI 3.1 first — the document is generated from your definitions, not maintained beside them, with JSON Schema 2020-12 validation of every request
  • MongoDB CRUD out of the box — six operations per collection, plus RQL querying, projections, sorting and pagination headers
  • One authorization decision — OAuth2 scopes or CASL abilities, enforced on requests, reflected in openapi.json?filter=authorized and in the MCP tool list, from a single method
  • Record- and field-level rules — CASL conditions become part of the MongoDB query; CASL fields redact responses and reject write bodies
  • MCP server — expose chosen operations as tools, grouped in independently scoped bundles
  • JSON-RPC — for the calls that don't fit REST
  • Extensible by design — a seven-stage operation pipeline, and Resource/Operation subclassing as a first-class path
  • Express-native — mount it in an app you own, or let it own the server
  • TypeScript, ESM — full type definitions, native ES modules

Requirements

  • Node.js >= 20.0.0
  • MongoDB 7.x or later, if you use MongoResource

Installation

npm install arrest      # or: pnpm add arrest / yarn add arrest

TypeScript projects need "module": "NodeNext" and, for the @rpc decorator, "experimentalDecorators": true. See Installation and setup.

Quick start

import { API, MongoResource } from 'arrest';

const api = new API({ title: 'My API', version: '1.0.0' });

api.addResource(new MongoResource('mongodb://localhost:27017/mydb', { name: 'Person', namePlural: 'People' }));

await api.listen(3000);

That serves a full CRUD API and its own documentation:

GET /people list, with RQL filtering (q), limit, skip, fields, sort, and JSON/JSONL/CSV output
POST /people create
GET /people/{id} read one
PUT /people/{id} update
PATCH /people/{id} RFC 6902 JSON Patch
DELETE /people/{id} delete
GET /openapi.json the OpenAPI 3.1 document describing all of it
$ curl -s localhost:3000/people -H 'content-type: application/json' \
    -d '{"name":"Ada Lovelace","email":"ada@example.com","country":"GB"}'
{"name":"Ada Lovelace","email":"ada@example.com","country":"GB","_id":"6a7448e1ba3533ca10cf6b9f"}

$ curl -s 'localhost:3000/people?q=eq(country,GB)&fields=name,country&limit=10'
[{"name":"Ada Lovelace","country":"GB"}]

Add a schema and every request is validated against it, in both the document and the code path:

api.registerSchema('person', {
  type: 'object',
  required: ['name', 'email'],
  properties: {
    name: { type: 'string', minLength: 1 },
    email: { type: 'string', format: 'email' },
    age: { type: 'integer', minimum: 0 },
  },
  additionalProperties: false,
});

api.addResource(
  new MongoResource(db, { name: 'Person', namePlural: 'People', requestSchema: { $ref: 'person' }, responseSchema: { $ref: 'person' } })
);

Documentation

The manual lives in docs/ and is in three parts:

  • Guide — how arrest works. Architecture, the OpenAPI document, schemas, the security model, Express integration, errors.
  • Tutorial — a fifteen-chapter course building one application, from new API() to an MCP server and a production shape. The code is in examples/tutorial/ and type-checked in CI.
  • Reference — the complete surface, one page per module.

Start with the introduction if arrest is new to you, or with chapter 00 to build something immediately.

What else it does

  • RQL queryingq=and(eq(country,IT),gt(age,40)) translated to MongoDB, with an aggregation pipeline when needed
  • Authorization — scopes or CASL abilities, one decision reused by request enforcement, document filtering and MCP tool listing
  • Field and record redaction — declare fields and conditions once; responses are filtered and forbidden writes refused
  • MCP server — opt-in per resource, named bundles, per-tool descriptions and schemas
  • Output formats — JSON, JSONL and CSV from the same operation
  • JSON Patch — RFC 6902 translated to atomic MongoDB updates
  • The pipeline — seven override points between request and response
  • Custom operations and resourcesgetCustomInfo plus a handler, and you have a documented, validated, authorized endpoint
  • JSON-RPC@rpc-decorated methods on a single endpoint
  • Dynamic schemas and resources — schemas and MCP tools resolved per request

Contributing

Contributions are welcome. The project uses pnpm and requires 100% test coverage — statements, branches, functions and lines — which CI enforces.

pnpm install
pnpm run build
pnpm test                 # mocha; MongoDB tests start a container via mongodoki
pnpm run check-coverage   # must report 100%
pnpm run check:examples   # type-checks the tutorial application

Tests are written in TypeScript under test/ts/ and compiled before running. Commit with conventional commits, branch from master, and open a pull request.

License

MIT — see LICENSE.

Related projects

About

Swagger REST framework for Node.js, with support for MongoDB and JSON-Schema

Topics

Resources

Stars

18 stars

Watchers

9 watching

Forks

Releases

Packages

Used by

Contributors

Languages