title: 'GraphQL & Federation · Techniques' description: 'Guidance for running GraphQL servers, Apollo subgraphs, and Bun-based gateways.'

Techniques

GraphQL & Federation

Build monolith schemas or stitch multiple subgraphs without leaving Bun. Nael offers batteries-included modules for Apollo Federation v2, data loaders, persisted queries, and Better Auth-aware contexts.

Install the stack

Each example depends on @nl-framework/graphql plus the official Apollo subgraph runtime and Bun's HTTP integration layer.

Install GraphQL packages
bun add @nl-framework/graphql @apollo/subgraph @as-integrations/bun-http
Bun GraphQL server

Bootstrap a schema once and reuse across HTTP + WebSocket transports. The factory wires context objects, converters, and introspection defaults for you.

GraphQL module
const app = await NaelFactory.create(GraphQLModule.forRoot({  autoSchemaFile: join(process.cwd(), "schema.gql"),  playground: process.env.NODE_ENV !== "production",  context: ({ req, res }) => ({ req, res, requestId: randomUUID() }),  plugins: [BetterAuthGraphQLPlugin],}));await app.listen();
Subgraph composition

Use the federation helper to convert standard resolvers into reference resolvers. Schema directives and custom scalars are auto-registered via the module metadata.

Reference resolver
@Resolver(() => Fleet)export class FleetResolver {  constructor(private readonly service: FleetService) {}  @ResolveReference()  resolveReference(ref: FleetReference) {    return this.service.lookup(ref.id)  }}

Gateway best practices

The examples/federation-gateway folder demonstrates a Bun-native Apollo Gateway. Poll Uplink or self-hosted supergraphs and push tenant metadata through headers.

Gateway bootstrap
NaelFactory.create(FederationGatewayModule.forRoot({  supergraphSdl: readFileSync("./supergraph.graphql", "utf8"),  pollingInterval: 2000,  buildService: () => new RemoteGraphQLDataSource({    willSendRequest({ request, context }) {      request.http?.headers.set("x-tenant", context.tenantId)    },  }),}));
  • Attach BetterAuthGraphQLPlugin so user sessions flow across subgraphs.
  • Use DataLoaderFactory from @nl-framework/core to dedupe downstream fetches.
  • Emit schema.gql artifacts for contract testing via nl generate schema.
  • Enable persisted queries using the built-in Redis cache adapter.

Local dev workflow

  • Run bun run --cwd examples/federated-graphql dev to boot multiple subgraphs in watch mode.
  • Point the gateway to ./supergraph.example.graphql until Rover outputs the official build.
  • Use nl doctor --checks graphql to ensure SDL + router versions stay aligned.
  • Adopt the printSchemaWithDirectives helper when debugging custom directives.