Cloud launching May 2026. The library is MIT and shipping today.
kavachOS

Express quickstart

Express. Classic. Boring. Ships.

The Express adapter is for teams that already have a Node server and want to add real auth without rewriting. Nothing fancy, nothing breaking.

ExpressNode 20+ships today

Install

Install the core library and the Express adapter in one step.

terminalbash
pnpm add kavachos @kavachos/express

Configure the auth module

The Express adapter gives you a single middleware and a typed req.session. No magic, no decorators.

src/auth.tsts
import { createAuth } from "kavachos";
import { expressAdapter } from "@kavachos/express";
import { postgresAdapter } from "kavachos/adapters/postgres";
import { db } from "./db";

const auth = createAuth({
  secret: process.env.KAVACHOS_SECRET!,
  baseUrl: process.env.APP_URL!,
  database: postgresAdapter(db),
  providers: [
    { id: "github", clientId: process.env.GITHUB_ID!, clientSecret: process.env.GITHUB_SECRET! },
  ],
});

export const { router, middleware, agents } = expressAdapter(auth);

Mount the router and middleware

Mount the adapter router under /auth, then add the session middleware to every protected route.

src/server.tsts
import express from "express";
import { router, middleware } from "./auth";

const app = express();

app.use("/auth", router);
app.use("/dashboard", middleware.require());

app.get("/dashboard", (req, res) => {
  res.send(`hi ${req.session!.user.name}`);
});

app.listen(3000);

Typed request shape

Augment Express's Request type once, then req.session is fully typed across your codebase.

src/types.d.tsts
import type { Session } from "kavachos";

declare global {
  namespace Express {
    interface Request {
      session?: Session;
    }
  }
}

Issue an agent token

From any route with a session, create a narrow delegation for an agent worker.

src/routes/agents.tsts
import { Router } from "express";
import { agents, middleware } from "../auth";

export const agentsRouter = Router();

agentsRouter.post("/", middleware.require(), async (req, res) => {
  const parent = req.session!.subject.id;
  const agent = await agents.create({
    parent,
    name: "research.assistant",
    scopes: ["tools:call:search"],
    ttl: "15m",
  });
  const token = await agents.issueToken(agent.id, {
    audience: "https://your.mcp.server",
  });
  res.json({ token });
});

What is next

You have a working flow. Now pick the next layer based on what you are building: agent identity, MCP OAuth, SCIM, or enterprise SSO.

Ship the rest of the stack.

Library is open source. Cloud is in early access. Wire the next layer when you need it.