我试图创建一个React组件来抽象化为我的表单创建一个Input组。所有输入均具有相同的布局-一个标签,其下方是“输入”,如果出现错误/信息文本,则会在“输入”下显示。
以前,我是在处理自己的表单状态/处理程序。现在,我正在使用formik(通过Yup验证)进行试验,并遇到了嵌套信息时动态访问error
和touched
字段的问题。
这是我的输入组组件:
import React from 'react';
import { FormGroup, Label, Input, FormFeedback, FormText } from 'reactstrap';
import { Field, ErrorMessage } from 'formik';
const InputGroup = ({ name, label, type, info, required }) => {
return (
<FormGroup>
<Label htmlFor={name}>{label}{required && '*'}</Label>
<Field name={name}>
{({field, form}) => (
<Input {...field} id={name} type={
invalid={form.errors[name] && form.touched[name]} //problem here
/>
)}
</Field>
{info && <FormText color="muted">{info}</FormText>}
<ErrorMessage name={name}>
{msg => <FormFeedback>{msg}</FormFeedback>}
</ErrorMessage>
</FormGroup>
)
}
InputGroup.propTypes = {
label: PropTypes.string,
name: PropTypes.string.isRequired,
type: PropTypes.string,
info: PropTypes.string,
required: PropTypes.bool
};
InputGroup.defaultProps = {
type: 'text',
required: false
};
当我使用引导程序(reactstrap@7.x)时,<FormFeedback>
元素要求随附的<Input>
用invalid
标签标记。在上面的代码中,如果formik的invalid=true/false
对象上的对应字段存在(即存在错误)并且form.errors
对象为true(即用户触摸了输入),我将动态分配form.touched
当将formik设置为具有平坦的InitialValues(例如,下面)时,此方法就可以很好地工作,因为invalid={form.errors[name] && form.touched[name]}
的值为(例如)invalid={form.errors[firstName] && form.touched[firstName]}
initialValues = {
firstName: '',
lastName: '',
email: '',
password: ''
}
但是,当使用嵌套的initialValues(例如下面的内容)设置formik时,
invalid={form.errors[name] && form.touched[name]}
的值为invalid={form.errors[name.first] && form.touched[name.first]}
。最终,这将始终为false,因此输入始终为invalid=false
,因此永远不会用错误样式或显示的错误消息来标记输入。
initialValues = {
name: {
first: '',
last: ''
},
email: '',
password: ''
}
我该如何设置我的InputGroup组件,以便我可以动态访问formik的错误和接触的对象上的必填字段,而不管它是平面的还是嵌套的?
答案 0 :(得分:0)
Formik具有函数getIn()
,该函数可以通过路径(例如,类似于name.first
的路径)从对象中提取值。
<Field name={name}>
{({ field, form }) => (
<Input
{...field}
id={name}
invalid={getIn(form.errors, name) && getIn(form.touched, name)}
/>
)}
</Field>
在CodeSandbox上查看example here。
答案 1 :(得分:0)
Formik 还支持来自 meta
组件的 Field
参数,有为确切字段指定的信息(value
、touched
、error
)。< /p>
const CustomFormikInput = (props) => {
return <Field name={props.name}>
{({ field, meta }) => {
console.log(JSON.stringify(meta)); // Log meta output
const errorMsg = meta.touched ? meta.error : undefined;
return <div>
<input {...field} {...props} />
{errorMsg}
</div>;
}}
</Field>;
}