Skip to main content
Version: Next (2.x)

Context

The context object is shared across every resolver and middleware in a request. Use it for per-request state like auth, loaders, transport-specific helpers, or anything resolvers shouldn't reach for themselves.

Define the context type

Declare the shape your app needs:

src/types/context.ts
import type { PubSub } from "graphql-yoga";
import type { PubSubMap } from "../lib/pubsub.ts";

export type Context = {
userId?: string;
pubsub: PubSub<PubSubMap>;
};

export type ServerContext = {};

Wire it up

Baeta picks up the context type from the Ctx alias in src/modules/types.ts. Point it at your Context:

src/modules/types.ts
import type { Context } from "../types/context.ts";

export type Ctx = Context;

For everything else in that file, see Custom Types.

Using context in resolvers

ctx is fully typed:

const { Query } = UserModule;

const userQuery = Query.user.resolve(({ args, ctx }) => {
// ctx is typed as Context
return db.user.findUnique({
where: args.where,
});
});

Using context in middlewares

Middlewares get the same typed ctx:

const updateUserMutation = Mutation.updateUser
.$use(async (next, { ctx }) => {
// ctx is typed as Context
const result = await next();
ctx.pubsub.publish("user-updated", result);
return result;
})
.resolve(async ({ args }) => {
return db.user.update({ where: args.where, data: args.data });
});