معاملات البحث (Search Parameters)
الدرس 13 من 34 · دورة TanStack Router الكاملة · 6 دقيقة و46 ثانية
الفيديو الأصلي باللغة الإنجليزية. إذا تعذّر تشغيله هنا، شاهده على موقع المؤلف. التفريغ النصي العربي الكامل أدناه.
مستودع الكود لهذا الدرس
الفرع:
search-1
[00:00] معاملات البحث (search parameters) وسيلةٌ رائعة لتخزين حالة (state) تطبيقك. فلنقل أنّه لديك تطبيقٌ فيه ربّما كثيرٌ من التصفية (filtering) والترقيم الصفحي (pagination) والترتيب (sorting) وما إلى ذلك. إذا خزّنت هذه المعلومات، أي المعلومات
[00:13] الخاصة بالصفحة الحالية مثلًا والمرشّحات الحالية وما إلى ذلك في عنوان URL، فهذا يعني أنّه يمكنك بسهولةٍ أن تشارك هذا الرابط أو تحفظه في المفضّلة (bookmark) أو تفتحه في تبويبٍ جديد من دون أن تفقد الحالة، بما أنّ الحالة تعيش في عنوان URL.
[00:29] على عكس ما إذا خزّنت حالتك أو خزّنت هذه المعلومات في حالة React (react state)؛ فما إن تبتعد عن الصفحة بالتنقّل أو تُحدِّثها أو ما شابه ذلك حتى تفقد هذه الحالة.
[00:40] إذًا إن كان لديك تطبيقٌ يعتمد اعتمادًا كبيرًا على معاملات البحث في فعل أمورٍ من قبيل التصفية والترقيم الصفحي والترتيب وما إلى ذلك، فمن المهم أن تستطيع إدارة معاملات البحث بسهولة.
[00:51] أن تكون قادرًا على التحقّق من معاملات البحث (validate)، وأن تملك أمانَ أنواعٍ (type safety) لمعاملات البحث عندما تتعامل معها، وأن تستطيع كذلك تخزين بياناتٍ مركَّبةٍ من قبيل المصفوفات (arrays) والكائنات (objects) مثلًا في معاملات البحث، لا مجرّد
[01:05] سلاسلَ نصيةٍ (strings) بسيطة. ويتيح لنا TanStack Router فعل كل ذلك بسهولةٍ تامة. إذًا فلنرَ كيف يمكننا إدارة معاملات البحث في TanStack Router. سأفترض أنّ لَدَينا مسارًا جديدًا هنا، فلنقل مثلًا لمنتجاتنا (products). إذًا
[01:20] products.index.tsx.
[01:24] وربّما سنمتلك هنا قائمةً بالمنتجات أو ما شابه، وسنمتلك بعض المرشّحات لتصفية منتجاتنا، وترقيمًا صفحيًا وترتيبًا وما إلى ذلك.
[01:32] إذًا فلنُنشئ هذا المسار. والآن يمكننا زيارة هذا المسار بالذهاب إلى /products.
[01:40] والآن فلنقل في صفحتنا الرئيسية (homepage) مثلًا: فلتأتَ إلى index ولنقل أنّه هنا سنمتلك رابطًا سَيَنقلنا إلى مسار products، فلنجعله «منتجات مع مرشّحات» (products with filters)، وفلنقل أنّنا
[01:56] نحتاج إلى تضمين بعض المرشّحات في معاملات البحث لدينا.
[01:59] إذًا سنجد أنّه يمكننا ببساطة الوصول إلى مسار products لدينا، وكي نضيف بعض معاملات البحث نضيف ببساطة خاصية (prop) search هنا ثم نضع معاملاتنا في كائنٍ (object). وسأضع هنا بعض العناصر، وكما ذكرنا
[02:15] في TanStack Router يمكننا تمرير أيّ شيءٍ هنا: يمكننا تمرير سلاسلٍ نصية، أي sortBy على أساس السعر مثلًا، ويمكن تمرير مصفوفات، فلنقل بالتصفية حسب نوع المنتج (product type) ونمرّر مصفوفةً هنا، ويمكن أن يكون لَدَينا ترقيمٌ صفحي (pagination) يكون كائنًا مع
[02:28] الصفحة وحجمِ الصفحة (page size)، ويمكن أن يكون لَدَينا مصفوفةً أخرى للتصفية حسب الألوان، ويمكن أن تكون لَدَينا قيمةٌ منطقية (boolean) أيضًا وهكذا.
[02:37] الآن، إن حفظنا هذا وذهبنا إلى صفحتنا الرئيسية ونقرنا على هذا الرابط، أي هذا — «منتجات مع مرشّحات» (products with filters) — ففلنضف في الواقع سطرًا جديدًا هنا.
[02:51] وسَننتقل باستخدام رابطٍ يحوي كل شيءٍ لدينا، أي كل معاملات البحث لدينا. وكما ترى هنا، لدينا products ثم لدينا sort by والمصفوفة والكائن المُشفَّرَين (encoded) وما إلى ذلك. إذًا في معاملات
[03:04] البحث لدينا يمكننا تمرير أيّ بياناتٍ قابلةٍ للتسلسل (serializable) بتنسيق JSON، من قبيل المصفوفات والكائنات وما رأيناه هنا، وسَيَسلسُلها TanStack Router في عنوان URL كما نرى هنا، وعندما نستخدمها في مسارنا سَيَفكّ تسلسلها (deserialize)
[03:18] ويُعِيدُها إلى هذه الحالة التي هنا، حيث سَيَكُون لَدَينا كائنٌ يضمّ سلاسلَنا النصية ومصفوفاتنا وكائناتنا وما إلى ذلك. وإذا ألقيتَ نظرةً على أدوات المطوّر هنا فسنجد معاملات البحث لدينا، وكما
[03:33] ترى — ولست متأكّدًا إن كان بوسعي تحريك هذا مثلًا — لدينا معاملات البحث هنا: لدينا sort by price، ولدينا المصفوفة وكائنُ الترقيم الصفحي وما إلى ذلك. أظنّ أنّنا نحتاج فقط إلى... نعم، ها هو ذا. والآن
[03:49] بالطبع يمكننا الوصول إلى معاملات البحث لدينا في مكوّن (component) لدينا أو في دوالّ التحميل (load functions) التي سنتناولها لاحقًا بالطبع. إذًا فلنجرب في مكوّننا الوصول إلى معاملات البحث لدينا. ويمكن فعل ذلك
[04:03] بأن نصل في مسارنا إلى خُطّاف (hook) آخر اسمه use search، إذًا use search هكذا.
[04:12] ومن هنا يمكننا الحصول على معاملات البحث لدينا. فلنجرب في الواقع طباعتها (log) وينبغي أن نحصل على الأشياء نفسها التي رأيناها في أدوات المطوّر، أي لَدَينا الكائنُ الذي يضمّ الألوان (colors) والترقيم الصفحي ونوعَ المنتج (product type) وما
[04:27] إلى ذلك. وبالطبع الآن يمكننا استخدام هذه المعلومات في مكوّننا كي نُبرز — ربّما — المرشّحات المحدَّدة حاليًا وما إلى ذلك. غير أنّه كما ترى، حين أنشأنا هذا الرابط في صفحتنا الرئيسية ليصل إلى مسار
[04:41] products لم نحصل على أيّ أمان أنواع (type safety) عندما حدّدنا معاملات البحث هنا؛ إذ يمكننا أن نمرّر أيّ شيءٍ ولن نحصل على أيّ أخطاء، فيمكننا مثلًا جعل هذا قيمةً منطقية ولن نحصل على خطأ وهكذا. إذًا فلنرَ الآن كيف
[04:54] يمكننا التحقّق من معاملات البحث وإضافة أمان الأنواع إليها. ففي مكوّننا، أي المكوّن الذي نمرّر فيه معاملات البحث — وهو في حالتنا مكوّن products — يمكننا هنا تمرير دالّة (function) اسمها validateSearch.
[05:09] وفي validateSearch سَنحصل على معاملات البحث التي نمرّرها في عنوان URL، فستكون كائنًا (object)؛ إذ يمكننا أن نمنحها نوعًا (type) من طبقة record بحيث يكون مفتاحُها (key) سلسلةً نصيةً (string)، وقيمتُها سَتَكُون
[05:22] unknown، صحيح؟ وفي هذه الدالّة يمكننا أن نُرجِع كائنًا فيضمّ ذلك الكائنُ معاملاتِ البحث التي تحقّقنا منها ووهبناها نوعًا. فما نستقبلُه هنا بوصفه وسيطًا (argument) هو كلّ ما نمرّره إلى عنوان URL، والذي يمكن أن يكون أيّ
[05:40] بياناتٍ من دون نوعٍ ومن دون تحقّق. وفي هذه الدالّة سنأخذ هذه البيانات ونتحقّق منها ونمنحها نوعًا؛ فلنفعل ذلك الآن من أجل sortBy على سبيل المثال: فلنقل أنّ sortBy يجب أن يكون سلسلةً نصية؛ إذًا هنا يمكننا أن نمرّر
[05:57] search.sortBy بوصفه string، أي نمنحه نوع سلسلةٍ نصية، وربّما إن لم يكن موجودًا فلنمرّر سلسلةً نصية فارغة.
[06:07] إذًا الآن بسبب هذا سَنحصل على أخطاء لأنّنا نمرّر أشياءً لم نحدّدها هنا؛ فلنزِلها — على سبيل المثال — الآن، أو لنعلّقها (comment) مثلًا. والآن لن نحصل على أيّ خطأ لأنّنا نمرّر sort by
[06:20] بوصفه سلسلةً نصية. وإن مرّرناه مثلًا بوصفه قيمةً منطقية فسَنحصل على خطأ لأنّنا حدّدنا هنا أنّه سلسلةٌ نصية.
[06:29] والآن سيظلُّ عملُ هذا الرابط على حاله، غير أنّنا لن نحصل، بالطبع، إلا على معامل sort by هنا.
[06:36] غير أنّه من المستحسن، لا سيّما إذا كان ربّما لديك كثيرٌ من معاملات البحث في مكوّنك، أن تستخدم مكتبةً (library) للتحقّق (validation) مثل Zod. إذًا في حالةِ…