Я использую Redux Form Field Array, и при добавлении нового элемента в массив полей приложение вылетает из-за следующей ошибки:
Превышена максимальная глубина обновления. Это может произойти, когда компонент повторно вызывает setState внутри componentWillUpdate или componentDidUpdate. React ограничивает количество вложенных обновлений для предотвращения бесконечных циклов.
Код компонента:
import React from 'react';
import {reduxForm, Field, FieldArray} from 'redux-form';
import {
Button,
CircularProgress,
Grid,
}from '@material-ui/core';
import {Link} from 'react-router-dom';
import { makeStyles } from '@material-ui/styles';
import {FileInput, SelectInput, LocationInput, TextInput } from './FormFields';
import { SERVICES } from '../Routing/routes';
const userStyles = makeStyles(theme=>({
section:{
maxWidth:theme.breakpoints.values.md,
margin:'0 auto',
},
form:{
position:'relative',
paddingBottom:theme.spacing(8)
},
actionButtons:{
position:'fixed',
bottom:0,
right:0,
padding:theme.spacing(3),
backgroundColor:theme.palette.secondary.main,
borderTop: `1px solid ${theme.palette.primary.main}`
},
button:{
marginLeft:theme.spacing(1)
}
}));
const ProviderServiceForm = (props) =>{
const classes = userStyles();
const {handleSubmit, onFormSubmit, pending} = props;
const renderSubmitIcon = () =>{
if(pending)
return <CircularProgress color="primary" size={20}/>
else
return
}
const renderField = ({ input, label, type, meta: { touched, error } }) => (
<div>
<label>{label}</label>
<div>
<input {...input} type={type} placeholder={label} />
{touched && error && <span>{error}</span>}
</div>
</div>
);
const renderVariants = ({ fields, meta: { error, submitFailed } }) =>(
<ul>
<li>
<Button onClick={() => fields.push({})}>Añadir</Button>
{submitFailed && error && <span>{error}</span>}
</li>
{fields.map((variant,index)=>(
<li key={index}>
<h4>Variante #{index + 1}</h4>
<Field
name={`${variant}.title`}
type="text"
component={renderField}
label="First Name"
/>
</li>
))}
</ul>
);
return(
<div className={classes.section}>
<form onSubmit={handleSubmit(onFormSubmit)} className={classes.form}>
<input type="hidden" value="something"/>
<FieldArray name="variants" component={renderVariants}/>
<Field name="placeName" label="Nombre del centro o del lugar" component={TextInput} autoComplete="organization"/>
<Field name="address" label="Dirección" component={LocationInput} autoComplete="off"/>
<Field name="adressDetails" label="Planta, Piso, Puerta..." component={TextInput} autoComplete="address-level3"/>
<Field name="category" label="Categoría de servicios" component={SelectInput} autoComplete="category"/>
<Field name="image" type="file" label="Sube una foto..." component={FileInput}/>
<Grid container className={classes.actionButtons} justify="flex-end">
<Link to={SERVICES} style={{ textDecoration: 'none' }}>
<Button type="submit" variant="outlined" color="primary" disabled={pending}>Cancelar</Button>
</Link>
<Button type="submit" variant="contained" color="primary" className={classes.button} disabled={pending} startIcon={renderSubmitIcon()}>Guardar</Button>
</Grid>
</form>
</div>
)
}
const validate = (formValues) =>{
const errors = {}
if (!formValues.variants || !formValues.variants.length) {
errors.variants = { _error: 'Almenos tienes que introducir una variante' };
} else {
const variantsArrayErrors = [];
formValues.variants.forEach((variant, variantIndex) => {
const variantErrors = {};
if (!variant || !variant.title) {
variantErrors.title = 'Tienes que introducir un título';
variantsArrayErrors[variantIndex] = variantErrors;
}
if (!variant || !variant.price > 0) {
variantErrors.price = 'Tienes que poner un precio superior a 0€';
variantsArrayErrors[variantIndex] = variantErrors;
}
});
if (variantsArrayErrors.length) {
errors.variants = variantsArrayErrors;
}
}
if (!formValues.placeName){
errors.placeName = 'Debes intriducir el nombre del centro o lugar'
}
if (!formValues.address){
errors.address = 'Debes intriducir una dirección válida'
}
if(!formValues.category){
errors.category = 'Tienes que seleccionar una categoría';
}
if(!formValues.image){
errors.image = 'Debes seleccionar una imagen de Portada';
}
return errors;
}
export default reduxForm({
form:'ProviderServiceForm',
validate,
})(ProviderServiceForm);
Я думаю, что ошибка возникает, когда я выполняю следующий код строки :
<Button onClick={() => fields.push({})}>Añadir</Button>
Когда я получаю sh новое значение, компонент перерисовывается бесконечно.
Я удивлен, так как большая часть кода Field Array была скопирована из документации избыточной формы :
https://redux-form.com/8.3.0/examples/fieldarrays/
Есть идеи, как это исправить?
Заранее спасибо.