无法使用 Formik & Yup

问题描述

简单的字段验证良好并正确显示错误。但是,当我将错误显示添加到 FieldArray 内的字段时,我在这一行上得到“无法读取未定义的属性 '0'”

className={errors.steps[index].direction && touched.steps[index].direction ? 'family-input family-input-error ' : 'family-input'}

我假设这是因为错误对象在页面加载时为空。我不确定我可能哪里出错了,我希望得到一些帮助!

提前致谢。

是的架构 -

const RecipeSchema = Yup.object().shape({
  name: Yup.string()
    .required("required"),imageRef: Yup.string()
    .required('required'),categories: array().of(
    Yup.object().shape({
      id: Yup.number(),}),).required('required'),cookingTime: Yup.string()
    .required('required'),servings: Yup.string()
      .required('required'),author: Yup.string()
      .required('required'),steps: array().of(
    Yup.object().shape({
      direction: Yup.string()
        .required('required'),ingredients: array().of(
        Yup.object().shape({
          amount: Yup.string()
            .required('required'),measure: Yup.string()
            .required('required'),name: Yup.string()
            .required('required'),})  
      )
    })
  ).required(),});

表格 -

  <Formik
        initialValues={{
          name: '',imageRef: '',cookingTime:'',servings: '',author: '',steps: [{
            direction: '',ingredients: [{
              name: '',measure: '',amount: ''
            }]
          }],categories: []
        }}
        validationSchema={RecipeSchema}
        onSubmit={values => {
          console.log(values);
          onSubmit(values);
        }}

        render={({ touched,errors,values,setFieldValue }) => (
          <Form>
            <div className="px-2">
              <Field name="name" className={errors.name && touched.name ? 'family-input family-input-error ' : 'family-input'} placeholder="Name" autoComplete="off" />
              <label htmlFor="imageRef" className="image-input family-input">
                <svg id="add" xmlns="http://www.w3.org/2000/svg" width="50" height="50" viewBox="0 0 50 50">
                  <g id="Group_58" data-name="Group 58">
                    <path id="Path_52" data-name="Path 52" d="M47.917,22.917H27.083V2.083a2.083,2.083,1,0-4.167,0V22.917H2.083a2.083,4.167H22.917V47.917a2.083,4.167,0V27.083H47.917a2.083,0-4.167Z" fill="#525174" />
                  </g>
                </svg>
                <Field name="imageRef" type="file" className={errors.imageRef && touched.imageRef ? 'family-input family-input-error' : ' family-input'}/>
              </label>
              
              {/* Todo: style this input to match the rest & style the pills to brand */}
              <Select placeholder="Select Categories.." name="categories"  classNamePrefix="recipe-category-select" className={errors.categories && touched.categories ? 'family-input-error ' : ''} onChange={(evt) => setFieldValue('categories',toFieldCategory(evt))} isMulti options={categories}></Select>
              <Field name="cookingTime" className="family-input" placeholder="Cooking Time" autoComplete="off"  className={errors.cookingTime && touched.cookingTime ? 'family-input family-input-error ' : 'family-input'} />
              <Field name="servings" className="family-input" placeholder="Servings" autoComplete="off" className={errors.servings && touched.servings ? 'family-input family-input-error ' : 'family-input'} />
              <Field name="author" className="family-input" placeholder="Author" autoComplete="off" className={errors.author && touched.author ? 'family-input family-input-error ' : 'family-input'}/>
            </div>
            <FieldArray
              name="steps"
              render={arrayHelpers => (
                <div className="recipe-steps">
                  <div className="header p-2">
                    <h2>Steps</h2>
                    <div onClick={() => arrayHelpers.push({direction: '',ingredients: []})}>
                      <svg id="add" xmlns="http://www.w3.org/2000/svg" width="30" height="30" viewBox="0 0 50 50">
                        <g id="Group_58" data-name="Group 58">
                          <path id="Path_52" data-name="Path 52" d="M47.917,0-4.167Z" fill="#525174" />
                        </g>
                      </svg>
                    </div>
                  </div>
                  {values.steps.map((step,index) => (
                    <div className="recipe-steps-accordion" key={index}>
                      <div className="recipe-step-header" data-toggle="collapse" data-target={"#recipe-step-body" + index}>
                        <Row>
                          <Col className="left">
                            <h3>Step {index + 1}</h3>
                          </Col>
                          <Col className="right">
                            <svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 40.001 40" onClick={() => arrayHelpers.remove(index)} >
                              <g id="close_3_" data-name="close (3)" transform="translate(0 -0.001)">
                                <path id="Path_21" data-name="Path 21" d="M23.539,20l15.73-15.73A2.5,2.5,35.731.734L20,16.464,4.27.734A2.5,.733,4.271L16.464,20,35.732A2.5,4.27,39.268L20,23.538l15.73,15.73a2.5,3.537-3.537Z" fill="#fff" />
                              </g>
                            </svg>
                          </Col>
                        </Row>
                      </div>
                      <div id={"recipe-step-body" + index} className="recipe-step-body collapse px-2">
                        <Field name={`steps[${index}].direction`} as="textarea" placeholder="Direction" />
                        {/*  className={errors.steps[index].direction && touched.steps[index].direction ? 'family-input family-input-error ' : 'family-input' } */}
                        <FieldArray
                          name={`steps[${index}].ingredients`}
                          render={arrayHelpers1 => (
                            <div className="step-ingredients" key={index}>
                              <div className="header p-2">
                                <Col className="left">
                                  <h2>Ingredients</h2>
                                </Col>
                                <Col className="right">
                                  <div>
                                    <svg id="add" xmlns="http://www.w3.org/2000/svg" width="30" height="30" viewBox="0 0 50 50" onClick={() => arrayHelpers1.push({name: '',measure: 'Tbsp',amount: ''})}>
                                      <g id="Group_58" data-name="Group 58">
                                        <path id="Path_52" data-name="Path 52" d="M47.917,0-4.167Z" fill="#525174" />
                                      </g>
                                    </svg>
                                  </div>
                                </Col>
                              </div>
                              {
                                values.steps[index].ingredients ?
                                  values.steps[index].ingredients.map((ingredient,innerIndex) => (
                                    <div className="px-2" key={innerIndex}>
                                      <Row className="ingredient">
                                      <svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 40.001 40" onClick={() => arrayHelpers1.remove(innerIndex)} >
                                        <g id="close_3_" data-name="close (3)" transform="translate(0 -0.001)">
                                          <path id="Path_21" data-name="Path 21" d="M23.539,3.537-3.537Z" fill="#525174" />
                                        </g>
                                      </svg>
                                        <Col xs={12}>
                                          <Field name={`steps[${index}].ingredients[${innerIndex}].name`} className="family-input" placeholder="name" />
                                        </Col>
                                        <Col xs={6}>
                                          <Field name={`steps[${index}].ingredients[${innerIndex}].amount`} className="family-input dense" placeholder="amount" />
                                        </Col>
                                        <Col xs={6}>
                                          <Field name={`steps[${index}].ingredients[${innerIndex}].measure`} as="select" className="family-input dense" placeholder="measure">
                                            {measurements.map((measurement,measureIndex) => 
                                              <option key={measureIndex} value={measurement}>{measurement}</option>
                                            )}
                                          </Field>
                                        </Col>
                                      </Row>
                                    </div>
                                  ))

                                  : <div>no ingredients</div>
                              }

                            </div>
                          )}
                        />
                      </div>
                    </div>
                  ))}
                </div>
              )}
            />

            <button className="family-submit-btn" type="submit">SAVE RECIPE</button>
          </Form>
        )}
      />

解决方法

暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!

如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。

小编邮箱:dio#foxmail.com (将#修改为@)

相关问答

Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其...
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。...
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbc...