@orpc/server 0.1.0 → 0.1.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/chunk-26DTFWOI.js +200 -0
- package/dist/chunk-26DTFWOI.js.map +1 -0
- package/dist/fetch.js +87 -91
- package/dist/fetch.js.map +1 -1
- package/dist/index.js +6 -9
- package/dist/index.js.map +1 -1
- package/dist/src/adapters/fetch.d.ts +9 -3
- package/dist/src/adapters/fetch.d.ts.map +1 -1
- package/dist/src/builder.d.ts +4 -4
- package/dist/src/builder.d.ts.map +1 -1
- package/dist/src/index.d.ts +2 -2
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/middleware.d.ts +17 -7
- package/dist/src/middleware.d.ts.map +1 -1
- package/dist/src/procedure-builder.d.ts +4 -4
- package/dist/src/procedure-builder.d.ts.map +1 -1
- package/dist/src/procedure-caller.d.ts +0 -5
- package/dist/src/procedure-caller.d.ts.map +1 -1
- package/dist/src/procedure-implementer.d.ts +4 -5
- package/dist/src/procedure-implementer.d.ts.map +1 -1
- package/dist/src/procedure.d.ts +8 -9
- package/dist/src/procedure.d.ts.map +1 -1
- package/dist/src/router-builder.d.ts +2 -2
- package/dist/src/router-builder.d.ts.map +1 -1
- package/dist/src/router-caller.d.ts +1 -6
- package/dist/src/router-caller.d.ts.map +1 -1
- package/dist/src/router-implementer.d.ts +2 -2
- package/dist/src/router-implementer.d.ts.map +1 -1
- package/dist/src/router.d.ts +1 -1
- package/dist/src/router.d.ts.map +1 -1
- package/dist/src/types.d.ts +1 -10
- package/dist/src/types.d.ts.map +1 -1
- package/dist/src/utils.d.ts +1 -2
- package/dist/src/utils.d.ts.map +1 -1
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/package.json +5 -5
- package/src/adapters/fetch.test.ts +32 -17
- package/src/adapters/fetch.ts +134 -123
- package/src/builder.test.ts +48 -39
- package/src/builder.ts +32 -30
- package/src/index.ts +2 -2
- package/src/middleware.test.ts +54 -73
- package/src/middleware.ts +39 -22
- package/src/procedure-builder.test.ts +26 -22
- package/src/procedure-builder.ts +15 -15
- package/src/procedure-caller.test.ts +25 -70
- package/src/procedure-caller.ts +69 -88
- package/src/procedure-implementer.test.ts +27 -22
- package/src/procedure-implementer.ts +16 -17
- package/src/procedure.test.ts +17 -12
- package/src/procedure.ts +46 -45
- package/src/router-builder.test.ts +4 -4
- package/src/router-builder.ts +12 -10
- package/src/router-caller.test.ts +6 -6
- package/src/router-caller.ts +5 -16
- package/src/router-implementer.test.ts +12 -12
- package/src/router-implementer.ts +9 -6
- package/src/router.test.ts +4 -4
- package/src/router.ts +12 -10
- package/src/types.test.ts +1 -1
- package/src/types.ts +1 -15
- package/src/utils.test.ts +2 -229
- package/src/utils.ts +5 -84
- package/dist/chunk-ACLC6USM.js +0 -262
- package/dist/chunk-ACLC6USM.js.map +0 -1
package/src/types.ts
CHANGED
@@ -7,22 +7,8 @@ export type MergeContext<
|
|
7
7
|
TB extends Context,
|
8
8
|
> = TA extends undefined ? TB : TB extends undefined ? TA : TA & TB
|
9
9
|
|
10
|
-
export interface Meta
|
10
|
+
export interface Meta {
|
11
11
|
path: string[]
|
12
12
|
internal: boolean
|
13
13
|
procedure: WELL_DEFINED_PROCEDURE
|
14
14
|
}
|
15
|
-
|
16
|
-
export type Promisable<T> = T | Promise<T>
|
17
|
-
|
18
|
-
export interface UnsubscribeFn {
|
19
|
-
(): void
|
20
|
-
}
|
21
|
-
|
22
|
-
export interface Hooks<T> {
|
23
|
-
onSuccess: (fn: (output: T) => Promisable<void>) => UnsubscribeFn
|
24
|
-
onError: (fn: (error: unknown) => Promisable<void>) => UnsubscribeFn
|
25
|
-
onFinish: (
|
26
|
-
fn: (output: T | undefined, error: unknown | undefined) => Promisable<void>,
|
27
|
-
) => UnsubscribeFn
|
28
|
-
}
|
package/src/utils.test.ts
CHANGED
@@ -1,6 +1,6 @@
|
|
1
|
-
import {
|
1
|
+
import { mergeContext } from './utils'
|
2
2
|
|
3
|
-
|
3
|
+
it('mergeContext', () => {
|
4
4
|
expect(mergeContext(undefined, undefined)).toBe(undefined)
|
5
5
|
expect(mergeContext(undefined, { foo: 'bar' })).toEqual({ foo: 'bar' })
|
6
6
|
expect(mergeContext({ foo: 'bar' }, undefined)).toEqual({ foo: 'bar' })
|
@@ -14,230 +14,3 @@ test('mergeContext', () => {
|
|
14
14
|
bar: 'bar',
|
15
15
|
})
|
16
16
|
})
|
17
|
-
|
18
|
-
describe('hook', async () => {
|
19
|
-
it('on success', async () => {
|
20
|
-
const onSuccess = vi.fn()
|
21
|
-
const onError = vi.fn()
|
22
|
-
const onFinish = vi.fn()
|
23
|
-
|
24
|
-
await hook(async (hooks) => {
|
25
|
-
hooks.onSuccess(onSuccess)
|
26
|
-
hooks.onError(onError)
|
27
|
-
hooks.onFinish(onFinish)
|
28
|
-
|
29
|
-
return 'foo'
|
30
|
-
})
|
31
|
-
|
32
|
-
expect(onSuccess).toHaveBeenCalledWith('foo')
|
33
|
-
expect(onError).not.toHaveBeenCalled()
|
34
|
-
expect(onFinish).toHaveBeenCalledWith('foo', undefined)
|
35
|
-
})
|
36
|
-
|
37
|
-
it('on failed', async () => {
|
38
|
-
const onSuccess = vi.fn()
|
39
|
-
const onError = vi.fn()
|
40
|
-
const onFinish = vi.fn()
|
41
|
-
const error = new Error('foo')
|
42
|
-
|
43
|
-
try {
|
44
|
-
await hook(async (hooks) => {
|
45
|
-
hooks.onSuccess(onSuccess)
|
46
|
-
hooks.onError(onError)
|
47
|
-
hooks.onFinish(onFinish)
|
48
|
-
|
49
|
-
throw error
|
50
|
-
})
|
51
|
-
} catch (e) {
|
52
|
-
expect(e).toBe(error)
|
53
|
-
}
|
54
|
-
|
55
|
-
expect(onSuccess).not.toHaveBeenCalled()
|
56
|
-
expect(onError).toHaveBeenCalledWith(error)
|
57
|
-
expect(onFinish).toHaveBeenCalledWith(undefined, error)
|
58
|
-
})
|
59
|
-
|
60
|
-
it('throw the last error', async () => {
|
61
|
-
const error = new Error('foo')
|
62
|
-
const error1 = new Error('1')
|
63
|
-
const error2 = new Error('2')
|
64
|
-
|
65
|
-
try {
|
66
|
-
await hook(async (hooks) => {
|
67
|
-
hooks.onSuccess(() => {
|
68
|
-
throw error
|
69
|
-
})
|
70
|
-
})
|
71
|
-
} catch (e) {
|
72
|
-
expect(e).toBe(error)
|
73
|
-
}
|
74
|
-
|
75
|
-
try {
|
76
|
-
await hook(async (hooks) => {
|
77
|
-
hooks.onError(() => {
|
78
|
-
throw error1
|
79
|
-
})
|
80
|
-
})
|
81
|
-
} catch (e) {
|
82
|
-
expect(e).toBe(error1)
|
83
|
-
}
|
84
|
-
|
85
|
-
try {
|
86
|
-
await hook(async (hooks) => {
|
87
|
-
hooks.onFinish(() => {
|
88
|
-
throw error2
|
89
|
-
})
|
90
|
-
})
|
91
|
-
} catch (e) {
|
92
|
-
expect(e).toBe(error2)
|
93
|
-
}
|
94
|
-
|
95
|
-
try {
|
96
|
-
await hook(async (hooks) => {
|
97
|
-
hooks.onError((e) => {
|
98
|
-
expect(e).toBe(error)
|
99
|
-
throw error1
|
100
|
-
})
|
101
|
-
hooks.onFinish((_, error) => {
|
102
|
-
expect(error).toBe(error1)
|
103
|
-
throw error2
|
104
|
-
})
|
105
|
-
|
106
|
-
throw error
|
107
|
-
})
|
108
|
-
} catch (e) {
|
109
|
-
expect(e).toBe(error2)
|
110
|
-
}
|
111
|
-
})
|
112
|
-
|
113
|
-
it('Fist In Last Out', async () => {
|
114
|
-
const ref = { value: 0 }
|
115
|
-
const hooked = hook(async (hooks) => {
|
116
|
-
hooks.onSuccess(() => {
|
117
|
-
expect(ref).toEqual({ value: 2 })
|
118
|
-
ref.value++
|
119
|
-
})
|
120
|
-
hooks.onSuccess(() => {
|
121
|
-
expect(ref).toEqual({ value: 1 })
|
122
|
-
ref.value++
|
123
|
-
})
|
124
|
-
hooks.onSuccess(() => {
|
125
|
-
expect(ref).toEqual({ value: 0 })
|
126
|
-
ref.value++
|
127
|
-
})
|
128
|
-
|
129
|
-
hooks.onFinish(() => {
|
130
|
-
expect(ref).toEqual({ value: 5 })
|
131
|
-
ref.value++
|
132
|
-
})
|
133
|
-
hooks.onFinish(() => {
|
134
|
-
expect(ref).toEqual({ value: 4 })
|
135
|
-
ref.value++
|
136
|
-
})
|
137
|
-
hooks.onFinish(() => {
|
138
|
-
expect(ref).toEqual({ value: 3 })
|
139
|
-
ref.value++
|
140
|
-
})
|
141
|
-
})
|
142
|
-
|
143
|
-
await expect(hooked).resolves.toEqual(undefined)
|
144
|
-
expect(ref).toEqual({ value: 6 })
|
145
|
-
})
|
146
|
-
|
147
|
-
it('Fist In Last Out - onError', async () => {
|
148
|
-
const ref = { value: 0 }
|
149
|
-
const hooked = hook(async (hooks) => {
|
150
|
-
hooks.onError(() => {
|
151
|
-
expect(ref).toEqual({ value: 2 })
|
152
|
-
ref.value++
|
153
|
-
})
|
154
|
-
hooks.onError(() => {
|
155
|
-
expect(ref).toEqual({ value: 1 })
|
156
|
-
ref.value++
|
157
|
-
})
|
158
|
-
hooks.onError(() => {
|
159
|
-
expect(ref).toEqual({ value: 0 })
|
160
|
-
ref.value++
|
161
|
-
})
|
162
|
-
|
163
|
-
hooks.onFinish(() => {
|
164
|
-
expect(ref).toEqual({ value: 5 })
|
165
|
-
ref.value++
|
166
|
-
})
|
167
|
-
hooks.onFinish(() => {
|
168
|
-
expect(ref).toEqual({ value: 4 })
|
169
|
-
ref.value++
|
170
|
-
})
|
171
|
-
hooks.onFinish(() => {
|
172
|
-
expect(ref).toEqual({ value: 3 })
|
173
|
-
ref.value++
|
174
|
-
})
|
175
|
-
|
176
|
-
throw new Error('foo')
|
177
|
-
})
|
178
|
-
|
179
|
-
await expect(hooked).rejects.toThrow('foo')
|
180
|
-
expect(ref).toEqual({ value: 6 })
|
181
|
-
})
|
182
|
-
|
183
|
-
it('ensure run every onSuccess and onFinish even on throw many times', async () => {
|
184
|
-
const error = new Error('foo')
|
185
|
-
const error1 = new Error('1')
|
186
|
-
const error2 = new Error('2')
|
187
|
-
|
188
|
-
const onError = vi.fn(() => {
|
189
|
-
throw error
|
190
|
-
})
|
191
|
-
const onFinish = vi.fn(() => {
|
192
|
-
throw error1
|
193
|
-
})
|
194
|
-
|
195
|
-
try {
|
196
|
-
await hook(async (hooks) => {
|
197
|
-
hooks.onError(onError)
|
198
|
-
hooks.onError(onError)
|
199
|
-
hooks.onError(onError)
|
200
|
-
hooks.onFinish(onFinish)
|
201
|
-
hooks.onFinish(onFinish)
|
202
|
-
hooks.onFinish(onFinish)
|
203
|
-
|
204
|
-
throw error2
|
205
|
-
})
|
206
|
-
} catch (e) {
|
207
|
-
expect(e).toBe(error1)
|
208
|
-
}
|
209
|
-
|
210
|
-
expect(onError).toHaveBeenCalledTimes(3)
|
211
|
-
expect(onFinish).toHaveBeenCalledTimes(3)
|
212
|
-
})
|
213
|
-
|
214
|
-
it('can unsubscribe', async () => {
|
215
|
-
const onSuccess = vi.fn()
|
216
|
-
const onError = vi.fn()
|
217
|
-
const onFinish = vi.fn()
|
218
|
-
|
219
|
-
await hook(async (hooks) => {
|
220
|
-
hooks.onSuccess(onSuccess)()
|
221
|
-
hooks.onSuccess(onSuccess)()
|
222
|
-
hooks.onError(onError)()
|
223
|
-
hooks.onFinish(onFinish)()
|
224
|
-
|
225
|
-
return 'foo'
|
226
|
-
})
|
227
|
-
|
228
|
-
await expect(
|
229
|
-
hook(async (hooks) => {
|
230
|
-
hooks.onSuccess(onSuccess)()
|
231
|
-
hooks.onSuccess(onSuccess)()
|
232
|
-
hooks.onError(onError)()
|
233
|
-
hooks.onFinish(onFinish)()
|
234
|
-
|
235
|
-
throw new Error('foo')
|
236
|
-
}),
|
237
|
-
).rejects.toThrow('foo')
|
238
|
-
|
239
|
-
expect(onSuccess).not.toHaveBeenCalled()
|
240
|
-
expect(onError).not.toHaveBeenCalled()
|
241
|
-
expect(onFinish).not.toHaveBeenCalled()
|
242
|
-
})
|
243
|
-
})
|
package/src/utils.ts
CHANGED
@@ -1,95 +1,16 @@
|
|
1
|
-
import type { Context,
|
1
|
+
import type { Context, MergeContext } from './types'
|
2
2
|
|
3
3
|
export function mergeContext<A extends Context, B extends Context>(
|
4
4
|
a: A,
|
5
5
|
b: B,
|
6
6
|
): MergeContext<A, B> {
|
7
|
-
if (!a)
|
8
|
-
|
7
|
+
if (!a)
|
8
|
+
return b as any
|
9
|
+
if (!b)
|
10
|
+
return a as any
|
9
11
|
|
10
12
|
return {
|
11
13
|
...a,
|
12
14
|
...b,
|
13
15
|
} as any
|
14
16
|
}
|
15
|
-
|
16
|
-
export async function hook<T>(
|
17
|
-
fn: (hooks: Hooks<T>) => Promisable<T>,
|
18
|
-
): Promise<T> {
|
19
|
-
const onSuccessFns: ((output: T) => Promisable<void>)[] = []
|
20
|
-
const onErrorFns: ((error: unknown) => Promisable<void>)[] = []
|
21
|
-
const onFinishFns: ((
|
22
|
-
output: T | undefined,
|
23
|
-
error: unknown | undefined,
|
24
|
-
) => Promisable<void>)[] = []
|
25
|
-
|
26
|
-
const hooks: Hooks<T> = {
|
27
|
-
onSuccess(fn) {
|
28
|
-
onSuccessFns.unshift(fn)
|
29
|
-
|
30
|
-
return () => {
|
31
|
-
const index = onSuccessFns.indexOf(fn)
|
32
|
-
if (index !== -1) onSuccessFns.splice(index, 1)
|
33
|
-
}
|
34
|
-
},
|
35
|
-
|
36
|
-
onError(fn) {
|
37
|
-
onErrorFns.unshift(fn)
|
38
|
-
|
39
|
-
return () => {
|
40
|
-
const index = onErrorFns.indexOf(fn)
|
41
|
-
if (index !== -1) onErrorFns.splice(index, 1)
|
42
|
-
}
|
43
|
-
},
|
44
|
-
|
45
|
-
onFinish(fn) {
|
46
|
-
onFinishFns.unshift(fn)
|
47
|
-
|
48
|
-
return () => {
|
49
|
-
const index = onFinishFns.indexOf(fn)
|
50
|
-
if (index !== -1) onFinishFns.splice(index, 1)
|
51
|
-
}
|
52
|
-
},
|
53
|
-
}
|
54
|
-
|
55
|
-
let error: unknown = undefined
|
56
|
-
let output: T | undefined = undefined
|
57
|
-
|
58
|
-
try {
|
59
|
-
output = await fn(hooks)
|
60
|
-
|
61
|
-
for (const onSuccessFn of onSuccessFns) {
|
62
|
-
await onSuccessFn(output)
|
63
|
-
}
|
64
|
-
|
65
|
-
return output
|
66
|
-
} catch (e) {
|
67
|
-
error = e
|
68
|
-
|
69
|
-
for (const onErrorFn of onErrorFns) {
|
70
|
-
try {
|
71
|
-
await onErrorFn(error)
|
72
|
-
} catch (e) {
|
73
|
-
error = e
|
74
|
-
}
|
75
|
-
}
|
76
|
-
|
77
|
-
throw error
|
78
|
-
} finally {
|
79
|
-
let hasNewError = false
|
80
|
-
|
81
|
-
for (const onFinishFn of onFinishFns) {
|
82
|
-
try {
|
83
|
-
await onFinishFn(output, error)
|
84
|
-
} catch (e) {
|
85
|
-
error = e
|
86
|
-
hasNewError = true
|
87
|
-
}
|
88
|
-
}
|
89
|
-
|
90
|
-
if (hasNewError) {
|
91
|
-
// biome-ignore lint/correctness/noUnsafeFinally: this behavior is expected
|
92
|
-
throw error
|
93
|
-
}
|
94
|
-
}
|
95
|
-
}
|
package/dist/chunk-ACLC6USM.js
DELETED
@@ -1,262 +0,0 @@
|
|
1
|
-
// src/utils.ts
|
2
|
-
function mergeContext(a, b) {
|
3
|
-
if (!a) return b;
|
4
|
-
if (!b) return a;
|
5
|
-
return {
|
6
|
-
...a,
|
7
|
-
...b
|
8
|
-
};
|
9
|
-
}
|
10
|
-
async function hook(fn) {
|
11
|
-
const onSuccessFns = [];
|
12
|
-
const onErrorFns = [];
|
13
|
-
const onFinishFns = [];
|
14
|
-
const hooks = {
|
15
|
-
onSuccess(fn2) {
|
16
|
-
onSuccessFns.unshift(fn2);
|
17
|
-
return () => {
|
18
|
-
const index = onSuccessFns.indexOf(fn2);
|
19
|
-
if (index !== -1) onSuccessFns.splice(index, 1);
|
20
|
-
};
|
21
|
-
},
|
22
|
-
onError(fn2) {
|
23
|
-
onErrorFns.unshift(fn2);
|
24
|
-
return () => {
|
25
|
-
const index = onErrorFns.indexOf(fn2);
|
26
|
-
if (index !== -1) onErrorFns.splice(index, 1);
|
27
|
-
};
|
28
|
-
},
|
29
|
-
onFinish(fn2) {
|
30
|
-
onFinishFns.unshift(fn2);
|
31
|
-
return () => {
|
32
|
-
const index = onFinishFns.indexOf(fn2);
|
33
|
-
if (index !== -1) onFinishFns.splice(index, 1);
|
34
|
-
};
|
35
|
-
}
|
36
|
-
};
|
37
|
-
let error = void 0;
|
38
|
-
let output = void 0;
|
39
|
-
try {
|
40
|
-
output = await fn(hooks);
|
41
|
-
for (const onSuccessFn of onSuccessFns) {
|
42
|
-
await onSuccessFn(output);
|
43
|
-
}
|
44
|
-
return output;
|
45
|
-
} catch (e) {
|
46
|
-
error = e;
|
47
|
-
for (const onErrorFn of onErrorFns) {
|
48
|
-
try {
|
49
|
-
await onErrorFn(error);
|
50
|
-
} catch (e2) {
|
51
|
-
error = e2;
|
52
|
-
}
|
53
|
-
}
|
54
|
-
throw error;
|
55
|
-
} finally {
|
56
|
-
let hasNewError = false;
|
57
|
-
for (const onFinishFn of onFinishFns) {
|
58
|
-
try {
|
59
|
-
await onFinishFn(output, error);
|
60
|
-
} catch (e) {
|
61
|
-
error = e;
|
62
|
-
hasNewError = true;
|
63
|
-
}
|
64
|
-
}
|
65
|
-
if (hasNewError) {
|
66
|
-
throw error;
|
67
|
-
}
|
68
|
-
}
|
69
|
-
}
|
70
|
-
|
71
|
-
// src/middleware.ts
|
72
|
-
var decoratedMiddlewareSymbol = Symbol("\u{1F512}decoratedMiddleware");
|
73
|
-
function decorateMiddleware(middleware) {
|
74
|
-
if (Reflect.get(middleware, decoratedMiddlewareSymbol)) {
|
75
|
-
return middleware;
|
76
|
-
}
|
77
|
-
const concat = (concatMiddleware, mapInput2) => {
|
78
|
-
const concatMiddleware_ = mapInput2 ? decorateMiddleware(concatMiddleware).mapInput(mapInput2) : concatMiddleware;
|
79
|
-
return decorateMiddleware(async (input, context, meta, ...rest) => {
|
80
|
-
const input_ = input;
|
81
|
-
const context_ = context;
|
82
|
-
const meta_ = meta;
|
83
|
-
const m1 = await middleware(input_, context_, meta_, ...rest);
|
84
|
-
const m2 = await concatMiddleware_(
|
85
|
-
input_,
|
86
|
-
mergeContext(context_, m1?.context),
|
87
|
-
meta_,
|
88
|
-
...rest
|
89
|
-
);
|
90
|
-
return { context: mergeContext(m1?.context, m2?.context) };
|
91
|
-
});
|
92
|
-
};
|
93
|
-
const mapInput = (map) => {
|
94
|
-
return decorateMiddleware(
|
95
|
-
(input, ...rest) => middleware(map(input), ...rest)
|
96
|
-
);
|
97
|
-
};
|
98
|
-
return Object.assign(middleware, {
|
99
|
-
[decoratedMiddlewareSymbol]: true,
|
100
|
-
concat,
|
101
|
-
mapInput
|
102
|
-
});
|
103
|
-
}
|
104
|
-
|
105
|
-
// src/procedure-caller.ts
|
106
|
-
import { ORPCError } from "@orpc/shared/error";
|
107
|
-
function createProcedureCaller(options) {
|
108
|
-
const internal = options.internal ?? true;
|
109
|
-
const path = options.path ?? [];
|
110
|
-
const procedure = options.procedure;
|
111
|
-
const validate = options.validate ?? true;
|
112
|
-
const caller = async (input) => {
|
113
|
-
const handler = async (input2, context, partialMeta, middlewares) => {
|
114
|
-
if (middlewares[0]) {
|
115
|
-
const [middleware, ...rest] = middlewares;
|
116
|
-
return await hook(async (hooks) => {
|
117
|
-
const mid = await middleware(input2, context, {
|
118
|
-
...partialMeta,
|
119
|
-
...hooks
|
120
|
-
});
|
121
|
-
return await handler(
|
122
|
-
input2,
|
123
|
-
mergeContext(context, mid?.context),
|
124
|
-
partialMeta,
|
125
|
-
rest
|
126
|
-
);
|
127
|
-
});
|
128
|
-
}
|
129
|
-
return await hook(async (hooks) => {
|
130
|
-
const output = await procedure.zz$p.handler(input2, context, {
|
131
|
-
...partialMeta,
|
132
|
-
...hooks
|
133
|
-
});
|
134
|
-
const validOutput = await (async () => {
|
135
|
-
if (!validate) return output;
|
136
|
-
const schema = procedure.zz$p.contract.zz$cp.OutputSchema;
|
137
|
-
if (!schema) return output;
|
138
|
-
const result = await schema.safeParseAsync(output);
|
139
|
-
if (result.error)
|
140
|
-
throw new ORPCError({
|
141
|
-
message: "Validation output failed",
|
142
|
-
code: "INTERNAL_SERVER_ERROR",
|
143
|
-
cause: result.error
|
144
|
-
});
|
145
|
-
return result.data;
|
146
|
-
})();
|
147
|
-
return validOutput;
|
148
|
-
});
|
149
|
-
};
|
150
|
-
return await hook(async (hooks) => {
|
151
|
-
options.hooks?.(options.context, {
|
152
|
-
...hooks,
|
153
|
-
path,
|
154
|
-
procedure,
|
155
|
-
internal
|
156
|
-
});
|
157
|
-
const validInput = (() => {
|
158
|
-
if (!validate) return input;
|
159
|
-
const schema = procedure.zz$p.contract.zz$cp.InputSchema;
|
160
|
-
if (!schema) return input;
|
161
|
-
try {
|
162
|
-
return schema.parse(input);
|
163
|
-
} catch (e) {
|
164
|
-
throw new ORPCError({
|
165
|
-
message: "Validation input failed",
|
166
|
-
code: "BAD_REQUEST",
|
167
|
-
cause: e
|
168
|
-
});
|
169
|
-
}
|
170
|
-
})();
|
171
|
-
return await handler(
|
172
|
-
validInput,
|
173
|
-
options.context,
|
174
|
-
{ path, procedure, internal },
|
175
|
-
procedure.zz$p.middlewares ?? []
|
176
|
-
);
|
177
|
-
});
|
178
|
-
};
|
179
|
-
return caller;
|
180
|
-
}
|
181
|
-
|
182
|
-
// src/procedure.ts
|
183
|
-
import {
|
184
|
-
DecoratedContractProcedure,
|
185
|
-
isContractProcedure
|
186
|
-
} from "@orpc/contract";
|
187
|
-
import { OpenAPIDeserializer } from "@orpc/transformer";
|
188
|
-
var Procedure = class {
|
189
|
-
constructor(zz$p) {
|
190
|
-
this.zz$p = zz$p;
|
191
|
-
}
|
192
|
-
};
|
193
|
-
var DECORATED_PROCEDURE_SYMBOL = Symbol("DECORATED_PROCEDURE");
|
194
|
-
function decorateProcedure(procedure) {
|
195
|
-
if (DECORATED_PROCEDURE_SYMBOL in procedure) {
|
196
|
-
return procedure;
|
197
|
-
}
|
198
|
-
const serverAction = async (input) => {
|
199
|
-
const input_ = (() => {
|
200
|
-
if (!(input instanceof FormData)) return input;
|
201
|
-
const transformer = new OpenAPIDeserializer({
|
202
|
-
schema: procedure.zz$p.contract.zz$cp.InputSchema
|
203
|
-
});
|
204
|
-
return transformer.deserializeAsFormData(input);
|
205
|
-
})();
|
206
|
-
const procedureCaller = createProcedureCaller({
|
207
|
-
procedure,
|
208
|
-
context: void 0,
|
209
|
-
internal: false,
|
210
|
-
validate: true
|
211
|
-
});
|
212
|
-
return await procedureCaller(input_);
|
213
|
-
};
|
214
|
-
return Object.assign(serverAction, {
|
215
|
-
[DECORATED_PROCEDURE_SYMBOL]: true,
|
216
|
-
zz$p: procedure.zz$p,
|
217
|
-
prefix(prefix) {
|
218
|
-
return decorateProcedure({
|
219
|
-
zz$p: {
|
220
|
-
...procedure.zz$p,
|
221
|
-
contract: DecoratedContractProcedure.decorate(
|
222
|
-
procedure.zz$p.contract
|
223
|
-
).prefix(prefix)
|
224
|
-
}
|
225
|
-
});
|
226
|
-
},
|
227
|
-
route(opts) {
|
228
|
-
return decorateProcedure({
|
229
|
-
zz$p: {
|
230
|
-
...procedure.zz$p,
|
231
|
-
contract: DecoratedContractProcedure.decorate(
|
232
|
-
procedure.zz$p.contract
|
233
|
-
).route(opts)
|
234
|
-
}
|
235
|
-
});
|
236
|
-
},
|
237
|
-
use(middleware, mapInput) {
|
238
|
-
const middleware_ = mapInput ? decorateMiddleware(middleware).mapInput(mapInput) : middleware;
|
239
|
-
return decorateProcedure({
|
240
|
-
zz$p: {
|
241
|
-
...procedure.zz$p,
|
242
|
-
middlewares: [middleware_, ...procedure.zz$p.middlewares ?? []]
|
243
|
-
}
|
244
|
-
});
|
245
|
-
}
|
246
|
-
});
|
247
|
-
}
|
248
|
-
function isProcedure(item) {
|
249
|
-
if (item instanceof Procedure) return true;
|
250
|
-
return (typeof item === "object" || typeof item === "function") && item !== null && "zz$p" in item && typeof item.zz$p === "object" && item.zz$p !== null && "contract" in item.zz$p && isContractProcedure(item.zz$p.contract) && "handler" in item.zz$p && typeof item.zz$p.handler === "function";
|
251
|
-
}
|
252
|
-
|
253
|
-
export {
|
254
|
-
mergeContext,
|
255
|
-
hook,
|
256
|
-
decorateMiddleware,
|
257
|
-
createProcedureCaller,
|
258
|
-
Procedure,
|
259
|
-
decorateProcedure,
|
260
|
-
isProcedure
|
261
|
-
};
|
262
|
-
//# sourceMappingURL=chunk-ACLC6USM.js.map
|
@@ -1 +0,0 @@
|
|
1
|
-
{"version":3,"sources":["../src/utils.ts","../src/middleware.ts","../src/procedure-caller.ts","../src/procedure.ts"],"sourcesContent":["import type { Context, Hooks, MergeContext, Promisable } from './types'\n\nexport function mergeContext<A extends Context, B extends Context>(\n a: A,\n b: B,\n): MergeContext<A, B> {\n if (!a) return b as any\n if (!b) return a as any\n\n return {\n ...a,\n ...b,\n } as any\n}\n\nexport async function hook<T>(\n fn: (hooks: Hooks<T>) => Promisable<T>,\n): Promise<T> {\n const onSuccessFns: ((output: T) => Promisable<void>)[] = []\n const onErrorFns: ((error: unknown) => Promisable<void>)[] = []\n const onFinishFns: ((\n output: T | undefined,\n error: unknown | undefined,\n ) => Promisable<void>)[] = []\n\n const hooks: Hooks<T> = {\n onSuccess(fn) {\n onSuccessFns.unshift(fn)\n\n return () => {\n const index = onSuccessFns.indexOf(fn)\n if (index !== -1) onSuccessFns.splice(index, 1)\n }\n },\n\n onError(fn) {\n onErrorFns.unshift(fn)\n\n return () => {\n const index = onErrorFns.indexOf(fn)\n if (index !== -1) onErrorFns.splice(index, 1)\n }\n },\n\n onFinish(fn) {\n onFinishFns.unshift(fn)\n\n return () => {\n const index = onFinishFns.indexOf(fn)\n if (index !== -1) onFinishFns.splice(index, 1)\n }\n },\n }\n\n let error: unknown = undefined\n let output: T | undefined = undefined\n\n try {\n output = await fn(hooks)\n\n for (const onSuccessFn of onSuccessFns) {\n await onSuccessFn(output)\n }\n\n return output\n } catch (e) {\n error = e\n\n for (const onErrorFn of onErrorFns) {\n try {\n await onErrorFn(error)\n } catch (e) {\n error = e\n }\n }\n\n throw error\n } finally {\n let hasNewError = false\n\n for (const onFinishFn of onFinishFns) {\n try {\n await onFinishFn(output, error)\n } catch (e) {\n error = e\n hasNewError = true\n }\n }\n\n if (hasNewError) {\n // biome-ignore lint/correctness/noUnsafeFinally: this behavior is expected\n throw error\n }\n }\n}\n","import type { Context, MergeContext, Meta, Promisable } from './types'\nimport { mergeContext } from './utils'\n\nexport interface Middleware<\n TContext extends Context,\n TExtraContext extends Context,\n TInput,\n TOutput,\n> {\n (\n input: TInput,\n context: TContext,\n meta: Meta<TOutput>,\n ): Promisable<\n TExtraContext extends undefined ? void : { context: TExtraContext }\n >\n}\n\nexport interface MapInputMiddleware<TInput, TMappedInput> {\n (input: TInput): TMappedInput\n}\n\nexport interface DecoratedMiddleware<\n TContext extends Context,\n TExtraContext extends Context,\n TInput,\n TOutput,\n> extends Middleware<TContext, TExtraContext, TInput, TOutput> {\n concat<UExtraContext extends Context = undefined, UInput = TInput>(\n middleware: Middleware<\n MergeContext<TContext, TExtraContext>,\n UExtraContext,\n UInput & TInput,\n TOutput\n >,\n ): DecoratedMiddleware<\n TContext,\n MergeContext<TExtraContext, UExtraContext>,\n TInput & UInput,\n TOutput\n >\n\n concat<\n UExtraContext extends Context = undefined,\n UInput = TInput,\n UMappedInput = unknown,\n >(\n middleware: Middleware<\n MergeContext<TContext, TExtraContext>,\n UExtraContext,\n UMappedInput,\n TOutput\n >,\n mapInput: MapInputMiddleware<UInput, UMappedInput>,\n ): DecoratedMiddleware<\n TContext,\n MergeContext<TExtraContext, UExtraContext>,\n TInput & UInput,\n TOutput\n >\n\n mapInput<UInput = unknown>(\n map: MapInputMiddleware<UInput, TInput>,\n ): DecoratedMiddleware<TContext, TExtraContext, UInput, TOutput>\n}\n\nconst decoratedMiddlewareSymbol = Symbol('🔒decoratedMiddleware')\n\nexport function decorateMiddleware<\n TContext extends Context,\n TExtraContext extends Context,\n TInput,\n TOutput,\n>(\n middleware: Middleware<TContext, TExtraContext, TInput, TOutput>,\n): DecoratedMiddleware<TContext, TExtraContext, TInput, TOutput> {\n if (Reflect.get(middleware, decoratedMiddlewareSymbol)) {\n return middleware as any\n }\n\n const concat = (\n concatMiddleware: Middleware<any, any, any, any>,\n mapInput?: MapInputMiddleware<any, any>,\n ) => {\n const concatMiddleware_ = mapInput\n ? decorateMiddleware(concatMiddleware).mapInput(mapInput)\n : concatMiddleware\n\n return decorateMiddleware(async (input, context, meta, ...rest) => {\n const input_ = input as any\n const context_ = context as any\n const meta_ = meta as any\n\n const m1 = await middleware(input_, context_, meta_, ...rest)\n const m2 = await concatMiddleware_(\n input_,\n mergeContext(context_, m1?.context),\n meta_,\n ...rest,\n )\n\n return { context: mergeContext(m1?.context, m2?.context) }\n })\n }\n\n const mapInput = <UInput = unknown>(\n map: MapInputMiddleware<UInput, TInput>,\n ): DecoratedMiddleware<TContext, TExtraContext, UInput, TOutput> => {\n return decorateMiddleware((input, ...rest) =>\n middleware(map(input), ...rest),\n )\n }\n\n return Object.assign(middleware, {\n [decoratedMiddlewareSymbol]: true,\n concat: concat as any,\n mapInput,\n })\n}\n","import type { SchemaInput, SchemaOutput } from '@orpc/contract'\nimport { ORPCError } from '@orpc/shared/error'\nimport type { Middleware } from './middleware'\nimport type { Procedure } from './procedure'\nimport type { Context, Hooks, Meta, Promisable } from './types'\nimport { hook, mergeContext } from './utils'\n\nexport interface CreateProcedureCallerOptions<\n TProcedure extends Procedure<any, any, any, any, any>,\n TValidate extends boolean,\n> {\n procedure: TProcedure\n\n /**\n * The context used when calling the procedure.\n */\n context: TProcedure extends Procedure<infer UContext, any, any, any, any>\n ? UContext\n : never\n\n /**\n * Helpful hooks to do some logics on specific time.\n */\n hooks?: (\n context: TProcedure extends Procedure<infer UContext, any, any, any, any>\n ? UContext\n : never,\n meta: Meta<unknown>,\n ) => Promisable<void>\n\n /**\n * This is helpful for logging and analytics.\n */\n path?: string[]\n\n /**\n * This flag helpful when you want bypass some logics not necessary to internal server calls.\n *\n * @default true\n */\n internal?: boolean\n\n /**\n * Indicate whether validate input and output.\n *\n * @default true\n */\n validate?: TValidate\n}\n\nexport type ProcedureCaller<\n TProcedure extends Procedure<any, any, any, any, any>,\n TValidate extends boolean,\n> = TProcedure extends Procedure<\n any,\n any,\n infer UInputSchema,\n infer UOutputSchema,\n infer UHandlerOutput\n>\n ? (\n input: TValidate extends true\n ? SchemaInput<UInputSchema>\n : SchemaOutput<UInputSchema>,\n ) => Promise<\n TValidate extends true\n ? SchemaOutput<UOutputSchema, UHandlerOutput>\n : SchemaInput<UOutputSchema, UHandlerOutput>\n >\n : never\n\nexport function createProcedureCaller<\n TProcedure extends Procedure<any, any, any, any, any>,\n TValidate extends boolean = true,\n>(\n options: CreateProcedureCallerOptions<TProcedure, TValidate>,\n): ProcedureCaller<TProcedure, TValidate> {\n const internal = options.internal ?? true\n const path = options.path ?? []\n const procedure = options.procedure\n const validate = options.validate ?? true\n\n const caller = async (input: unknown) => {\n const handler = async (\n input: unknown,\n context: Context,\n partialMeta: Omit<Meta<unknown>, keyof Hooks<unknown>>,\n middlewares: Middleware<any, any, any, any>[],\n ): Promise<unknown> => {\n if (middlewares[0]) {\n const [middleware, ...rest] = middlewares\n\n return await hook(async (hooks) => {\n const mid = await middleware(input, context, {\n ...partialMeta,\n ...hooks,\n })\n return await handler(\n input,\n mergeContext(context, mid?.context),\n partialMeta,\n rest,\n )\n })\n }\n\n return await hook(async (hooks) => {\n const output = await procedure.zz$p.handler(input, context, {\n ...partialMeta,\n ...hooks,\n })\n\n const validOutput = await (async () => {\n if (!validate) return output\n const schema = procedure.zz$p.contract.zz$cp.OutputSchema\n if (!schema) return output\n const result = await schema.safeParseAsync(output)\n if (result.error)\n throw new ORPCError({\n message: 'Validation output failed',\n code: 'INTERNAL_SERVER_ERROR',\n cause: result.error,\n })\n return result.data\n })()\n\n return validOutput\n })\n }\n\n return await hook(async (hooks) => {\n options.hooks?.(options.context, {\n ...hooks,\n path,\n procedure,\n internal,\n })\n\n const validInput = (() => {\n if (!validate) return input\n const schema = procedure.zz$p.contract.zz$cp.InputSchema\n if (!schema) return input\n\n try {\n return schema.parse(input)\n } catch (e) {\n throw new ORPCError({\n message: 'Validation input failed',\n code: 'BAD_REQUEST',\n cause: e,\n })\n }\n })()\n\n return await handler(\n validInput,\n options.context,\n { path, procedure, internal },\n procedure.zz$p.middlewares ?? [],\n )\n })\n }\n\n return caller as ProcedureCaller<TProcedure, TValidate>\n}\n","import {\n type ContractProcedure,\n DecoratedContractProcedure,\n type HTTPPath,\n type SchemaInput,\n type SchemaOutput,\n isContractProcedure,\n} from '@orpc/contract'\nimport type { RouteOptions, Schema } from '@orpc/contract'\nimport { OpenAPIDeserializer } from '@orpc/transformer'\nimport {\n type MapInputMiddleware,\n type Middleware,\n decorateMiddleware,\n} from './middleware'\nimport { createProcedureCaller } from './procedure-caller'\nimport type { Context, MergeContext, Meta, Promisable } from './types'\n\nexport class Procedure<\n TContext extends Context,\n TExtraContext extends Context,\n TInputSchema extends Schema,\n TOutputSchema extends Schema,\n THandlerOutput extends SchemaOutput<TOutputSchema>,\n> {\n constructor(\n public zz$p: {\n middlewares?: Middleware<any, any, any, any>[]\n contract: ContractProcedure<TInputSchema, TOutputSchema>\n handler: ProcedureHandler<\n TContext,\n TExtraContext,\n TInputSchema,\n TOutputSchema,\n THandlerOutput\n >\n },\n ) {}\n}\n\nexport type DecoratedProcedure<\n TContext extends Context,\n TExtraContext extends Context,\n TInputSchema extends Schema,\n TOutputSchema extends Schema,\n THandlerOutput extends SchemaOutput<TOutputSchema>,\n> = Procedure<\n TContext,\n TExtraContext,\n TInputSchema,\n TOutputSchema,\n THandlerOutput\n> & {\n prefix(\n prefix: HTTPPath,\n ): DecoratedProcedure<\n TContext,\n TExtraContext,\n TInputSchema,\n TOutputSchema,\n THandlerOutput\n >\n\n route(\n opts: RouteOptions,\n ): DecoratedProcedure<\n TContext,\n TExtraContext,\n TInputSchema,\n TOutputSchema,\n THandlerOutput\n >\n\n use<\n UExtraContext extends\n | Partial<MergeContext<Context, MergeContext<TContext, TExtraContext>>>\n | undefined = undefined,\n >(\n middleware: Middleware<\n MergeContext<TContext, TExtraContext>,\n UExtraContext,\n SchemaOutput<TInputSchema>,\n SchemaOutput<TOutputSchema, THandlerOutput>\n >,\n ): DecoratedProcedure<\n TContext,\n MergeContext<TExtraContext, UExtraContext>,\n TInputSchema,\n TOutputSchema,\n THandlerOutput\n >\n\n use<\n UExtraContext extends\n | Partial<MergeContext<Context, MergeContext<TContext, TExtraContext>>>\n | undefined = undefined,\n UMappedInput = unknown,\n >(\n middleware: Middleware<\n MergeContext<TContext, TExtraContext>,\n UExtraContext,\n UMappedInput,\n SchemaOutput<TOutputSchema, THandlerOutput>\n >,\n mapInput: MapInputMiddleware<\n SchemaOutput<TInputSchema, THandlerOutput>,\n UMappedInput\n >,\n ): DecoratedProcedure<\n TContext,\n MergeContext<TExtraContext, UExtraContext>,\n TInputSchema,\n TOutputSchema,\n THandlerOutput\n >\n} & (undefined extends TContext\n ? (\n input: SchemaInput<TInputSchema> | FormData,\n ) => Promise<SchemaOutput<TOutputSchema, THandlerOutput>>\n : // biome-ignore lint/complexity/noBannedTypes: {} seem has no side-effect on this case\n {})\n\nexport interface ProcedureHandler<\n TContext extends Context,\n TExtraContext extends Context,\n TInputSchema extends Schema,\n TOutputSchema extends Schema,\n TOutput extends SchemaOutput<TOutputSchema>,\n> {\n (\n input: SchemaOutput<TInputSchema>,\n context: MergeContext<TContext, TExtraContext>,\n meta: Meta<unknown>,\n ): Promisable<SchemaInput<TOutputSchema, TOutput>>\n}\n\nconst DECORATED_PROCEDURE_SYMBOL = Symbol('DECORATED_PROCEDURE')\n\nexport function decorateProcedure<\n TContext extends Context,\n TExtraContext extends Context,\n TInputSchema extends Schema,\n TOutputSchema extends Schema,\n THandlerOutput extends SchemaOutput<TOutputSchema>,\n>(\n procedure: Procedure<\n TContext,\n TExtraContext,\n TInputSchema,\n TOutputSchema,\n THandlerOutput\n >,\n): DecoratedProcedure<\n TContext,\n TExtraContext,\n TInputSchema,\n TOutputSchema,\n THandlerOutput\n> {\n if (DECORATED_PROCEDURE_SYMBOL in procedure) {\n return procedure as any\n }\n\n const serverAction = async (input: unknown) => {\n const input_ = (() => {\n if (!(input instanceof FormData)) return input\n\n const transformer = new OpenAPIDeserializer({\n schema: procedure.zz$p.contract.zz$cp.InputSchema,\n })\n\n return transformer.deserializeAsFormData(input)\n })()\n\n const procedureCaller = createProcedureCaller({\n procedure,\n context: undefined as any,\n internal: false,\n validate: true,\n })\n\n return await procedureCaller(input_ as any)\n }\n\n return Object.assign(serverAction, {\n [DECORATED_PROCEDURE_SYMBOL]: true,\n zz$p: procedure.zz$p,\n\n prefix(prefix: HTTPPath) {\n return decorateProcedure({\n zz$p: {\n ...procedure.zz$p,\n contract: DecoratedContractProcedure.decorate(\n procedure.zz$p.contract,\n ).prefix(prefix),\n },\n })\n },\n\n route(opts: RouteOptions) {\n return decorateProcedure({\n zz$p: {\n ...procedure.zz$p,\n contract: DecoratedContractProcedure.decorate(\n procedure.zz$p.contract,\n ).route(opts),\n },\n })\n },\n\n use(\n middleware: Middleware<any, any, any, any>,\n mapInput?: MapInputMiddleware<any, any>,\n ) {\n const middleware_ = mapInput\n ? decorateMiddleware(middleware).mapInput(mapInput)\n : middleware\n\n return decorateProcedure({\n zz$p: {\n ...procedure.zz$p,\n middlewares: [middleware_, ...(procedure.zz$p.middlewares ?? [])],\n },\n })\n },\n }) as any\n}\n\nexport type WELL_DEFINED_PROCEDURE = Procedure<\n Context,\n Context,\n Schema,\n Schema,\n unknown\n>\n\nexport function isProcedure(item: unknown): item is WELL_DEFINED_PROCEDURE {\n if (item instanceof Procedure) return true\n\n return (\n (typeof item === 'object' || typeof item === 'function') &&\n item !== null &&\n 'zz$p' in item &&\n typeof item.zz$p === 'object' &&\n item.zz$p !== null &&\n 'contract' in item.zz$p &&\n isContractProcedure(item.zz$p.contract) &&\n 'handler' in item.zz$p &&\n typeof item.zz$p.handler === 'function'\n )\n}\n"],"mappings":"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","names":["fn","e","mapInput","input"]}
|