اختار المؤلف صندوق البرمجيات الحرة والمفتوحة المصدر لتلقي تبرع كجزء من برنامج كتابة من أجل التبرعات.
المقدمة
فلاسك هو إطار عمل خفيف لغة برمجة Python يوفر أدوات وميزات مفيدة لإنشاء تطبيقات ويب بلغة Python. SQLAlchemy هو مجموعة أدوات SQL توفر وصولاً فعّالًا وأداءً عاليًا لقواعد البيانات العلاقية. يوفر وسائل للتفاعل مع عدة محركات قواعد بيانات مثل SQLite وMySQL وPostgreSQL. يمنحك وصولًا إلى وظائف SQL في قاعدة البيانات. كما يمنحك Mapper Relational Object (ORM) ، الذي يسمح لك بإجراء الاستعلامات ومعالجة البيانات باستخدام كائنات وطرق Python. Flask-SQLAlchemy هو امتداد Flask يجعل استخدام SQLAlchemy مع Flask أسهل ، من خلال توفير أدوات وطرق للتفاعل مع قاعدة البيانات في تطبيقات Flask الخاصة بك من خلال SQLAlchemy.
A many-to-many database relationship is a relationship between two database tables where a record in each table can reference several records in the other table. For example, in a blog, a table for posts can have a many-to-many relationship with a table for storing authors. Each post can have many authors, and each author can write many posts. Therefore, there is a many-to-many relationship between posts and authors. For another example, in a social media application, each post may have many hashtags, and each hashtag may have many posts.
في هذا البرنامج التعليمي ، ستقوم بتعديل تطبيق تم إنشاؤه باستخدام Flask و Flask-SQLAlchemy عن طريق إضافة علاقة كثير إلى كائن. ستكون لديك علاقة بين المشاركات والعلامات، حيث يمكن أن يحتوي كل مدونة على العديد من العلامات، ويمكن أن تحتوي كل علامة على عدة مشاركات موسومة بها.
على الرغم من أنه يمكنك متابعة هذا البرنامج التعليمي بشكل مستقل، إلا أنه أيضًا استمرار لبرنامج التعليمي كيفية استخدام علاقات قاعدة بيانات واحد-إلى-العديد مع Flask-SQLAlchemy، الذي تقوم فيه بإنشاء قاعدة بيانات متعددة الجداول مع علاقة واحد-إلى-العديد بين المشاركات والتعليقات في تطبيق مدونة.
بحلول نهاية البرنامج التعليمي، ستحتوي تطبيقك على ميزة جديدة لإضافة علامات إلى المشاركات. يمكن وضع علامات على المشاركات بعدة علامات، وسيعرض كل صفحة علامة جميع المشاركات التي تم وضع علامة عليها.
المتطلبات المسبقة
-
بيئة تطوير Python 3 محلية. اتبع البرنامج التعليمي المناسب لنظام التوزيع الخاص بك في سلسلة كيفية تثبيت وإعداد بيئة تطوير محلية لـ Python 3. في هذا البرنامج التعليمي، سنسمي دليل مشروعنا
flask_app
. -
فهم المفاهيم الأساسية لـ Flask، مثل المسارات، وظائف العرض، والقوالب. إذا كنت غير ملم بـ Flask، تحقق من كيفية إنشاء تطبيق ويب أولي باستخدام Flask و Python و كيفية استخدام القوالب في تطبيق Flask.
-
فهم المفاهيم الأساسية لـ HTML. يمكنك مراجعة سلسلة الدروس الخاصة بنا كيفية بناء موقع ويب باستخدام HTML للحصول على المعرفة الأساسية.
-
(اختياري) في الخطوة 1، ستستنسخ تطبيق المدونة الذي ستعمل عليه في هذا البرنامج التعليمي. ومع ذلك، يمكنك العمل اختيارياً من خلال البرنامج التعليمي كيفية استخدام علاقات قاعدة بيانات واحد إلى العديد مع Flask-SQLAlchemy. يمكنك الوصول إلى الشيفرة النهائية من هذه الصفحة.
الخطوة 1 — إعداد التطبيق الويب
في هذه الخطوة، ستقوم بإعداد تطبيق المدونة ليكون جاهزًا للتعديل. كما ستستعرض نماذج قاعدة البيانات Flask-SQLAlchemy ومسارات Flask لفهم هيكل التطبيق. إذا قمت بمتابعة البرنامج التعليمي في قسم الشروط المسبقة وما زلت تمتلك الشيفرة والبيئة الافتراضية على جهازك المحلي، يمكنك تخطي هذه الخطوة.
لتوضيح إضافة علاقة كثير إلى كثير في تطبيق ويب Flask باستخدام Flask-SQLAlchemy، ستستخدم شيفرة التطبيق في الدورة التعليمية السابقة، والتي هي نظام مدونة مع القدرة على إضافة وعرض المشاركات، والتعليق على المشاركات، وقراءة وحذف التعليقات الحالية.
استنسخ المستودع وغير اسمه من flask-slqa-bloggy
إلى flask_app
باستخدام الأمر التالي:
انتقل إلى flask_app
:
ثم أنشئ بيئة افتراضية جديدة:
قم بتنشيط البيئة:
قم بتثبيت Flask و Flask-SQLAlchemy:
بعد ذلك، قم بتعيين المتغيرات البيئية التالية:
FLASK_APP
يشير إلى التطبيق الذي تعمل عليه حاليًا، والذي هو app.py
في هذه الحالة. FLASK_ENV
يحدد الوضع. ستعيده إلى development
لوضع التطوير؛ وهذا سيتيح لك تصحيح التطبيق. تذكر أن لا تستخدم هذا الوضع في بيئة الإنتاج.
من ثم، افتح وحدة التحكم في Flask لإنشاء جداول قاعدة البيانات:
ثم استيراد كائن قاعدة البيانات db
في Flask-SQLAlchemy، ونموذج Post
، ونموذج Comment
، وإنشاء جداول قاعدة البيانات باستخدام وظيفة db.create_all()
:
من ثم قم بملء قاعدة البيانات باستخدام برنامج init_db.py
:
هذا يضيف ثلاث مشاركات وأربع تعليقات إلى قاعدة البيانات.
شغل خادم التطوير:
إذا ذهبت إلى المتصفح، ستجد التطبيق يعمل على الرابط التالي:
http://127.0.0.1:5000/
سترى صفحة مشابهة للتالية:
إذا واجهت خطأ، تأكد من اتباع الخطوات أعلاه بشكل صحيح.
لإيقاف خادم التطوير، استخدم CTRL + C
.
بعد ذلك، ستتعرف على نماذج قواعد البيانات Flask-SQLAlchemy لفهم العلاقات الحالية بين الجداول. إذا كنت ملمًا بمحتويات ملف app.py
، يمكنك تخطي الخطوة التالية.
افتح ملف app.py
:
محتويات الملف كما يلي:
هنا، لديك نموذجي قاعدة بيانات يمثلان جدولين:
-
Post
: الذي يحتوي على عمود ID، وعنوان، ومحتوى، وعلاقة واحد-إلى-الكثير مع جدول التعليقات. -
Comment
: الذي يحتوي على عمود ID، وعمود للمحتوى، وعمودpost_id
للإشارة إلى المقالة التي ينتمي التعليق إليها.
تحت النماذج، لديك المسارات التالية:
/
: صفحة الفهرس، التي تعرض جميع المقالات في قاعدة البيانات./<int:post_id>/
: صفحة المقالة الفردية. على سبيل المثال، الرابطhttp://127.0.0.1:5000/2/
يعرض تفاصيل المقالة الثانية في قاعدة البيانات وتعليقاتها./comments/
: صفحة تعرض جميع التعليقات في قاعدة البيانات وروابط إلى المنشور الذي تم نشر كل تعليق عليه./comments/<int:comment_id>/delete
: مسار يحذف تعليقًا من خلال زر حذف التعليق.
أغلق ملف app.py
.
في الخطوة التالية، ستستخدم علاقة كثير إلى كثير لإنشاء رابط بين جدولين.
الخطوة 2 — إعداد نماذج قاعدة البيانات لعلاقة كثير إلى كثير
في هذه الخطوة، ستضيف نموذج قاعدة بيانات سيمثل جدول الوسوم. ستربطه بجدول المنشورات الحالي باستخدام جدول الارتباط، وهو جدول يربط جدولين بعلاقة كثير إلى كثير. تربط علاقة كثير إلى كثير جدولين حيث لكل عنصر في جدول عناصر ذات صلة كثيرة في الجدول الآخر. في جدول الارتباط، سيشير كل منشور إلى وسومه وستشير كل وسم إلى المنشورات الموسومة به. ستقوم أيضًا بإدراج بعض المنشورات والوسوم في قاعدة بياناتك، وطباعة المنشورات مع وسومها، وطباعة الوسوم والمنشورات ذات الصلة بها.
لنفترض أن لديك جدول بسيط للمنشورات في البلوق على النحو التالي:
Posts
+----+-----------------------------------+
| id | content |
+----+-----------------------------------+
| 1 | A post on life and death |
| 2 | A post on joy |
+----+-----------------------------------+
وجدول للوسوم على النحو التالي:
Tags
+----+-------+
| id | name |
+----+-------+
| 1 | life |
| 2 | death |
| 3 | joy |
+----+-------+
لنفترض أنك تريد وسمًا عن الحياة والموت
بالوسوم الحياة
و الموت
. يمكنك القيام بذلك عن طريق إضافة صف جديد في جدول المنشورات على النحو التالي:
Posts
+----+-----------------------------------+------+
| id | content | tags |
+----+-----------------------------------+------+
| 1 | A post on life and death | 1, 2 |
| 2 | A post on joy | |
+----+------------------------------------------+
هذا النهج لا يعمل، لأن كل عمود يجب أن يحتوي على قيمة واحدة فقط. إذا كان لديك قيم متعددة، فإن العمليات الأساسية مثل إضافة وتحديث البيانات تصبح مُعقدة وبطيئة. بدلاً من ذلك، يجب أن يكون هناك جدول ثالث يشير إلى المفاتيح الأساسية للجداول ذات الصلة – يُطلق على هذا الجدول في كثير من الأحيان جدول الارتباط أو جدول الانضمام، ويخزن معرفات كل عنصر من كل جدول.
فيما يلي مثال على جدول ارتباط يربط بين المنشورات والوسوم:
post_tag
+----+---------+-------------+
| id | post_id | tag_id |
+----+---------+-------------+
| 1 | 1 | 1 |
| 2 | 1 | 2 |
+----+---------+-------------+
في الصف الأول، المنشور بالمعرف 1
(أي عن الحياة والموت
) يرتبط بالوسم ذي المعرف 1
(الحياة
). في الصف الثاني، يرتبط نفس المنشور أيضًا بالوسم ذي المعرف 2
(الموت
). وهذا يعني أن المنشور موسوم بالوسوم الحياة
و الموت
. بالمثل، يمكنك توسيم كل منشور بعلامات متعددة.
الآن، ستقوم بتعديل ملف app.py
لإضافة نموذج جديد لقاعدة البيانات يمثل الجدول الذي ستستخدمه لتخزين الوسوم. كما ستضيف جدول ارتباط يُسمى post_tag
يربط المنشورات بالوسوم.
أولاً، قم بفتح app.py
لتأسيس علاقة بين المنشورات والوسوم:
أضف جدول post_tag
ونموذج Tag
أدناه من كائن db
وقبل نموذج Post
، ثم أضف عمود وهمي tags
إلى نموذج Post
بحيث يمكنك الوصول إلى علامات المنشور عبر post.tags
والوصول إلى منشورات العلامة عبر tag.posts
:
احفظ وأغلق الملف.
هنا تستخدم دالة db.Table()
لإنشاء جدول يحتوي على عمودين. بالنسبة لجداول الارتباط، الممارسة الأفضل هي استخدام جدول بدلاً من نموذج قاعدة بيانات.
يحتوي جدول post_tag
على عمودين يمثلان مفاتيح خارجية، وهي مفاتيح تُستخدم للإشارة إلى أعمدة المفتاح الأساسي في جدول آخر:
post_id
: مفتاح خارجي من نوع عدد صحيح يمثل معرف المنشور ويشير إلى عمود المعرف في جدولpost
.tag_id
: مفتاح خارجي من نوع عدد صحيح يمثل معرف العلامة ويشير إلى عمود المعرف في جدولtag
.
تُنشئ هذه المفاتيح العلاقات بين الجداول.
أسفل جدول post_tag
، تُنشئ نموذج Tag
الذي يمثل الجدول الذي ستخزن فيه علاماتك. يحتوي هذا الجدول على عمودين:
id
: معرف العلامة.name
: اسم العلامة.
تستخدم اسم العلامة في الطريقة الخاصة __repr__()
لتوفير تمثيل سلسلة واضح لكل كائن علامة لأغراض التصحيح.
تضيف متغير الفئة tags
إلى نموذج Post
. تستخدم طريقة db.relationship()
، ممررة لها اسم نموذج الوسوم (Tag
في هذه الحالة).
تمرر الجدول التابع للعلاقة post_tag
إلى المعلمة secondary
لإنشاء علاقة كثير إلى كثير بين المشاركات والوسوم.
تستخدم المعلمة backref
لإضافة مرجع خلفي يتصرف مثل عمود إلى نموذج Tag
. بهذه الطريقة، يمكنك الوصول إلى مشاركات الوسم عبر tag.posts
والوسوم لمشاركة عبر post.tags
. سترى مثالًا يوضح هذا لاحقًا.
بعد ذلك، قم بتحرير برنامج Python init_db.py
لتعديل قاعدة البيانات بإضافة جدول الارتباط post_tag
وجدول الوسوم الذي سيعتمد على نموذج Tag
:
عدل الملف ليبدو كما يلي:
احفظ وأغلق الملف.
هنا، تقوم باستيراد نموذج Tag
. تقوم بحذف كل شيء في قاعدة البيانات باستخدام الدالة db.drop_all()
لإضافة العلامات وجداول post_tag
بأمان وتجنب أي من المشاكل الشائعة المتعلقة بإضافة جداول جديدة إلى قاعدة بيانات. ثم تقوم بإنشاء جميع الجداول من جديد باستخدام الدالة db.create_all()
.
بعد الشفرة من البرنامج التعليمي السابق الذي يعلن عن المنشورات والتعليقات، تستخدم نموذج Tag
لإنشاء أربع علامات.
ثم تضيف العلامات إلى المنشورات باستخدام السمة tags
التي تمت إضافتها عبر السطر tags = db.relationship('Tag', secondary=post_tag, backref='posts')
في ملف app.py
. تعين العلامات للمنشورات باستخدام طريقة append()
مشابهة لقوائم Python.
بعد ذلك، تضيف العلامات التي أنشأتها إلى جلسة قاعدة البيانات باستخدام الدالة db.session.add_all()
.
ملاحظة:
الدالة db.create_all()
لا تقوم بإعادة إنشاء أو تحديث جدول إذا كان موجودًا بالفعل. على سبيل المثال، إذا قمت بتعديل النموذج الخاص بك عن طريق إضافة عمود جديد وقمت بتشغيل الدالة db.create_all()
، فلن يتم تطبيق التغيير الذي قمت به على النموذج إذا كان الجدول موجودًا بالفعل في قاعدة البيانات. الحل هو حذف جميع جداول قاعدة البيانات الحالية باستخدام الدالة db.drop_all()
ثم إعادة إنشاؤها باستخدام الدالة db.create_all()
، كما هو موضح في ملف init_db.py
.
سيقوم هذا العملية بتطبيق التعديلات التي تقوم بها على نماذجك ولكن سيتم أيضًا حذف جميع البيانات الحالية في قاعدة البيانات. لتحديث قاعدة البيانات والحفاظ على البيانات الحالية، ستحتاج إلى استخدام ترحيل الهيكل الجدولي، الذي يتيح لك تعديل الجداول الخاصة بك والحفاظ على البيانات. يمكنك استخدام إضافة Flask-Migrate
لتنفيذ ترحيلات هيكل SQLAlchemy عبر واجهة سطر الأوامر في Flask.
قم بتشغيل برنامج init_db.py
لتطبيق التغييرات على قاعدة البيانات:
يجب أن يتم تنفيذ البرنامج بنجاح دون أي إخراج. إذا رأيت خطأ، تأكد من أنك قمت بإجراء التغييرات بشكل صحيح على ملف init_db.py
.
للاطلاع على المشاركات والعلامات التي توجد حاليًا في قاعدة البيانات، افتح واجهة سطر الأوامر لـ Flask:
قم بتنفيذ الكود البايثوني التالي الذي يكرر عبر المشاركات والعلامات:
هنا، تقوم بإستيراد نموذج Post
من app.py
. تستعلم جدول المشاركات وتُحضر كل المشاركات في قاعدة البيانات. تكرر عبر المشاركات، وتطبع عنوان المشاركة وقائمة العلامات المرتبطة بكل مشاركة.
ستحصل على إخراج مشابه للتالي:
Output
Post The First
[<Tag "animals">, <Tag "writing">]
---
Post The Third
[<Tag "cooking">, <Tag "tech">, <Tag "writing">]
---
Post The Second
[]
---
يمكنك الوصول إلى أسماء العلامات باستخدام tag.name
كما هو موضح في المثال التالي، الذي يمكنك تنفيذه باستخدام واجهة سطر الأوامر لـ Flask:
هنا، بالإضافة إلى طباعة عنوان المشاركة، تكرر عبر العلامات في كل مشاركة وتطبع اسم العلامة.
ستحصل على إخراج مشابه للتالي:
OutputTITLE: Post The First
-
TAGS:
> animals
> writing
------------------------------
TITLE: Post The Third
-
TAGS:
> cooking
> tech
> writing
------------------------------
TITLE: Post The Second
-
TAGS:
------------------------------
كما ترى، تم ربط العلامات التي أضفتها إلى المشاركات في برنامج init_db.py
بشكل صحيح مع المشاركات التي تم وسمها.
لعرض ديمو لكيفية الوصول إلى المشاركات الموسومة بوسم محدد عبر tag.posts
، قم بتشغيل الكود التالي في قالب Flask:
قم بإدخال نموذج Tag
. ثم استخدم الطريقة filter_by()
على السمة query
ممررًا لها معلمة name
للحصول على الوسم writing
بواسطة اسمه، واحصل على النتيجة الأولى باستخدام الطريقة first()
. قم بتخزين كائن الوسم في متغير يسمى writing_tag
. لمزيد من المعلومات حول الطريقة filter_by
، انظر الخطوة 4 من كيفية استخدام Flask-SQLAlchemy للتفاعل مع قواعد البيانات في تطبيق Flask.
قم بتكرار المشاركات التي تم وسمها بالوسم writing
، والتي تم الوصول إليها عبر writing_tag.posts
. قم بطباعة عنوان المشاركة، والمحتوى، وقائمة أسماء العلامات التي تقوم بإنشائها باستخدام التركيب القائم على القوائم استنادًا إلى العلامات للمشاركة، التي يتم الوصول إليها عبر post.tags
.
ستحصل على مخرجات مشابهة لما يلي:
OutputPost The Third
------
Content for the third post
-
['cooking', 'tech', 'writing']
--------------------
Post The First
------
Content for the first post
-
['animals', 'writing']
--------------------
هنا ترى المشاركتان التي تم وسمهما بالوسم writing
، ويتم عرض أسماء العلامات في قائمة Python.
يمكنك الآن الوصول إلى المشاركات وعلاماتها والوصول إلى المشاركات التي تحمل وسمًا محددًا.
لقد قمت بإضافة نموذج قاعدة بيانات يمثل جدول العلامات. قمت بربط المشاركات بالعلامات باستخدام جدول الارتباط، وقمت بإدراج عدد قليل من العلامات في قاعدة البيانات ووسمت المشاركات بها. لقد قمت بالوصول إلى المشاركات وعلاماتها ومشاركات العلامة الفردية. في الخطوة التالية، ستستخدم واجهة سطر الأوامر في Flask لإضافة مشاركات جديدة وعلامات جديدة وربط بين العلامات والمشاركات، وستتعلم كيفية إزالة العلامات من مشاركة.
الخطوة 3 — إدارة البيانات في العلاقة العديد إلى العديد
في هذه الخطوة، ستستخدم واجهة سطر الأوامر في Flask لإضافة مشاركات جديدة إلى قاعدة البيانات، وإضافة علامات، وربط بين المشاركات والعلامات. ستقوم بالوصول إلى المشاركات مع علاماتها، وسترى كيفية فصل عنصر عن آخر في العلاقات العديد إلى العديد.
أولاً، بعد تفعيل بيئة البرمجة الخاصة بك، افتح واجهة سطر الأوامر في Flask إذا لم تكن قد فعلت بالفعل:
ثم، قم بإضافة عدد قليل من المشاركات والعلامات:
from app import db, Post, Tag
life_death_post = Post(title='A post on life and death', content='life and death')
joy_post = Post(title='A post on joy', content='joy')
life_tag = Tag(name='life')
death_tag = Tag(name='death')
joy_tag = Tag(name='joy')
life_death_post.tags.append(life_tag)
life_death_post.tags.append(death_tag)
joy_post.tags.append(joy_tag)
db.session.add_all([life_death_post, joy_post, life_tag, death_tag, joy_tag])
db.session.commit()
هذا ينشئ مشاركتين وثلاث علامات. تقوم بوسم المشاركات بعلاماتها المتعلقة، وتستخدم الطريقة add_all()
لإضافة العناصر المنشأة حديثًا إلى جلسة قاعدة البيانات. ثم تقوم بتأكيد التغييرات وتطبيقها على قاعدة البيانات باستخدام الطريقة commit()
.
ثم، استخدم واجهة سطر الأوامر في Flask للحصول على جميع المشاركات وعلاماتها كما فعلت في الخطوة السابقة:
posts = Post.query.all()
for post in posts:
print(post.title)
print(post.tags)
print('---')
ستحصل على نتيجة مماثلة للتالية:
Output
Post The First
[<Tag "animals">, <Tag "writing">]
---
Post The Third
[<Tag "cooking">, <Tag "tech">, <Tag "writing">]
---
Post The Second
[]
---
A post on life and death
[<Tag "life">, <Tag "death">]
---
A post on joy
[<Tag "joy">]
---
يمكنك رؤية أن المشاركات تمت إضافتها بالإضافة إلى علاماتها.
لتوضيح كيفية كسر العلاقة بين عنصرين في علاقة قاعدة بيانات كثير إلى كثير، دعونا نفترض أن المنشور بعنوان المنشور الثالث
لم يعد يتعلق بالطبخ، لذا عليك أن تقوم بإزالة العلامة الطبخ
منه.
أولاً، احصل على المنشور والعلامة التي تريد إزالتها:
هنا تقوم بجلب المنشور بعنوان المنشور الثالث
باستخدام طريقة filter_by()
. ثم تحصل على العلامة الطبخ
. بعد ذلك، تقوم بطباعة عنوان المنشور، وعلاماته، والمنشورات الموسومة بعلامة الطبخ
.
طريقة filter_by()
تعيد كائن استعلام، ويمكنك استخدام طريقة all()
للحصول على قائمة بجميع النتائج. ولكن نظرًا لأننا نتوقع نتيجة واحدة فقط في هذه الحالة، نستخدم الطريقة first()
للحصول على النتيجة الأولى (والوحيدة). للمزيد حول الطريقتين first()
و all()
، تحقق من الخطوة 4 من كيفية استخدام Flask-SQLAlchemy للتفاعل مع قواعد البيانات في تطبيق Flask.
ستحصل على النتيجة التالية:
Output
Post The Third
[<Tag "cooking">, <Tag "tech">, <Tag "writing">]
[<Post "Post The Third">]
هنا ترى عنوان المنشور، وعلامات المنشور، وقائمة المنشورات الموسومة بعلامة الطبخ
.
لإزالة العلامة الطبخ
من المنشور، استخدم الطريقة remove()
كما يلي:
هنا تستخدم الطريقة remove()
لفصل العلامة الطبخ
عن المنشور. ثم تستخدم طريقة db.session.commit()
لتطبيق التغييرات على قاعدة البيانات.
ستحصل على إخراج يؤكد إزالة الوسم من المنشور:
Output[<Tag "tech">, <Tag "writing">]
[]
كما يمكنك أن ترى، فإن الوسم cooking
لم يعد في قائمة post.tags
، وتمت إزالة المنشور من قائمة tag.posts
.
اخرج من قشرة اللفافة:
لقد أضفت منشورات وعلامات جديدة. لقد وسمت المنشورات وأزلت العلامات من المنشورات. فيما يلي، ستقوم بعرض العلامات لكل منشور في صفحة الفهرس الخاصة بمدونة الويب Flask الخاصة بك.
الخطوة 4 — عرض العلامات تحت كل منشور
في هذه الخطوة، ستقوم بتحرير قالب الفهرس لعرض العلامات تحت كل منشور.
أولاً، دعنا نلقي نظرة على الصفحة الرئيسية الحالية لمدونة الويب Flask.
عند تنشيط بيئة البرمجة الخاصة بك، قل لـ Flask عن التطبيق (app.py
في هذه الحالة) باستخدام المتغير المحيطي FLASK_APP
. ثم قم بتعيين المتغير المحيطي FLASK_ENV
إلى development
لتشغيل التطبيق في وضع التطوير:
ثم قم بتشغيل التطبيق:
مع تشغيل خادم التطوير، قم بزيارة الرابط التالي في متصفحك:
http://127.0.0.1:5000/
سترى صفحة مشابهة للصورة التالية:
اترك خادم التطوير يعمل وافتح نافذة طرفية جديدة.
سيتعين عليك عرض العلامات لكل مشاركة على صفحتين: تحت كل مشاركة على صفحة الفهرس وتحت محتوى المشاركة على صفحة المشاركة. ستستخدم نفس الكود لعرض العلامات. لتجنب تكرار الكود، ستستخدم ماكرو جينجا، والذي يتصرف مثل دالة Python. يحتوي الماكرو على كود HTML ديناميكي يمكن عرضه في أي مكان تقوم بدعوة الماكرو إليه، وتطبيق التعديلات عليه يجعل الكود قابلاً لإعادة الاستخدام.
أولاً، قم بفتح ملف جديد يسمى macros.html
في الدليل templates
الخاص بك:
أضف الكود التالي إليه:
احفظ وأغلق الملف.
هنا، تستخدم الكلمة المفتاحية macro
لتعريف ماكرو يُدعى display_tags()
مع معامل يُدعى post
. تستخدم علامة <div>
، حيث تعرض عنوانًا <h4>
. تستخدم حلقة for
للانتقال من خلال العلامات لكائن المشاركة الذي سيتم تمريره كمعامل عند استدعاء الماكرو، بشكل مشابه لكيفية تمرير الوسيط في استدعاء دالة Python. تحصل على العلامات من خلال post.tags
. تعرض اسم العلامة داخل علامة <a>
. في وقت لاحق، ستقوم بتحرير قيمة السمة href
لربطها بصفحة العلامة التي ستنشئها حيث يتم عرض جميع المشاركات الموسومة بعلامة معينة. تحدد نهاية الماكرو باستخدام الكلمة المفتاحية endmacro
.
بعد ذلك، لعرض العلامات تحت كل مشاركة على صفحة الفهرس، افتح ملف القالب index.html
:
أولاً، ستحتاج إلى استيراد ماكرو display_tags()
من ملف macros.html
. أضف الاستيراد التالي في الأعلى فوق السطر {% extends 'base.html' %}
:
بعد ذلك، قم بتحرير حلقة for post in posts
، بالاستدعاء ماكرو display_tags()
كما يلي:
احفظ وأغلق الملف.
تستدعي ماكرو display_tags()
، مرر إليها كائن post
. سيتم عرض أسماء العلامات تحت كل مشاركة.
قم بتحديث صفحة الفهرس في متصفحك وسترى العلامات تحت كل مشاركة، كما هو موضح في الصورة التالية:
بعد ذلك، ستضيف العلامات تحت محتوى المشاركة على صفحة المشاركة. افتح ملف القالب post.html
:
أولاً، استورد ماكرو display_tags
في الأعلى:
ثم اتصل بماكرو display_tags()
، مرر إليه كائن post
تحت محتوى المشاركة وفوق علامة <hr>
:
<div class="post">
<p><b>#{{ post.id }}</b></p>
<b>
<p class="title">{{ post.title }}</p>
</b>
<div class="content">
<p>{{ post.content }}</p>
</div>
{{ display_tags(post) }}
<hr>
<h3>Comments</h3>
احفظ وأغلق الملف.
الآن، انتقل إلى صفحة مشاركة:
http://127.0.0.1:5000/2
سترى أن العلامات معروضة بنفس الطريقة كما هو معروض على صفحة الفهرس.
لقد عرضت العلامات التي أضفتها إلى المشاركات تحت كل مشاركة. في الخطوة التالية، ستضيف مسارًا جديدًا إلى تطبيق Flask الخاص بك يعرض جميع المشاركات الموسومة بعلامة محددة. ثم ستجعل الروابط التي عرضتها في هذه الخطوة تعمل.
الخطوة 5 — عرض الوسوم ومشاركاتها
في هذه الخطوة، ستقوم بإضافة مسار وقالب إلى تطبيق الويب الخاص بك لعرض الوسوم التي لديك في قاعدة البيانات ومشاركاتها.
أولاً، ستقوم بإضافة مسار لعرض مشاركات كل وسم. على سبيل المثال، سيعرض المسار /tags/tag_name/
صفحة تعرض جميع المشاركات الموسومة بوسم يسمى tag_name
.
افتح app.py
للتحرير:
أضف المسار التالي إلى نهاية الملف:
# ...
@app.route('/tags/<tag_name>/')
def tag(tag_name):
tag = Tag.query.filter_by(name=tag_name).first_or_404()
return render_template('tag.html', tag=tag)
احفظ وأغلق الملف.
هنا تستخدم متغير URL يسمى tag_name
الذي يحدد الوسم والمشاركات الموسومة به التي سيتم عرضها على صفحة الوسم. يتم تمرير اسم الوسم إلى وظيفة العرض tag()
عبر معلمة tag_name
، التي تستخدمها على طريقة filter_by()
للاستعلام عن الوسم. تستخدم first_or_404()
للحصول على كائن الوسم وتخزينه في متغير يسمى tag
، أو للرد برسالة خطأ 404 Not Found
في حالة عدم وجود وسم بالاسم المعطى في قاعدة البيانات.
ثم تقوم بعرض ملف القالب المسمى tag.html
، ممررًا له كائن tag
.
افتح الملف الجديد templates/tag.html
للتحرير:
أضف الكود التالي إليه:
احفظ وأغلق الملف.
تستورد الماكرو display_tags()
من macros.html
، وتوسّع القالب الأساسي.
في كتلة المحتوى، تحدد عنوانًا كعنوان بعنوان العلامة المضافة. ثم تكرر العملية عبر المنشورات الموسومة بالعلامة المعطاة، التي تصل إليها عبر tag.posts
. تعرض هوية المنشور، وعنوان المنشور، ومحتوى المنشور. ثم تستدعي الماكرو display_tags()
لعرض كل العلامات المرتبطة بالمنشور.
مع تشغيل الخادم التطويري، انتقل إلى العنوان التالي:
http://127.0.0.1:5000/tags/writing/
هذه هي الصفحة الخاصة بالعلامة writing
. كما ترى، يتم عرض جميع المنشورات التي تم وسمها بـ writing
:
الآن قم بتعديل الماكرو display_tags()
لجعل روابط العلامات وظيفية. افتح macros.html
:
عدل قيمة سمة href
كما يلي:
احفظ وأغلق الملف.
قم بتحديث الصفحات التي تم استخدام الماكرو display_tags()
فيها، وسترى أن روابط العلامات الآن تعمل:
http://127.0.0.1:5000/
http://127.0.0.1:5000/2/
http://127.0.0.1:5000/tags/writing/
كما ترى، باستخدام الماكروهات Jinja يمكنك إعادة استخدام الشفرة، وتحرير الماكرو يطبق التغييرات عبر العديد من القوالب.
لقد أضفت صفحة للعلامات الفردية حيث يمكن للمستخدمين مشاهدة جميع المنشورات التي تم وسمها بعلامة محددة، والعلامات تحت المنشورات الآن تؤدي إلى هذه الصفحة الجديدة.
الختام
تتضمن الميزة التي أضفتها إلى نظام التدوين الخاص بك كيفية إدارة العلاقات الكثير إلى الكثير باستخدام امتداد Flask-SQLAlchemy. تعلمت كيفية ربط جداول متعلقة بينها باستخدام جدول ارتباط (المعروف أيضًا باسم جدول الانضمام), وربط إدخال بآخر، وإضافة الإدخال إلى قاعدة البيانات، والوصول إلى البيانات وفصلها من الإدخال.
إذا كنت ترغب في قراءة المزيد حول Flask، فاطلع على الدروس الأخرى في سلسلة كيفية بناء تطبيقات الويب باستخدام Flask.