@tanstack/react-form 0.13.7 → 0.14.0
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/createFormFactory.cjs.map +1 -1
- package/dist/cjs/createFormFactory.d.cts +3 -3
- package/dist/cjs/types.d.cts +2 -2
- package/dist/cjs/useField.cjs +4 -17
- package/dist/cjs/useField.cjs.map +1 -1
- package/dist/cjs/useField.d.cts +4 -12
- package/dist/cjs/useForm.cjs +4 -6
- package/dist/cjs/useForm.cjs.map +1 -1
- package/dist/cjs/useForm.d.cts +3 -4
- package/dist/esm/createFormFactory.d.ts +3 -3
- package/dist/esm/createFormFactory.js.map +1 -1
- package/dist/esm/types.d.ts +2 -2
- package/dist/esm/useField.d.ts +4 -12
- package/dist/esm/useField.js +5 -18
- package/dist/esm/useField.js.map +1 -1
- package/dist/esm/useForm.d.ts +3 -4
- package/dist/esm/useForm.js +4 -6
- package/dist/esm/useForm.js.map +1 -1
- package/package.json +2 -2
- package/src/createFormFactory.ts +4 -4
- package/src/tests/createFormFactory.test.tsx +4 -5
- package/src/tests/useField.test-d.tsx +5 -5
- package/src/tests/useField.test.tsx +160 -86
- package/src/tests/useForm.test-d.tsx +1 -1
- package/src/tests/useForm.test.tsx +24 -25
- package/src/types.ts +8 -2
- package/src/useField.tsx +23 -53
- package/src/useForm.tsx +8 -13
- package/dist/cjs/formContext.cjs +0 -14
- package/dist/cjs/formContext.cjs.map +0 -1
- package/dist/cjs/formContext.d.cts +0 -10
- package/dist/esm/formContext.d.ts +0 -10
- package/dist/esm/formContext.js +0 -14
- package/dist/esm/formContext.js.map +0 -1
- package/src/formContext.ts +0 -17
|
@@ -1,8 +1,7 @@
|
|
|
1
|
-
/// <reference lib="dom" />
|
|
2
1
|
import * as React from 'react'
|
|
2
|
+
import { describe, expect, it, vi } from 'vitest'
|
|
3
3
|
import { render, waitFor } from '@testing-library/react'
|
|
4
4
|
import userEvent from '@testing-library/user-event'
|
|
5
|
-
import '@testing-library/jest-dom'
|
|
6
5
|
import { createFormFactory, useForm } from '../index'
|
|
7
6
|
import { sleep } from './utils'
|
|
8
7
|
import type { FieldApi, FormApi } from '../index'
|
|
@@ -27,7 +26,7 @@ describe('useField', () => {
|
|
|
27
26
|
})
|
|
28
27
|
|
|
29
28
|
return (
|
|
30
|
-
|
|
29
|
+
<>
|
|
31
30
|
<form.Field
|
|
32
31
|
name="firstName"
|
|
33
32
|
children={(field) => {
|
|
@@ -41,7 +40,7 @@ describe('useField', () => {
|
|
|
41
40
|
)
|
|
42
41
|
}}
|
|
43
42
|
/>
|
|
44
|
-
|
|
43
|
+
</>
|
|
45
44
|
)
|
|
46
45
|
}
|
|
47
46
|
|
|
@@ -67,7 +66,7 @@ describe('useField', () => {
|
|
|
67
66
|
})
|
|
68
67
|
|
|
69
68
|
return (
|
|
70
|
-
|
|
69
|
+
<>
|
|
71
70
|
<form.Field
|
|
72
71
|
name="firstName"
|
|
73
72
|
defaultValue="otherName"
|
|
@@ -82,7 +81,7 @@ describe('useField', () => {
|
|
|
82
81
|
)
|
|
83
82
|
}}
|
|
84
83
|
/>
|
|
85
|
-
|
|
84
|
+
</>
|
|
86
85
|
)
|
|
87
86
|
}
|
|
88
87
|
|
|
@@ -109,7 +108,7 @@ describe('useField', () => {
|
|
|
109
108
|
})
|
|
110
109
|
|
|
111
110
|
return (
|
|
112
|
-
|
|
111
|
+
<>
|
|
113
112
|
<form.Field
|
|
114
113
|
name="firstName"
|
|
115
114
|
validators={{
|
|
@@ -128,7 +127,7 @@ describe('useField', () => {
|
|
|
128
127
|
</div>
|
|
129
128
|
)}
|
|
130
129
|
/>
|
|
131
|
-
|
|
130
|
+
</>
|
|
132
131
|
)
|
|
133
132
|
}
|
|
134
133
|
|
|
@@ -156,7 +155,7 @@ describe('useField', () => {
|
|
|
156
155
|
})
|
|
157
156
|
|
|
158
157
|
return (
|
|
159
|
-
|
|
158
|
+
<>
|
|
160
159
|
<form.Field
|
|
161
160
|
name="firstName"
|
|
162
161
|
defaultMeta={{ isTouched: true }}
|
|
@@ -176,7 +175,7 @@ describe('useField', () => {
|
|
|
176
175
|
</div>
|
|
177
176
|
)}
|
|
178
177
|
/>
|
|
179
|
-
|
|
178
|
+
</>
|
|
180
179
|
)
|
|
181
180
|
}
|
|
182
181
|
|
|
@@ -206,7 +205,7 @@ describe('useField', () => {
|
|
|
206
205
|
})
|
|
207
206
|
|
|
208
207
|
return (
|
|
209
|
-
|
|
208
|
+
<>
|
|
210
209
|
<form.Field
|
|
211
210
|
name="firstName"
|
|
212
211
|
defaultMeta={{ isTouched: true }}
|
|
@@ -230,7 +229,7 @@ describe('useField', () => {
|
|
|
230
229
|
</div>
|
|
231
230
|
)}
|
|
232
231
|
/>
|
|
233
|
-
|
|
232
|
+
</>
|
|
234
233
|
)
|
|
235
234
|
}
|
|
236
235
|
|
|
@@ -262,7 +261,7 @@ describe('useField', () => {
|
|
|
262
261
|
})
|
|
263
262
|
|
|
264
263
|
return (
|
|
265
|
-
|
|
264
|
+
<>
|
|
266
265
|
<form.Field
|
|
267
266
|
name="firstName"
|
|
268
267
|
defaultMeta={{ isTouched: true }}
|
|
@@ -285,7 +284,7 @@ describe('useField', () => {
|
|
|
285
284
|
</div>
|
|
286
285
|
)}
|
|
287
286
|
/>
|
|
288
|
-
|
|
287
|
+
</>
|
|
289
288
|
)
|
|
290
289
|
}
|
|
291
290
|
|
|
@@ -316,7 +315,7 @@ describe('useField', () => {
|
|
|
316
315
|
})
|
|
317
316
|
|
|
318
317
|
return (
|
|
319
|
-
|
|
318
|
+
<>
|
|
320
319
|
<form.Field
|
|
321
320
|
name="firstName"
|
|
322
321
|
defaultMeta={{ isTouched: true }}
|
|
@@ -344,7 +343,7 @@ describe('useField', () => {
|
|
|
344
343
|
</div>
|
|
345
344
|
)}
|
|
346
345
|
/>
|
|
347
|
-
|
|
346
|
+
</>
|
|
348
347
|
)
|
|
349
348
|
}
|
|
350
349
|
|
|
@@ -379,7 +378,7 @@ describe('useField', () => {
|
|
|
379
378
|
})
|
|
380
379
|
|
|
381
380
|
return (
|
|
382
|
-
|
|
381
|
+
<>
|
|
383
382
|
<form.Field
|
|
384
383
|
name="firstName"
|
|
385
384
|
defaultMeta={{ isTouched: true }}
|
|
@@ -404,7 +403,7 @@ describe('useField', () => {
|
|
|
404
403
|
</div>
|
|
405
404
|
)}
|
|
406
405
|
/>
|
|
407
|
-
|
|
406
|
+
</>
|
|
408
407
|
)
|
|
409
408
|
}
|
|
410
409
|
|
|
@@ -432,7 +431,7 @@ describe('useField', () => {
|
|
|
432
431
|
},
|
|
433
432
|
})
|
|
434
433
|
return (
|
|
435
|
-
|
|
434
|
+
<>
|
|
436
435
|
<form.Field
|
|
437
436
|
name="firstName"
|
|
438
437
|
defaultValue="hello"
|
|
@@ -448,7 +447,7 @@ describe('useField', () => {
|
|
|
448
447
|
)
|
|
449
448
|
}}
|
|
450
449
|
/>
|
|
451
|
-
|
|
450
|
+
</>
|
|
452
451
|
)
|
|
453
452
|
}
|
|
454
453
|
|
|
@@ -475,7 +474,7 @@ describe('useField', () => {
|
|
|
475
474
|
},
|
|
476
475
|
})
|
|
477
476
|
return (
|
|
478
|
-
|
|
477
|
+
<>
|
|
479
478
|
<form.Field
|
|
480
479
|
name="firstName"
|
|
481
480
|
defaultValue="hello"
|
|
@@ -491,7 +490,7 @@ describe('useField', () => {
|
|
|
491
490
|
)
|
|
492
491
|
}}
|
|
493
492
|
/>
|
|
494
|
-
|
|
493
|
+
</>
|
|
495
494
|
)
|
|
496
495
|
}
|
|
497
496
|
|
|
@@ -529,74 +528,69 @@ describe('useField', () => {
|
|
|
529
528
|
|
|
530
529
|
return (
|
|
531
530
|
<div>
|
|
532
|
-
<form
|
|
533
|
-
|
|
534
|
-
|
|
535
|
-
|
|
536
|
-
|
|
537
|
-
|
|
538
|
-
|
|
539
|
-
>
|
|
540
|
-
|
|
541
|
-
|
|
542
|
-
{showField ? (
|
|
543
|
-
<form.Field
|
|
544
|
-
name="firstName"
|
|
545
|
-
validators={{
|
|
546
|
-
onChange: ({ value }) =>
|
|
547
|
-
!value ? 'A first name is required' : undefined,
|
|
548
|
-
}}
|
|
549
|
-
children={(field) => {
|
|
550
|
-
// Avoid hasty abstractions. Render props are great!
|
|
551
|
-
return (
|
|
552
|
-
<>
|
|
553
|
-
<label htmlFor={field.name}>First Name:</label>
|
|
554
|
-
<input
|
|
555
|
-
name={field.name}
|
|
556
|
-
value={field.state.value}
|
|
557
|
-
onBlur={field.handleBlur}
|
|
558
|
-
onChange={(e) => field.handleChange(e.target.value)}
|
|
559
|
-
/>
|
|
560
|
-
<FieldInfo field={field} />
|
|
561
|
-
</>
|
|
562
|
-
)
|
|
563
|
-
}}
|
|
564
|
-
/>
|
|
565
|
-
) : null}
|
|
566
|
-
</div>
|
|
567
|
-
<div>
|
|
531
|
+
<form
|
|
532
|
+
onSubmit={(e) => {
|
|
533
|
+
e.preventDefault()
|
|
534
|
+
e.stopPropagation()
|
|
535
|
+
void form.handleSubmit()
|
|
536
|
+
}}
|
|
537
|
+
>
|
|
538
|
+
<div>
|
|
539
|
+
{/* A type-safe field component*/}
|
|
540
|
+
{showField ? (
|
|
568
541
|
<form.Field
|
|
569
|
-
name="
|
|
570
|
-
|
|
571
|
-
|
|
572
|
-
|
|
573
|
-
|
|
574
|
-
|
|
575
|
-
|
|
576
|
-
|
|
577
|
-
|
|
578
|
-
|
|
579
|
-
|
|
580
|
-
|
|
581
|
-
|
|
542
|
+
name="firstName"
|
|
543
|
+
validators={{
|
|
544
|
+
onChange: ({ value }) =>
|
|
545
|
+
!value ? 'A first name is required' : undefined,
|
|
546
|
+
}}
|
|
547
|
+
children={(field) => {
|
|
548
|
+
// Avoid hasty abstractions. Render props are great!
|
|
549
|
+
return (
|
|
550
|
+
<>
|
|
551
|
+
<label htmlFor={field.name}>First Name:</label>
|
|
552
|
+
<input
|
|
553
|
+
name={field.name}
|
|
554
|
+
value={field.state.value}
|
|
555
|
+
onBlur={field.handleBlur}
|
|
556
|
+
onChange={(e) => field.handleChange(e.target.value)}
|
|
557
|
+
/>
|
|
558
|
+
<FieldInfo field={field} />
|
|
559
|
+
</>
|
|
560
|
+
)
|
|
561
|
+
}}
|
|
582
562
|
/>
|
|
583
|
-
|
|
584
|
-
|
|
585
|
-
|
|
586
|
-
|
|
587
|
-
|
|
588
|
-
|
|
589
|
-
|
|
563
|
+
) : null}
|
|
564
|
+
</div>
|
|
565
|
+
<div>
|
|
566
|
+
<form.Field
|
|
567
|
+
name="lastName"
|
|
568
|
+
children={(field) => (
|
|
569
|
+
<>
|
|
570
|
+
<label htmlFor={field.name}>Last Name:</label>
|
|
571
|
+
<input
|
|
572
|
+
name={field.name}
|
|
573
|
+
value={field.state.value}
|
|
574
|
+
onBlur={field.handleBlur}
|
|
575
|
+
onChange={(e) => field.handleChange(e.target.value)}
|
|
576
|
+
/>
|
|
577
|
+
<FieldInfo field={field} />
|
|
578
|
+
</>
|
|
590
579
|
)}
|
|
591
580
|
/>
|
|
592
|
-
|
|
593
|
-
|
|
594
|
-
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
|
|
598
|
-
|
|
599
|
-
|
|
581
|
+
</div>
|
|
582
|
+
<form.Subscribe
|
|
583
|
+
selector={(state) => [state.canSubmit, state.isSubmitting]}
|
|
584
|
+
children={([canSubmit, isSubmitting]) => (
|
|
585
|
+
<button type="submit" disabled={!canSubmit}>
|
|
586
|
+
{isSubmitting ? '...' : 'Submit'}
|
|
587
|
+
</button>
|
|
588
|
+
)}
|
|
589
|
+
/>
|
|
590
|
+
<button type="button" onClick={() => setShowField((prev) => !prev)}>
|
|
591
|
+
{showField ? 'Hide field' : 'Show field'}
|
|
592
|
+
</button>
|
|
593
|
+
</form>
|
|
600
594
|
</div>
|
|
601
595
|
)
|
|
602
596
|
}
|
|
@@ -613,4 +607,84 @@ describe('useField', () => {
|
|
|
613
607
|
await user.click(getByText('Submit'))
|
|
614
608
|
expect(queryByText('A first name is required')).not.toBeInTheDocument()
|
|
615
609
|
})
|
|
610
|
+
|
|
611
|
+
it('should handle arrays with subvalues', async () => {
|
|
612
|
+
const fn = vi.fn()
|
|
613
|
+
function Comp() {
|
|
614
|
+
const form = useForm({
|
|
615
|
+
defaultValues: {
|
|
616
|
+
people: [] as Array<{ age: number; name: string }>,
|
|
617
|
+
},
|
|
618
|
+
onSubmit: ({ value }) => fn(value),
|
|
619
|
+
})
|
|
620
|
+
|
|
621
|
+
return (
|
|
622
|
+
<div>
|
|
623
|
+
<form
|
|
624
|
+
onSubmit={(e) => {
|
|
625
|
+
e.preventDefault()
|
|
626
|
+
e.stopPropagation()
|
|
627
|
+
void form.handleSubmit()
|
|
628
|
+
}}
|
|
629
|
+
>
|
|
630
|
+
<form.Field name="people">
|
|
631
|
+
{(field) => {
|
|
632
|
+
return (
|
|
633
|
+
<div>
|
|
634
|
+
{field.state.value.map((_, i) => {
|
|
635
|
+
return (
|
|
636
|
+
<form.Field key={i} name={`people[${i}].name`}>
|
|
637
|
+
{(subField) => {
|
|
638
|
+
return (
|
|
639
|
+
<div>
|
|
640
|
+
<label>
|
|
641
|
+
<div>Name for person {i}</div>
|
|
642
|
+
<input
|
|
643
|
+
value={subField.state.value}
|
|
644
|
+
onChange={(e) =>
|
|
645
|
+
subField.handleChange(e.target.value)
|
|
646
|
+
}
|
|
647
|
+
/>
|
|
648
|
+
</label>
|
|
649
|
+
</div>
|
|
650
|
+
)
|
|
651
|
+
}}
|
|
652
|
+
</form.Field>
|
|
653
|
+
)
|
|
654
|
+
})}
|
|
655
|
+
<button
|
|
656
|
+
onClick={() => field.pushValue({ name: '', age: 0 })}
|
|
657
|
+
type="button"
|
|
658
|
+
>
|
|
659
|
+
Add person
|
|
660
|
+
</button>
|
|
661
|
+
</div>
|
|
662
|
+
)
|
|
663
|
+
}}
|
|
664
|
+
</form.Field>
|
|
665
|
+
<form.Subscribe
|
|
666
|
+
selector={(state) => [state.canSubmit, state.isSubmitting]}
|
|
667
|
+
children={([canSubmit, isSubmitting]) => (
|
|
668
|
+
<button type="submit" disabled={!canSubmit}>
|
|
669
|
+
{isSubmitting ? '...' : 'Submit'}
|
|
670
|
+
</button>
|
|
671
|
+
)}
|
|
672
|
+
/>
|
|
673
|
+
</form>
|
|
674
|
+
</div>
|
|
675
|
+
)
|
|
676
|
+
}
|
|
677
|
+
|
|
678
|
+
const { getByText, findByLabelText, queryByText, findByText } = render(
|
|
679
|
+
<Comp />,
|
|
680
|
+
)
|
|
681
|
+
|
|
682
|
+
expect(queryByText('Name for person 0')).not.toBeInTheDocument()
|
|
683
|
+
await user.click(getByText('Add person'))
|
|
684
|
+
const input = await findByLabelText('Name for person 0')
|
|
685
|
+
expect(input).toBeInTheDocument()
|
|
686
|
+
await user.type(input, 'John')
|
|
687
|
+
await user.click(await findByText('Submit'))
|
|
688
|
+
expect(fn).toHaveBeenCalledWith({ people: [{ name: 'John', age: 0 }] })
|
|
689
|
+
})
|
|
616
690
|
})
|
|
@@ -1,8 +1,7 @@
|
|
|
1
|
-
|
|
2
|
-
import '
|
|
1
|
+
import * as React from 'react'
|
|
2
|
+
import { describe, expect, it, vi } from 'vitest'
|
|
3
3
|
import { render, waitFor } from '@testing-library/react'
|
|
4
4
|
import userEvent from '@testing-library/user-event'
|
|
5
|
-
import * as React from 'react'
|
|
6
5
|
import { createFormFactory, useForm } from '../index'
|
|
7
6
|
import { sleep } from './utils'
|
|
8
7
|
|
|
@@ -21,7 +20,7 @@ describe('useForm', () => {
|
|
|
21
20
|
const form = formFactory.useForm()
|
|
22
21
|
|
|
23
22
|
return (
|
|
24
|
-
|
|
23
|
+
<>
|
|
25
24
|
<form.Field
|
|
26
25
|
name="firstName"
|
|
27
26
|
defaultValue={''}
|
|
@@ -36,7 +35,7 @@ describe('useForm', () => {
|
|
|
36
35
|
)
|
|
37
36
|
}}
|
|
38
37
|
/>
|
|
39
|
-
|
|
38
|
+
</>
|
|
40
39
|
)
|
|
41
40
|
}
|
|
42
41
|
|
|
@@ -64,14 +63,14 @@ describe('useForm', () => {
|
|
|
64
63
|
})
|
|
65
64
|
|
|
66
65
|
return (
|
|
67
|
-
|
|
66
|
+
<>
|
|
68
67
|
<form.Field
|
|
69
68
|
name="firstName"
|
|
70
69
|
children={(field) => {
|
|
71
70
|
return <p>{field.state.value}</p>
|
|
72
71
|
}}
|
|
73
72
|
/>
|
|
74
|
-
|
|
73
|
+
</>
|
|
75
74
|
)
|
|
76
75
|
}
|
|
77
76
|
|
|
@@ -96,7 +95,7 @@ describe('useForm', () => {
|
|
|
96
95
|
})
|
|
97
96
|
|
|
98
97
|
return (
|
|
99
|
-
|
|
98
|
+
<>
|
|
100
99
|
<form.Field
|
|
101
100
|
name="firstName"
|
|
102
101
|
children={(field) => {
|
|
@@ -112,7 +111,7 @@ describe('useForm', () => {
|
|
|
112
111
|
/>
|
|
113
112
|
<button onClick={form.handleSubmit}>Submit</button>
|
|
114
113
|
{submittedData && <p>Submitted data: {submittedData.firstName}</p>}
|
|
115
|
-
|
|
114
|
+
</>
|
|
116
115
|
)
|
|
117
116
|
}
|
|
118
117
|
|
|
@@ -146,9 +145,9 @@ describe('useForm', () => {
|
|
|
146
145
|
return (
|
|
147
146
|
<>
|
|
148
147
|
{mountForm ? (
|
|
149
|
-
|
|
148
|
+
<>
|
|
150
149
|
<h1>{formMounted ? 'Form mounted' : 'Not mounted'}</h1>
|
|
151
|
-
|
|
150
|
+
</>
|
|
152
151
|
) : (
|
|
153
152
|
<button onClick={() => setMountForm(true)}>Mount form</button>
|
|
154
153
|
)}
|
|
@@ -184,7 +183,7 @@ describe('useForm', () => {
|
|
|
184
183
|
})
|
|
185
184
|
const onChangeError = form.useStore((s) => s.errorMap.onChange)
|
|
186
185
|
return (
|
|
187
|
-
|
|
186
|
+
<>
|
|
188
187
|
<form.Field
|
|
189
188
|
name="firstName"
|
|
190
189
|
children={(field) => (
|
|
@@ -198,7 +197,7 @@ describe('useForm', () => {
|
|
|
198
197
|
)}
|
|
199
198
|
/>
|
|
200
199
|
<p>{onChangeError}</p>
|
|
201
|
-
|
|
200
|
+
</>
|
|
202
201
|
)
|
|
203
202
|
}
|
|
204
203
|
|
|
@@ -233,7 +232,7 @@ describe('useForm', () => {
|
|
|
233
232
|
|
|
234
233
|
const errors = form.useStore((s) => s.errors)
|
|
235
234
|
return (
|
|
236
|
-
|
|
235
|
+
<>
|
|
237
236
|
<form.Field
|
|
238
237
|
name="firstName"
|
|
239
238
|
children={(field) => (
|
|
@@ -249,7 +248,7 @@ describe('useForm', () => {
|
|
|
249
248
|
</div>
|
|
250
249
|
)}
|
|
251
250
|
/>
|
|
252
|
-
|
|
251
|
+
</>
|
|
253
252
|
)
|
|
254
253
|
}
|
|
255
254
|
|
|
@@ -281,7 +280,7 @@ describe('useForm', () => {
|
|
|
281
280
|
})
|
|
282
281
|
const errors = form.useStore((s) => s.errorMap)
|
|
283
282
|
return (
|
|
284
|
-
|
|
283
|
+
<>
|
|
285
284
|
<form.Field
|
|
286
285
|
name="firstName"
|
|
287
286
|
defaultMeta={{ isTouched: true }}
|
|
@@ -298,7 +297,7 @@ describe('useForm', () => {
|
|
|
298
297
|
</div>
|
|
299
298
|
)}
|
|
300
299
|
/>
|
|
301
|
-
|
|
300
|
+
</>
|
|
302
301
|
)
|
|
303
302
|
}
|
|
304
303
|
|
|
@@ -332,7 +331,7 @@ describe('useForm', () => {
|
|
|
332
331
|
|
|
333
332
|
const errors = form.useStore((s) => s.errorMap)
|
|
334
333
|
return (
|
|
335
|
-
|
|
334
|
+
<>
|
|
336
335
|
<form.Field
|
|
337
336
|
name="firstName"
|
|
338
337
|
defaultMeta={{ isTouched: true }}
|
|
@@ -350,7 +349,7 @@ describe('useForm', () => {
|
|
|
350
349
|
</div>
|
|
351
350
|
)}
|
|
352
351
|
/>
|
|
353
|
-
|
|
352
|
+
</>
|
|
354
353
|
)
|
|
355
354
|
}
|
|
356
355
|
const { getByTestId, getByText, queryByText } = render(<Comp />)
|
|
@@ -387,7 +386,7 @@ describe('useForm', () => {
|
|
|
387
386
|
})
|
|
388
387
|
const errors = form.useStore((s) => s.errorMap)
|
|
389
388
|
return (
|
|
390
|
-
|
|
389
|
+
<>
|
|
391
390
|
<form.Field
|
|
392
391
|
name="firstName"
|
|
393
392
|
defaultMeta={{ isTouched: true }}
|
|
@@ -404,7 +403,7 @@ describe('useForm', () => {
|
|
|
404
403
|
</div>
|
|
405
404
|
)}
|
|
406
405
|
/>
|
|
407
|
-
|
|
406
|
+
</>
|
|
408
407
|
)
|
|
409
408
|
}
|
|
410
409
|
|
|
@@ -446,7 +445,7 @@ describe('useForm', () => {
|
|
|
446
445
|
const errors = form.useStore((s) => s.errorMap)
|
|
447
446
|
|
|
448
447
|
return (
|
|
449
|
-
|
|
448
|
+
<>
|
|
450
449
|
<form.Field
|
|
451
450
|
name="firstName"
|
|
452
451
|
defaultMeta={{ isTouched: true }}
|
|
@@ -464,7 +463,7 @@ describe('useForm', () => {
|
|
|
464
463
|
</div>
|
|
465
464
|
)}
|
|
466
465
|
/>
|
|
467
|
-
|
|
466
|
+
</>
|
|
468
467
|
)
|
|
469
468
|
}
|
|
470
469
|
|
|
@@ -508,7 +507,7 @@ describe('useForm', () => {
|
|
|
508
507
|
const errors = form.useStore((s) => s.errors)
|
|
509
508
|
|
|
510
509
|
return (
|
|
511
|
-
|
|
510
|
+
<>
|
|
512
511
|
<form.Field
|
|
513
512
|
name="firstName"
|
|
514
513
|
defaultMeta={{ isTouched: true }}
|
|
@@ -525,7 +524,7 @@ describe('useForm', () => {
|
|
|
525
524
|
</div>
|
|
526
525
|
)}
|
|
527
526
|
/>
|
|
528
|
-
|
|
527
|
+
</>
|
|
529
528
|
)
|
|
530
529
|
}
|
|
531
530
|
|
package/src/types.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import type {
|
|
2
2
|
DeepKeys,
|
|
3
3
|
DeepValue,
|
|
4
|
-
|
|
4
|
+
FieldApiOptions,
|
|
5
5
|
Validator,
|
|
6
6
|
} from '@tanstack/form-core'
|
|
7
7
|
|
|
@@ -15,6 +15,12 @@ export type UseFieldOptions<
|
|
|
15
15
|
| Validator<TParentData, unknown>
|
|
16
16
|
| undefined = undefined,
|
|
17
17
|
TData extends DeepValue<TParentData, TName> = DeepValue<TParentData, TName>,
|
|
18
|
-
> =
|
|
18
|
+
> = FieldApiOptions<
|
|
19
|
+
TParentData,
|
|
20
|
+
TName,
|
|
21
|
+
TFieldValidator,
|
|
22
|
+
TFormValidator,
|
|
23
|
+
TData
|
|
24
|
+
> & {
|
|
19
25
|
mode?: 'value' | 'array'
|
|
20
26
|
}
|