@tanstack/start-client-core 1.114.7 → 1.114.9
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/cjs/createServerFn.cjs +142 -0
- package/dist/cjs/createServerFn.cjs.map +1 -1
- package/dist/cjs/createServerFn.d.cts +6 -1
- package/dist/cjs/index.cjs +6 -5
- package/dist/cjs/index.cjs.map +1 -1
- package/dist/cjs/index.d.cts +1 -1
- package/dist/cjs/tests/createServerFn.test-d.d.cts +1 -0
- package/dist/esm/createServerFn.d.ts +6 -1
- package/dist/esm/createServerFn.js +141 -0
- package/dist/esm/createServerFn.js.map +1 -1
- package/dist/esm/index.d.ts +1 -1
- package/dist/esm/index.js +2 -1
- package/dist/esm/tests/createServerFn.test-d.d.ts +1 -0
- package/package.json +1 -1
- package/src/createServerFn.ts +255 -1
- package/src/index.tsx +1 -1
- package/src/tests/createServerFn.test-d.ts +488 -0
|
@@ -0,0 +1,488 @@
|
|
|
1
|
+
import { describe, expectTypeOf, test } from 'vitest'
|
|
2
|
+
import { createMiddleware } from '../createMiddleware'
|
|
3
|
+
import { createServerFn } from '../createServerFn'
|
|
4
|
+
import type { Constrain, Validator } from '@tanstack/router-core'
|
|
5
|
+
|
|
6
|
+
test('createServerFn method with autocomplete', () => {
|
|
7
|
+
createServerFn().handler((options) => {
|
|
8
|
+
expectTypeOf(options.method).toEqualTypeOf<'GET' | 'POST'>()
|
|
9
|
+
})
|
|
10
|
+
})
|
|
11
|
+
|
|
12
|
+
test('createServerFn without middleware', () => {
|
|
13
|
+
expectTypeOf(createServerFn()).toHaveProperty('handler')
|
|
14
|
+
expectTypeOf(createServerFn()).toHaveProperty('middleware')
|
|
15
|
+
expectTypeOf(createServerFn()).toHaveProperty('validator')
|
|
16
|
+
|
|
17
|
+
createServerFn({ method: 'GET' }).handler((options) => {
|
|
18
|
+
expectTypeOf(options).toEqualTypeOf<{
|
|
19
|
+
method: 'GET'
|
|
20
|
+
context: undefined
|
|
21
|
+
data: undefined
|
|
22
|
+
signal: AbortSignal
|
|
23
|
+
response: 'data'
|
|
24
|
+
}>()
|
|
25
|
+
})
|
|
26
|
+
})
|
|
27
|
+
|
|
28
|
+
test('createServerFn with validator', () => {
|
|
29
|
+
const fnAfterValidator = createServerFn({
|
|
30
|
+
method: 'GET',
|
|
31
|
+
}).validator((input: { input: string }) => ({
|
|
32
|
+
a: input.input,
|
|
33
|
+
}))
|
|
34
|
+
|
|
35
|
+
expectTypeOf(fnAfterValidator).toHaveProperty('handler')
|
|
36
|
+
expectTypeOf(fnAfterValidator).toHaveProperty('middleware')
|
|
37
|
+
expectTypeOf(fnAfterValidator).not.toHaveProperty('validator')
|
|
38
|
+
|
|
39
|
+
const fn = fnAfterValidator.handler((options) => {
|
|
40
|
+
expectTypeOf(options).toEqualTypeOf<{
|
|
41
|
+
method: 'GET'
|
|
42
|
+
context: undefined
|
|
43
|
+
data: {
|
|
44
|
+
a: string
|
|
45
|
+
}
|
|
46
|
+
signal: AbortSignal
|
|
47
|
+
response: 'data'
|
|
48
|
+
}>()
|
|
49
|
+
})
|
|
50
|
+
|
|
51
|
+
expectTypeOf(fn).parameter(0).toEqualTypeOf<{
|
|
52
|
+
data: { input: string }
|
|
53
|
+
headers?: HeadersInit
|
|
54
|
+
type?: 'static' | 'dynamic'
|
|
55
|
+
signal?: AbortSignal
|
|
56
|
+
}>()
|
|
57
|
+
|
|
58
|
+
expectTypeOf<ReturnType<typeof fn>>().resolves.toEqualTypeOf<void>()
|
|
59
|
+
})
|
|
60
|
+
|
|
61
|
+
test('createServerFn with middleware and context', () => {
|
|
62
|
+
const middleware1 = createMiddleware().server(({ next }) => {
|
|
63
|
+
return next({ context: { a: 'a' } as const })
|
|
64
|
+
})
|
|
65
|
+
|
|
66
|
+
const middleware2 = createMiddleware().server(({ next }) => {
|
|
67
|
+
return next({ context: { b: 'b' } as const })
|
|
68
|
+
})
|
|
69
|
+
|
|
70
|
+
const middleware3 = createMiddleware()
|
|
71
|
+
.middleware([middleware1, middleware2])
|
|
72
|
+
.client(({ next }) => {
|
|
73
|
+
return next({ context: { c: 'c' } as const })
|
|
74
|
+
})
|
|
75
|
+
|
|
76
|
+
const middleware4 = createMiddleware()
|
|
77
|
+
.middleware([middleware3])
|
|
78
|
+
.client(({ context, next }) => {
|
|
79
|
+
return next({ sendContext: context })
|
|
80
|
+
})
|
|
81
|
+
.server(({ context, next }) => {
|
|
82
|
+
expectTypeOf(context).toEqualTypeOf<{
|
|
83
|
+
readonly a: 'a'
|
|
84
|
+
readonly b: 'b'
|
|
85
|
+
readonly c: 'c'
|
|
86
|
+
}>()
|
|
87
|
+
return next({ context: { d: 'd' } as const })
|
|
88
|
+
})
|
|
89
|
+
|
|
90
|
+
const fnWithMiddleware = createServerFn({ method: 'GET' }).middleware([
|
|
91
|
+
middleware4,
|
|
92
|
+
])
|
|
93
|
+
|
|
94
|
+
expectTypeOf(fnWithMiddleware).toHaveProperty('handler')
|
|
95
|
+
expectTypeOf(fnWithMiddleware).toHaveProperty('validator')
|
|
96
|
+
expectTypeOf(fnWithMiddleware).not.toHaveProperty('middleware')
|
|
97
|
+
|
|
98
|
+
fnWithMiddleware.handler((options) => {
|
|
99
|
+
expectTypeOf(options).toEqualTypeOf<{
|
|
100
|
+
method: 'GET'
|
|
101
|
+
context: {
|
|
102
|
+
readonly a: 'a'
|
|
103
|
+
readonly b: 'b'
|
|
104
|
+
readonly c: 'c'
|
|
105
|
+
readonly d: 'd'
|
|
106
|
+
}
|
|
107
|
+
data: undefined
|
|
108
|
+
signal: AbortSignal
|
|
109
|
+
response: 'data'
|
|
110
|
+
}>()
|
|
111
|
+
})
|
|
112
|
+
})
|
|
113
|
+
|
|
114
|
+
describe('createServerFn with middleware and validator', () => {
|
|
115
|
+
const middleware1 = createMiddleware().validator(
|
|
116
|
+
(input: { readonly inputA: 'inputA' }) =>
|
|
117
|
+
({
|
|
118
|
+
outputA: 'outputA',
|
|
119
|
+
}) as const,
|
|
120
|
+
)
|
|
121
|
+
|
|
122
|
+
const middleware2 = createMiddleware().validator(
|
|
123
|
+
(input: { readonly inputB: 'inputB' }) =>
|
|
124
|
+
({
|
|
125
|
+
outputB: 'outputB',
|
|
126
|
+
}) as const,
|
|
127
|
+
)
|
|
128
|
+
|
|
129
|
+
const middleware3 = createMiddleware().middleware([middleware1, middleware2])
|
|
130
|
+
|
|
131
|
+
test(`response: 'data'`, () => {
|
|
132
|
+
const fn = createServerFn({ method: 'GET', response: 'data' })
|
|
133
|
+
.middleware([middleware3])
|
|
134
|
+
.validator(
|
|
135
|
+
(input: { readonly inputC: 'inputC' }) =>
|
|
136
|
+
({
|
|
137
|
+
outputC: 'outputC',
|
|
138
|
+
}) as const,
|
|
139
|
+
)
|
|
140
|
+
.handler((options) => {
|
|
141
|
+
expectTypeOf(options).toEqualTypeOf<{
|
|
142
|
+
method: 'GET'
|
|
143
|
+
context: undefined
|
|
144
|
+
data: {
|
|
145
|
+
readonly outputA: 'outputA'
|
|
146
|
+
readonly outputB: 'outputB'
|
|
147
|
+
readonly outputC: 'outputC'
|
|
148
|
+
}
|
|
149
|
+
signal: AbortSignal
|
|
150
|
+
response: 'data'
|
|
151
|
+
}>()
|
|
152
|
+
|
|
153
|
+
return 'some-data' as const
|
|
154
|
+
})
|
|
155
|
+
|
|
156
|
+
expectTypeOf(fn).parameter(0).toEqualTypeOf<{
|
|
157
|
+
data: {
|
|
158
|
+
readonly inputA: 'inputA'
|
|
159
|
+
readonly inputB: 'inputB'
|
|
160
|
+
readonly inputC: 'inputC'
|
|
161
|
+
}
|
|
162
|
+
headers?: HeadersInit
|
|
163
|
+
type?: 'static' | 'dynamic'
|
|
164
|
+
signal?: AbortSignal
|
|
165
|
+
}>()
|
|
166
|
+
|
|
167
|
+
expectTypeOf(fn).returns.resolves.toEqualTypeOf<'some-data'>()
|
|
168
|
+
expectTypeOf(() =>
|
|
169
|
+
fn({
|
|
170
|
+
data: { inputA: 'inputA', inputB: 'inputB', inputC: 'inputC' },
|
|
171
|
+
}),
|
|
172
|
+
).returns.resolves.toEqualTypeOf<'some-data'>()
|
|
173
|
+
})
|
|
174
|
+
|
|
175
|
+
test(`response: 'full'`, () => {
|
|
176
|
+
const fn = createServerFn({ method: 'GET', response: 'full' })
|
|
177
|
+
.middleware([middleware3])
|
|
178
|
+
.validator(
|
|
179
|
+
(input: { readonly inputC: 'inputC' }) =>
|
|
180
|
+
({
|
|
181
|
+
outputC: 'outputC',
|
|
182
|
+
}) as const,
|
|
183
|
+
)
|
|
184
|
+
.handler((options) => {
|
|
185
|
+
expectTypeOf(options).toEqualTypeOf<{
|
|
186
|
+
method: 'GET'
|
|
187
|
+
context: undefined
|
|
188
|
+
data: {
|
|
189
|
+
readonly outputA: 'outputA'
|
|
190
|
+
readonly outputB: 'outputB'
|
|
191
|
+
readonly outputC: 'outputC'
|
|
192
|
+
}
|
|
193
|
+
signal: AbortSignal
|
|
194
|
+
response: 'full'
|
|
195
|
+
}>()
|
|
196
|
+
|
|
197
|
+
return 'some-data' as const
|
|
198
|
+
})
|
|
199
|
+
|
|
200
|
+
expectTypeOf(fn).parameter(0).toEqualTypeOf<{
|
|
201
|
+
data: {
|
|
202
|
+
readonly inputA: 'inputA'
|
|
203
|
+
readonly inputB: 'inputB'
|
|
204
|
+
readonly inputC: 'inputC'
|
|
205
|
+
}
|
|
206
|
+
headers?: HeadersInit
|
|
207
|
+
type?: 'static' | 'dynamic'
|
|
208
|
+
signal?: AbortSignal
|
|
209
|
+
}>()
|
|
210
|
+
|
|
211
|
+
expectTypeOf(() =>
|
|
212
|
+
fn({
|
|
213
|
+
data: { inputA: 'inputA', inputB: 'inputB', inputC: 'inputC' },
|
|
214
|
+
}),
|
|
215
|
+
).returns.resolves.toEqualTypeOf<{
|
|
216
|
+
result: 'some-data'
|
|
217
|
+
context: undefined
|
|
218
|
+
error: unknown
|
|
219
|
+
}>()
|
|
220
|
+
})
|
|
221
|
+
})
|
|
222
|
+
|
|
223
|
+
test('createServerFn overrides properties', () => {
|
|
224
|
+
const middleware1 = createMiddleware()
|
|
225
|
+
.validator(
|
|
226
|
+
() =>
|
|
227
|
+
({
|
|
228
|
+
input: 'a' as 'a' | 'b' | 'c',
|
|
229
|
+
}) as const,
|
|
230
|
+
)
|
|
231
|
+
.client(({ context, next }) => {
|
|
232
|
+
expectTypeOf(context).toEqualTypeOf<undefined>()
|
|
233
|
+
|
|
234
|
+
const newContext = { context: 'a' } as const
|
|
235
|
+
return next({ sendContext: newContext, context: newContext })
|
|
236
|
+
})
|
|
237
|
+
.server(({ data, context, next }) => {
|
|
238
|
+
expectTypeOf(data).toEqualTypeOf<{ readonly input: 'a' | 'b' | 'c' }>()
|
|
239
|
+
|
|
240
|
+
expectTypeOf(context).toEqualTypeOf<{
|
|
241
|
+
readonly context: 'a'
|
|
242
|
+
}>()
|
|
243
|
+
|
|
244
|
+
const newContext = { context: 'b' } as const
|
|
245
|
+
return next({ sendContext: newContext, context: newContext })
|
|
246
|
+
})
|
|
247
|
+
|
|
248
|
+
const middleware2 = createMiddleware()
|
|
249
|
+
.middleware([middleware1])
|
|
250
|
+
.validator(
|
|
251
|
+
() =>
|
|
252
|
+
({
|
|
253
|
+
input: 'b' as 'b' | 'c',
|
|
254
|
+
}) as const,
|
|
255
|
+
)
|
|
256
|
+
.client(({ context, next }) => {
|
|
257
|
+
expectTypeOf(context).toEqualTypeOf<{ readonly context: 'a' }>()
|
|
258
|
+
|
|
259
|
+
const newContext = { context: 'aa' } as const
|
|
260
|
+
|
|
261
|
+
return next({ sendContext: newContext, context: newContext })
|
|
262
|
+
})
|
|
263
|
+
.server(({ context, next }) => {
|
|
264
|
+
expectTypeOf(context).toEqualTypeOf<{ readonly context: 'aa' }>()
|
|
265
|
+
|
|
266
|
+
const newContext = { context: 'bb' } as const
|
|
267
|
+
|
|
268
|
+
return next({ sendContext: newContext, context: newContext })
|
|
269
|
+
})
|
|
270
|
+
|
|
271
|
+
createServerFn()
|
|
272
|
+
.middleware([middleware2])
|
|
273
|
+
.validator(
|
|
274
|
+
() =>
|
|
275
|
+
({
|
|
276
|
+
input: 'c',
|
|
277
|
+
}) as const,
|
|
278
|
+
)
|
|
279
|
+
.handler(({ data, context }) => {
|
|
280
|
+
expectTypeOf(data).toEqualTypeOf<{
|
|
281
|
+
readonly input: 'c'
|
|
282
|
+
}>()
|
|
283
|
+
expectTypeOf(context).toEqualTypeOf<{ readonly context: 'bb' }>()
|
|
284
|
+
})
|
|
285
|
+
})
|
|
286
|
+
|
|
287
|
+
test('createServerFn where validator is a primitive', () => {
|
|
288
|
+
createServerFn({ method: 'GET' })
|
|
289
|
+
.validator(() => 'c' as const)
|
|
290
|
+
.handler((options) => {
|
|
291
|
+
expectTypeOf(options).toEqualTypeOf<{
|
|
292
|
+
method: 'GET'
|
|
293
|
+
context: undefined
|
|
294
|
+
data: 'c'
|
|
295
|
+
signal: AbortSignal
|
|
296
|
+
response: 'data'
|
|
297
|
+
}>()
|
|
298
|
+
})
|
|
299
|
+
})
|
|
300
|
+
|
|
301
|
+
test('createServerFn where validator is optional if object is optional', () => {
|
|
302
|
+
const fn = createServerFn({ method: 'GET' })
|
|
303
|
+
.validator((input: 'c' | undefined) => input)
|
|
304
|
+
.handler((options) => {
|
|
305
|
+
expectTypeOf(options).toEqualTypeOf<{
|
|
306
|
+
method: 'GET'
|
|
307
|
+
context: undefined
|
|
308
|
+
data: 'c' | undefined
|
|
309
|
+
signal: AbortSignal
|
|
310
|
+
response: 'data'
|
|
311
|
+
}>()
|
|
312
|
+
})
|
|
313
|
+
|
|
314
|
+
expectTypeOf(fn).parameter(0).toEqualTypeOf<
|
|
315
|
+
| {
|
|
316
|
+
data?: 'c' | undefined
|
|
317
|
+
headers?: HeadersInit
|
|
318
|
+
type?: 'static' | 'dynamic'
|
|
319
|
+
signal?: AbortSignal
|
|
320
|
+
}
|
|
321
|
+
| undefined
|
|
322
|
+
>()
|
|
323
|
+
|
|
324
|
+
expectTypeOf<ReturnType<typeof fn>>().resolves.toEqualTypeOf<void>()
|
|
325
|
+
})
|
|
326
|
+
|
|
327
|
+
test('createServerFn where data is optional if there is no validator', () => {
|
|
328
|
+
const fn = createServerFn({ method: 'GET' }).handler((options) => {
|
|
329
|
+
expectTypeOf(options).toEqualTypeOf<{
|
|
330
|
+
method: 'GET'
|
|
331
|
+
context: undefined
|
|
332
|
+
data: undefined
|
|
333
|
+
signal: AbortSignal
|
|
334
|
+
response: 'data'
|
|
335
|
+
}>()
|
|
336
|
+
})
|
|
337
|
+
|
|
338
|
+
expectTypeOf(fn).parameter(0).toEqualTypeOf<
|
|
339
|
+
| {
|
|
340
|
+
data?: undefined
|
|
341
|
+
headers?: HeadersInit
|
|
342
|
+
type?: 'static' | 'dynamic'
|
|
343
|
+
signal?: AbortSignal
|
|
344
|
+
}
|
|
345
|
+
| undefined
|
|
346
|
+
>()
|
|
347
|
+
|
|
348
|
+
expectTypeOf<ReturnType<typeof fn>>().resolves.toEqualTypeOf<void>()
|
|
349
|
+
})
|
|
350
|
+
|
|
351
|
+
test('createServerFn returns Date', () => {
|
|
352
|
+
const fn = createServerFn().handler(() => ({
|
|
353
|
+
dates: [new Date(), new Date()] as const,
|
|
354
|
+
}))
|
|
355
|
+
|
|
356
|
+
expectTypeOf(fn()).toEqualTypeOf<Promise<{ dates: readonly [Date, Date] }>>()
|
|
357
|
+
})
|
|
358
|
+
|
|
359
|
+
test('createServerFn returns undefined', () => {
|
|
360
|
+
const fn = createServerFn().handler(() => ({
|
|
361
|
+
nothing: undefined,
|
|
362
|
+
}))
|
|
363
|
+
|
|
364
|
+
expectTypeOf(fn()).toEqualTypeOf<Promise<{ nothing: undefined }>>()
|
|
365
|
+
})
|
|
366
|
+
|
|
367
|
+
test('createServerFn cannot return function', () => {
|
|
368
|
+
expectTypeOf(createServerFn().handler<{ func: () => 'func' }>)
|
|
369
|
+
.parameter(0)
|
|
370
|
+
.returns.toEqualTypeOf<
|
|
371
|
+
| { func: 'Function is not serializable' }
|
|
372
|
+
| Promise<{ func: 'Function is not serializable' }>
|
|
373
|
+
>()
|
|
374
|
+
})
|
|
375
|
+
|
|
376
|
+
test('createServerFn cannot validate function', () => {
|
|
377
|
+
const validator = createServerFn().validator<
|
|
378
|
+
(input: { func: () => 'string' }) => { output: 'string' }
|
|
379
|
+
>
|
|
380
|
+
|
|
381
|
+
expectTypeOf(validator)
|
|
382
|
+
.parameter(0)
|
|
383
|
+
.toEqualTypeOf<
|
|
384
|
+
Constrain<
|
|
385
|
+
(input: { func: () => 'string' }) => { output: 'string' },
|
|
386
|
+
Validator<{ func: 'Function is not serializable' }, any>
|
|
387
|
+
>
|
|
388
|
+
>()
|
|
389
|
+
})
|
|
390
|
+
|
|
391
|
+
test('createServerFn can validate Date', () => {
|
|
392
|
+
const validator = createServerFn().validator<
|
|
393
|
+
(input: Date) => { output: 'string' }
|
|
394
|
+
>
|
|
395
|
+
|
|
396
|
+
expectTypeOf(validator)
|
|
397
|
+
.parameter(0)
|
|
398
|
+
.toEqualTypeOf<
|
|
399
|
+
Constrain<(input: Date) => { output: 'string' }, Validator<Date, any>>
|
|
400
|
+
>()
|
|
401
|
+
})
|
|
402
|
+
|
|
403
|
+
test('createServerFn can validate FormData', () => {
|
|
404
|
+
const validator = createServerFn().validator<
|
|
405
|
+
(input: FormData) => { output: 'string' }
|
|
406
|
+
>
|
|
407
|
+
|
|
408
|
+
expectTypeOf(validator)
|
|
409
|
+
.parameter(0)
|
|
410
|
+
.toEqualTypeOf<
|
|
411
|
+
Constrain<
|
|
412
|
+
(input: FormData) => { output: 'string' },
|
|
413
|
+
Validator<FormData, any>
|
|
414
|
+
>
|
|
415
|
+
>()
|
|
416
|
+
})
|
|
417
|
+
|
|
418
|
+
describe('response', () => {
|
|
419
|
+
describe('data', () => {
|
|
420
|
+
test(`response: 'data' is passed into handler without response being set`, () => {
|
|
421
|
+
createServerFn().handler((options) => {
|
|
422
|
+
expectTypeOf(options.response).toEqualTypeOf<'data'>()
|
|
423
|
+
})
|
|
424
|
+
})
|
|
425
|
+
|
|
426
|
+
test(`response: 'data' is passed into handler with explicit response: 'data'`, () => {
|
|
427
|
+
createServerFn({ response: 'data' }).handler((options) => {
|
|
428
|
+
expectTypeOf(options.response).toEqualTypeOf<'data'>()
|
|
429
|
+
})
|
|
430
|
+
})
|
|
431
|
+
})
|
|
432
|
+
describe('full', () => {
|
|
433
|
+
test(`response: 'full' is passed into handler`, () => {
|
|
434
|
+
createServerFn({ response: 'full' }).handler((options) => {
|
|
435
|
+
expectTypeOf(options.response).toEqualTypeOf<'full'>()
|
|
436
|
+
})
|
|
437
|
+
})
|
|
438
|
+
})
|
|
439
|
+
|
|
440
|
+
describe('raw', () => {
|
|
441
|
+
test(`response: 'raw' is passed into handler`, () => {
|
|
442
|
+
createServerFn({ response: 'raw' }).handler((options) => {
|
|
443
|
+
expectTypeOf(options.response).toEqualTypeOf<'raw'>()
|
|
444
|
+
return null
|
|
445
|
+
})
|
|
446
|
+
})
|
|
447
|
+
})
|
|
448
|
+
test(`client receives Response when Response is returned`, () => {
|
|
449
|
+
const fn = createServerFn({ response: 'raw' }).handler(() => {
|
|
450
|
+
return new Response('Hello World')
|
|
451
|
+
})
|
|
452
|
+
|
|
453
|
+
expectTypeOf(fn()).toEqualTypeOf<Promise<Response>>()
|
|
454
|
+
})
|
|
455
|
+
|
|
456
|
+
test(`client receives Response when ReadableStream is returned`, () => {
|
|
457
|
+
const fn = createServerFn({ response: 'raw' }).handler(() => {
|
|
458
|
+
return new ReadableStream()
|
|
459
|
+
})
|
|
460
|
+
|
|
461
|
+
expectTypeOf(fn()).toEqualTypeOf<Promise<Response>>()
|
|
462
|
+
})
|
|
463
|
+
|
|
464
|
+
test(`client receives Response when string is returned`, () => {
|
|
465
|
+
const fn = createServerFn({ response: 'raw' }).handler(() => {
|
|
466
|
+
return 'hello'
|
|
467
|
+
})
|
|
468
|
+
|
|
469
|
+
expectTypeOf(fn()).toEqualTypeOf<Promise<Response>>()
|
|
470
|
+
})
|
|
471
|
+
})
|
|
472
|
+
|
|
473
|
+
test('createServerFn can be used as a mutation function', () => {
|
|
474
|
+
const serverFn = createServerFn()
|
|
475
|
+
.validator((data: number) => data)
|
|
476
|
+
.handler(() => 'foo')
|
|
477
|
+
|
|
478
|
+
type MutationFunction<TData = unknown, TVariables = unknown> = (
|
|
479
|
+
variables: TVariables,
|
|
480
|
+
) => Promise<TData>
|
|
481
|
+
|
|
482
|
+
// simplifeid "clone" of @tansctack/react-query's useMutation
|
|
483
|
+
const useMutation = <TData, TVariables>(
|
|
484
|
+
fn: MutationFunction<TData, TVariables>,
|
|
485
|
+
) => {}
|
|
486
|
+
|
|
487
|
+
useMutation(serverFn)
|
|
488
|
+
})
|