Skip to Content

Handler Hooks

Custom route handlers are provided through the handlers field on OberonPlugin:

handlers?: Record< string, (adapter: OberonAdapter) => OberonHandler >

Each key in that record maps to the first CMS path segment.

Dispatch model

The Adapter dispatches Plugin HTTP requests by:

  • resolving the requested path
  • taking path[0] as the action key
  • looking up handlers[action]
  • selecting the method-specific handler such as GET or POST

If no action is present, the response is 404. If the action exists but does not implement the requested HTTP method, the response is 405.

OberonHandler

type OberonHandler = { [key in OberonMethod]?: (req: Request) => Promise<Response> | Response }

For plugin handlers used in Oberon, the practical shape is the no-params form:

  • keys are HTTP methods
  • each method receives the standard Web Request
  • methods return Response or Promise<Response>

Framework entrypoint

Each Framework integration projects the Adapter dispatch method into its native route-handler shape. Next.js routes export the methods returned by its integration:

import { createRestHandler } from "@oberoncms/plugin-nextjs" import { adapter } from "@/oberon/adapter" export const { GET, POST, PUT, PATCH, DELETE } = createRestHandler(adapter)

TanStack Start routes use its integration’s handler map directly:

import { createRestHandler } from "@oberoncms/plugin-tanstack" import { createFileRoute } from "@tanstack/react-router" export const Route = createFileRoute("/cms/api/$")({ server: { handlers: createRestHandler(adapter), }, })

Minimal handler example

import type { OberonPlugin } from "@oberoncms/core" export const plugin: OberonPlugin = () => ({ name: "health-plugin", handlers: { health: () => ({ GET: async () => Response.json({ ok: true }), }), }, })

That handler is mounted under the health action key and is reached through the CMS catch-all route when the first path segment is health.

Adapter passed to handler factories

Each factory is invoked once with the final OberonAdapter. It contains the composed Plugin capabilities and core-derived helpers such as can. Runtime requests reuse the returned Handler.

handlers: { asset: (adapter) => ({ GET: async () => Response.json(await adapter.getKV({ namespace: "my-plugin", key: "asset" })), }), }

Runtime and settings

  • prebuild
  • getSetting

Pages

  • addPage
  • deletePage
  • getAllPages
  • getAllPaths
  • getPageData
  • publishPageData

Images

  • addImage
  • deleteImage
  • getAllImages

Users and permissions

  • addUser
  • deleteUser
  • getAllUsers
  • changeRole
  • can
  • will
  • whoWill

Site and migrations

  • getConfig
  • migrateData

Auth

  • signIn
  • signOut

When to use handlers vs adapter hooks

Use adapter hooks when you are extending Oberon behavior itself. Use handlers when you need a CMS route endpoint keyed by a custom action segment.

Last updated on