@orpc/server
Advanced tools
Comparing version 0.0.0-next-20241123144325 to 0.0.0-next-20241126025042
import { | ||
createProcedureCaller, | ||
isProcedure | ||
} from "./chunk-26DTFWOI.js"; | ||
} from "./chunk-LYQ2OSU4.js"; | ||
@@ -16,2 +16,3 @@ // src/adapters/fetch.ts | ||
mapValues, | ||
resolvePromisableValue, | ||
trim | ||
@@ -554,2 +555,3 @@ } from "@orpc/shared"; | ||
const serializer = isORPCTransformer ? new ORPCSerializer() : new OpenAPISerializer({ accept }); | ||
const context = await resolvePromisableValue(requestOptions.context); | ||
const handler = async () => { | ||
@@ -631,5 +633,3 @@ const url = new URL(requestOptions.request.url); | ||
const caller = createProcedureCaller({ | ||
context: requestOptions.context, | ||
internal: false, | ||
validate: true, | ||
context, | ||
procedure, | ||
@@ -646,3 +646,3 @@ path | ||
try { | ||
return await options.hooks?.(requestOptions.context, { | ||
return await options.hooks?.(context, { | ||
next: handler, | ||
@@ -649,0 +649,0 @@ response: (response) => response |
@@ -8,3 +8,3 @@ import { | ||
mergeContext | ||
} from "./chunk-26DTFWOI.js"; | ||
} from "./chunk-LYQ2OSU4.js"; | ||
@@ -34,3 +34,3 @@ // src/builder.ts | ||
} | ||
handler(handler) { | ||
func(func) { | ||
return decorateProcedure({ | ||
@@ -40,3 +40,3 @@ zz$p: { | ||
contract: this.zz$pi.contract, | ||
handler | ||
func | ||
} | ||
@@ -96,3 +96,3 @@ }); | ||
*/ | ||
handler(handler) { | ||
func(func) { | ||
return decorateProcedure({ | ||
@@ -102,3 +102,3 @@ zz$p: { | ||
contract: this.zz$pb.contract, | ||
handler | ||
func | ||
} | ||
@@ -282,3 +282,3 @@ }); | ||
*/ | ||
handler(handler) { | ||
func(func) { | ||
return decorateProcedure({ | ||
@@ -291,3 +291,3 @@ zz$p: { | ||
}), | ||
handler | ||
func | ||
} | ||
@@ -360,4 +360,2 @@ }); | ||
function createRouterCaller(options) { | ||
const internal = options.internal ?? true; | ||
const validate = options.validate ?? true; | ||
const caller = {}; | ||
@@ -371,5 +369,3 @@ for (const key in options.router) { | ||
context: options.context, | ||
path, | ||
internal, | ||
validate | ||
path | ||
}); | ||
@@ -380,5 +376,3 @@ } else { | ||
context: options.context, | ||
basePath: path, | ||
internal, | ||
validate | ||
basePath: path | ||
}); | ||
@@ -385,0 +379,0 @@ } |
@@ -1,2 +0,2 @@ | ||
import type { PartialOnUndefinedDeep, Promisable } from '@orpc/shared'; | ||
import type { PartialOnUndefinedDeep, Promisable, PromisableValue } from '@orpc/shared'; | ||
import type { Router } from '../router'; | ||
@@ -37,3 +37,3 @@ export interface FetchHandlerHooks { | ||
*/ | ||
context: TRouter extends Router<infer UContext> ? UContext : never; | ||
context: PromisableValue<TRouter extends Router<infer UContext> ? UContext : never>; | ||
}>; | ||
@@ -40,0 +40,0 @@ export interface FetchHandler<TRouter extends Router<any>> { |
@@ -6,3 +6,3 @@ import type { IsEqual } from '@orpc/shared'; | ||
import { type DecoratedMiddleware, type MapInputMiddleware, type Middleware } from './middleware'; | ||
import { type DecoratedProcedure, type ProcedureHandler } from './procedure'; | ||
import { type DecoratedProcedure, type ProcedureFunc } from './procedure'; | ||
import { ProcedureBuilder } from './procedure-builder'; | ||
@@ -34,3 +34,3 @@ import { ProcedureImplementer } from './procedure-implementer'; | ||
*/ | ||
handler<UHandlerOutput = undefined>(handler: ProcedureHandler<TContext, TExtraContext, undefined, undefined, UHandlerOutput>): DecoratedProcedure<TContext, TExtraContext, undefined, undefined, UHandlerOutput>; | ||
func<UFuncOutput = undefined>(func: ProcedureFunc<TContext, TExtraContext, undefined, undefined, UFuncOutput>): DecoratedProcedure<TContext, TExtraContext, undefined, undefined, UFuncOutput>; | ||
/** | ||
@@ -37,0 +37,0 @@ * Convert to ProcedureImplementer | RouterBuilder |
import type { MapInputMiddleware, Middleware } from './middleware'; | ||
import type { Context, MergeContext } from './types'; | ||
import { type ContractProcedure, type RouteOptions, type Schema, type SchemaInput, type SchemaOutput } from '@orpc/contract'; | ||
import { type DecoratedProcedure, type ProcedureHandler } from './procedure'; | ||
import { type DecoratedProcedure, type ProcedureFunc } from './procedure'; | ||
import { ProcedureImplementer } from './procedure-implementer'; | ||
@@ -29,4 +29,4 @@ export declare class ProcedureBuilder<TContext extends Context, TExtraContext extends Context, TInputSchema extends Schema, TOutputSchema extends Schema> { | ||
*/ | ||
handler<UHandlerOutput extends SchemaOutput<TOutputSchema>>(handler: ProcedureHandler<TContext, TExtraContext, TInputSchema, TOutputSchema, UHandlerOutput>): DecoratedProcedure<TContext, TExtraContext, TInputSchema, TOutputSchema, UHandlerOutput>; | ||
func<UFuncOutput extends SchemaOutput<TOutputSchema>>(func: ProcedureFunc<TContext, TExtraContext, TInputSchema, TOutputSchema, UFuncOutput>): DecoratedProcedure<TContext, TExtraContext, TInputSchema, TOutputSchema, UFuncOutput>; | ||
} | ||
//# sourceMappingURL=procedure-builder.d.ts.map |
import type { SchemaInput, SchemaOutput } from '@orpc/contract'; | ||
import type { Procedure } from './procedure'; | ||
export interface CreateProcedureCallerOptions<TProcedure extends Procedure<any, any, any, any, any>, TValidate extends boolean> { | ||
import { type PromisableValue } from '@orpc/shared'; | ||
export interface CreateProcedureCallerOptions<TProcedure extends Procedure<any, any, any, any, any>> { | ||
procedure: TProcedure; | ||
@@ -8,22 +9,12 @@ /** | ||
*/ | ||
context: TProcedure extends Procedure<infer UContext, any, any, any, any> ? UContext : never; | ||
context: PromisableValue<TProcedure extends Procedure<infer UContext, any, any, any, any> ? UContext : never>; | ||
/** | ||
* This is helpful for logging and analytics. | ||
* | ||
* @internal | ||
*/ | ||
path?: string[]; | ||
/** | ||
* This flag helpful when you want bypass some logics not necessary to internal server calls. | ||
* | ||
* @default true | ||
*/ | ||
internal?: boolean; | ||
/** | ||
* Indicate whether validate input and output. | ||
* | ||
* @default true | ||
*/ | ||
validate?: TValidate; | ||
} | ||
export type ProcedureCaller<TProcedure extends Procedure<any, any, any, any, any>, TValidate extends boolean> = TProcedure extends Procedure<any, any, infer UInputSchema, infer UOutputSchema, infer UHandlerOutput> ? (input: TValidate extends true ? SchemaInput<UInputSchema> : SchemaOutput<UInputSchema>) => Promise<TValidate extends true ? SchemaOutput<UOutputSchema, UHandlerOutput> : SchemaInput<UOutputSchema, UHandlerOutput>> : never; | ||
export declare function createProcedureCaller<TProcedure extends Procedure<any, any, any, any, any>, TValidate extends boolean = true>(options: CreateProcedureCallerOptions<TProcedure, TValidate>): ProcedureCaller<TProcedure, TValidate>; | ||
export type ProcedureCaller<TProcedure extends Procedure<any, any, any, any, any>> = TProcedure extends Procedure<any, any, infer UInputSchema, infer UOutputSchema, infer UFuncOutput> ? (input: SchemaInput<UInputSchema> | FormData) => Promise<SchemaOutput<UOutputSchema, UFuncOutput>> : never; | ||
export declare function createProcedureCaller<TProcedure extends Procedure<any, any, any, any, any>>(options: CreateProcedureCallerOptions<TProcedure>): ProcedureCaller<TProcedure>; | ||
//# sourceMappingURL=procedure-caller.d.ts.map |
import type { ContractProcedure, Schema, SchemaInput, SchemaOutput } from '@orpc/contract'; | ||
import type { Context, MergeContext } from './types'; | ||
import { type MapInputMiddleware, type Middleware } from './middleware'; | ||
import { type DecoratedProcedure, type ProcedureHandler } from './procedure'; | ||
import { type DecoratedProcedure, type ProcedureFunc } from './procedure'; | ||
export declare class ProcedureImplementer<TContext extends Context, TExtraContext extends Context, TInputSchema extends Schema, TOutputSchema extends Schema> { | ||
@@ -16,4 +16,4 @@ zz$pi: { | ||
use<UExtraContext extends Partial<MergeContext<Context, MergeContext<TContext, TExtraContext>>> | undefined = undefined, UMappedInput = unknown>(middleware: Middleware<MergeContext<TContext, TExtraContext>, UExtraContext, UMappedInput, SchemaInput<TOutputSchema>>, mapInput: MapInputMiddleware<SchemaOutput<TInputSchema>, UMappedInput>): ProcedureImplementer<TContext, MergeContext<TExtraContext, UExtraContext>, TInputSchema, TOutputSchema>; | ||
handler<UHandlerOutput extends SchemaOutput<TOutputSchema>>(handler: ProcedureHandler<TContext, TExtraContext, TInputSchema, TOutputSchema, UHandlerOutput>): DecoratedProcedure<TContext, TExtraContext, TInputSchema, TOutputSchema, UHandlerOutput>; | ||
func<UFuncOutput extends SchemaOutput<TOutputSchema>>(func: ProcedureFunc<TContext, TExtraContext, TInputSchema, TOutputSchema, UFuncOutput>): DecoratedProcedure<TContext, TExtraContext, TInputSchema, TOutputSchema, UFuncOutput>; | ||
} | ||
//# sourceMappingURL=procedure-implementer.d.ts.map |
import type { Promisable } from '@orpc/shared'; | ||
import type { ProcedureCaller } from './procedure-caller'; | ||
import type { Context, MergeContext, Meta } from './types'; | ||
import { type ContractProcedure, type HTTPPath, type RouteOptions, type Schema, type SchemaInput, type SchemaOutput } from '@orpc/contract'; | ||
import { type MapInputMiddleware, type Middleware } from './middleware'; | ||
export declare class Procedure<TContext extends Context, TExtraContext extends Context, TInputSchema extends Schema, TOutputSchema extends Schema, THandlerOutput extends SchemaOutput<TOutputSchema>> { | ||
export declare class Procedure<TContext extends Context, TExtraContext extends Context, TInputSchema extends Schema, TOutputSchema extends Schema, TFuncOutput extends SchemaOutput<TOutputSchema>> { | ||
zz$p: { | ||
middlewares?: Middleware<any, any, any, any>[]; | ||
contract: ContractProcedure<TInputSchema, TOutputSchema>; | ||
handler: ProcedureHandler<TContext, TExtraContext, TInputSchema, TOutputSchema, THandlerOutput>; | ||
func: ProcedureFunc<TContext, TExtraContext, TInputSchema, TOutputSchema, TFuncOutput>; | ||
}; | ||
@@ -14,16 +15,16 @@ constructor(zz$p: { | ||
contract: ContractProcedure<TInputSchema, TOutputSchema>; | ||
handler: ProcedureHandler<TContext, TExtraContext, TInputSchema, TOutputSchema, THandlerOutput>; | ||
func: ProcedureFunc<TContext, TExtraContext, TInputSchema, TOutputSchema, TFuncOutput>; | ||
}); | ||
} | ||
export type DecoratedProcedure<TContext extends Context, TExtraContext extends Context, TInputSchema extends Schema, TOutputSchema extends Schema, THandlerOutput extends SchemaOutput<TOutputSchema>> = Procedure<TContext, TExtraContext, TInputSchema, TOutputSchema, THandlerOutput> & { | ||
prefix: (prefix: HTTPPath) => DecoratedProcedure<TContext, TExtraContext, TInputSchema, TOutputSchema, THandlerOutput>; | ||
route: (opts: RouteOptions) => DecoratedProcedure<TContext, TExtraContext, TInputSchema, TOutputSchema, THandlerOutput>; | ||
use: (<UExtraContext extends Partial<MergeContext<Context, MergeContext<TContext, TExtraContext>>> | undefined = undefined>(middleware: Middleware<MergeContext<TContext, TExtraContext>, UExtraContext, SchemaOutput<TInputSchema>, SchemaInput<TOutputSchema, THandlerOutput>>) => DecoratedProcedure<TContext, MergeContext<TExtraContext, UExtraContext>, TInputSchema, TOutputSchema, THandlerOutput>) & (<UExtraContext extends Partial<MergeContext<Context, MergeContext<TContext, TExtraContext>>> | undefined = undefined, UMappedInput = unknown>(middleware: Middleware<MergeContext<TContext, TExtraContext>, UExtraContext, UMappedInput, SchemaInput<TOutputSchema, THandlerOutput>>, mapInput: MapInputMiddleware<SchemaOutput<TInputSchema, THandlerOutput>, UMappedInput>) => DecoratedProcedure<TContext, MergeContext<TExtraContext, UExtraContext>, TInputSchema, TOutputSchema, THandlerOutput>); | ||
} & (undefined extends TContext ? (input: SchemaInput<TInputSchema> | FormData) => Promise<SchemaOutput<TOutputSchema, THandlerOutput>> : unknown); | ||
export interface ProcedureHandler<TContext extends Context, TExtraContext extends Context, TInputSchema extends Schema, TOutputSchema extends Schema, TOutput extends SchemaOutput<TOutputSchema>> { | ||
export type DecoratedProcedure<TContext extends Context, TExtraContext extends Context, TInputSchema extends Schema, TOutputSchema extends Schema, TFuncOutput extends SchemaOutput<TOutputSchema>> = Procedure<TContext, TExtraContext, TInputSchema, TOutputSchema, TFuncOutput> & { | ||
prefix: (prefix: HTTPPath) => DecoratedProcedure<TContext, TExtraContext, TInputSchema, TOutputSchema, TFuncOutput>; | ||
route: (opts: RouteOptions) => DecoratedProcedure<TContext, TExtraContext, TInputSchema, TOutputSchema, TFuncOutput>; | ||
use: (<UExtraContext extends Partial<MergeContext<Context, MergeContext<TContext, TExtraContext>>> | undefined = undefined>(middleware: Middleware<MergeContext<TContext, TExtraContext>, UExtraContext, SchemaOutput<TInputSchema>, SchemaInput<TOutputSchema, TFuncOutput>>) => DecoratedProcedure<TContext, MergeContext<TExtraContext, UExtraContext>, TInputSchema, TOutputSchema, TFuncOutput>) & (<UExtraContext extends Partial<MergeContext<Context, MergeContext<TContext, TExtraContext>>> | undefined = undefined, UMappedInput = unknown>(middleware: Middleware<MergeContext<TContext, TExtraContext>, UExtraContext, UMappedInput, SchemaInput<TOutputSchema, TFuncOutput>>, mapInput: MapInputMiddleware<SchemaOutput<TInputSchema, TFuncOutput>, UMappedInput>) => DecoratedProcedure<TContext, MergeContext<TExtraContext, UExtraContext>, TInputSchema, TOutputSchema, TFuncOutput>); | ||
} & (undefined extends TContext ? ProcedureCaller<Procedure<TContext, TExtraContext, TInputSchema, TOutputSchema, TFuncOutput>> : unknown); | ||
export interface ProcedureFunc<TContext extends Context, TExtraContext extends Context, TInputSchema extends Schema, TOutputSchema extends Schema, TOutput extends SchemaOutput<TOutputSchema>> { | ||
(input: SchemaOutput<TInputSchema>, context: MergeContext<TContext, TExtraContext>, meta: Meta): Promisable<SchemaInput<TOutputSchema, TOutput>>; | ||
} | ||
export declare function decorateProcedure<TContext extends Context, TExtraContext extends Context, TInputSchema extends Schema, TOutputSchema extends Schema, THandlerOutput extends SchemaOutput<TOutputSchema>>(procedure: Procedure<TContext, TExtraContext, TInputSchema, TOutputSchema, THandlerOutput>): DecoratedProcedure<TContext, TExtraContext, TInputSchema, TOutputSchema, THandlerOutput>; | ||
export declare function decorateProcedure<TContext extends Context, TExtraContext extends Context, TInputSchema extends Schema, TOutputSchema extends Schema, TFuncOutput extends SchemaOutput<TOutputSchema>>(procedure: Procedure<TContext, TExtraContext, TInputSchema, TOutputSchema, TFuncOutput>): DecoratedProcedure<TContext, TExtraContext, TInputSchema, TOutputSchema, TFuncOutput>; | ||
export type WELL_DEFINED_PROCEDURE = Procedure<Context, Context, Schema, Schema, unknown>; | ||
export declare function isProcedure(item: unknown): item is WELL_DEFINED_PROCEDURE; | ||
//# sourceMappingURL=procedure.d.ts.map |
@@ -0,5 +1,6 @@ | ||
import type { PromisableValue } from '@orpc/shared'; | ||
import type { Router } from './router'; | ||
import { type Procedure } from './procedure'; | ||
import { type ProcedureCaller } from './procedure-caller'; | ||
export interface CreateRouterCallerOptions<TRouter extends Router<any>, TValidate extends boolean> { | ||
export interface CreateRouterCallerOptions<TRouter extends Router<any>> { | ||
router: TRouter; | ||
@@ -9,24 +10,14 @@ /** | ||
*/ | ||
context: TRouter extends Router<infer UContext> ? UContext : never; | ||
context: PromisableValue<TRouter extends Router<infer UContext> ? UContext : never>; | ||
/** | ||
* This is helpful for logging and analytics. | ||
* | ||
* @internal | ||
*/ | ||
basePath?: string[]; | ||
/** | ||
* This flag helpful when you want bypass some logics not necessary to internal server calls. | ||
* | ||
* @default true | ||
*/ | ||
internal?: boolean; | ||
/** | ||
* Indicate whether validate input and output. | ||
* | ||
* @default true | ||
*/ | ||
validate?: TValidate; | ||
} | ||
export type RouterCaller<TRouter extends Router<any>, TValidate extends boolean> = { | ||
[K in keyof TRouter]: TRouter[K] extends Procedure<any, any, any, any, any> ? ProcedureCaller<TRouter[K], TValidate> : TRouter[K] extends Router<any> ? RouterCaller<TRouter[K], TValidate> : never; | ||
export type RouterCaller<TRouter extends Router<any>> = { | ||
[K in keyof TRouter]: TRouter[K] extends Procedure<any, any, any, any, any> ? ProcedureCaller<TRouter[K]> : TRouter[K] extends Router<any> ? RouterCaller<TRouter[K]> : never; | ||
}; | ||
export declare function createRouterCaller<TRouter extends Router<any>, TValidate extends boolean = true>(options: CreateRouterCallerOptions<TRouter, TValidate>): RouterCaller<TRouter, TValidate>; | ||
export declare function createRouterCaller<TRouter extends Router<any>>(options: CreateRouterCallerOptions<TRouter>): RouterCaller<TRouter>; | ||
//# sourceMappingURL=router-caller.d.ts.map |
@@ -8,3 +8,3 @@ import type { ContractProcedure, ContractRouter, SchemaInput, SchemaOutput } from '@orpc/contract'; | ||
export type HandledRouter<TRouter extends Router<any>> = { | ||
[K in keyof TRouter]: TRouter[K] extends Procedure<infer UContext, infer UExtraContext, infer UInputSchema, infer UOutputSchema, infer UHandlerOutput> ? DecoratedProcedure<UContext, UExtraContext, UInputSchema, UOutputSchema, UHandlerOutput> : TRouter[K] extends Router<any> ? HandledRouter<TRouter[K]> : never; | ||
[K in keyof TRouter]: TRouter[K] extends Procedure<infer UContext, infer UExtraContext, infer UInputSchema, infer UOutputSchema, infer UFuncOutput> ? DecoratedProcedure<UContext, UExtraContext, UInputSchema, UOutputSchema, UFuncOutput> : TRouter[K] extends Router<any> ? HandledRouter<TRouter[K]> : never; | ||
}; | ||
@@ -19,4 +19,4 @@ export type RouterWithContract<TContext extends Context, TContract extends ContractRouter> = { | ||
export type InferRouterOutputs<T extends Router<any>> = { | ||
[K in keyof T]: T[K] extends Procedure<any, any, any, infer UOutputSchema, infer UHandlerOutput> ? SchemaOutput<UOutputSchema, UHandlerOutput> : T[K] extends Router<any> ? InferRouterOutputs<T[K]> : never; | ||
[K in keyof T]: T[K] extends Procedure<any, any, any, infer UOutputSchema, infer UFuncOutput> ? SchemaOutput<UOutputSchema, UFuncOutput> : T[K] extends Router<any> ? InferRouterOutputs<T[K]> : never; | ||
}; | ||
//# sourceMappingURL=router.d.ts.map |
@@ -6,5 +6,4 @@ import type { WELL_DEFINED_PROCEDURE } from './procedure'; | ||
path: string[]; | ||
internal: boolean; | ||
procedure: WELL_DEFINED_PROCEDURE; | ||
} | ||
//# sourceMappingURL=types.d.ts.map |
{ | ||
"name": "@orpc/server", | ||
"type": "module", | ||
"version": "0.0.0-next-20241123144325", | ||
"version": "0.0.0-next-20241126025042", | ||
"author": { | ||
@@ -43,5 +43,5 @@ "name": "unnoq", | ||
"dependencies": { | ||
"@orpc/contract": "0.0.0-next-20241123144325", | ||
"@orpc/shared": "0.0.5", | ||
"@orpc/transformer": "0.0.4" | ||
"@orpc/contract": "0.0.0-next-20241126025042", | ||
"@orpc/shared": "0.0.0-next-20241126025042", | ||
"@orpc/transformer": "0.0.0-next-20241126025042" | ||
}, | ||
@@ -48,0 +48,0 @@ "devDependencies": { |
@@ -9,9 +9,9 @@ import { ORPC_HEADER, ORPC_HEADER_VALUE } from '@orpc/contract' | ||
const router = os.router({ | ||
throw: os.handler(() => { | ||
throw: os.func(() => { | ||
throw new Error('test') | ||
}), | ||
ping: os.handler(() => { | ||
ping: os.func(() => { | ||
return 'ping' | ||
}), | ||
ping2: os.route({ method: 'GET', path: '/ping2' }).handler(() => { | ||
ping2: os.route({ method: 'GET', path: '/ping2' }).func(() => { | ||
return 'ping2' | ||
@@ -26,6 +26,6 @@ }), | ||
const router = osw.router({ | ||
ping: osw.handler(async () => 'pong'), | ||
ping: osw.func(async () => 'pong'), | ||
ping2: osw | ||
.route({ method: 'GET', path: '/ping2' }) | ||
.handler(async () => 'pong2'), | ||
.func(async () => 'pong2'), | ||
}) | ||
@@ -42,3 +42,3 @@ const handler = createFetchHandler({ | ||
}), | ||
context: { auth: true }, | ||
context: () => ({ auth: true }), | ||
}) | ||
@@ -109,3 +109,3 @@ | ||
const router = os.router({ | ||
ping: os.handler(() => { | ||
ping: os.func(() => { | ||
throw new ORPCError({ code: 'TIMEOUT' }) | ||
@@ -131,3 +131,3 @@ }), | ||
const router = os.router({ | ||
ping: os.handler(() => { | ||
ping: os.func(() => { | ||
throw new ORPCError({ | ||
@@ -158,3 +158,3 @@ code: 'PAYLOAD_TOO_LARGE', | ||
const router = os.router({ | ||
ping: os.handler(() => { | ||
ping: os.func(() => { | ||
throw new ORPCError({ | ||
@@ -166,3 +166,3 @@ code: 'PAYLOAD_TOO_LARGE', | ||
ping2: os.handler(() => { | ||
ping2: os.func(() => { | ||
throw new ORPCError({ | ||
@@ -205,3 +205,3 @@ code: 'PAYLOAD_TOO_LARGE', | ||
.output(z.string()) | ||
.handler(() => { | ||
.func(() => { | ||
return 'unnoq' | ||
@@ -239,3 +239,3 @@ }), | ||
.output(z.string()) | ||
.handler(() => { | ||
.func(() => { | ||
return 12344 as any | ||
@@ -344,3 +344,3 @@ }), | ||
const router = os.router({ | ||
signal: os.input(z.instanceof(Blob)).handler((input) => { | ||
signal: os.input(z.instanceof(Blob)).func((input) => { | ||
return input | ||
@@ -352,3 +352,3 @@ }), | ||
) | ||
.handler((input) => { | ||
.func((input) => { | ||
return input | ||
@@ -430,3 +430,3 @@ }), | ||
const router = os.router({ | ||
ping: os.handler(async () => 'pong'), | ||
ping: os.func(async () => 'pong'), | ||
}) | ||
@@ -540,3 +540,3 @@ const handler = createFetchHandler({ | ||
) | ||
.handler(input => input), | ||
.func(input => input), | ||
@@ -553,3 +553,3 @@ find: os | ||
) | ||
.handler(input => input), | ||
.func(input => input), | ||
}) | ||
@@ -608,3 +608,3 @@ | ||
) | ||
.handler(input => input), | ||
.func(input => input), | ||
}) | ||
@@ -611,0 +611,0 @@ |
@@ -6,2 +6,3 @@ /// <reference lib="dom" /> | ||
Promisable, | ||
PromisableValue, | ||
} from '@orpc/shared' | ||
@@ -19,2 +20,3 @@ import type { Router } from '../router' | ||
mapValues, | ||
resolvePromisableValue, | ||
trim, | ||
@@ -96,2 +98,4 @@ } from '@orpc/shared' | ||
const context = await resolvePromisableValue(requestOptions.context) | ||
const handler = async () => { | ||
@@ -202,5 +206,3 @@ const url = new URL(requestOptions.request.url) | ||
const caller = createProcedureCaller({ | ||
context: requestOptions.context, | ||
internal: false, | ||
validate: true, | ||
context, | ||
procedure, | ||
@@ -221,3 +223,3 @@ path, | ||
try { | ||
return await options.hooks?.(requestOptions.context as any, { | ||
return await options.hooks?.(context as any, { | ||
next: handler, | ||
@@ -276,3 +278,5 @@ response: response => response, | ||
*/ | ||
context: TRouter extends Router<infer UContext> ? UContext : never | ||
context: PromisableValue< | ||
TRouter extends Router<infer UContext> ? UContext : never | ||
> | ||
}> | ||
@@ -279,0 +283,0 @@ |
@@ -77,3 +77,3 @@ import type { | ||
) | ||
.handler((_, context) => { | ||
.func((_, context) => { | ||
expectTypeOf(context).toMatchTypeOf<{ user: string }>() | ||
@@ -149,3 +149,3 @@ }) | ||
expect( | ||
osw.router.handler(() => { | ||
osw.router.func(() => { | ||
return { name: '' } | ||
@@ -291,3 +291,3 @@ }), | ||
const procedure = osw.handler((input, context, meta) => { | ||
const procedure = osw.func((input, context, meta) => { | ||
expectTypeOf(input).toEqualTypeOf<unknown>() | ||
@@ -323,3 +323,3 @@ expectTypeOf(context).toEqualTypeOf<{ auth: boolean }>() | ||
const procedure = osw.handler((input, context, meta) => { | ||
const procedure = osw.func((input, context, meta) => { | ||
expectTypeOf(input).toEqualTypeOf<unknown>() | ||
@@ -326,0 +326,0 @@ expectTypeOf(context).toMatchTypeOf<{ auth: boolean }>() |
@@ -23,3 +23,3 @@ import type { IsEqual } from '@orpc/shared' | ||
decorateProcedure, | ||
type ProcedureHandler, | ||
type ProcedureFunc, | ||
} from './procedure' | ||
@@ -141,4 +141,4 @@ import { ProcedureBuilder } from './procedure-builder' | ||
*/ | ||
handler<UHandlerOutput = undefined>( | ||
handler: ProcedureHandler< | ||
func<UFuncOutput = undefined>( | ||
func: ProcedureFunc< | ||
TContext, | ||
@@ -148,3 +148,3 @@ TExtraContext, | ||
undefined, | ||
UHandlerOutput | ||
UFuncOutput | ||
>, | ||
@@ -156,3 +156,3 @@ ): DecoratedProcedure< | ||
undefined, | ||
UHandlerOutput | ||
UFuncOutput | ||
> { | ||
@@ -166,3 +166,3 @@ return decorateProcedure({ | ||
}), | ||
handler, | ||
func, | ||
}, | ||
@@ -169,0 +169,0 @@ }) |
@@ -252,3 +252,3 @@ import type { DecoratedMiddleware, Middleware, MiddlewareMeta } from './middleware' | ||
}) | ||
.handler(() => { | ||
.func(() => { | ||
handlerCalled = true | ||
@@ -255,0 +255,0 @@ return 'from handler' |
@@ -166,3 +166,3 @@ import type { MiddlewareMeta } from './middleware' | ||
it('infer types', () => { | ||
const handler = builder.handler((input, context, meta) => { | ||
const handler = builder.func((input, context, meta) => { | ||
expectTypeOf(input).toEqualTypeOf<unknown>() | ||
@@ -200,3 +200,3 @@ expectTypeOf(context).toEqualTypeOf<{ auth: boolean }>() | ||
.use(mid2) | ||
.handler((input, context, meta) => { | ||
.func((input, context, meta) => { | ||
expectTypeOf(input).toEqualTypeOf<unknown>() | ||
@@ -203,0 +203,0 @@ expectTypeOf(context).toEqualTypeOf< |
@@ -14,3 +14,3 @@ import type { MapInputMiddleware, Middleware } from './middleware' | ||
decorateProcedure, | ||
type ProcedureHandler, | ||
type ProcedureFunc, | ||
} from './procedure' | ||
@@ -136,4 +136,4 @@ import { ProcedureImplementer } from './procedure-implementer' | ||
handler<UHandlerOutput extends SchemaOutput<TOutputSchema>>( | ||
handler: ProcedureHandler< | ||
func<UFuncOutput extends SchemaOutput<TOutputSchema>>( | ||
func: ProcedureFunc< | ||
TContext, | ||
@@ -143,3 +143,3 @@ TExtraContext, | ||
TOutputSchema, | ||
UHandlerOutput | ||
UFuncOutput | ||
>, | ||
@@ -151,3 +151,3 @@ ): DecoratedProcedure< | ||
TOutputSchema, | ||
UHandlerOutput | ||
UFuncOutput | ||
> { | ||
@@ -158,3 +158,3 @@ return decorateProcedure({ | ||
contract: this.zz$pb.contract, | ||
handler, | ||
func, | ||
}, | ||
@@ -161,0 +161,0 @@ }) |
@@ -5,5 +5,4 @@ import { z } from 'zod' | ||
describe('createProcedureCaller', () => { | ||
let internal = false | ||
let path = ['ping'] | ||
let context = { auth: true } | ||
const path = ['ping'] | ||
const context = { auth: true } | ||
@@ -14,5 +13,4 @@ const osw = os.context<{ auth?: boolean }>() | ||
.output(z.object({ value: z.number().transform(v => v.toString()) })) | ||
.handler((input, context, meta) => { | ||
.func((input, context, meta) => { | ||
expect(context).toEqual(context) | ||
expect(meta.internal).toBe(internal) | ||
expect(meta.path).toBe(path) | ||
@@ -39,4 +37,3 @@ | ||
procedure, | ||
context, | ||
internal, | ||
context: async () => context, | ||
path, | ||
@@ -59,29 +56,4 @@ }) | ||
it('without validate', async () => { | ||
internal = true | ||
path = [] | ||
context = { auth: false } | ||
const caller = createProcedureCaller({ | ||
procedure, | ||
context, | ||
internal, | ||
path, | ||
validate: false, | ||
}) | ||
expectTypeOf(caller).toMatchTypeOf< | ||
(input: { value: number }) => Promise<{ | ||
value: number | ||
}> | ||
>() | ||
expect(await caller({ value: 123 })).toEqual({ value: 123 }) | ||
// @ts-expect-error it's not validate so bellow still works | ||
expect(await caller({ value: '123' })).toEqual({ value: '123' }) | ||
}) | ||
it('without validate and schema', () => { | ||
const procedure = osw.handler(() => { | ||
const procedure = osw.func(() => { | ||
return { value: true } | ||
@@ -93,4 +65,2 @@ }) | ||
context, | ||
internal, | ||
validate: false, | ||
}) | ||
@@ -154,3 +124,3 @@ | ||
.use(mid2) | ||
.handler((input, context, meta) => { | ||
.func((input, context, meta) => { | ||
expect(context).toEqual({ userId: '1', auth: false }) | ||
@@ -171,2 +141,23 @@ | ||
}) | ||
it('accept form data', async () => { | ||
const ping = osw | ||
.input(z.object({ id: z.number() })) | ||
.output(z.object({ id: z.number() })) | ||
.func((input, context, meta) => { | ||
expect(context).toEqual(context) | ||
return input | ||
}) | ||
const caller = createProcedureCaller({ | ||
procedure: ping, | ||
context, | ||
}) | ||
const form = new FormData() | ||
form.append('id', '1') | ||
expect(await caller(form)).toEqual({ id: 1 }) | ||
}) | ||
}) |
@@ -5,3 +5,5 @@ import type { SchemaInput, SchemaOutput } from '@orpc/contract' | ||
import type { Context } from './types' | ||
import { type PromisableValue, resolvePromisableValue } from '@orpc/shared' | ||
import { ORPCError } from '@orpc/shared/error' | ||
import { OpenAPIDeserializer } from '@orpc/transformer' | ||
import { mergeContext } from './utils' | ||
@@ -11,3 +13,2 @@ | ||
TProcedure extends Procedure<any, any, any, any, any>, | ||
TValidate extends boolean, | ||
> { | ||
@@ -19,24 +20,14 @@ procedure: TProcedure | ||
*/ | ||
context: TProcedure extends Procedure<infer UContext, any, any, any, any> | ||
? UContext | ||
: never | ||
context: PromisableValue< | ||
TProcedure extends Procedure<infer UContext, any, any, any, any> | ||
? UContext | ||
: never | ||
> | ||
/** | ||
* This is helpful for logging and analytics. | ||
* | ||
* @internal | ||
*/ | ||
path?: string[] | ||
/** | ||
* This flag helpful when you want bypass some logics not necessary to internal server calls. | ||
* | ||
* @default true | ||
*/ | ||
internal?: boolean | ||
/** | ||
* Indicate whether validate input and output. | ||
* | ||
* @default true | ||
*/ | ||
validate?: TValidate | ||
} | ||
@@ -46,3 +37,2 @@ | ||
TProcedure extends Procedure<any, any, any, any, any>, | ||
TValidate extends boolean, | ||
> = TProcedure extends Procedure< | ||
@@ -53,12 +43,8 @@ any, | ||
infer UOutputSchema, | ||
infer UHandlerOutput | ||
infer UFuncOutput | ||
> | ||
? ( | ||
input: TValidate extends true | ||
? SchemaInput<UInputSchema> | ||
: SchemaOutput<UInputSchema>, | ||
input: SchemaInput<UInputSchema> | FormData, | ||
) => Promise< | ||
TValidate extends true | ||
? SchemaOutput<UOutputSchema, UHandlerOutput> | ||
: SchemaInput<UOutputSchema, UHandlerOutput> | ||
SchemaOutput<UOutputSchema, UFuncOutput> | ||
> | ||
@@ -69,21 +55,29 @@ : never | ||
TProcedure extends Procedure<any, any, any, any, any>, | ||
TValidate extends boolean = true, | ||
>( | ||
options: CreateProcedureCallerOptions<TProcedure, TValidate>, | ||
): ProcedureCaller<TProcedure, TValidate> { | ||
const internal = options.internal ?? true | ||
options: CreateProcedureCallerOptions<TProcedure>, | ||
): ProcedureCaller<TProcedure> { | ||
const path = options.path ?? [] | ||
const procedure = options.procedure | ||
const validate = options.validate ?? true | ||
const caller = async (input: unknown): Promise<unknown> => { | ||
const input_ = (() => { | ||
if (!(input instanceof FormData)) { | ||
return input | ||
} | ||
const transformer = new OpenAPIDeserializer({ | ||
schema: procedure.zz$p.contract.zz$cp.InputSchema, | ||
}) | ||
return transformer.deserializeAsFormData(input) | ||
})() | ||
const validInput = (() => { | ||
if (!validate) | ||
return input | ||
const schema = procedure.zz$p.contract.zz$cp.InputSchema | ||
if (!schema) | ||
return input | ||
if (!schema) { | ||
return input_ | ||
} | ||
try { | ||
return schema.parse(input) | ||
return schema.parse(input_) | ||
} | ||
@@ -101,3 +95,3 @@ catch (e) { | ||
let currentMidIndex = 0 | ||
let currentContext: Context = options.context | ||
let currentContext: Context = await resolvePromisableValue(options.context) | ||
@@ -113,3 +107,2 @@ const next: MiddlewareMeta<unknown>['next'] = async (nextOptions) => { | ||
procedure, | ||
internal, | ||
next, | ||
@@ -121,6 +114,5 @@ output: output => ({ output, context: undefined }), | ||
return { | ||
output: await await procedure.zz$p.handler(validInput, currentContext, { | ||
output: await await procedure.zz$p.func(validInput, currentContext, { | ||
path, | ||
procedure, | ||
internal, | ||
}), | ||
@@ -135,7 +127,7 @@ context: currentContext, | ||
const validOutput = await (async () => { | ||
if (!validate) | ||
return output | ||
const schema = procedure.zz$p.contract.zz$cp.OutputSchema | ||
if (!schema) | ||
if (!schema) { | ||
return output | ||
} | ||
const result = await schema.safeParseAsync(output) | ||
@@ -155,3 +147,3 @@ if (result.error) { | ||
return caller as ProcedureCaller<TProcedure, TValidate> | ||
return caller as ProcedureCaller<TProcedure> | ||
} |
@@ -114,5 +114,5 @@ import type { DecoratedProcedure, Meta, MiddlewareMeta } from '.' | ||
it('auto infer output schema if output schema is not specified', async () => { | ||
const sr = os.handler(() => ({ a: 1 })) | ||
const sr = os.func(() => ({ a: 1 })) | ||
const result = await sr.zz$p.handler({}, undefined, { | ||
const result = await sr.zz$p.func({}, undefined, { | ||
method: 'GET', | ||
@@ -133,5 +133,5 @@ path: '/', | ||
const sr = srb1.handler(() => ({ b: 1 })) | ||
const sr = srb1.func(() => ({ b: 1 })) | ||
const result = await sr.zz$p.handler({}, {}, { | ||
const result = await sr.zz$p.func({}, {}, { | ||
method: 'GET', | ||
@@ -147,3 +147,3 @@ path: '/', | ||
it('infer types', () => { | ||
const handler = implementer1.handler((input, context, meta) => { | ||
const handler = implementer1.func((input, context, meta) => { | ||
expectTypeOf(input).toEqualTypeOf<unknown>() | ||
@@ -169,3 +169,3 @@ expectTypeOf(context).toEqualTypeOf<{ auth: boolean }>() | ||
implementer2.handler((input, context, meta) => { | ||
implementer2.func((input, context, meta) => { | ||
expectTypeOf(input).toEqualTypeOf<{ id: string }>() | ||
@@ -181,3 +181,3 @@ expectTypeOf(context).toEqualTypeOf<{ auth: boolean }>() | ||
// @ts-expect-error mismatch output | ||
implementer2.handler(() => {}) | ||
implementer2.func(() => {}) | ||
}) | ||
@@ -201,3 +201,3 @@ | ||
.use(mid2) | ||
.handler((input, context, meta) => { | ||
.func((input, context, meta) => { | ||
expectTypeOf(input).toEqualTypeOf<{ id: string }>() | ||
@@ -204,0 +204,0 @@ expectTypeOf(context).toEqualTypeOf< |
@@ -11,3 +11,3 @@ import type { ContractProcedure, Schema, SchemaInput, SchemaOutput } from '@orpc/contract' | ||
decorateProcedure, | ||
type ProcedureHandler, | ||
type ProcedureFunc, | ||
} from './procedure' | ||
@@ -80,4 +80,4 @@ | ||
handler<UHandlerOutput extends SchemaOutput<TOutputSchema>>( | ||
handler: ProcedureHandler< | ||
func<UFuncOutput extends SchemaOutput<TOutputSchema>>( | ||
func: ProcedureFunc< | ||
TContext, | ||
@@ -87,3 +87,3 @@ TExtraContext, | ||
TOutputSchema, | ||
UHandlerOutput | ||
UFuncOutput | ||
>, | ||
@@ -95,3 +95,3 @@ ): DecoratedProcedure< | ||
TOutputSchema, | ||
UHandlerOutput | ||
UFuncOutput | ||
> { | ||
@@ -102,3 +102,3 @@ return decorateProcedure({ | ||
contract: this.zz$pi.contract, | ||
handler, | ||
func, | ||
}, | ||
@@ -105,0 +105,0 @@ }) |
@@ -21,3 +21,3 @@ import type { MiddlewareMeta } from '.' | ||
}), | ||
handler: () => {}, | ||
func: () => {}, | ||
}), | ||
@@ -33,3 +33,3 @@ ), | ||
}), | ||
handler: () => {}, | ||
func: () => {}, | ||
}, | ||
@@ -62,3 +62,3 @@ }).toSatisfy(isProcedure) | ||
it('sets route options correctly', () => { | ||
const p = os.context<{ auth: boolean }>().handler(() => { | ||
const p = os.context<{ auth: boolean }>().func(() => { | ||
return 'test' | ||
@@ -75,7 +75,7 @@ }) | ||
const handler = () => 'test' | ||
const p = os.context<{ auth: boolean }>().handler(handler) | ||
const p = os.context<{ auth: boolean }>().func(handler) | ||
const p2 = p.route({ path: '/test' }) | ||
expect(p2.zz$p.handler).toBe(handler) | ||
expect(p2.zz$p.func).toBe(handler) | ||
// Context type is preserved through the route method | ||
@@ -97,3 +97,3 @@ expectTypeOf(p2).toEqualTypeOf< | ||
.route({ path: '/api', method: 'POST' }) | ||
.handler(() => 'test') | ||
.func(() => 'test') | ||
@@ -113,3 +113,3 @@ const p2 = p.prefix('/v1') | ||
.use(mid) | ||
.handler((input, context) => { | ||
.func((input, context) => { | ||
expectTypeOf(context).toEqualTypeOf< | ||
@@ -129,3 +129,3 @@ { auth: boolean } & { userId: string } | ||
.route({ path: '/test1', method: 'GET' }) | ||
.handler(() => 'test') | ||
.func(() => 'test') | ||
@@ -146,3 +146,3 @@ const p2 = p.route({ path: '/test2', method: 'POST' }) | ||
.route({ path: '/test' }) | ||
.handler((input) => { | ||
.func((input) => { | ||
expectTypeOf(input).toEqualTypeOf<{ id: number }>() | ||
@@ -168,3 +168,3 @@ return 'test' | ||
it('prefix method', () => { | ||
const p = os.context<{ auth: boolean }>().handler(() => { | ||
const p = os.context<{ auth: boolean }>().func(() => { | ||
return 'unnoq' | ||
@@ -180,3 +180,3 @@ }) | ||
.route({ path: '/test1' }) | ||
.handler(() => { | ||
.func(() => { | ||
return 'unnoq' | ||
@@ -196,3 +196,3 @@ }) | ||
}) | ||
.handler(() => { | ||
.func(() => { | ||
return 'unnoq' | ||
@@ -265,3 +265,3 @@ }) | ||
const p1 = os.use(mid1).handler(() => 'unnoq') | ||
const p1 = os.use(mid1).func(() => 'unnoq') | ||
const p2 = p1.use(mid2).use(mid3) | ||
@@ -275,8 +275,8 @@ | ||
it('only accept undefined context', () => { | ||
expectTypeOf(os.handler(() => {})).toMatchTypeOf<(...args: any[]) => any>() | ||
expectTypeOf(os.func(() => {})).toMatchTypeOf<(...args: any[]) => any>() | ||
expectTypeOf( | ||
os.context<{ auth: boolean } | undefined>().handler(() => {}), | ||
os.context<{ auth: boolean } | undefined>().func(() => {}), | ||
).toMatchTypeOf<(...args: any[]) => any>() | ||
expectTypeOf( | ||
os.context<{ auth: boolean }>().handler(() => {}), | ||
os.context<{ auth: boolean }>().func(() => {}), | ||
).not.toMatchTypeOf<(...args: any[]) => any>() | ||
@@ -289,3 +289,3 @@ }) | ||
.output(z.string()) | ||
.handler(() => 'string') | ||
.func(() => 'string') | ||
@@ -296,3 +296,3 @@ expectTypeOf(p).toMatchTypeOf< | ||
const p2 = os.input(z.object({ id: z.number() })).handler(() => 12333) | ||
const p2 = os.input(z.object({ id: z.number() })).func(() => 12333) | ||
@@ -307,3 +307,3 @@ expectTypeOf(p2).toMatchTypeOf< | ||
.input(z.object({ id: z.number(), date: z.date() })) | ||
.handler(async (input, context) => { | ||
.func(async (input, context) => { | ||
expect(context).toBe(undefined) | ||
@@ -322,3 +322,3 @@ return input | ||
.input(z.object({ id: z.number(), nested: z.object({ date: z.date() }) })) | ||
.handler(async input => input) | ||
.func(async input => input) | ||
@@ -325,0 +325,0 @@ const form = new FormData() |
import type { Promisable } from '@orpc/shared' | ||
import type { ProcedureCaller } from './procedure-caller' | ||
import type { Context, MergeContext, Meta } from './types' | ||
@@ -13,3 +14,2 @@ import { | ||
} from '@orpc/contract' | ||
import { OpenAPIDeserializer } from '@orpc/transformer' | ||
import { | ||
@@ -27,3 +27,3 @@ decorateMiddleware, | ||
TOutputSchema extends Schema, | ||
THandlerOutput extends SchemaOutput<TOutputSchema>, | ||
TFuncOutput extends SchemaOutput<TOutputSchema>, | ||
> { | ||
@@ -34,3 +34,3 @@ constructor( | ||
contract: ContractProcedure<TInputSchema, TOutputSchema> | ||
handler: ProcedureHandler< | ||
func: ProcedureFunc< | ||
TContext, | ||
@@ -40,3 +40,3 @@ TExtraContext, | ||
TOutputSchema, | ||
THandlerOutput | ||
TFuncOutput | ||
> | ||
@@ -52,3 +52,3 @@ }, | ||
TOutputSchema extends Schema, | ||
THandlerOutput extends SchemaOutput<TOutputSchema>, | ||
TFuncOutput extends SchemaOutput<TOutputSchema>, | ||
> = Procedure< | ||
@@ -59,3 +59,3 @@ TContext, | ||
TOutputSchema, | ||
THandlerOutput | ||
TFuncOutput | ||
> & { | ||
@@ -69,3 +69,3 @@ prefix: ( | ||
TOutputSchema, | ||
THandlerOutput | ||
TFuncOutput | ||
> | ||
@@ -80,3 +80,3 @@ | ||
TOutputSchema, | ||
THandlerOutput | ||
TFuncOutput | ||
> | ||
@@ -93,3 +93,3 @@ | ||
SchemaOutput<TInputSchema>, | ||
SchemaInput<TOutputSchema, THandlerOutput> | ||
SchemaInput<TOutputSchema, TFuncOutput> | ||
>, | ||
@@ -101,3 +101,3 @@ ) => DecoratedProcedure< | ||
TOutputSchema, | ||
THandlerOutput | ||
TFuncOutput | ||
>) & (< | ||
@@ -113,6 +113,6 @@ UExtraContext extends | ||
UMappedInput, | ||
SchemaInput<TOutputSchema, THandlerOutput> | ||
SchemaInput<TOutputSchema, TFuncOutput> | ||
>, | ||
mapInput: MapInputMiddleware< | ||
SchemaOutput<TInputSchema, THandlerOutput>, | ||
SchemaOutput<TInputSchema, TFuncOutput>, | ||
UMappedInput | ||
@@ -125,11 +125,15 @@ >, | ||
TOutputSchema, | ||
THandlerOutput | ||
TFuncOutput | ||
>) | ||
} & (undefined extends TContext | ||
? ( | ||
input: SchemaInput<TInputSchema> | FormData, | ||
) => Promise<SchemaOutput<TOutputSchema, THandlerOutput>> | ||
? ProcedureCaller<Procedure< | ||
TContext, | ||
TExtraContext, | ||
TInputSchema, | ||
TOutputSchema, | ||
TFuncOutput | ||
>> | ||
: unknown) | ||
export interface ProcedureHandler< | ||
export interface ProcedureFunc< | ||
TContext extends Context, | ||
@@ -155,3 +159,3 @@ TExtraContext extends Context, | ||
TOutputSchema extends Schema, | ||
THandlerOutput extends SchemaOutput<TOutputSchema>, | ||
TFuncOutput extends SchemaOutput<TOutputSchema>, | ||
>( | ||
@@ -163,3 +167,3 @@ procedure: Procedure< | ||
TOutputSchema, | ||
THandlerOutput | ||
TFuncOutput | ||
>, | ||
@@ -171,3 +175,3 @@ ): DecoratedProcedure< | ||
TOutputSchema, | ||
THandlerOutput | ||
TFuncOutput | ||
> { | ||
@@ -178,25 +182,6 @@ if (DECORATED_PROCEDURE_SYMBOL in procedure) { | ||
const serverAction = async (input: unknown): Promise<SchemaOutput<TOutputSchema, THandlerOutput>> => { | ||
const input_ = (() => { | ||
if (!(input instanceof FormData)) | ||
return input | ||
const transformer = new OpenAPIDeserializer({ | ||
schema: procedure.zz$p.contract.zz$cp.InputSchema, | ||
}) | ||
return transformer.deserializeAsFormData(input) | ||
})() | ||
const procedureCaller = createProcedureCaller({ | ||
procedure, | ||
context: undefined as any, | ||
internal: false, | ||
validate: true, | ||
}) | ||
return await procedureCaller(input_ as any) | ||
} | ||
return Object.assign(serverAction, { | ||
return Object.assign(createProcedureCaller({ | ||
procedure, | ||
context: undefined as any, | ||
}), { | ||
[DECORATED_PROCEDURE_SYMBOL]: true, | ||
@@ -265,5 +250,5 @@ zz$p: procedure.zz$p, | ||
&& isContractProcedure(item.zz$p.contract) | ||
&& 'handler' in item.zz$p | ||
&& typeof item.zz$p.handler === 'function' | ||
&& 'func' in item.zz$p | ||
&& typeof item.zz$p.func === 'function' | ||
) | ||
} |
@@ -9,6 +9,6 @@ import { ContractProcedure } from '@orpc/contract' | ||
.route({ method: 'GET', path: '/ping', tags: ['ping'] }) | ||
.handler(() => 'ping') | ||
.func(() => 'ping') | ||
const pong = os | ||
.output(z.object({ id: z.string() })) | ||
.handler(() => ({ id: '123' })) | ||
.func(() => ({ id: '123' })) | ||
@@ -84,3 +84,3 @@ describe('prefix', () => { | ||
}), | ||
handler: () => {}, | ||
func: () => {}, | ||
}) | ||
@@ -94,3 +94,3 @@ | ||
}), | ||
handler: () => {}, | ||
func: () => {}, | ||
}, | ||
@@ -97,0 +97,0 @@ }) |
@@ -5,4 +5,4 @@ import { z } from 'zod' | ||
describe('createRouterCaller', () => { | ||
let internal = false | ||
let context = { auth: true } | ||
const internal = false | ||
const context = { auth: true } | ||
@@ -14,5 +14,4 @@ const osw = os.context<{ auth?: boolean }>() | ||
.output(z.object({ value: z.number().transform(v => v.toString()) })) | ||
.handler((input, context, meta) => { | ||
.func((input, context, meta) => { | ||
expect(context).toEqual(context) | ||
expect(meta.internal).toEqual(internal) | ||
@@ -22,5 +21,4 @@ return input | ||
const pong = osw.handler((_, context, meta) => { | ||
const pong = osw.func((_, context, meta) => { | ||
expect(context).toEqual(context) | ||
expect(meta.internal).toBe(internal) | ||
@@ -56,3 +54,2 @@ return { value: true } | ||
context, | ||
internal, | ||
}) | ||
@@ -105,48 +102,4 @@ | ||
it('without validate', () => { | ||
internal = true | ||
context = { auth: false } | ||
const caller = createRouterCaller({ | ||
router, | ||
context, | ||
internal, | ||
validate: false, | ||
}) | ||
expectTypeOf(caller.ping).toMatchTypeOf< | ||
(input: { value: number }) => Promise<{ | ||
value: number | ||
}> | ||
>() | ||
expectTypeOf(caller.pong).toMatchTypeOf< | ||
(input: unknown) => Promise<{ | ||
value: boolean | ||
}> | ||
>() | ||
expectTypeOf(caller.nested.ping).toMatchTypeOf< | ||
(input: { value: number }) => Promise<{ | ||
value: number | ||
}> | ||
>() | ||
expectTypeOf(caller.nested.pong).toMatchTypeOf< | ||
(input: unknown) => Promise<{ | ||
value: boolean | ||
}> | ||
>() | ||
expect(caller.ping({ value: 123 })).resolves.toEqual({ value: 123 }) | ||
expect(caller.pong({ value: 123 })).resolves.toEqual({ value: true }) | ||
expect(caller.nested.ping({ value: 123 })).resolves.toEqual({ value: 123 }) | ||
expect(caller.nested.pong({ value: 123 })).resolves.toEqual({ value: true }) | ||
// @ts-expect-error it's not validate so bellow still works | ||
expect(caller.ping({ value: '123' })).resolves.toEqual({ value: '123' }) | ||
}) | ||
it('path', () => { | ||
const ping = osw.handler((_, __, { path }) => { | ||
const ping = osw.func((_, __, { path }) => { | ||
return path | ||
@@ -153,0 +106,0 @@ }) |
@@ -1,2 +0,2 @@ | ||
import type {} from '@orpc/contract' | ||
import type { PromisableValue } from '@orpc/shared' | ||
import type { Router } from './router' | ||
@@ -8,3 +8,2 @@ import { isProcedure, type Procedure } from './procedure' | ||
TRouter extends Router<any>, | ||
TValidate extends boolean, | ||
> { | ||
@@ -16,22 +15,12 @@ router: TRouter | ||
*/ | ||
context: TRouter extends Router<infer UContext> ? UContext : never | ||
context: PromisableValue< | ||
TRouter extends Router<infer UContext> ? UContext : never | ||
> | ||
/** | ||
* This is helpful for logging and analytics. | ||
* | ||
* @internal | ||
*/ | ||
basePath?: string[] | ||
/** | ||
* This flag helpful when you want bypass some logics not necessary to internal server calls. | ||
* | ||
* @default true | ||
*/ | ||
internal?: boolean | ||
/** | ||
* Indicate whether validate input and output. | ||
* | ||
* @default true | ||
*/ | ||
validate?: TValidate | ||
} | ||
@@ -41,8 +30,7 @@ | ||
TRouter extends Router<any>, | ||
TValidate extends boolean, | ||
> = { | ||
[K in keyof TRouter]: TRouter[K] extends Procedure<any, any, any, any, any> | ||
? ProcedureCaller<TRouter[K], TValidate> | ||
? ProcedureCaller<TRouter[K]> | ||
: TRouter[K] extends Router<any> | ||
? RouterCaller<TRouter[K], TValidate> | ||
? RouterCaller<TRouter[K]> | ||
: never | ||
@@ -53,9 +41,5 @@ } | ||
TRouter extends Router<any>, | ||
TValidate extends boolean = true, | ||
>( | ||
options: CreateRouterCallerOptions<TRouter, TValidate>, | ||
): RouterCaller<TRouter, TValidate> { | ||
const internal = options.internal ?? true | ||
const validate = options.validate ?? true | ||
options: CreateRouterCallerOptions<TRouter>, | ||
): RouterCaller<TRouter> { | ||
const caller: Record<string, unknown> = {} | ||
@@ -72,4 +56,2 @@ | ||
path, | ||
internal, | ||
validate, | ||
}) | ||
@@ -82,4 +64,2 @@ } | ||
basePath: path, | ||
internal, | ||
validate, | ||
}) | ||
@@ -89,3 +69,3 @@ } | ||
return caller as RouterCaller<TRouter, TValidate> | ||
return caller as RouterCaller<TRouter> | ||
} |
@@ -20,11 +20,11 @@ import { oc } from '@orpc/contract' | ||
const p1 = osw.p1.handler(() => { | ||
const p1 = osw.p1.func(() => { | ||
return 'unnoq' | ||
}) | ||
const p2 = osw.nested.p2.handler(() => { | ||
const p2 = osw.nested.p2.func(() => { | ||
return 'unnoq' | ||
}) | ||
const p3 = osw.nested2.p3.handler(() => { | ||
const p3 = osw.nested2.p3.func(() => { | ||
return 'unnoq' | ||
@@ -41,3 +41,3 @@ }) | ||
nested: { | ||
p2: os.contract(cp2).handler(() => ''), | ||
p2: os.contract(cp2).func(() => ''), | ||
}, | ||
@@ -52,3 +52,3 @@ nested2: { | ||
// @ts-expect-error p1 is mismatch | ||
p1: os.handler(() => {}), | ||
p1: os.func(() => {}), | ||
nested: { | ||
@@ -82,3 +82,3 @@ p2, | ||
.output(z.string()) | ||
.handler(() => 'unnoq'), | ||
.func(() => 'unnoq'), | ||
nested: { | ||
@@ -85,0 +85,0 @@ p2, |
@@ -9,7 +9,7 @@ import type { InferRouterInputs, InferRouterOutputs } from '.' | ||
.output(z.object({ pong: z.number().transform(() => '1') })) | ||
.handler(() => ({ pong: 1 })), | ||
.func(() => ({ pong: 1 })), | ||
user: { | ||
find: os | ||
.input(z.object({ find: z.number().transform(() => '1') })) | ||
.handler(() => ({ user: { id: 1 } })) | ||
.func(() => ({ user: { id: 1 } })) | ||
, | ||
@@ -16,0 +16,0 @@ }, |
@@ -9,3 +9,3 @@ import { oc } from '@orpc/contract' | ||
osw.router({ | ||
ping: osw.context<{ auth: boolean }>().handler(() => { | ||
ping: osw.context<{ auth: boolean }>().func(() => { | ||
return { pong: 'ping' } | ||
@@ -15,3 +15,3 @@ }), | ||
// @ts-expect-error userId is not match | ||
ping2: osw.context<{ userId: number }>().handler(() => { | ||
ping2: osw.context<{ userId: number }>().func(() => { | ||
return { name: 'unnoq' } | ||
@@ -21,3 +21,3 @@ }), | ||
nested: { | ||
ping: osw.context<{ auth: boolean }>().handler(() => { | ||
ping: osw.context<{ auth: boolean }>().func(() => { | ||
return { pong: 'ping' } | ||
@@ -27,3 +27,3 @@ }), | ||
// @ts-expect-error userId is not match | ||
ping2: osw.context<{ userId: number }>().handler(() => { | ||
ping2: osw.context<{ userId: number }>().func(() => { | ||
return { name: 'unnoq' } | ||
@@ -38,6 +38,6 @@ }), | ||
const pongContract = oc.input(z.string()).output(z.string()) | ||
const ping = os.contract(pingContract).handler(() => { | ||
const ping = os.contract(pingContract).func(() => { | ||
return 'ping' | ||
}) | ||
const pong = os.contract(pongContract).handler(() => { | ||
const pong = os.contract(pongContract).func(() => { | ||
return 'pong' | ||
@@ -93,3 +93,3 @@ }) | ||
// @ts-expect-error nested.pong is mismatch | ||
pong: os.handler(() => 'ping'), | ||
pong: os.func(() => 'ping'), | ||
}, | ||
@@ -129,3 +129,3 @@ } | ||
const router = osw.router({ | ||
p1: osw.p1.handler(() => { | ||
p1: osw.p1.func(() => { | ||
return 'unnoq' | ||
@@ -135,3 +135,3 @@ }), | ||
nested: osw.nested.router({ | ||
p2: osw.nested.p2.handler(() => { | ||
p2: osw.nested.p2.func(() => { | ||
return 'unnoq' | ||
@@ -142,3 +142,3 @@ }), | ||
nested2: { | ||
p3: osw.nested2.p3.handler(() => { | ||
p3: osw.nested2.p3.func(() => { | ||
return 'unnoq' | ||
@@ -145,0 +145,0 @@ }), |
@@ -27,3 +27,3 @@ import type { | ||
infer UOutputSchema, | ||
infer UHandlerOutput | ||
infer UFuncOutput | ||
> | ||
@@ -35,3 +35,3 @@ ? DecoratedProcedure< | ||
UOutputSchema, | ||
UHandlerOutput | ||
UFuncOutput | ||
> | ||
@@ -88,4 +88,4 @@ : TRouter[K] extends Router<any> | ||
export type InferRouterOutputs<T extends Router<any>> = { | ||
[K in keyof T]: T[K] extends Procedure<any, any, any, infer UOutputSchema, infer UHandlerOutput> | ||
? SchemaOutput<UOutputSchema, UHandlerOutput> | ||
[K in keyof T]: T[K] extends Procedure<any, any, any, infer UOutputSchema, infer UFuncOutput> | ||
? SchemaOutput<UOutputSchema, UFuncOutput> | ||
: T[K] extends Router<any> | ||
@@ -92,0 +92,0 @@ ? InferRouterOutputs<T[K]> |
@@ -12,4 +12,3 @@ import type { WELL_DEFINED_PROCEDURE } from './procedure' | ||
path: string[] | ||
internal: boolean | ||
procedure: WELL_DEFINED_PROCEDURE | ||
} |
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
356470
5462
+ Added@orpc/contract@0.0.0-next-20241126025042(transitive)
+ Added@orpc/shared@0.0.0-next-20241126025042(transitive)
+ Added@orpc/transformer@0.0.0-next-20241126025042(transitive)
- Removed@orpc/contract@0.0.0-next-20241123144325(transitive)
- Removed@orpc/shared@0.0.5(transitive)
- Removed@orpc/transformer@0.0.4(transitive)