复杂表单
什么是复杂表单?
复杂表单通常包含的数据结构不仅仅是简单的键值对。例如,一个包含每个人自己的电子邮件、电话和街道地址的人员列表。这本质上是一个对象数组。
输入命名
对象
通过在名称中使用 .
(点)来创建嵌套项。例如,person.name
将被转换为 { person: { name: 'sam' } }
。
数组
通过在名称中指定从零开始的索引来创建数组,可以是顶级的也可以是嵌套的。例如,person.pets.0
将被转换为 { person: { pets: [ 'cat' ] } }
。
示例
创建复杂表单的关键在于输入的命名。下面是上述列表的示例:
<form>
<input name="person.0.name" value="Sam">
<input name="person.0.email" value="sam@complexform.com">
<input name="person.0.pets.0" value="cat">
<input name="person.0.pets.1" value="dog">
<input name="person.0.address.street" value="1234 Example Ave.">
<input name="person.0.address.city" value="Qwik">
<input name="person.0.address.state" value="IA">
<input name="person.0.address.zip" value="00000">
<input name="person.0.pets.0" value="beaver">
<input name="person.1.name" value="Bonnie">
<input name="person.1.email" value="bonnie@hishai.net">
<input name="person.1.address.street" value="768 Resolution Way">
<input name="person.1.address.city" value="Jaffa">
<input name="person.1.address.state" value="IL">
<input name="person.1.address.zip" value="01948">
</form>
输出对象
提交表单后,数据将被解析为如下的对象:
{
"person": [
{
"name": "Sam",
"email": "sam@complexform.com",
"address": {
"street": "1234 Example Ave.",
"city": "Qwik",
"state": "IA",
"zip": "00000"
},
"pets": ["beaver"]
},
{
"name": "Bonnie",
"email": "bonnie@hishai.net",
"address": {
"street": "768 Resolution Way",
"city": "Jaffa",
"state": "IL",
"zip": "01948"
}
}
]
}
与 Actions 结合使用
可以使用 zod$、routeAction$ 和 globalAction$ 来验证复杂表单。继续上面的示例,代码如下:
export const action = routeAction$(
async (person) => {
return { success: true, person, };
},
// 使用 Zod 模式验证 FormData
zod$({
person: z.array(
z.object({
name: z.string(),
email: z.string().email(),
address: z.object({
street: z.string(),
city: z.string(),
state: z.string(),
zip: z.coerce.number()
}),
pets: z.array(z.string())
})
),
})
);