إنشاء مكتبة التحقق من صحة التفاعل الخاصة بك: تجربة المطور (الجزء 3)

نشرت: 2022-03-10
ملخص سريع ↬ لقد رأينا بالفعل كيف يمكننا تنفيذ الأجزاء الأساسية لمكتبة التحقق من الصحة الخاصة بنا ، وكيفية إضافة جميع الميزات الرائعة التي نحتاجها. سيركز هذا الجزء الأخير من هذه السلسلة على تحسين تجربة المستخدم للأشخاص الذين سيستخدمون مكتبة التحقق لدينا: المطورين.

إذا كنت تتابع سلسلة المقالات الصغيرة هذه ، فقد تعلمت الآن كيفية تجميع مكتبة التحقق الخاصة بك. يمكنه التعامل مع أي تحدٍ يمكنك طرحه عليه تقريبًا ، كما أنه يساعد في حل مشكلات إمكانية الوصول! عيبه الوحيد هو أنه سيء ​​للعمل معه.

نعم هذا صحيح. تجربة المستخدم من وجهة نظر المطور مفقودة بشكل خطير. لا نحصل على أي تحذيرات مفيدة عندما نخطئ في تهجئة الكلمات أو نسيء استخدام واجهات برمجة التطبيقات أو ، حسنًا ، أي شيء ، حقًا!

ستوجهك هذه المقالة إلى كيفية تحسين تجربة المطور لمكتبة التحقق الخاصة بك - أو أي مكتبة لهذا الغرض.

  • الجزء الأول: الأساسيات
  • الجزء 2: الميزات
  • الجزء 3: التجربة

يبدأ

منذ الجزء الأخير من هذه المقالة ، قمنا بسحب جميع رموز المكتبة في ملفاتها الخاصة. ألق نظرة على العرض التوضيحي لـ CodeSandbox لمعرفة ما بدأنا به.

المزيد بعد القفز! أكمل القراءة أدناه ↓

وظائف الراحة

نريد أن تكون مكتبتنا بسيطة قدر الإمكان لاستخدامها في الحالات الأكثر شيوعًا. تتمثل إحدى طرق التحرك نحو هذا الهدف في إضافة وظائف أداة ملائمة لوظائف معينة.

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

 const isFormValid = useMemo( () => Object.values(errors).every(error => error === null), [errors] );

سنقدم هذه العلامة في معالج النموذج onSubmit بنا ، وكذلك في طريقة العرض الخاصة بنا.

  • انظر عرض CodeSandbox

هناك الكثير مما يمكن كتابته ، لكنني سأجعل ذلك تمرينًا للقارئ.

ثوابت وتحذيرات التنمية

واحدة من أعظم ميزات React هي العديد من تحذيرات وحدة التحكم المفيدة أثناء التطوير. يجب أن نقدم نفس النوع من الجودة لمستخدمينا أيضًا.

للبدء ، سننشئ وظيفتين - warning لتسجيل التحذيرات إلى وحدة التحكم ، invariant عند حدوث خطأ - وكلاهما في حالة عدم استيفاء شرط معين.

 function warning(condition, message) { if (process.env.NODE_ENV === 'production' || condition) { return; } console.warn('useValidation: ' + message); } function invariant(condition, message) { if (process.env.NODE_ENV === 'production' || condition) { return; } throw new Error('useValidation: ' + message); }

تريد استخدام invariant إذا كان الخطأ سيؤدي إلى تدمير مكتبتك (أو جعلها عديمة الفائدة) ، warning من الممارسات السيئة أو النصائح الأخرى.

متى تحذر

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

