import type { StandardSchemaV1 } from "./standard-schema.ts"; export interface SchemaContext< B = unknown, Q = Record, P = Record, H = Record, > { body: B; query: Q; params: P; headers: H; } export interface Schemas< B = unknown, Q = Record, P = Record, H = Record, RI = never, RO = RI, > { body?: StandardSchemaV1; query?: StandardSchemaV1, Q>; params?: StandardSchemaV1, P>; headers?: StandardSchemaV1, H>; response?: StandardSchemaV1; } export type SchemaHandler = ( ctx: SchemaContext, ) => Response | Promise; type SchemaResponseHandler = (ctx: SchemaContext) => RI | Promise; type RequestSchemas< B = unknown, Q = Record, P = Record, H = Record, > = Omit, "response"> & { response?: undefined; }; type ResponseSchemas< B = unknown, Q = Record, P = Record, H = Record, RI = unknown, RO = RI, > = Schemas & { response: StandardSchemaV1; }; export type ValidationSource = "body" | "query" | "params" | "headers" | "response"; export interface SchemaAwareHandler< B = unknown, Q = Record, P = Record, H = Record, RI = never, RO = RI, > { readonly __ravenSchemaHandler: true; readonly schemas: Schemas; readonly handler: [RI] extends [never] ? SchemaHandler : SchemaResponseHandler; } export type AnySchemas = Schemas; export type AnySchemaAwareHandler = SchemaAwareHandler; export function withSchema( schemas: RequestSchemas, handler: SchemaHandler, ): SchemaAwareHandler; export function withSchema( schemas: ResponseSchemas, handler: SchemaResponseHandler, ): SchemaAwareHandler; export function withSchema( schemas: Schemas, handler: SchemaHandler | SchemaResponseHandler, ): SchemaAwareHandler { return { __ravenSchemaHandler: true, schemas, handler: handler as SchemaAwareHandler["handler"], }; } export function isSchemaAwareHandler(value: unknown): value is AnySchemaAwareHandler { return ( typeof value === "object" && value !== null && "__ravenSchemaHandler" in value && (value as { __ravenSchemaHandler?: boolean }).__ravenSchemaHandler === true ); }