Ant-design: لماذا نحتاج دائمًا إلى `` callback () `في وظيفة التحقق من الصحة في مكون النموذج؟

تم إنشاؤها على ٣ مارس ٢٠١٧  ·  38تعليقات  ·  مصدر: ant-design/ant-design

نشكرك على تقديم سلسلة من المكونات مثل Form.

وصف المشكلة

نظرًا لأن كل حقل في النموذج يحتاج إلى التحقق مرة أخرى قبل الإرسال ، يتم استخدام validateFieldsAndScroll . لكن الاكتشاف لم يدخل حيز التنفيذ.

بعد التصحيح ، وجد أنه إذا تم تمرير مجموعة من الحقول المحددة إلى الوظيفة ، فيمكن أن تصبح نافذة المفعول. ولكن طالما أن هذه المجموعة من الملفات تحتوي على أي شخص يحدد استخدام validator في قواعد التحقق للتحقق الإضافي ، فلن يتم تفعيل طريقة validateFields بالكامل.

في النهاية ، اكتشفت أن السبب في ذلك هو أنني لم أرجع دائمًا callback() في رد الاتصال المقابل validator في البداية (أعتقد أنه أكثر من ذلك بكثير ، ويمكنك فعل ذلك لمدخل واحد دون كتابة في البداية. فحص عادي). بعد إضافته ، لا بأس.

يربك

معذرةً ، هل هذا خطأ؟ نظرًا لأنه لم يتم الإشارة إليه في المستند ، يجب إرجاع validator في callback() .
إذا كان من الضروري إرجاع callback ، فمن المستحسن تذكير المطور في المستند ، أو يمكن أن يكون افتراضيًا.

قطعة رمز

handleSubmit = (e) => {
        e.preventDefault()

        const { onSubmit } = this.props
        const { validateFieldsAndScroll, getFieldsValue, resetFields } = this.props.form

        validateFieldsAndScroll((err, values) => {
              if (!err) {
                  onSubmit(getFieldsValue())
              }
        })
}
handleConfirmPassword = (rule, value, callback) => {
        const { getFieldValue } = this.props.form
        if (value && value !== getFieldValue('newPassword')) {
            callback('两次输入不一致!')
        }

        // Note: 必须总是返回一个 callback,否则 validateFieldsAndScroll 无法响应
        callback()
 }

render()

<FormItem
    {...formItemLayout}
    label="确认密码"
>
{
    getFieldDecorator('confirmPassword', {
           rules: [{
                  required: true,
                  message: '请再次输入以确认新密码',
            }, {
                  validator: this.handleConfirmPassword
            }],
    })(<Input type="password" />)
}
</FormItem>

بيئة

  • إصدار antd: الأحدث
  • نظام التشغيل ونسخته: OS X
  • المتصفح ونسخته: الكروم الأحدث
Usage ❓FAQ 🙅🏻‍♀️ WON'T RESOLVE

التعليق الأكثر فائدة

اشتكيت من https://www.zhihu.com/question/33629737/answer/150154145

يمكنك إضافة مستند يوضح أن أحد مبادئنا للمصدر المفتوح هو التستر على الماء والأرض.

ال 38 كومينتر

إنه مصمم: https://github.com/yiminghe/async-validator/

راجع للشغل ، كيف يعرف المدقق غير المتزامن انتهاء الإجراء غير المتزامن ، إذا لم تستخدم callback لإخطاره؟

اشتكيت من https://www.zhihu.com/question/33629737/answer/150154145

يمكنك إضافة مستند يوضح أن أحد مبادئنا للمصدر المفتوح هو التستر على الماء والأرض.

تم تحديث الوثيقة.

مرحبًا ، هل يمكن كتابة هذا الاستخدام في الفصل فقط؟
هل من الممكن كتابة مكون React بطريقة وظيفية بحتة ، إذا كان الأمر كذلك ، فهل هناك أي حالات؟

تصميم واجهة برمجة التطبيقات هذا غير أنيق حقًا. أشعر أنني أريد فقط التحقق مما إذا كان قد تم تحديد مربع اختيار معين:

rules: [
            {
              message: 'You need to agree to our terms to sign up.',
              validator: (rule, value, cb) => (value === true ? cb() : cb(true)),
            },
          ],

والمعامل الأول المعطى لرد الاتصال هو رسالة الخطأ ، وهي أيضًا زائدة عن الحاجة مع message (على الرغم من أنه يبدو أنه طالما تم إرجاع أي شيء ، فسيتم استخدام message ، يجب تغطيته بواسطة message رسالة خطأ).

يجب أن يكون الاستخدام المتوقع لمعظم المستخدمين هو إرجاع true أو false مباشرة لتحديد الصواب أو الخطأ:

rules: [
            {
              message: 'You need to agree to our terms to sign up.',
              validator: (rule, value, cb) => value === true,
            },
          ],

متاح ، ولكن لا يزال يوصى بتحسين واجهة برمجة التطبيقات هذه ، أي استخدام https://github.com/yiminghe/async-validator/ ، ولكن يمكن إكمال ANT هنا ويمكن تغليفه بالمكالمة

يمكن لـ neekey الذهاب التحقق غير المتزامن

neekey هذه الواجهة الغريبة هي تحقيق:

  • التحقق غير المتزامن
  • دعم أخطاء مختلفة وإرجاع رسائل مختلفة

هل هناك طريقة أفضل؟

<Row>
                <Col span={24} key={"method"}>
                    <FormItem {...formItemMethodLayout} label="请求方法">
                        {getFieldDecorator("method", {
                            initialValue: this.state.data.method,
                            validateTrigger: "onChange",
                            rules: [{
                                required: true,
                                message: `请选择请求方法`
                            }, {
                                //validator: this.state.checkUnique ? this.checkConfirmMethod.bind(this) : (rule, value, callback) => {callback();},
                                validator: (这如何判断当前组件是否开始校验了) ?
 this.checkConfirmMethod.bind(this) : (如果不是当前组件开始校验,就调用其他函数),
                            }]
                        })(
                            <Select placeholder={"请选择请求方法"} onChange={::this.handleChange.bind(this)}>
                                {this.state.apiRequestMethodSelect}
                            </Select>
                        )}
                    </FormItem>
                </Col>
            </Row

في كل مرة أجد فيها التحقق من الوظيفة ، سآتي إلى هنا لرؤيتها مرة واحدة. من الصعب حقًا تذكرها

وظيفة المدقق

startNumValidator = (rule, value, callback) => {
    const { exportDataCount } = this.props;
    const reg = /^[1-9][0-9]*$/;
    let errors = [];
    if (!reg.test(value) || value > exportDataCount) {
      errors.push(new Error('illegal value'));
    }
    callback(errors);
  }

أليس خطأ موحدًا في رد الاتصال؟ إنه شعور معقول تمامًا.
لا أعرف ما إذا كان الإصدار الجديد من antd قد بدأ في التمييز بين التحقق غير المتزامن والمتزامن؟ المدقق (المتزامن) غير المتزامن (غير المتزامن)

كيفية استدعاء هذه الرسالة في رد الاتصال الذي أرجعته الخلفية بعد الطلب

واجهت مشكلة عند استخدام المدقق في القاعدة لإجراء التحقق المخصص
validateFunc = (القاعدة ، القيمة ، رد الاتصال) => {
إذا كان هذا صحيحا) {
console.log (11) ؛
رد الاتصال ("رسالة خطأ") ؛
إرجاع؛
}
أتصل مرة أخرى()؛
} ؛
أريد أن يتم عرض نتيجة التحقق "رسالة خطأ" ضمن مكون FormItem المقابل ، ولكن بعد تنفيذ رد الاتصال ، لا يتم عرض "رسالة الخطأ" ضمن مكون FormItem المقابل ، ولكن تتم طباعتها على وحدة التحكم. لماذا؟

كيف تكتب منطق 在对应的FormItem组件下显示 ؟

يمكن لـ neekey الذهاب التحقق غير المتزامن

قال أحدهم ، عارض ذلك ، قال yiminghe رد الاتصال هو أكثر مباشرة .عمرها 9102 سنة وما زلت أستخدم عمليات الاسترجاعات وانتظرها

كيف تكتب منطق 在对应的FormItem组件下显示 ؟

لقد غيرت نظام التحقق المخصص ، وتم الحكم في onFieldsChange () ، إذا لم يتم استيفاء القواعد المخصصة ، فسيتم تغيير الأخطاء مباشرةً ، وبعد ذلك سيتم عرض معلومات الخطأ في عنصر التحكم.
onFieldsChange(props, changedFields) { const { dispatch, detail } = props; const finalChangedFields = { ...changedFields }; // 校验时间大小是否符合规则 if ( _.has(changedFields, 'currentDate') && detail?.targetDate && compareCurrentTimeEarlierThanTargetTime( finalChangedFields.currentDate, detail?.targetDate ) ) { finalChangedFields.currentDate.errors = [ { message: 'current Date should be latter than target Date', field: 'currentDate', }, ]; } dispatch({ type: 'controllerModel/saveDetail', payload: { changedFields: finalChangedFields, data: detail, }, }); }

لماذا لا تختفي المطالبة التالية بعد اجتياز التحقق؟

اطرح سؤالاً ، ألا يستطيع هذا المدقق إجراء التحقق عند تحميل الصفحة؟

تضمين التغريدة
يجب استدعاء ميزة

<Form>
          <Form.Item ...>
            {getFieldDecorator('name', {validator: (rule, value, callback) => setTimeout(callback(), 1000)})(
                <Input placeholder="name" />
            )}
          </Form.Item>
....

وقبل إطلاق setTimeout ، لا يتم تحميل المكون بالكامل. ثم يتم تنشيط المهلة ، ويتم تشغيل رد الاتصال الخاص بها و

سيستخدم المكون setState (أعتقد) والذي سينتج عنه الخطأ التالي:

تحذير: لا يمكن إجراء تحديث حالة React على مكون غير محمّل. هذا هو no-op ، لكنه يشير إلى تسرب الذاكرة في التطبيق الخاص بك. لإصلاح ذلك ، قم بإلغاء جميع الاشتراكات والمهام غير المتزامنة في طريقة componentWillUnmount.

للأسف لا يمكن إلغاء رد الاتصال! لا توجد طريقة لتجنب هذا الخطأ!

تضمين التغريدة
واجهت هذه المشكلة.
الحل هو تمرير undefined إلى callback . سوف يمر المدقق عندما تكون المعلمة الأولى لـ callback صفيفًا فارغًا. وتقوم بتعيين قيمة افتراضية للمعامل ، لذا فإن undefined يعمل أيضًا.

تعريف callback : L146

لماذا يظهر المدقق غير المتزامن: [""] بعد اجتياز التحقق المخصص ،

إذا كان هناك فحصان فسيفشل الشيك الأول ، لماذا؟
""
قواعد: [
{
مطلوب: صحيح ،
الرسالة: "الرجاء إدخال رقم هاتفك" ،
} ،
{
المدقق: (القاعدة ، القيمة ، رد الاتصال) => {
يحاول {
إذا (this.props.form.getFieldValue ('بادئة') == 86 && value) {
const reg = / ^ 1d {10} $ / ؛
إذا (! reg.test (القيمة)) {
رمي خطأ جديد ("شيء خاطئ!") ؛
}
}
} catch (يخطئ) {
رد الاتصال (يخطئ) ؛
}
} ،
الرسالة: "الرجاء إدخال رقم هاتف محمول صالح" ،
} ،
] ،

 rules: [
                {
                  required: true,
                  message: '请输入手机号',
                },
                {
                  validator: (rule, value, callback) => {
                    try {
                      if (this.props.form.getFieldValue('prefix') == 86 && value) {
                        const reg = /^1\d{10}$/;
                        if (!reg.test(value)) {
                          throw new Error('Something wrong!');
                        }
                      }
                    } catch (err) {
                      callback(err);
                       return // +
                    }
                     callback() // +
                  },
                  message: '请输入有效手机号',
                },
              ],

واجهت مشكلة عند استخدام المدقق في القاعدة لإجراء التحقق المخصص
validateFunc = (القاعدة ، القيمة ، رد الاتصال) => {
إذا كان هذا صحيحا) {
console.log (11) ؛
رد الاتصال ("رسالة خطأ") ؛
إرجاع؛
}
أتصل مرة أخرى()؛
} ؛
أريد أن يتم عرض نتيجة التحقق "رسالة خطأ" ضمن مكون FormItem المقابل ، ولكن بعد تنفيذ رد الاتصال ، لا يتم عرض "رسالة الخطأ" ضمن مكون FormItem المقابل ، ولكن تتم طباعتها على وحدة التحكم. لماذا؟

واجهت مشكلة عند استخدام المدقق في القاعدة لإجراء التحقق المخصص
validateFunc = (القاعدة ، القيمة ، رد الاتصال) => {
إذا كان هذا صحيحا) {
console.log (11) ؛
رد الاتصال ("رسالة خطأ") ؛
إرجاع؛
}
أتصل مرة أخرى()؛
} ؛
أريد أن يتم عرض نتيجة التحقق "رسالة خطأ" ضمن مكون FormItem المقابل ، ولكن بعد تنفيذ رد الاتصال ، لا يتم عرض "رسالة الخطأ" ضمن مكون FormItem المقابل ، ولكن تتم طباعتها على وحدة التحكم. لماذا؟

هل قمت بحلها ، واجهت نفس الموقف

 rules: [
                {
                  required: true,
                  message: '请输入手机号',
                },
                {
                  validator: (rule, value, callback) => {
                    try {
                      if (this.props.form.getFieldValue('prefix') == 86 && value) {
                        const reg = /^1\d{10}$/;
                        if (!reg.test(value)) {
                          throw new Error('Something wrong!');
                        }
                      }
                    } catch (err) {
                      callback(err);
                       return // +
                    }
                     callback() // +
                  },
                  message: '请输入有效手机号',
                },
              ],

هل ستتكرر رسالة المطالبة؟ "الرجاء إدخال رقم هاتف محمول ، يرجى إدخال رقم هاتف محمول صالح" مشابه لهذا

 rules: [
                {
                  required: true,
                  message: '请输入手机号',
                },
                {
                  validator: (rule, value, callback) => {
                    try {
                      if (this.props.form.getFieldValue('prefix') == 86 && value) {
                        const reg = /^1\d{10}$/;
                        if (!reg.test(value)) {
                          throw new Error('Something wrong!');
                        }
                      }
                    } catch (err) {
                      callback(err);
                       return // +
                    }
                     callback() // +
                  },
                  message: '请输入有效手机号',
                },
              ],

هل ستتكرر رسالة المطالبة؟ "الرجاء إدخال رقم هاتف محمول ، يرجى إدخال رقم هاتف محمول صالح" مشابه لهذا

سوف لن

image

افعل ما يلي
image

لماذا لم يختف الشيك الأحمر؟ ؟ ؟ كيف يتم هذا النوع من التحقق من التأثير المتبادل الذي يفي بالمواصفات؟ ؟ ؟

يجب استدعاء رد نداء مدقق القاعدة سواء نجح أو فشل. الاختلاف هو أن المعلمات لم يتم تمريرها.

واجهت مشكلة عند استخدام المدقق في القاعدة لإجراء التحقق المخصص
validateFunc = (القاعدة ، القيمة ، رد الاتصال) => {
إذا كان هذا صحيحا) {
console.log (11) ؛
رد الاتصال ("رسالة خطأ") ؛
إرجاع؛
}
أتصل مرة أخرى()؛
} ؛
أريد أن يتم عرض نتيجة التحقق "رسالة خطأ" ضمن مكون FormItem المقابل ، ولكن بعد تنفيذ رد الاتصال ، لا يتم عرض "رسالة الخطأ" ضمن مكون FormItem المقابل ، ولكن تتم طباعتها على وحدة التحكم. لماذا؟

واجهت مشكلة عند استخدام المدقق في القاعدة لإجراء التحقق المخصص
validateFunc = (القاعدة ، القيمة ، رد الاتصال) => {
إذا كان هذا صحيحا) {
console.log (11) ؛
رد الاتصال ("رسالة خطأ") ؛
إرجاع؛
}
أتصل مرة أخرى()؛
} ؛
أريد أن يتم عرض نتيجة التحقق "رسالة خطأ" ضمن مكون FormItem المقابل ، ولكن بعد تنفيذ رد الاتصال ، لا يتم عرض "رسالة الخطأ" ضمن مكون FormItem المقابل ، ولكن تتم طباعتها على وحدة التحكم. لماذا؟

هل قمت بحلها ، واجهت نفس الموقف

لقد واجهت أيضًا هذه المشكلة. إذا كانت القيمة الأولية فارغة ، فيمكن تشغيل أداة التحقق المخصصة بشكل طبيعي خلال وقت الضبط بعد الإدخال العادي وسيتم تقديم مطالبة في حالة وجود خطأ ، ولكن بمجرد أن تحتوي القيمة الأولية الأولية على قيمة ، متى تنفذ Validatefields تحققًا موحدًا من صحة جميع مكونات النموذج ، وتطبع الأخطاء على أنها فارغة ، وبعد فترة ، سينبثق فشل التحقق من الصحة في وحدة التحكم مرة أخرى. المدقق المخصص هو إجراء غير متزامن

أعتقد أنك قمت بحذف الإرجاع ؛ في الوظيفة وحاول مرة أخرى. قد يكون ذلك مفيدًا.

------------------ الرسالة الأصلية ------------------
من: "Ivan-hl" < [email protected]> ؛
موعد التسليم: 20 نوفمبر 2019 (الأربعاء) 5:19 مساءً
المستلم: "ant-design / ant-design" < [email protected]> ؛
نسخة إلى: "wk" < [email protected]> ؛ "يدوي" < [email protected]> ؛
الموضوع: Re: [ant-design / ant-design] لماذا نحتاج دائمًا إلى callback() في وظيفة المدقق في مكون النموذج؟ لماذا يحتاج جسم الطريقة دائمًا إلى استدعاء () عند استخدام أداة التحقق في قواعد النموذج التحقق من الصحة؟ (# 5155)

واجهت مشكلة عند استخدام المدقق في القاعدة لإجراء التحقق المخصص
validateFunc = (القاعدة ، القيمة ، رد الاتصال) => {
إذا كان هذا صحيحا) {
console.log (11) ؛
رد الاتصال ("رسالة خطأ") ؛
إرجاع؛
}
أتصل مرة أخرى()؛
} ؛
أريد أن يتم عرض نتيجة التحقق "رسالة خطأ" ضمن مكون FormItem المقابل ، ولكن بعد تنفيذ رد الاتصال ، لا يتم عرض "رسالة الخطأ" ضمن مكون FormItem المقابل ، ولكن تتم طباعتها على وحدة التحكم. لماذا؟

واجهت مشكلة عند استخدام المدقق في القاعدة لإجراء التحقق المخصص
validateFunc = (القاعدة ، القيمة ، رد الاتصال) => {
إذا كان هذا صحيحا) {
console.log (11) ؛
رد الاتصال ("رسالة خطأ") ؛
إرجاع؛
}
أتصل مرة أخرى()؛
} ؛
أريد أن يتم عرض نتيجة التحقق "رسالة خطأ" ضمن مكون FormItem المقابل ، ولكن بعد تنفيذ رد الاتصال ، لا يتم عرض "رسالة الخطأ" ضمن مكون FormItem المقابل ، ولكن تتم طباعتها على وحدة التحكم. لماذا؟

هل قمت بحلها ، واجهت نفس الموقف

لقد واجهت أيضًا هذه المشكلة. إذا كانت القيمة الأولية فارغة ، فيمكن تشغيل أداة التحقق المخصصة بشكل طبيعي خلال وقت الضبط بعد الإدخال العادي وسيتم تقديم مطالبة في حالة وجود خطأ ، ولكن بمجرد أن تحتوي القيمة الأولية الأولية على قيمة ، متى تنفذ Validatefields تحققًا موحدًا من صحة جميع مكونات النموذج ، وتطبع الأخطاء على أنها فارغة ، وبعد فترة ، سينبثق فشل التحقق من الصحة في وحدة التحكم مرة أخرى. المدقق المخصص هو إجراء غير متزامن

-
أنت تتلقى هذا لأنك مشترك في هذا الموضوع.
قم بالرد على هذه الرسالة الإلكترونية مباشرةً ، أو اعرضها على GitHub ، أو قم بإلغاء الاشتراك.

سيء جدا

إذا كان هناك استثناء في وظيفة الفحص ، فلا توجد مطالبة.
حرض لفترة طويلة. . .

أتساءل إذا لم يتم الحفاظ على هذا AntdV

@ kongling94 ؟

واجهت نفس المشكلة ، لا مزيد من النص؟

<a-input id="code" placeholder="请输入用户ID"v-decorator="[ 'code', {rules: [{ required: true, message: '请输入用户ID' }, { validator: handleUsername }], validateTrigger: 'change'} ]" > </a-input>
handleUsername(rule, value, callback) { value = value.trim() if (value.length == 0) { this.username = ''; callback(); } else { fetchUsername({ code: value }) .then((rest) => { if (rest.code == 200) { this.username = rest.data; //callback(); } else { this.username = ''; callback(new Error(rest.msg)) return; } }).finally(() => { callback() }) } },
<a-form :label-col="labelCol" :wrapper-col="wrapperCol" :form="form" @submit="handleSubmit"> <a-button type="primary" htmlType="submit">确定</a-button> </a-form>
انقر لتأكيد عدم وجود استجابة وعدم وجود مطالبة ، أدخل المدقق غير المتزامن: ["الرمز مطلوب"] في وحدة التحكم
لم تدخل ValidateFields على الإطلاق
قم بإزالة المدقق والتحقق من برنامج ValidateTrigger ، ثم انقر فوق "موافق" وستظهر رسالة المطالبة بشكل طبيعي.
ما المشكلة؟

<a-input id="code" placeholder="请输入用户ID"v-decorator="[ 'code', {rules: [{ required: true, message: '请输入用户ID' }, { validator: handleUsername }], validateTrigger: 'change'} ]" > </a-input>
handleUsername(rule, value, callback) { value = value.trim() if (value.length == 0) { this.username = ''; callback(); } else { fetchUsername({ code: value }) .then((rest) => { if (rest.code == 200) { this.username = rest.data; //callback(); } else { this.username = ''; callback(new Error(rest.msg)) return; } }).finally(() => { callback() }) } },
<a-form :label-col="labelCol" :wrapper-col="wrapperCol" :form="form" @submit="handleSubmit"> <a-button type="primary" htmlType="submit">确定</a-button> </a-form>
انقر لتأكيد عدم وجود استجابة وعدم وجود مطالبة ، أدخل المدقق غير المتزامن: ["الرمز مطلوب"] في وحدة التحكم
لم تدخل ValidateFields على الإطلاق
قم بإزالة المدقق والتحقق من برنامج ValidateTrigger ، ثم انقر فوق "موافق" وستظهر رسالة المطالبة بشكل طبيعي.
ما المشكلة؟

هل حلت هذه المشكلة؟واجهت هذه المشكلة أيضًا

<a-input id="code" placeholder="请输入用户ID"v-decorator="[ 'code', {rules: [{ required: true, message: '请输入用户ID' }, { validator: handleUsername }], validateTrigger: 'change'} ]" > </a-input>
handleUsername(rule, value, callback) { value = value.trim() if (value.length == 0) { this.username = ''; callback(); } else { fetchUsername({ code: value }) .then((rest) => { if (rest.code == 200) { this.username = rest.data; //callback(); } else { this.username = ''; callback(new Error(rest.msg)) return; } }).finally(() => { callback() }) } },
<a-form :label-col="labelCol" :wrapper-col="wrapperCol" :form="form" @submit="handleSubmit"> <a-button type="primary" htmlType="submit">确定</a-button> </a-form>
انقر لتأكيد عدم وجود استجابة وعدم وجود مطالبة ، أدخل المدقق غير المتزامن: ["الرمز مطلوب"] في وحدة التحكم
لم تدخل ValidateFields على الإطلاق
قم بإزالة المدقق والتحقق من برنامج ValidateTrigger ، ثم انقر فوق "موافق" وستظهر رسالة المطالبة بشكل طبيعي.
ما المشكلة؟

هل حلت هذه المشكلة؟واجهت هذه المشكلة أيضًا

// 自定义密码校验
  handleConfirmPassword = (rule, value, callback) => {
    const { getFieldValue } = this.props.form;
    if (value && value !== getFieldValue('newPwd')) {
      callback('两次输入不一致!');
    }

    // Note: 必须总是返回一个 callback,否则 validateFieldsAndScroll 无法响应
    callback();
  };
我是这么解决的

ValidatorFun (قاعدة ، قيمة ، رد اتصال) {
const psw = this.form.getFieldValue ('newPwd')
إذا (value && value! == psw) {
rule.message = '两次 密码 不一致'
رد الاتصال (حكم)
}
أتصل مرة أخرى()
}

هل كانت هذه الصفحة مفيدة؟
0 / 5 - 0 التقييمات