نظرًا لأن مكتبتنا تقبل كائن تكوين كبير جدًا ، فمن المنطقي التحقق من صحة ذلك بطريقة ما - على الأقل أثناء التطوير. يمكننا حلها باستخدام نظام كتابة مثل TypeScript أو Flow ، لكن هذا يستثني جميع مستخدمي JavaScript العاديين.

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

 function validateConfigSchema(config) { if (process.env.NODE_ENV === 'production') { return; } if (typeof config === 'function') { config = config({}); } invariant( typeof config === 'object', `useValidation should be called with an object or a function returning an object. You passed a ${typeof config}.`, ); invariant( typeof config.fields === 'object', 'useValidation requires a `field` prop with an object containing the fields and their validators. Please refer to the documentation on usage: https://link.to/docs' ); invariant( Object.values(config.fields).every(field => typeof field === 'object'), 'useValidation requires that the `field` object only contains objects. It looks like yours isn\'t. Please refer to the documentation on usage: https://link.to/docs' ); warning( ['always', 'blur', 'submit', undefined].includes(config.showError), 'useValidation received an unsupported value in the `showError` prop. Valid values are "always", "blur" or "submit".' ) // And so on }

ربما يمكننا الاستمرار في القيام بذلك لفترة من الوقت إذا أردنا قضاء الوقت. ويجب عليك! إنها طريقة رائعة لتحسين تجربة المطور لتطبيقك.

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

السماح بالمرونة

تجربة المطور الجيدة في جزء كبير منها لا تقف في طريق المطورين. لنلقِ نظرة على بعض الطرق التي يمكننا من خلالها تحسين هذه التجربة.

تكوين الدعائم المتضاربة

أولاً ، تقوم أدوات الدعم لدينا بتطبيق بعض الدعائم على مدخلاتنا ونماذجنا التي يمكن للمستهلكين تجاوزها عن طريق الخطأ. بدلاً من ذلك ، دعنا نضيف كائن تجاوز خاص إلى حاصل على Prop الخاص بنا ، والذي سيؤلف أي دعائم متضاربة معًا.

إليك كيفية تنفيذ ذلك في getFieldProps :

 getFieldProps: (fieldName, overrides = {}) => ({ onChange: e => { const { value } = e.target; if (!config.fields[fieldName]) { return; } dispatch({ type: 'change', payload: { [fieldName]: value }, }); if (overrides.onChange) { overrides.onChange(e); } }, onBlur: e => { dispatch({ type: 'blur', payload: fieldName }); if (overrides.onBlur) { overrides.onBlur(e) } }, name: overrides.name || fieldName, value: state.values[fieldName] || '', }),

يمكن اتباع نهج مماثل في getFormProps .

ساعد في تجنب حفر الدعامة

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

أولاً ، لنقم بإنشاء ValidationContext باستخدام طريقة createContext في React:

 export const ValidationContext = React.createContext({});

بعد ذلك ، لنقم بإنشاء مكون ValidationProvider ، والذي يوفر جميع القيم من خطاف useValidation في السياق بدلاً من ذلك:

 export const ValidationProvider = props => { const context = useValidation(props.config); return ( {props.children} ); }; export const ValidationProvider = props => { const context = useValidation(props.config); return ( {props.children} ); }; export const ValidationProvider = props => { const context = useValidation(props.config); return ( {props.children} ); };

الآن ، بدلاً من استدعاء useValidation مباشرةً ، سنلف النموذج الخاص بنا في مكون ValidationProvider ، ونحصل على إمكانية الوصول إلى عناصر التحقق من الصحة ( getFormProps ، errors ، إلخ) باستخدام الخطاف useContext . ستستخدمه على النحو التالي:

 Import React, { useContext } from 'react'; import { ValidationContext } from './useValidation'; function UsernameForm(props) { const { getFieldProps, errors } = useContext(ValidationContext); return ( <> <input {...getFieldProps('username')} /> {errors.username && {errors.username}></span>} </> ); }

بهذه الطريقة ، تحصل على أفضل ما في العالمين! تحصل على رابط بسيط لتلك السيناريوهات البسيطة ، وتحصل على المرونة التي تحتاجها لتلك الأجزاء المعقدة.

التوثيق هو المفتاح

عندما أستخدم مكتبة لم أكتب بنفسي ، أحب التوثيق الرائع. ولكن ما الذي يجب أن تركز عليه ، وأين يجب أن توثق؟

يجب أن تكون الخطوة الأولى هي تجميع طريقة بسيطة لفهم README ، مع إتاحة أبسط أمثلة الاستخدام بسهولة. كتب Andrew Healey مقالًا رائعًا عن كيفية كتابة قراءة جيدة ، وأنا أوصي بشدة بقراءتها.

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

هناك أدوات رائعة لإنشاء مواقع التوثيق. المفضل لدي هو docusaurus من Facebook (تفاخر متواضع: استخدمناه عند إنشاء موقع create-react-app ) ، ولكن هناك العديد من البدائل الجيدة.

لن نستعرض كيفية كتابة وثائق جيدة في هذه المقالة. هناك العديد من المقالات الجيدة - حتى مجتمع يسمى "اكتب المستندات". لقد كتبوا دليلًا رائعًا لكيفية البدء في كتابة وثائق رائعة.

ملخص

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

لقد مررنا بكيفية تنفيذنا للأشياء خطوة بخطوة ، وآمل أن يكون لديك فهم أعمق لكيفية إنشاء مكتبتك الخاصة ، وكيف تجعلها شيئًا يحب الناس استخدامه.

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

لإنهاء هذه المقالة - ها هي النسخة النهائية:

  • انظر عرض CodeSandbox

شكرا للقراءة!