以编程方式呈现的 Redux 字段的动态验证
Dynamic validations for programmatically rendered Redux Fields
无法找到我遇到的问题的直接答案,所以希望 SO 上的人可以帮助我...
我有一个简单的 Redux 表单,它只有一个 First Name
和 Last Name
输入字段。这些字段不是显式写出,而是以编程方式呈现,如下所示:
...
renderNameInput(field) {
const { content } = this.props;
return (
<Field
id={field}
name={field}
component={FormField}
validate={this.nameValidations}
error={!this.isNameValid(field) ? content.nameError : null}
/>
);
}
...
render() {
<form onSubmit={handleSubmit}>
<div>
{this.renderNameInput('firstName')}
{this.renderNameInput('lastName')}
</div>
</form>
}
我遇到的问题是当字段未验证时显示错误。每个字段最少需要 2 个字符,最多需要 16 个字符(尽管这与我的具体问题无关)。
我想做的是,当其中一个输入无效时,错误会显示在该输入下。如果两个输入都无效,则错误将显示在两个输入下(在各自位置显示错误的结构和样式当然已经完成,只是不是这个问题的一部分)
这是我检查错误的方法:
...
isNameValid(field) {
const { formState = {} } = this.props;
const { syncErrors } = formState;
if (syncErrors && syncErrors[field]) {
return false;
}
}
...
组件连接到 Redux 存储,所以我可以访问表单中的 formState
和 initial
和 values
对象,以及它们何时被visit
ed、touch
ed 等
如果 - 当用户更改输入值时 - 在商店中查看 Redux 状态时 syncErrors
对象看起来像这样( 任意 ):
syncErrors: {
firstName: 'Must be at least 2 characters'
}
然后我想在 firstName
输入下显示一条错误消息,但在 lastName
输入下什么也没有。同样,如果 lastName
是 syncErrors
对象的一部分,那么错误也会显示在该输入下。如果 firstName
和 lastName
都在 syncErrors
中,则错误将显示在两个输入下。
我希望这是有道理的,并且有人可以为我指明正确的方向。如果需要任何说明,请告诉我。
谢谢!
如果您将错误消息作为 prop 传递给 Field
组件,那么您可能只想向显示的 Field
组件添加一些代码如果有一个错误。它应该看起来像这样:
{this.props.error ? (<p>{this.props.error}</p>) : null}
由于无法更改Field
组件中出现的内容,我建议允许renderNameInput
所在的组件访问Redux中的错误对象。这样您就可以使 renderNameInput
return 成为 Field
组件和错误消息。像这样:
renderNameInput(field) {
const { content, error } = this.props;
return (
<div>
<Field
id={field}
name={field}
component={FormField}
validate={this.nameValidations}
error={!this.isNameValid(field) ? content.nameError : null}
/>
<p>{error[field] ? (<p>{error[field]}</p>) : null}}</p>
</div>
);
}
我真的弄明白了。我做了这个方法:
...
isNameError(field) {
const { content, formState = {}, submitFailed } = this.props;
const { initial, syncErrors, values } = formState;
if (!submitFailed || !syncErrors) {
return null;
}
const isNotSameValues = initial[field] !== values[field];
const invalidField = Boolean(isNotSameValues && syncErrors[field]);
if (invalidField) {
return content.nameError;
}
}
...
因为这个组件是用 reduxForm
包装的,所以我能够使用传递给我包装组件的某些道具 - submitFailed
和 syncErrors
。如果表单字段没有通过我的验证检查,syncErrors
对象将填充表单字段名称作为键,验证错误(错误消息)作为值。
此外,当表单因验证失败而提交失败时,submitFailed
属性 - 一个布尔值 - 被设置为 true
。
我将我的组件连接到 Redux 存储,因此我能够访问 formState
,并使用 initial
和 values
属性比较每个输入字段值和 运行 验证检查。
在我最初的 renderNameInput
方法中使用它看起来像这样:
...
renderNameInput(field) {
const { content, formState = {}, submitFailed } = this.props;
const label = get(content, `${field}Field.text`, '');
return (
<Field
id={field}
name={field}
component={FormField}
validate={this.nameValidations}
error={isNameError(field)}
/>
);
}
...
每个输入字段都会单独验证,如果它没有通过初始提交的检查,那么错误消息会显示在每个输入下方。当该输入通过检查时,错误消失,我可以提交。
非常感谢你的帮助,@ldtcoop!
无法找到我遇到的问题的直接答案,所以希望 SO 上的人可以帮助我...
我有一个简单的 Redux 表单,它只有一个 First Name
和 Last Name
输入字段。这些字段不是显式写出,而是以编程方式呈现,如下所示:
...
renderNameInput(field) {
const { content } = this.props;
return (
<Field
id={field}
name={field}
component={FormField}
validate={this.nameValidations}
error={!this.isNameValid(field) ? content.nameError : null}
/>
);
}
...
render() {
<form onSubmit={handleSubmit}>
<div>
{this.renderNameInput('firstName')}
{this.renderNameInput('lastName')}
</div>
</form>
}
我遇到的问题是当字段未验证时显示错误。每个字段最少需要 2 个字符,最多需要 16 个字符(尽管这与我的具体问题无关)。
我想做的是,当其中一个输入无效时,错误会显示在该输入下。如果两个输入都无效,则错误将显示在两个输入下(在各自位置显示错误的结构和样式当然已经完成,只是不是这个问题的一部分)
这是我检查错误的方法:
...
isNameValid(field) {
const { formState = {} } = this.props;
const { syncErrors } = formState;
if (syncErrors && syncErrors[field]) {
return false;
}
}
...
组件连接到 Redux 存储,所以我可以访问表单中的 formState
和 initial
和 values
对象,以及它们何时被visit
ed、touch
ed 等
如果 - 当用户更改输入值时 - 在商店中查看 Redux 状态时 syncErrors
对象看起来像这样( 任意 ):
syncErrors: {
firstName: 'Must be at least 2 characters'
}
然后我想在 firstName
输入下显示一条错误消息,但在 lastName
输入下什么也没有。同样,如果 lastName
是 syncErrors
对象的一部分,那么错误也会显示在该输入下。如果 firstName
和 lastName
都在 syncErrors
中,则错误将显示在两个输入下。
我希望这是有道理的,并且有人可以为我指明正确的方向。如果需要任何说明,请告诉我。
谢谢!
如果您将错误消息作为 prop 传递给 Field
组件,那么您可能只想向显示的 Field
组件添加一些代码如果有一个错误。它应该看起来像这样:
{this.props.error ? (<p>{this.props.error}</p>) : null}
由于无法更改Field
组件中出现的内容,我建议允许renderNameInput
所在的组件访问Redux中的错误对象。这样您就可以使 renderNameInput
return 成为 Field
组件和错误消息。像这样:
renderNameInput(field) {
const { content, error } = this.props;
return (
<div>
<Field
id={field}
name={field}
component={FormField}
validate={this.nameValidations}
error={!this.isNameValid(field) ? content.nameError : null}
/>
<p>{error[field] ? (<p>{error[field]}</p>) : null}}</p>
</div>
);
}
我真的弄明白了。我做了这个方法:
...
isNameError(field) {
const { content, formState = {}, submitFailed } = this.props;
const { initial, syncErrors, values } = formState;
if (!submitFailed || !syncErrors) {
return null;
}
const isNotSameValues = initial[field] !== values[field];
const invalidField = Boolean(isNotSameValues && syncErrors[field]);
if (invalidField) {
return content.nameError;
}
}
...
因为这个组件是用 reduxForm
包装的,所以我能够使用传递给我包装组件的某些道具 - submitFailed
和 syncErrors
。如果表单字段没有通过我的验证检查,syncErrors
对象将填充表单字段名称作为键,验证错误(错误消息)作为值。
此外,当表单因验证失败而提交失败时,submitFailed
属性 - 一个布尔值 - 被设置为 true
。
我将我的组件连接到 Redux 存储,因此我能够访问 formState
,并使用 initial
和 values
属性比较每个输入字段值和 运行 验证检查。
在我最初的 renderNameInput
方法中使用它看起来像这样:
...
renderNameInput(field) {
const { content, formState = {}, submitFailed } = this.props;
const label = get(content, `${field}Field.text`, '');
return (
<Field
id={field}
name={field}
component={FormField}
validate={this.nameValidations}
error={isNameError(field)}
/>
);
}
...
每个输入字段都会单独验证,如果它没有通过初始提交的检查,那么错误消息会显示在每个输入下方。当该输入通过检查时,错误消失,我可以提交。
非常感谢你的帮助,@ldtcoop!