لوحة المتصدرين
المحتوى الأكثر حصولًا على سمعة جيدة
المحتوى الأعلى تقييمًا في 12/01/24 في كل الموقع
-
3 نقاط
-
PS C:\Users\titans\Desktop\5-landing-pages> git push origin main >> Everything up-to-date وعندما اذهب إلى المستودع لا أجد اي تغيرات وحاولت بطرق كثيرة مع انه عندما اقوم بتنفيذ الأمر git status يظهر لي الفرع الصحيح و ويظهرلي الن جميع الملفات يتب تعقبها وتكون بلون الأخضر فا لا أعرف سبب المشكلة مع العلم انني استخدم Windows PowerShell المسؤول اقتباس2 نقاط
-
ده فعلا اللي انا عملته ممكن تجرب من ال url ده هيتلاقي الصوره لما تيجي تطلب ال url كذا مره الصوره مره هتيجي و مره مش هتيجي https://coral-app-3s2ln.ondigitalocean.app/users/1733063730601.jpg2 نقاط
-
سؤال يعني عن دورة علوم الحسوب انا لدي خلفية برمجية عن C++ يعني عندي الاساسيات الى الoop و الoop متمكنة منه بطريقة بسيطة سؤالي انا الان اشتركت في دورة علوم الحسوب و الsection الاول الخاص بالسكراتش بسيط جداً هل سأحصل على فائدة من باقي الدورة؟؟1 نقطة
-
قد لا يكون سكراتش مفيدا لك بحكم أنه لديك أساسيات بهذا المجال لكن بالطبع ستسفيد من بقية الدورة, فيمكنك من خلال الدورة تعلم التالي: لغة برمجة JavaScript مما يعلمك كيفية التعامل مع لغة جديدة بناء على اللغة التي تم تعلمها سابقا قواعد بيانات SQL قواعد بيانات NoSQL الخوارزميات والتفكير المنطقي في حل المشاكل نظم التشغيل لغة بايثون المستخدمة في مجالات شتى مفاهيم عن الحاسوب بشكل عام كالشبكات أنماط التصميم وغيرها الكثير من المعلومات, أتمنى لك التوفيق.1 نقطة
-
انا بعمل مشروع ب node.js & express.js و استعملت multer عشان احفظ صوره ال user لما يعمل register و بتتحفظ علي ال local host صح و بتتعرض صح المشكله بتيجي لما الكلام ده يحصل علي السيرفر digitalocean ساعتها باجي اعمل get لل endpoint اللي هتجيب صوره معينه هنا بقي ساعات بتشتغل و الصوره تتعرض و ساعات السيرفر ميعرفش يجيب الصوره و الاقي error 404 barber-backend-master2.zip1 نقطة
-
1 نقطة
-
طالما لديكِ إلمام بأساسيات البرمجة من خلال لغة قوية جدًا مثل C++ فلا حاجة إطلاقًا لدراسة مسار سكراتش فهو مناسب لتقديم مفاهيم البرمجة بشكل مبسط لمن ليس لديهم أي دراية بمجال البرمجة. على عكسك أنتِ، بالتالي عليكِ دراسة المسارات التالية لمسار سكراتش بالكامل وستجدي استفادة منهم، حيث سيتم التطرق إلى: أساسيات البرمجة من خلال جافاسكريبت (ستتمكني من دراسته بسهولة بما أن لديك خلفية برمجية وستتعلمي لغة جافاسكريبت أيضًا) أنظمة التشغيل ونظام لينكس قواعد البيانات مجال الويب والواجهة الأمامية والخلفية البرمجة كائنية التوجه من خلال بايثون الخوارزميات وبنى المعطيات algorithm and data structure أنماط التصميم design patterns أساسيات هندسة البرمجيات Software Development Life Cycle (SDLC) إعادة تصميم البرمجيات Refactoring وكل ما سبق مطلوب منك معرفته ودراسته لتصبحي مهندسة برمجيات software engineer.1 نقطة
-
هل تقوم بإستخدام إعدادات تحتوي على أكثر من خادم (scaled instances) أو Load Balancer ؟ إذا كان كذلك فالسبب هو أنه يتم رفع الصورة على أحد الخوادم فقط ولكن عند طلب الصورة يتم توجيه الطلب إلى خادم آخر لا يحتوي على الصورة لهذا مرات كثيرة تظهر الصورة ومرات أخرى لا تظهر وهذا بسبب أن المرات التي تظهر فيها الخادم الذي يوجد به الصورة هو الذي إستقبل الطلب . ولهذا يمكنك إيقاف تلك الخاصية مؤقتا وأنظر هل يتم حل المشكلة أم لا . يمكنك تجربة وضع صورة ثابته لديك في المشروع ووضع مسار خاص بها وقم برفعها على السيرفر واذهب إلى المسار وانظر هل تظهر تلك المشكلة أم لا . إذا لم تظهر فكما أخبرتك يبدوا أنك تستخدم الخوادم الموزعة .1 نقطة
-
دورة علوم الحاسوب توفر معلومات مكثفة حول مختلف مفاهيم لغات وتقنيات البرمجةةو هي أساسية لزيادة معلوماتك حول مجال التقنية بشكل عام. و بانتهائك منها سيكون لديك خبرة جيّدة بدءً من الأساسيات والأفكار والمناهج النظرية مثل هندسة البرمجيات والبرمجة كائنية التوجه إلى التعامل مع أنظمة التشغيل ولغات البرمجة التي تم التطرق لها من خلال الأمثلة العملية في الدروس، وأيضاً سيكون لديك معرفة شاملة حول قواعد البيانات وطرق التعامل مع النوعين العلائقي وغير العلائقي. وهي لا تقوم بتعيلم شئ محدد بل هي نظرة شاملة كما وضحت لمجالات التقينة عامة وذلك لإعطاء الأساسيات اللازمة في البدء في البرمجة أو إذا لم تكن تعلم أى المجالات التي تريد العمل بها ولهذا في تساعدك في إختيار المجال المناسب . وإليك الإجابة التالية لمزيد من التفاصيل حول تلك الدورة : لذلك إذا كان لديك الأساسيات الخاصة بالرمجة مثل oop وبعض لغات البرمجة فمن الممكن أن لا تضيف الكثير لك سوى في المسارات الأخرى مثل قواعد البيانات والتعامل مع الخوادم والحاسوب و الخوارزميات وبنى المعطيات . وإذا كنت تعرف المجال الذي تريد العمل به فيمكنك البدء في تلك الدورة مباشرة . إذا لم تكن مشترك في دورة أخرى وكنت قد إشتريت تلك الدورة مؤخرا وليس من وقت طويل ولم ترد ان تكمل الأساسيات - مع أني أنصحك بذلك إذا لم تكن متمكنا منها أو ليس لديك الخبرة الكافية - فيمكنك حينها محادثة الدعم من خلال الرابط التالي ويمكنك طلب تبديل الدورة إلى الدورة المناسبة: https://support.academy.hsoub.com/conversations1 نقطة
-
مرحباً مؤمن ، المشكلة التي تواجهها تتعلق بإعدادات السيرفر على DigitalOcean وطريقة الوصول إلى الملفات المخزنة ، لذلك من الصعب مساعدتك مع عدم وصولنا للسيرفر الخاص بك على DigitalOcean ، لكن مثل هذه المشكلة ربما تكون بسبب عدم توافق طريقة الحفظ على السيرفر عند استخدام multer، الصور يتم حفظها في ملف معين على السيرفر. تحتاج إلى التأكد من أن Express يقوم بخدمة الملفات الثابتة من هذا المسار (static path). أضف الكود التالي في ملف app.js أو index.js الخاص بك : const path = require('path'); app.use('/uploads', express.static(path.join(__dirname, 'uploads'))); هذا سيجعل الملفات الموجودة في مجلد uploads ، وبالتالي يمكنك الوصول إليها بالشكل التالي /uploads/<filename> في حال لم ينجح الأمر ، جرب تتبع عنوان URL عند طلب الصورة ، وتحقق من وجود الصورة في الرابط او أنه يتم استخدام رابط بشكل خطأ.1 نقطة
-
السلام عليكم لدي مشكلة error: failed to push some refs to 'https://github.com/OsamaCoding/5-landing-page.git' مع انه عندما اقوم بتنفيذ الأمر git status يظهر لي الفرع الصحيح و ويظهرلي الن جميع الملفات يتب تعقبها وتكون بلون الأخضر فا لا أعرف سبب المشكلة مع العلم انني استخدم Windows PowerShell المسؤول1 نقطة
-
1 نقطة
-
مرحبا عزيزي. يمكنك السؤال في أى وقت عن أى شئ غير واضح لديك . ولكن يجب السؤال أسفل الدرس الذي تريد الإستفسار عنه . حيث ستجد صندوق للتعليقات كما هنا يمكنك وضعك سؤالك هناك أسفل الدرس حيث هنا هو قسم الأسئلة العامة ولا نقوم بالإجابة على أسئلة الدورات هنا وسيتم الرد على جميع أسئلتكم . إذا كنت بالفعل قد أضفت سؤال ولم يتم الرد عليه يرجى إرسال رابط السؤال في رسالة لى أو يمكنك وضعه هنا .1 نقطة
-
وعليكم السلام, التعلم العميق هو يعتبر جزء من تعلم الالة فلتعلم التعلم العميق تحتاج إلى أساسيات تعلم الالة كما أن تعلم الأساسيات ستساعدك على التخصص في المجالات الأخرى بشكل أسرع. يوجد مقال في الأكادمية يوضح الموضوع بشكل مفصل. يمكنك الإطلاع عليه من هنا. وبشكل عام انظر ما هو المجال المناسب وابحث في سوق العمل عن ما هو مطلوب وما هي التكنولوجيات المطلوبة وتخصص فيه فسوق العمل مهم جدا.1 نقطة
-
حان الوقت الآن لإنشاء تطبيق مدونة متكامل باستخدام إطار عمل جانغو Django، فقد تعلمنا في المقال السابق كيف يمكن للنماذج Model والعروض View والقوالب Template أن تعمل معًا لإنشاء تطبيق جانغو لكن هذه العملية صعبة نوعًا ما، إذ يتوجب علينا كتابة 5 إجراءات على الأقل لكل ميزة نريد تحقيقها، وستكون الشيفرة البرمجية مكررةً في معظمها. لذا سنستخدم في هذا المقال واحدة من أفضل ميزات جانغو، وهي لوحة المدير Admin Panel المُضمَّنة، فما عليك سوى كتابة إجراء العرض لمعظم الميزات التي ترغب في إنشائها لتطبيقك، وسيتولى جانغو الباقي نيابة عنك تلقائيًا. إنشاء طبقة النموذج Model سنبدأ أولًا بتصميم بنية قاعدة البيانات. تصميم بنية قاعدة البيانات بالنسبة لأيّ نظام تدوين أساسي، ستحتاج إلى 4 نماذج على الأقل هي User و Category و Tag و Post، وسنضيف في المقال التالي بعض الميزات المتقدمة لاحقًا، ولكن سنكتفي حاليًا بهذه النماذج الأربعة فقط. نموذج المستخدم User المفتاح نوعه معلومات عنه المعرّف id عدد صحيح Integer يتزايد تلقائيًا الاسم name سلسلة نصية String - البريد الإلكتروني email سلسلة نصية فريد كلمة السر password سلسلة نصية - إن النموذج User مُضمَّن مسبقًا في جانغو، إذ يوفّر هذا النموذج المُضمَّن بعض الميزات الأساسية مثل تشفير كلمات المرور Password Hashing واستثياق المستخدمين User Authentication، بالإضافة إلى نظام الأذونات المُضمَّن مع مدير جانغو Django Admin كما سنوضّح لاحقًا. نموذج الفئة Category المفتاح نوعه معلومات عنه المعرّف id عدد صحيح Integer يتزايد تلقائيًا الاسم name سلسلة نصية String - الاسم المختصر slug سلسلة نصية فريد الوصف description نص - نموذج الوسم Tag المفتاح نوعه معلومات عنه المعرّف id عدد صحيح Integer يتزايد تلقائيًا الاسم name سلسلة نصية String - الاسم المختصر slug سلسلة نصية فريد الوصف description نص - نموذج المنشور Post المفتاح نوعه معلومات عنه المعرّف id عدد صحيح Integer يتزايد تلقائيًا العنوان title سلسلة نصية String - الاسم المختصر slug سلسلة نصية فريد المحتوى content نص - featured_image سلسلة نصية String - is_published قيمة منطقية Boolean - is_featured قيمة منطقية - created_at تاريخ Date - نموذج الموقع Site ستحتاج أيضًا إلى جدول آخر لتخزين المعلومات الأساسية للموقع بالكامل مثل الاسم والوصف والشعار. المفتاح نوعه معلومات عنه الاسم name سلسلة نصية String - الوصف description نص text - الشعار logo سلسلة نصية - العلاقات توجد ست علاقات بالنسبة لهذا التطبيق وهي: لكل مستخدم عدة منشورات لكل فئة عدة منشورات ينتمي كل وسم إلى منشورات متعددة ينتمي كل منشور إلى مستخدم واحد ينتمي كل منشور إلى فئة واحدة ينتمي كل منشور إلى وسوم متعددة تطبيق التصميم باستخدام جانغو الآن، بعد أن انتهينا من تصميم هذا النموذج، سنبدأ في تطبيقه كما سنوضح في الخطوات التالية نموذج الموقع Site لنبدأ بنموذج الموقع Site مع توفير خصائص لحفظ بيانات الموقع مثل اسم الموقع ووصفه وصورة الشعار كما يلي: class Site(models.Model): name = models.CharField(max_length=200) description = models.TextField() logo = models.ImageField(upload_to="logo/") class Meta: verbose_name_plural = "site" def __str__(self): return self.name لاحظ أن نوع حقل الصورة ImageField() هو سلسلة نصية string، إذ لا يمكن لقواعد البيانات تخزين الصور، لذا تُخزَّن الصور في نظام ملفات خادمك، وسيحتفظ هذا الحقل بالمسار الذي يشير لموقع الصورة. سنرفع الصور في هذا المثال إلى المجلد mediafiles/logo/، وتذكّر إضافة مجلد ملفات الوسائط MEDIA_ROOT = "mediafiles/" في الملف settings.py الذي أعددناه سابقًا. ملاحظة: تحتاج لأن تثبّت مكتبة Pillow على جهازك ليعمل الحقل ImageField() كما يلي: pip install Pillow نموذج الفئة Category بعدها سنصميم نموذج الفئة Category الذي سيُستخدم لتنظيم المحتويات ضمن المدونة ضمن فئات ويحدد الحقول التي سنحتاج إليها لتمثيل الفئات بشكل صحيح في قاعدة البيانات. يتضمن نموذج الفئة Category المحتويات التالية: class Category(models.Model): name = models.CharField(max_length=200) slug = models.SlugField(unique=True) description = models.TextField() class Meta: verbose_name_plural = "categories" def __str__(self): return self.name ينبغي أن يكون النموذج Category مفهومًا بالنسبة لك، لكن دعنا نوضّح الصنف Meta، الذي سنستخدمه لإضافة البيانات الوصفية Metadata إلى النماذج. تمثّل البيانات الوصفية للنموذج أيّ شيء ليس حقلًا مثل خيارات الترتيب واسم جدول قاعدة البيانات وما إلى ذلك، حيث استخدمنا في مثالنا الخيار verbose_name_plural لتحديد صيغة الجمع لكلمة "category"، فجانغو ليس ذكيًا مثل لارافيل Laravel في هذا الجانب، فإن لم نمنح جانغو صيغة الجمع الصحيحة، فسوف يستخدم الجمع "categorys"، وهذا خاطئ. تحدد الدالة __str__(self) الحقل الذي سيستخدمه جانغو عند الإشارة إلى فئة معينة، حيث استخدمنا في مثالنا الحقل name، وسنوضّح أهمية ذلك عندما نصل إلى قسم مدير جانغو. نموذج الوسم Tag يتضمن نموذج الوسم Tag لتخزين الوسوم التي سترتبط بالمنشورات وهو يتضمن اسم الوسم والرابط اللطيف له ووصفه كما توضح الشيفرة التالية: class Tag(models.Model): name = models.CharField(max_length=200) slug = models.SlugField(unique=True) description = models.TextField() def __str__(self): return self.name نموذج المنشور Post لنعرف أخيرًا نموذج المنشور Post الذي يتضمن اسم المنشور والرابط اللطيف والمحتوى الرئيسي والصورة البارزة للمنشور وتاريخ إنشائه وحقلين منطقيين يوضحان هل نشر أم لا وهل هو منشور مميز أما لا كما توضح الشيفرة التالية: from ckeditor.fields import RichTextField . . . class Post(models.Model): title = models.CharField(max_length=200) slug = models.SlugField(unique=True) content = RichTextField() featured_image = models.ImageField(upload_to="images/") is_published = models.BooleanField(default=False) is_featured = models.BooleanField(default=False) created_at = models.DateField(auto_now=True) # تعريف العلاقات category = models.ForeignKey(Category, on_delete=models.CASCADE) tag = models.ManyToManyField(Tag) user = models.ForeignKey(settings.AUTH_USER_MODEL, on_delete=models.CASCADE) def __str__(self): return self.title لاحظ في السطر 1 أنه إذا نسختَ هذه الشيفرة البرمجية ولصقتها لديك، فسيخبرك محرّر نصوصك بعدم العثور على RichTextField و ckeditor، لأنها حزمة خارجية ولا تُضمَّن في إطار عمل جانغو. تذكّر أنه يمكنك فقط إضافة نص عادي عند إنشاء منشور في المقال السابق، وهذا ليس مثاليًا لمقال في مدونة. إذ تمنحك محرّرات النصوص الغنية أو محرّرات WYSIWYG القدرة على تحرير صفحات HTML مباشرةً دون كتابة الشيفرة البرمجية، حيث استخدمنا المحرّر CKEditor في هذا المقال. لذا يمكنك تثبيت المحرّر CKEditor من خلال تشغيل الأمر التالي: pip install django-ckeditor سجّل بعد ذلك ckeditor في ملف الإعدادات settings.py كما يلي: INSTALLED_APPS = [ "blog", "ckeditor", "django.contrib.admin", "django.contrib.auth", "django.contrib.contenttypes", "django.contrib.sessions", "django.contrib.messages", "django.contrib.staticfiles", ] تعريف العلاقات أخيرًا، يمكنك إضافة علاقات إلى النماذج، حيث سنضيف الأسطر الثلاثة التالية في النموذج Post للقيام بذلك كما يلي: category = models.ForeignKey(Category, on_delete=models.CASCADE) tag = models.ManyToManyField(Tag) user = models.ForeignKey(settings.AUTH_USER_MODEL, on_delete=models.CASCADE) بما أننا نستخدم نموذج المستخدم User المُضمَّن (settings.AUTH_USER_MODEL)، فتذكر استيراد الوحدة settings كما يلي: from django.conf import settings ولِّد بعد ذلك ملفات التهجير Migration Files وطبّقها على قاعدة البيانات باستخدام الأمرين التاليين: python manage.py makemigrations python manage.py migrate إعداد لوحة مدير المدونة الخطوة التالية هي إعداد لوحة المدير، حيث يأتي جانغو مع نظام إدارة مضمَّن معه، ويمكنك استخدامه من خلال التسجيل بمستخدم Superuser باستخدام الأمر التالي: python manage.py createsuperuser يمكنك بعد ذلك الوصول إلى لوحة المدير من خلال الانتقال إلى العنوان http://127.0.0.1:8000/admin/. لا تزال لوحة المدير فارغة حاليًا، ولا يوجد بها سوى تبويب الاستيثاق Authentication الذي يمكنك استخدامه لإسناد أدوار مختلفة للمستخدمين، وهذا أمر معقد إلى حد ما ويتطلب مقالًا آخر، لذا لن نتحدث عنه الآن، بل سنركز على كيفية ربط تطبيق المدونة blog بنظام المدير، حيث يجب أن تجد ملفًا بالاسم admin.py ضمن التطبيق blog، لذا أضف إليه الشيفرة البرمجية التالية: from django.contrib import admin from .models import Site, Category, Tag, Post # سجّل نماذجك هنا class CategoryAdmin(admin.ModelAdmin): prepopulated_fields = {"slug": ("name",)} class TagAdmin(admin.ModelAdmin): prepopulated_fields = {"slug": ("name",)} class PostAdmin(admin.ModelAdmin): prepopulated_fields = {"slug": ("title",)} admin.site.register(Site) admin.site.register(Category, CategoryAdmin) admin.site.register(Tag, TagAdmin) admin.site.register(Post, PostAdmin) نستورد في السطر 2 النماذج التي أنشأناها، ثم نسجل النماذج المستوردة باستخدام التابع admin.site.register(). لاحظ بعد ذلك وجود شيء إضافي عند تسجيل النموذج Category، وهو الصنف CategoryAdmin الذي عرّفناه في السطر 6، وبالتالي يمكنك تمرير بعض المعلومات الإضافية إلى نظام الإدارة في جانغو. يمكنك استخدام الميزة prepopulated_fields لتوليد أسماء لطيفة Slugs لجميع الفئات والوسوم والمنشورات، حيث تعتمد قيمة slug على الاسم name، ولنختبر ذلك من خلال إنشاء فئة جديدة. انتقل إلى العنوان http://127.0.0.1:8000/admin/، وانقر على الفئات Categories، وأضف فئة جديدة. تذكّر أننا حددنا صيغة الجمع للكلمة Category في نموذجنا، فإن لم نفعل ذلك، فسيستخدم جانغو الجمع Categorys بدلًا من ذلك كما شرحنا سابقًا. لاحظ توليد الاسم اللطيف تلقائيًا عند كتابة الاسم. حاول الآن إضافة بعض البيانات التجريبية، يجب أن يعمل كل شيء بنجاح. عمليات ضبط اختيارية Optional Configurations لم ينتهي عملنا بعد، لذا افتح لوحة الفئات، ستلاحظ أن بإمكانك الوصول إلى الفئات من صفحة المنشور، ولكن لا توجد طريقة للوصول إلى المنشورات المقابلة من صفحة الفئة. لحل هذه المشكلة، يمكنك استخدام الصنف InlineModelAdmin في الملف blog/admin.py كما يلي: class PostInlineCategory(admin.StackedInline): model = Post max_num = 2 class CategoryAdmin(admin.ModelAdmin): prepopulated_fields = {"slug": ("name",)} inlines = [ PostInlineCategory ] أنشأنا أولًا الصنف PostInlineCategory، ثم استخدمناه في CategoryAdmin، وتعني عبارة max_num = 2 عرض منشورين فقط في صفحة الفئة التي ستبدو كما يلي: يمكنك بعد ذلك تطبيق الشيء نفسه مع TagAdmin في الملف blog/admin.py: class PostInlineTag(admin.TabularInline): model = Post.tag.through max_num = 5 class TagAdmin(admin.ModelAdmin): prepopulated_fields = {"slug": ("name",)} inlines = [ PostInlineTag ] لاحظ أن هذه الشيفرة البرمجية مشابهة جدًا لما سبق، ولكن المتغير model ليس Post فقط، بل هو Post.tag.through، لأن العلاقة بين المنشور Post والوسم Tag هي علاقة متعدد إلى متعدد Many-to-Many، وستكون النتيجة النهائية كما يلي: بناء طبقة العروض View ركزنا في الأقسام السابقة على الواجهة الخلفية ولوحة مدير المدونة، وسنركز الآن على جزء الواجهة الأمامية، وهو الجزء الذي يمكن للمستخدمين رؤيته، حيث سنبدأ بدوال العرض View Functions. بما أننا أعددنا لوحة المدير لمدونتنا، فلن نحتاج إلى إنشاء عمليات CRUD الكاملة، وبالتالي وسنهتم فقط بكيفية استرداد المعلومات من قاعدة البيانات. سنحتاج إلى أربع صفحات هي: الصفحة الرئيسية وصفحة الفئة وصفحة الوسم وصفحة المنشور، وسنحتاج إلى دالة عرض واحدة لكلٍّ منها. عرض الصفحة الرئيسية home ضع المحتويات التالية في الملف blog/views.py: from .models import Site, Category, Tag, Post def home(request): site = Site.objects.first() posts = Post.objects.all().filter(is_published=True) categories = Category.objects.all() tags = Tag.objects.all() return render(request, 'home.html', { 'site': site, 'posts': posts, 'categories': categories, 'tags': tags, }) نستورد في السطر 1 النماذج التي أنشأناها في المقال السابق. يحتوي الموقع في السطر 4 على المعلومات الأساسية لموقعنا، حيث نسترد دائمًا السجل الأول من قاعدة البيانات. يضمن التابع filter(is_published=True) في السطر 5 عرض المقالات المنشورة فقط. بعد ذلك علينا تجهيز موجّه إرسال Dispatcher لعنوان URL المقابل لهذه الصفحة في الملف djangoBlog/urls.py كما يلي: path('', views.home, name='home'), عرض الفئة category ضع أيضًا المحتويات التالية في الملف blog/views.py: def category(request, slug): site = Site.objects.first() posts = Post.objects.filter(category__slug=slug).filter(is_published=True) requested_category = Category.objects.get(slug=slug) categories = Category.objects.all() tags = Tag.objects.all() return render(request, 'category.html', { 'site': site, 'posts': posts, 'category': requested_category, 'categories': categories, 'tags': tags, }) وتذكر تجهيز موجّه إرسال عنوان URL المقابل لهذه الصفحة في الملف djangoBlog/urls.py كما يلي: path('category/<slug:slug>', views.category, name='category'), مرّرنا متغيرًا إضافيًا هو slug من عنوان URL إلى دالة العرض، واستخدمنا هذا المتغير في السطرين 3 و 4 من الشيفرة البرمجية السابقة للعثور على الفئة والمنشورات الصحيحة. عرض الوسم tag ضع أيضًا المحتويات التالية في الملف blog/views.py: def tag(request, slug): site = Site.objects.first() posts = Post.objects.filter(tag__slug=slug).filter(is_published=True) requested_tag = Tag.objects.get(slug=slug) categories = Category.objects.all() tags = Tag.objects.all() return render(request, 'tag.html', { 'site': site, 'posts': posts, 'tag': requested_tag, 'categories': categories, 'tags': tags, }) تذكر تجهيز موجّه إرسال عنوان URL المقابل لهذه الصفحة في الملف djangoBlog/urls.py كما يلي: path('tag/<slug:slug>', views.tag, name='tag'), عرض المنشور post ضع أيضًا المحتويات التالية في الملف blog/views.py: def post(request, slug): site = Site.objects.first() requested_post = Post.objects.get(slug=slug) categories = Category.objects.all() tags = Tag.objects.all() return render(request, 'post.html', { 'site': site, 'post': requested_post, 'categories': categories, 'tags': tags, }) وتذكر تجهيز موجّه إرسال عنوان URL المقابل لهذه الصفحة في الملف djangoBlog/urls.py كما يلي: path('post/<slug:slug>', views.post, name='post'), إنشاء طبقة القوالب Template يمكنك استخدام قالب جاهز، فنحن في هذه السلسة لا نركز على لغتي HTML و CSS. وستكون بنية القالب الذي سنستخدمه كما يلي: templates ├── category.html ├── home.html ├── layout.html ├── post.html ├── search.html ├── tag.html └── vendor ├── list.html └── sidebar.html يحتوي الملف layout.html على ترويسة وتذييل الصفحة، وهو المكان الذي نستورد فيه عادة أكواد التنسيقات CSS وأكواد جافا سكريبت JavaScript. وتوجهنا دوال العرض إلى القوالب home و category و tag و post، وتتوسّع جميعها إلى القالب layout الذي يعتبر كأساس لها جميعًا. وتتواجد المكونات التي ستظهر عدة مرات في قوالب مختلفة ضمن المجلد vendor، ويمكنك استيرادها باستخدام الوسم include. قالب التخطيط Layout ضع المحتويات التالية في الملف layout.html: <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8" /> <meta http-equiv="X-UA-Compatible" content="IE=edge" /> <meta name="viewport" content="width=device-width, initial-scale=1.0" /> {% load static %} <link rel="stylesheet" href="{% static 'style.css' %}" /> {% block title %}{% endblock %} </head> <body class="container mx-auto font-serif"> <nav class="flex flex-row justify-between h-16 items-center border-b-2"> <div class="px-5 text-2xl"> <a href="/"> My Blog </a> </div> <div class="hidden lg:flex content-between space-x-10 px-10 text-lg"> <a href="https://github.com/ericnanhu" class="hover:underline hover:underline-offset-1" >GitHub</a > <a href="#" class="hover:underline hover:underline-offset-1">Link</a> <a href="#" class="hover:underline hover:underline-offset-1">Link</a> </div> </nav> {% block content %}{% endblock %} <footer class="bg-gray-700 text-white"> <div class="flex justify-center items-center sm:justify-between flex-wrap lg:max-w-screen-2xl mx-auto px-4 sm:px-8 py-10" > <p class="font-serif text-center mb-3 sm:mb-0"> Copyright © <a href="https://www.ericsdevblog.com/" class="hover:underline" >Eric Hu</a > </p> <div class="flex justify-center space-x-4"> . . . </div> </div> </footer> </body> </html> لاحظ في السطرين 7 و 8 الطريقة التي يمكنك بها استيراد الملفات الساكنة ملفات CSS و جافا سكريبت في جانغو، فكما وضحنا لن نتحدث في هذا المقال عن لغة CSS، ولكن ما يهمنا هو معرفة طريقة استيراد ملفات CSS إضافية لتطبيق جانغو. سيبحث جانغو عن الملفات الساكنة Static Files في مجلدات التطبيق الفردية افتراضيًا، حيث سيذهب إلى المجلد /blog في تطبيقنا blog، ويبحث عن المجلد static، ثم يبحث عن الملف style.css ضمن المجلد static كما هو محدد في القالب. blog ├── admin.py ├── apps.py ├── __init__.py ├── migrations ├── models.py ├── static │ ├── input.css │ └── style.css ├── tests.py └── views.py قالب الصفحة الرئيسية Home ضع المحتويات التالية في الملف home.html: {% extends 'layout.html' %} {% block title %} <title>Page Title</title> {% endblock %} {% block content %} <div class="grid grid-cols-4 gap-4 py-10"> <div class="col-span-3 grid grid-cols-1"> <!-- المنشور البارز --> <div class="mb-4 ring-1 ring-slate-200 rounded-md hover:shadow-md"> <a href="{% url 'post' featured_post.slug %}" ><img class="float-left mr-4 rounded-l-md object-cover h-full w-1/3" src="{{ featured_post.featured_image.url }}" alt="..." /></a> <div class="my-4 mr-4 grid gap-2"> <div class="text-sm text-gray-500"> {{ featured_post.created_at|date:"F j, o" }} </div> <h2 class="text-lg font-bold">{{ featured_post.title }}</h2> <p class="text-base"> {{ featured_post.content|striptags|truncatewords:80 }} </p> <a class="bg-blue-500 hover:bg-blue-700 rounded-md p-2 text-white uppercase text-sm font-semibold font-sans w-fit focus:ring" href="{% url 'post' featured_post.slug %}" >Read more →</a > </div> </div> {% include "vendor/list.html" %} </div> {% include "vendor/sidebar.html" %} </div> {% endblock %} لاحظ أننا فصلنا الشريط الجانبي وقائمة المنشورات ووضعناها في المجلد vendor بدلًا من كتابة شيفرتها البرمجية الثابتة، إذ سنستخدم المكونات نفسها في صفحة الفئة والوسم. قائمة المنشورات ضع أيضًا المحتويات التالية في الملف vendor/list.html: <!-- قائمة المنشورات --> <div class="grid grid-cols-3 gap-4"> {% for post in posts %} <!-- المنشور --> <div class="mb-4 ring-1 ring-slate-200 rounded-md h-fit hover:shadow-md"> <a href="{% url 'post' post.slug %}" ><img class="rounded-t-md object-cover h-60 w-full" src="{{ post.featured_image.url }}" alt="..." /></a> <div class="m-4 grid gap-2"> <div class="text-sm text-gray-500"> {{ post.created_at|date:"F j, o" }} </div> <h2 class="text-lg font-bold">{{ post.title }}</h2> <p class="text-base"> {{ post.content|striptags|truncatewords:30 }} </p> <a class="bg-blue-500 hover:bg-blue-700 rounded-md p-2 text-white uppercase text-sm font-semibold font-sans w-fit focus:ring" href="{% url 'post' post.slug %}" >Read more →</a > </div> </div> {% endfor %} </div> لاحظ في الأسطر من 3 إلى 27 كيف مرّرنا المتغير posts من العرض إلى القالب، حيث يحتوي هذا المتغير على مجموعة من المنشورات، وسنقوم بالمرور ضمن القالب على كل عنصر في هذه المجموعة باستخدام حلقة for. تذكّر في السطر 6 أننا أنشأنا موجّه إرسال عنوان URL كما يلي: path('post/<slug:slug>', views.post, name='post'), ستجد التعليمة {% url 'post' post.slug %} في القالب موجّهَ إرسال عنوان URL بالاسم 'posts'، وتسند القيمة post.slug إلى المتغير <slug:slug>، والذي سيُمرَّر بعد ذلك إلى دالة العرض المقابلة. ينسّق المرشّح Filter الذي هو date في السطر 14 بيانات التاريخ المُمرَّرة إلى القالب لأن القيمة الافتراضية ليست سهلة الاستخدام، ويمكنك العثور على تنسيقات تواريخ أخرى في توثيق جانغو الرسمي. وضعنا مرشحَين بعد post.content في السطر 18، حيث يزيل المرشّح الأول وسوم HTML، ويأخذ المرشّح الثاني أول 30 كلمة ويقتطع الباقي. قالب الشريط الجانبي Sidebar ضع أيضًا المحتويات التالية في الملف vendor/sidebar.html: <div class="col-span-1"> <div class="border rounded-md mb-4"> <div class="bg-slate-200 p-4">Search</div> <div class="p-4"> <form action="" method="get"> <input type="text" name="search" id="search" class="border rounded-md w-44 focus:ring p-2" placeholder="Search something..."> <button type="submit" class="bg-blue-500 hover:bg-blue-700 rounded-md p-2 text-white uppercase font-semibold font-sans w-fit focus:ring">Search</button> </form> </div> </div> <div class="border rounded-md mb-4"> <div class="bg-slate-200 p-4">Categories</div> <div class="p-4"> <ul class="list-none list-inside"> {% for category in categories %} <li> <a href="{% url 'category' category.slug %}" class="text-blue-500 hover:underline" >{{ category.name }}</a > </li> {% endfor %} </ul> </div> </div> <div class="border rounded-md mb-4"> <div class="bg-slate-200 p-4">Tags</div> <div class="p-4"> {% for tag in tags %} <span class="mr-2" ><a href="{% url 'tag' tag.slug %}" class="text-blue-500 hover:underline" >{{ tag.name }}</a ></span > {% endfor %} </div> </div> <div class="border rounded-md mb-4"> <div class="bg-slate-200 p-4">More Card</div> <div class="p-4"> <p> . . . </p> </div> </div> </div> قالب الفئة Category ضع المحتويات التالية في الملف category.html: {% extends 'layout.html' %} {% block title %} <title>Page Title</title> {% endblock %} {% block content %} <div class="grid grid-cols-4 gap-4 py-10"> <div class="col-span-3 grid grid-cols-1"> {% include "vendor/list.html" %} </div> {% include "vendor/sidebar.html" %} </div> {% endblock %} قالب الوسم Tag ضع المحتويات التالية في الملف tag.html: {% extends 'layout.html' %} {% block title %} <title>Page Title</title> {% endblock %} {% block content %} <div class="grid grid-cols-4 gap-4 py-10"> <div class="col-span-3 grid grid-cols-1"> {% include "vendor/list.html" %} </div> {% include "vendor/sidebar.html" %} </div> {% endblock %} قالب المنشور Post أخيرًا، يتضمن قالب المنشور المحتويات التالية: {% extends 'layout.html' %} {% block title %} <title>Page Title</title> {% endblock %} {% block content %} <div class="grid grid-cols-4 gap-4 py-10"> <div class="col-span-3"> <img class="rounded-md object-cover h-96 w-full" src="{{ post.featured_image.url }}" alt="..." /> <h2 class="mt-5 mb-2 text-center text-2xl font-bold">{{ post.title }}</h2> <p class="mb-5 text-center text-sm text-slate-500 italic">By {{ post.user|capfirst }} | {{ post.created_at }}</p> <div>{{ post.content|safe }}</div> <div class="my-5"> {% for tag in post.tag.all %} <a href="{% url 'tag' tag.slug %}" class="text-blue-500 hover:underline" mr-3">#{{ tag.name }}</a> {% endfor %} </div> </div> {% include "vendor/sidebar.html" %} </div> {% endblock %} لاحظ في السطر 19 أننا أضفنا المرشح safe، لأن جانغو سيعرض شيفرة HTML كنص عادي افتراضيًا لأسباب أمنية، لذا يجب ان نخبر جانغو بأنه يمكن عرض شيفرات HTML كما هي. أصبح كل شيءجاهزًا، كل ما عليك الأن هو تشغيل خادم التطوير باستخدام الأمر التالي، وعرض تطبيق جانغو الأول الخاص بك: python manage.py runserver ترجمة -وبتصرّف- للمقال Django for Beginners #4 - The Blog App لصاحبه Eric Hu. اقرأ أيضًا المقال السابق: استخدام عمليات CRUD لإدارة مدونة في جانغو إنشاء تطبيق جانغو وتوصيله بقاعدة بيانات إنشاء موقع ويب هيكلي بجانغو رفع مستوى أمان تطبيقات جانغو في بيئة الإنتاج البدء مع إطار العمل جانغو لإنشاء تطبيق ويب1 نقطة
-
بشكل عام التخصص في مجال واحد أفضل إذا كنت تريد التميز والاحترافية.ولكن في بعض المجالات يكون من الجيد أن تكون لديك معرفة وخبرة ولو بسيطة في التفرعات الأخرى من المجال بمعنى الإلمام بالتفرعات ذات الصلة يضيف ميزة تنافسية على سبيل المثال: التخصص في Back-End ممتازًا، ولكن وجود فهم أساسي عن Front-End يساعدك في التعاون مع الفرق الأخرى وتحسين جودة المنتج وزيادة فرص العمل للمتعلم. وبالنسبة لسؤالك مجال التعلم العميق أو التعلم الاله فيجب عليك معرفة أن التعلم العميق (Deep Learning) هو جزء من التعلم الآلي (Machine Learning)، أي أنه يعتمد عليه كقاعدة أساسية. لذلك يُفضل أن تبدأ بتعلم أساسيات التعلم الآلي أولاً ولكن ليس بشكل مكثف1 نقطة
-
التعلم العميق هو أحد فروع تعلم الآلة، وتعلم الآلة هو فرع من فروع الذكاء الاصطناعي (AI) يركز على تطوير خوارزميات وطرق يمكنها من التعلم من البيانات وتحسين أدائها دون الحاجة إلى برمجة صريحة، ويستخدم مختلف الأساليب والتقنيات، مثل التعلم الإشرافي والتعلم غير الإشرافي والتعلم المعزز. من جانبه، التعلم العميق هو فرع من فروع تعلم الآلة يركز على تطوير خوارزميات تعتمد على الشبكات العصبية الاصطناعية ANNs ذات الطبقات المتعددة، وهي تحاكي هيكل الدماغ البشري وتسمح للآلة بالتعلم من البيانات وتحليلها بطريقة أكثر تعقيداً، ويستخدم تقنيات مثل الشبكات العصبية التلافيفية CNNs والشبكات العصبية الدلالية RNNs والشبكات العصبية التلافيفية الدلالية LSTMs وغيرها. بالتالي عليك البدء بتعلم أساسيات "تعلم الآلة" قبل البدء في التعلم العميق من خلال دراسة التالي: Regularization. Underfitting and Overfitting and how to identify them Various cost functions A thorough understanding of stochastic gradient descent Hyper parameter tuning Cross validation techniques ثم دراسة: Regression Classification (Both Sample Based and Probabilistic) Decision Trees Neural Networks1 نقطة
-
يُعد عنوان URL بالإضافة إلى النص التشعبي Hypertext وبروتوكول HTTP أحد المفاهيم المفتاحية للويب فهو الآلية التي تستخدمها المتصفحات browsers للوصول أي مورد موجود في الويب. عنوان URL هو مجرّد عنوان فريد لمورد على الويب، نظريًا يدل كل عنوان URL صحيح على مورد فريد ومحدد كصفحة HTML أو ملف CSS أو صورة أو غيرها من الموارد، ولكن في واقع هناك بعض الاستثناءات، وأكثرها شيوعًا عنوان URL يشير إلى مورد لم يعد موجودًا أو تغيّر موقعه. وطالما أن المورد يُمثّل بعنوان URL والخادم هو من يتعامل مع عنوان URL فلذلك تقع على عاتق مالك الخادم مهمة إدارة الموارد وعناوين URL المرتبطة بها بعناية. سنتعرف في هذا المقال على تفاصيل عنوان URL وكيفية عمل هذه العناوين على الويب. ننصحك قبل الشروع في إكمال قراءة المقال أن تطلع على مقال كيف تعمل شبكة الإنترنت؟ وأن يكون مفهوم الروابط التشعبية واضحًا بالنسبة لك. تشريح عنوان URL إليك بعض الأمثلة عن عناوين URL: https://developer.mozilla.org https://developer.mozilla.org/en-US/docs/Learn/ https://developer.mozilla.org/en-US/search?q=URL يمكن كتابة أيًا من تلك العناوين في شريط العنوان في المتصفح لتحميل الصفحة أو المورد المرتبط به. يتكون عنوان URL من أجزاء مختلفة بعضها إلزامي وبعضها اختياري. لاحظ الأجزاء المظللة في العنوان التالي والتي تُعد الأكثر أهمية في عنوان URL: لتوضيح الفكرة يمكن أن نشبّه عنوان URL بعنوان بريدي نمطي، إذ يمثل المخطط Scheme الخدمة البريدية التي تريد استخدامها، ويمثل اسم النطاق Domain name اسم المدينة أو البلدة، وستعمل المنفذ Port عمل الرمز البريدي، وسيمثل المسار Path البناء الذي ينبغي تسليم البريد إليه. أما المعاملات Parameters فستمثل أي معلومات إضافية كرقم الشقة وستمثل المرساة Anchor مستلم الرسالة الفعلي الذي وجَّهت رسالتك إليه. بروتوكول عنوان URL وهو القسم الأول من URL ويشير إلى البروتوكول الذي ينبغي استخدامه لطلب مورد معين من الخادم (البروتوكول هو طريقة لإعداد آلية لتبادل البيانات ونقلها عبر شبكة من الحواسيب). يُستخدم عادة برتوكولي HTTP و HTTPS (النسخة الآمنة) في مواقع الويب ولا بد من مخاطبة صفحات الويب باستخدام أحدهما. مع ذلك تدرك المتصفحات تمامًا كيف تتعامل مع بروتوكولات Schemes أخرى مثل :mailto (لفتح واجهة بريد إلكتروني) فلا تتفاجأ إن رأيت بروتوكولات أخرى. التصريح Authority يأتي بعد البروتوكول التصريح ويفصل بينهما النمط //:. يتضمن التصريح في حال وجوده اسم النطاق (www.example.com مثلًا) ورقم المنفذ (80 مثلًا) يفصل بينهما الرمز :. يشير النطاق Domain إلى خادم الويب الذي يُرسل إليه الطلب ويكون عادة على شكل اسم، كما يمكن استخدام عنوان آي بي لكن استخدامه نادر وغير ملائم في معظم الأحيان. يشير المنفذ Port إلى البوابة المستخدمة للوصول إلى المورد. يُحذف المنفذ عادة عند استخدام الخادم المنافذ المعيارية للبروتوكول HTTP، إذ يستخدم المنفذ 80 لبروتوكول HTTP والمنفذ 443 لبروتوكول HTTPS عند منح الإذن بالوصول إلى المورد. ما عدا ذلك لا بد من كتابة المنفذ المستخدم. في بعض الحالات لا يستخدم URL قسم التصريح كما هو الحال في واجهات البريد الإلكتروني (mailto:foobar). إذ يحتوي URL مخططًا فقط دون تصريح، لذلك لن تجد النمط //، وإنما ستجد فقط النقطتين المتعامدتين التي تعمل فقط كفاصل بين المخطط وعنوان البريد الإلكتروني. المسار إلى مورد ويمثل الطريق للوصول إلى مورد موجود على خادم ويب (path/to/myfile.html/ مثلًا). مثَّلت هذه المسارات في بدايات الويب الموقع الفيزيائي لملف على خادم، لكنه حاليًا مجرد اختصار يتعامل معه الخادم بطريقة معينة للوصول إلى المورد وغالبًا لا يشير إلى المكان الحقيقي لوجود المورد. المعاملات وهي قائمة من العناصر الثنائية على شكل"مفتاح/قيمة" يفصل بينها الرمز & مثل القائمة key1=value1&key2=value2 كما في الصورة السابقة. يمكن لخادم ويب استخدام هذه المعاملات في تنفيذ عمليات إضافية قبل أن يعيد المورد المطلوب. لكل خادم ويب قواعده الخاصة المتعلقة بمعالجة المعاملات، ومن الأفضل دومًا أن تسأل مالك الخادم عن طريقة تعامل خادمه مع المعاملات. المربط يمثل المربط # (ويشار إليه المرساة أحيانًا) طريقة للاشارة إلى جزء معين من المورد نفسه، وتشبه فكرته فكرة "الاشارة المرجعية" داخل المورد نفسه. فلو كان المورد ملف HTML مثلًا، سينتقل المتصفح إلى النقطة التي يُعرّفها المربط "#"، وفي حال كان المربط يشير إلى نقطة زمنية معينة من ملفات الصوتية أو الفيديو سيحاول المتصفح الانتقال إلى الزمن الذي يحدده المربط. وتجدر الإشارة هنا، إلى أن القسم الذي يقع بعد الرمز "#" (ويُدعى "مُعرِّف القطعة Fragment Identifier") لن يُرسل أبدًا إلى الخادم مع الطلب. كيف تستخدم URL بإمكانك كتابة أي URL ضمن شريط العنوان في المتصفح لتحضر المورد الذي يمثله، لكن هذا الاستخدام ما هو إلا رأس الهرم فقط! تستخدم لغة HTML عناوين URL بكثرة لكي: تنشئ روابطًا مع مستندات أخرى باستخدام العنصر <a>. تربط مستندًا مع موارده عبر عناصر متعددة مثل <link> أو <script>. تعرض الوسائط مثل الصور (باستخدام العنصر <img>) والفيديو (باستخدام العنصر <video>) والملفات الصوتية (باستخدام العنصر<audio>). تعرض ملفات HTML أخرى باستخدام العنصر <iframe>. تستخدم التقنيات الأخرى مثل CSS وJavaScript عناوين URL بكثرة أيضًا، وهذه التقنيات هي ما تشكل الويب في الواقع. عناوين URL المطلقة والنسبية تُعد الأمثلة التي أوردناها سابقًا عن عنوان URL عناوينًا مطلقة Absolute URLs، لكن لا يزال هناك نمط آخر وهي العناوين النسبية Relative URLs ولا بدّ من الإشارة إلى الفوارق بينهما بشيء من التفصيل. تعتمد الأجزاء التي ينبغي استخدامها من عنوان URL والأخرى التي يمكن إهمالها على السياق الذي يستخدم فيه عنوان URL. فمثلًا في شريط عنوان متصفحك لا يوجب أي سياق محدد لعناوين URL لهذا لا بدّ من كتابة URL بشكله الكامل (أو المطلق) كما فعلنا في الأمثلة السابقة. لا حاجة بالطبع في حالة المتصفح أن تذكر البروتوكول لأن المتصفح يستخدم البروتوكول HTTP افتراضيًا، ولا نذكر أيضًا المنفذ الذي نحتاجه إلا في الحالة التي نتصل فيها مع الخادم عبر منفذ غير اعتيادي، ولكن لا بد من كتابة بقية أجزاء عنوان URL. عندما يُستخدم عنوان URL داخل مستند كصفحة HTML ستختلف الأمور قليلًا. إذ يمتلك المتصفح في هذه الحالة عنوان URL الخاص بالمستند ككل، وبالتالي سيتمكن من استخدام معلوماته لإكمال الأجزاء الناقصة لعنوان URL الموجود داخل المستند. يمكن التمييز بين عنوان URL المطلق والنسبي بالنظر فقط إلى جزء المسار، فإذا بدأ عنوان URL بالرمز / فسيحضر المتصفح المورد من أعلى عنوان جذري للخادم دون الحاجة إلى المكان الذي يشير إليه المستند. لنلق نظرة على بعض الأمثلة لتوضيح الأمر. أمثلة عن عناوين URL مطلقة يُعد العنوان الآتي مطلقًا أو كاملًا https://developer.mozailla.org/docs/learn بينما يعد العنوان التالي غير كامل إذ سيستخدم هذا العنوان البروتوكول الضمني للمستند الذي يتضمن عنوان URL. developer.mozilla.org/en-us/docs/Learn// أما العنوان الآتي فهو اسم نطاق ضمني، وهي الحالة الأكثر استخدامًا لعناوين URL المطلقة داخل مستندات HTML. /en-us/docs/learn/ يستخدم المتصفح في هذه الحالة نفس البروتوكول واسم النطاق المستخدمان في تحميل المستند الذي يحتوي على عنوان URL لاحظ أنه لا يمكن حذف اسم النطاق دون حذف البروتوكول أيضًا. أمثلة عن عناوين URL نسبية لتفهم الأمثلة التالية بطريقة صحيحة، سنفترض أن عناوين URL ستُستدعى من داخل المستند الموجود على عنوان URL التالي: https://developer.mozilla.org/en-us/docs/Learn يستخدم العنوان "Skills/Infrastructure/Understanding_URLs" فكرة الموارد الفرعية، فطالما أنّ عنوان URL لم يبدأ بالرمز / سيحاول المتصفح أن يجد المستند في مجلد فرعي ضمن المجلد الذي يحتوي المورد الحالي أي سنرغب في مثالنا في الوصول إلى عنوان URL التالي: https://developer.mozilla.org/en-us/docs/Learn/Skills/Infrastructure/Understanding_URLs. بينما يستخدم العنوان "../CSS/display" فكرة التراجع إلى الخلف في مسار الشجرة، ونستخدم في هذه الحالة النمط /.. الموروث من نظام ملفات يونكس لكي نخبر المتصفح أن ينتقل إلى المجلد الأعلى مباشرة. أي أننا نريد هنا الوصول إلى عنوان URL التالي: https://developer.mozilla.org/en-US/docs/Learn/../CSS/display والذي يمكن اختصاره إلى: https://developer.mozilla.org/en-US/docs/CSS/display عناوين URL الدلالية بالرغم من الصبغة التقنية الواضحة لهذا النوع، إلا أن عناوين URL الدلالية Semantic URLs هي طريقة دخول إلى موقع ويب معين يمكن للبشر فهمها. أي يمكن أن يحفظها المستخدم بسهولة ويدخلها بنفسه في شريط عنوان المتصفح، وطالما أنّ المستخدمين هم مركز اهتمام الويب، فمن أفضل الممارسات التي ينبغي نشرها هي بناء ما يُدعى عناوين URL واضحة ومقروءة Clean URL، وهي عناوين تستخدم كلمات في صلب موضوع محتوى العناوين يمكن لأي شخص فهمها دون أن تكون لديه أي فكرة تقنية عن كيفية إنجاز الأمر. لا علاقة بالطبع للدلالات اللغوية بالحواسيب، فلربما بدت لك عناوين URL كخليط من الرموز العشوائية، لكن هناك إيجابيات عدة لكتابة URL مقروء من قبل المستخدم منها: سهولة تعديلها. تجعل الكثير من النقاط أكثر وضوحًا للمستخدم مثل الموقع الذي يتواجد فيه وما الذي يفعله في هذا الموقع أو ما الذي يقرأه أو يتفاعل معه على الويب. يمكن لعناوين URL المقروءة أن تحسن ترتيب وتصنيف الصفحات في محركات البحث. ترجمة -وبتصرف- للمقال What is a URL. اقرأ أيضًا ما هو خادم الويب؟ ما هي الأدوات المستخدمة في بناء مواقع ويب؟ ما هي أدوات مطوري الويب المدمجة في المتصفحات؟ ما هي أسماء النطاقات في شبكة الإنترنت؟1 نقطة
-
سنجيب في هذه السلسلة من المقالات سلسلة تعلم تطوير الويب على بعض الأسئلة الأساسية حول برمجة موقع الويب من طرف الخادم، مثل ماهية البرمجة من طرف الخادم واختلافها عن البرمجة من طرف العميل وسبب فائدتها الكبيرة، كما سنقدم نظرةً عامةً على بعض أكثر أطر عمل الويب من طرف الخادم شيوعًا مع إرشادات حول كيفية اختيار إطار العمل الأنسب لإنشاء مشروعك الأول، وسنقدم مقدمةً تمهيديةً عالية المستوى حول أمان خادم الويب. المتطلبات الأساسية لا تحتاج إلى معرفة برمجة مواقع الويب من طرف الخادم أو أيّ نوع آخر من البرمجة قبل البدء، ولكن يجب أن تفهم شيئًا ما عن طريقة عمل مواقع الويب وخوادم الويب، لذلك نوصي بقراءة المقالات التالية: مدخل إلى خادم الويب. تثبيت البرمجيات الأساسية للانطلاق في تطوير الويب. رفع ملفات موقع الويب إلى خادم على الإنترنت. ستكون جاهزًا للعمل من خلال الفهم الأساسي الذي تكتسبه من هذه المقالات. تتألف هذه السلسلة الفرعية من المقالات التالية: مدخل إلى برمجة مواقع الويب من طرف الخادم: يتناول المقال الأول برمجة موقع الويب من طرف الخادم عالية المستوى، وتجيب على أسئلة، مثل ماهية البرمجة من طرف الخادم واختلافها عن البرمجة من طرف العميل وسبب فائدتها الكبيرة. ستفهم بعد قراءة هذا المقال القدرات الإضافية المتاحة لمواقع الويب من خلال كتابة الشيفرة البرمجية من طرف الخادم. نظرة عامة على تفاعلات الخادم مع العميل في موقع ويب ديناميكي: سنختبر ما يحدث عندما يتلقى الخادم طلبًا ديناميكيًا من متصفح بعد معرفة الغرض والفوائد المحتملة من البرمجة من طرف الخادم. بما أن معظم الشيفرة البرمجية من طرف الخادم لمواقع الويب تتعامل مع الطلبات والاستجابات بطريقة مماثلة، سيساعدك ذلك على فهم ما عليك فعله عند كتابة شيفرتك البرمجية. أطر عمل الويب من طرف الخادم: أوضح المقال السابق ما يجب على تطبيق الويب من طرف الخادم فعله للاستجابة لطلبات متصفح الويب، ويشرح هذا المقال كيف يمكن لأطر عمل الويب تبسيط هذه المهام، ويساعدك على اختيار إطار العمل المناسب لأول تطبيق ويب من طرف الخادم. تعرف على أمان مواقع الويب: يتطلب أمان الموقع الحذر في جميع جوانب بناء الموقع وتشغيله. يساعدك هذا المقال التمهيدي في فهم الخطوات الأولى المهمة الممكن اتخاذها لحماية تطبيق الويب من الهجمات الأكثر شيوعًا. ملاحظة: يتناول هذا المقال أطر العمل من طرف الخادم، وكيفية استخدامها لإنشاء مواقع الويب. إذا كنت تبحث عن معلومات حول أطر عمل جافا سكريبت JavaScript من طرف العميل، فاطلع على مقال فهم أدوات تطوير الويب من طرف العميل. لا تحتوي هذه السلسلة من المقالات على أي تقييم لأننا لم نعرض لك أي شيفرة برمجية بعد، إذ يجب أن يكون لديك في هذه المرحلة فهمٌ عام للوظائف التي يمكنك تقديمها من خلال البرمجة من طرف الخادم مع اتخاذ قرار بشأن إطار عمل الويب من طرف الخادم الذي ستستخدمه لإنشاء أول تطبيق من طرف الخادم. لنبدأ بمقالنا الأول من هذه السلسلة من خلال التعرُّف على مفهوم برمجة مواقع الويب من طرف الخادم. دورة تطوير تطبيقات الويب باستخدام لغة PHP احترف تطوير النظم الخلفية والووردبريس وتطبيقات الويب من الألف إلى الياء دون الحاجة لخبرة برمجية مسبقة اشترك الآن تمهيد إلى برمجة مواقع الويب من طرف الخادم server-side المتطلبات الأساسية: المهارات الحاسوبية الأساسية، وفهم أساسي لخادم الويب. الهدف: التعرف على مفهوم برمجة مواقع الويب من طرف الخادم، وما يمكن أن تفعله، وكيف تختلف عن البرمجة من طرف العميل. تستخدم معظمُ مواقع الويب واسعة النطاق الشيفرةَ البرمجية من طرف الخادم لعرض بيانات مختلفة ديناميكيًا عند الحاجة، وتُسحَب من قاعدة البيانات المخزنة على الخادم وتُرسَل إلى العميل لعرضها باستخدام شيفرة برمجية مثل شيفرة لغتي HTML وجافا سكريبت. من أهم فوائد الشيفرة البرمجية من طرف الخادم أنها تسمح لك بتخصيص محتوى موقع الويب لكل مستخدم، إذ يمكن للمواقع الديناميكية إبراز المحتوى الأكثر صلة بناءً على تفضيلات المستخدم وعاداته، ويمكن أن تسهّل الشيفرة البرمجية من طرف الخادم استخدامَ المواقع من خلال تخزين التفضيلات والمعلومات الشخصية، مثل إعادة استخدام تفاصيل بطاقة الائتمان المخزنة لتبسيط المدفوعات اللاحقة، كما يمكنها السماح بالتفاعل مع مستخدمي الموقع وإرسال الإشعارات والتحديثات عبر البريد الإلكتروني، أو عبر قنوات أخرى، مما يتيح مشاركةً أعمق بكثير مع المستخدمين. ملاحظة: يُوصَى بشدة بالتعرف على تطوير مواقع الويب من طرف الخادم في العالم الحديث لتطوير الويب. ما هي برمجة مواقع الويب من طرف الخادم؟ تتواصل متصفحات الويب مع خوادم الويب باستخدام بروتوكول نقل النص التشعبي HyperText Transfer Protocol -أو اختصارًا HTTP، إذ يُرسَل طلب HTTP من متصفحك إلى الخادم الهدف عند النقر على رابط على صفحة ويب، أو إرسال نموذج، أو إجراء بحث. يتضمن الطلب عنوان URL يحدد المورد المتأثر، وطريقةً تحدد الفعل المطلوب، مثل الحصول على المورد، أو حذفه، أو نشره، ويمكن أن يتضمن الطلب أيضًا معلومات إضافية مشفرة في معاملات URL (أزواج حقل-قيمة field-value المرسَلة عبر سلسلة الاستعلام query string)، مثل بيانات POST (البيانات المرسَلة باستخدام طريقة POST لبروتوكول HTTP) أو في ملفات تعريف الارتباط Cookies المرتبطة بها. تنتظر خوادم الويب رسائل طلب العميل وتعالجها عند وصولها وترد على متصفح الويب برسالة استجابة HTTP، إذ تحتوي الاستجابة على سطر حالة يشير إلى نجاح الطلب من عدمه مثل السطر "HTTP/1.1 200 OK"، الذي يشير إلى النجاح. يمكن أن يحتوي متن الاستجابة على الطلب الناجح للمورد المطلوب (مثل صفحة HTML جديدة أو صورة)، والذي يمكن عرضه بعد ذلك باستخدام متصفح الويب. المواقع الساكنة static sites يوضّح الشكل الآتي معمارية خادم الويب الأساسية لموقع ساكن Static Site يعيد المحتوى الثابت نفسه من الخادم كلما طلب موردًا معينًا؛ فإذا أراد المستخدم الانتقال إلى صفحة ما، فسيرسل المتصفح طلب HTTP من النوع "GET" يحدد عنوان URL الخاص به. يسترجع الخادمُ المستندَ المطلوب من نظام ملفاته ويعيد استجابة HTTP التي تحتوي على المستند وحالة النجاح (عادةً 200 OK). إذا تعذّر استرجاع الملف لسبب ما، ستُعاد حالة خطأ (اطلع على كيفية استكشاف وإصلاح رموز أخطاء HTTP الشائعة). المواقع الديناميكية dynamic sites موقع الويب الديناميكي هو الموقع الذي يُنشَأ فيه بعضٌ من محتوى الاستجابة ديناميكيًا عند الحاجة فقط، إذ تُنشَأ صفحات HTML من خلال إدخال بيانات من قاعدة بيانات إلى عناصر بديلة في قوالب HTML، وتُعَد هذه الطريقة أكثر فاعلية من استخدام مواقع الويب الساكنة لتخزين كميات كبيرة من المحتوى. يمكن للموقع الديناميكي إعادة بيانات مختلفة لعنوان URL بناءً على المعلومات التي يقدّمها المستخدم أو التفضيلات المخزنة ويمكنه إجراء عمليات أخرى بوصفها جزءًا من إعادة الاستجابة مثل إرسال الإشعارات. يجب تشغيل معظم الشيفرة البرمجية لدعم موقع ويب ديناميكي على الخادم، ويُعرَف إنشاء هذه الشيفرة البرمجية باسم "البرمجة من طرف الخادم" أو "كتابة سكريبتات الواجهة الخلفية" أحيانًا. يوضّح الشكل الآتي معمارية بسيطة لموقع ويب ديناميكي، إذ ترسل المتصفحات طلبات HTTP إلى الخادم الذي يعالجها ويعيد استجابات HTTP المناسبة. يجري التعامل مع طلبات الموارد الساكنة باستخدام طريقة التعامل مع المواقع الساكنة نفسها، فالموارد الساكنة هي ملفات لا تتغير مثل ملفات CSS وجافا سكريبت والصور وملفات PDF المُنشَأة مسبقًا وإلخ. تُمرّر طلبات الموارد الديناميكية (الخطوة رقم 2) إلى الشيفرة البرمجية من طرف الخادم (الموضحة في الشكل السابق بوصفها تطبيق ويب)، بينما يفسّر الخادم الطلب الديناميكي، ويقرأ المعلومات المطلوبة من قاعدة البيانات (الخطوة رقم 3)، ويجمع البيانات المسترجعة مع قوالب HTML (الخطوة رقم 4)، ويرسل استجابة تحتوي على ملف HTML المُنشَأ (الخطوتين 5 و 6). هل تتشابه البرمجة من طرف الخادم مع البرمجة من طرف العميل؟ لنوجّه انتباهنا الآن إلى الشيفرة البرمجية الموجودة في البرمجة من طرف الخادم وطرف العميل، فهما مختلفتان كثيرًا للأسباب التالية: لديهما أغراض واهتمامات مختلفة. لا تستخدمان لغات البرمجة نفسها باستثناء لغة جافا سكريبت التي يمكن استخدامها من طرف الخادم ومن طرف العميل. تعملان ضمن بيئات أنظمة تشغيل مختلفة. تُعرَف الشيفرة البرمجية التي تعمل في المتصفح باسم الشيفرة البرمجية من طرف العميل وتهتم بتحسين مظهر وسلوك صفحة الويب المعروضة، ويتضمن ذلك تحديد مكونات واجهة المستخدم وتنسيقها وإنشاء التخطيطات والتنقل والتحقق من صحة النموذج وما إلى ذلك؛ بينما تتضمن برمجة مواقع الويب من طرف الخادم اختيار المحتوى المُعاد إلى المتصفح استجابةً للطلبات، إذ تعالج الشيفرة البرمجية من طرف الخادم مهامًا، مثل التحقق من صحة البيانات والطلبات المُرسَلة واستخدام قواعد البيانات لتخزين البيانات واسترجاعها وإرسال البيانات الصحيحة إلى العميل كما هو مطلوب. تُكتَب الشيفرة البرمجية من طرف العميل باستخدام لغات HTML وCSS وجافا سكريبت، وتعمل ضمن متصفح ويب ولديها وصول ضئيل أو معدوم إلى نظام التشغيل الأساسي بما في ذلك الوصول المحدود إلى نظام الملفات. لا يستطيع مطورو الويب التحكم في المتصفح الذي يمكن أن يستخدمه كل مستخدم لعرض موقع الويب، إذ توفر المتصفحات مستويات غير متناسقة من التوافق مع ميزات الشيفرة البرمجية من طرف العميل، ويُعَد التعامل مع الاختلافات في دعم المتصفحات بسلاسة جزءًا من التحدي المتمثل في البرمجة من طرف العميل. يمكن كتابة الشيفرة البرمجية من طرف الخادم باستخدام لغات برمجة متعددة، إذ تشمل أمثلة لغات الويب الشائعة من طرف الخادم لغات PHP وبايثون Python وروبي Ruby وC# وجافا سكريبت (NodeJS)، وتتمتع الشيفرة البرمجية من طرف الخادم بالوصول الكامل إلى نظام تشغيل الخادم ويمكن للمطور اختيار لغة البرمجة (والإصدار المحدد) التي يرغبون في استخدامها. يكتب المطورون شيفرتهم البرمجية باستخدام أطر عمل الويب التي هي مجموعات من الدوال والكائنات والقواعد وبنيات الشيفرات البرمجية الأخرى المُصمَّمة لحل المشاكل الشائعة وتسريع التطوير وتبسيط الأنواع المختلفة من المهام التي تواجه مجالًا معينًا. تستخدم الشيفرة البرمجية لكل من العميل والخادم أطر عمل، ولكن المجالات مختلفة جدًا، وبالتالي تكون أطر العمل مختلفة أيضًا، إذ تعمل أطر عمل الويب من طرف العميل على تبسيط مهام التخطيط والعرض، بينما توفر أطر عمل الويب من طرف الخادم الكثير من وظائف خادم الويب الشائعة التي يمكن أن تضطر إلى تقديمها بنفسك، مثل دعم الجلسات ودعم المستخدمين والاستيثاق Authentication والوصول السهل إلى قاعدة البيانات ومكتبات القوالب وما إلى ذلك. ملاحظة: تُستخدَم أطر العمل من طرف العميل للمساعدة لتسريع تطوير الشيفرة البرمجية من طرف العميل، لكن يمكنك اختيار كتابة شيفرتك البرمجية يدويًا، والتي من الممكن أن تكون أسرع وأكثر فاعلية إذا أردتَ واجهة مستخدم موقع ويب صغيرة وبسيطة؛ بينما لن تفكر أبدًا في كتابة مكوِّن من طرف الخادم لتطبيق ويب بدون إطار عمل، فمن الصعب تقديم ميزة أساسية مثل خادم HTTP من الصفر باستخدام لغة بايثون، ولكن توفر أطر عمل الويب باستخدام لغة بايثون مثل إطار عمل جانغو Django ميزات مهمة إلى جانب أدوات أخرى مفيدة. فوائد واستخدامات البرمجة من طرف الخادم تُعَد البرمجة من طرف الخادم مفيدةً جدًا لأنها تتيح تقديم معلومات مُصمَّمة خصيصًا لكل مستخدم بكفاءة وبالتالي إنشاء تجربة مستخدم أفضل بكثير. تستخدم شركات مثل أمازون Amazon البرمجة من طرف الخادم لإنشاء نتائج البحث عن المنتجات، وتقديم اقتراحات المنتجات المستهدفة بناءً على تفضيلات العميل وعادات الشراء السابقة وتبسيط عمليات الشراء وما إلى ذلك؛ بينما تستخدم البنوك البرمجة من طرف الخادم لتخزين معلومات الحسابات والسماح للمستخدمين المُصرَّح لهم فقط بمشاهدة المعاملات وإجرائها؛ وتستخدم خدمات أخرى، مثل فيسبوك Facebook وتويتر Twitter وإنستغرام Instagram وويكيبيديا Wikipedia البرمجة من طرف الخادم لإظهار المحتوى ومشاركته والتحكم في الوصول إليه. سنذكر الآن بعض الاستخدامات والفوائد الشائعة للبرمجة من طرف الخادم، إذ ستلاحظ بعض التداخل بينها. تخزين المعلومات وتسليمها بفعالية هناك الكثير من المنتجات المتوفرة على أمازون والمنشورات المكتوبة على فيسبوك، وبالتالي سيكون إنشاء صفحة ساكنة منفصلة لكل منتج أو منشور غير عملي. تسمح البرمجة من طرف الخادم بتخزين المعلومات في قاعدة بيانات وبناء ملفات HTML وأنواع أخرى من الملفات (مثل ملفات PDF والصور وغيرها) وإعادتها ديناميكيًا. يمكن إعادة بيانات (JSON و XML وغيرها) لعرضها باستخدام أطر عمل الويب المناسبة من طرف العميل، وهذا يقلل من عبء المعالجة على الخادم وكمية البيانات التي يجب إرسالها. لا يقتصر عمل الخادم على إرسال المعلومات من قواعد البيانات، إذ يمكن أن يعيد نتيجة الأدوات البرمجية أو البيانات من خدمات الاتصالات، ويمكن استهداف المحتوى حسب نوع جهاز العميل الذي يستقبله. توجد المعلومات في قاعدة بيانات، لذا يمكن مشاركتها وتحديثها بسهولة أكبر مع أنظمة الأعمال الأخرى، فمثلًا يمكن أن يحدّث المتجر قاعدة بيانات مُخزنة عند بيع المنتجات إما عبر الإنترنت أو ضمن متجر. يمكنك معرفة فائدة الشيفرة البرمجية من طرف الخادم لتخزين المعلومات الفعال وتسليمها من خلال المثال التالي: اذهب إلى موقع أمازون أو أي موقع تجارة إلكترونية آخر. ابحث عن عدد من الكلمات الرئيسية ولاحظ عدم تغيّر بنية الصفحة بالرغم من تغيّر النتائج. افتح منتجين أو ثلاثة منتجات مختلفة، ولاحظ كيف أن لديها بنيةً وتخطيطًا مشتركًا مع سحب محتوى المنتجات المختلفة من قاعدة البيانات. يمكنك أن ترى فعليًا ملايين القيم المُعادة بالنسبة لمصطلح بحث شائع مثل "السمك"، إذ يسمح استخدام قاعدة البيانات بتخزينها ومشاركتها بفاعلية، كما يسمح بالتحكم في عرض المعلومات في مكان واحد فقط. تجربة مستخدم مخصصة يمكن للخوادم تخزين واستخدام المعلومات المتعلقة بالعملاء لتوفير تجربة مستخدم ملائمة ومُخصَّصة، فمثلًا تخزّن العديد من المواقع بطاقات الائتمان دون إدخال التفاصيل مرةً أخرى. يمكن لمواقع مثل خرائط جوجل استخدام المواقع المحفوظة أو الحالية لتوفير معلومات التوجيه والبحث، أو سجل السفر لإظهار الأنشطة التجارية المحلية في نتائج البحث. يمكن استخدام تحليل أعمق لعادات المستخدم لتوقّع اهتماماتهم وتخصيص الاستجابات والإشعارات، مثل تقديم قائمة بالمواقع التي زارها سابقًا أو التي يمكن أن يرغب في إلقاء نظرة عليها على الخريطة. تحفظ خرائط جوجل سجل البحث والزيارة، وتميّز المواقع التي تتكرر زيارتها، أو التي يتكرر البحث عنها أكثر من المواقع الأخرى. تُحسَّن نتائج بحث جوجل بناءً على عمليات البحث السابقة كما في المثال التالي: اذهب إلى بحث جوجل. ابحث عن "كرة القدم". حاول الآن كتابة كلمة "كرة" في مربع البحث ولاحظ توقعات البحث التي جرى إكمالها تلقائيًا. هل تعتقد أن هذه صدفة؟ حسنًا، إنها ليست كذلك. الوصول المتحكم فيه إلى المحتوى تسمح البرمجة من طرف الخادم للمواقع بتقييد الوصول إلى المستخدمين المُصرَّح لهم وتقديم المعلومات التي يُسمَح للمستخدم برؤيتها فقط. تشمل الأمثلة الواقعية مواقع الشبكات الاجتماعية التي تسمح للمستخدمين بتحديد مَن يمكنه رؤية المحتوى الذي ينشرونه على الموقع ويظهر على صفحتهم الرئيسية. ملاحظة: هناك أمثلة حقيقية أخرى، إذ يمكن التحكم في الوصول إلى المحتوى، مثل ما يمكنك رؤيته إذا ذهبت إلى موقع الإنترنت الخاص بالمصرف الذي تتعامل معه. سجّل الدخول إلى حسابك ولاحظ ما هي المعلومات الإضافية التي يمكنك رؤيتها وتعديلها، وما هي المعلومات التي يمكنك رؤيتها والتي يمكن للمصرف تغييرها فقط. تخزين معلومات الجلسة أو الحالة تسمح البرمجة من طرف الخادم للمطورين بالاستفادة من الجلسات sessions، والتي هي آلية تسمح للخادم بتخزين معلومات عن المستخدم الحالي للموقع وإرسال استجابات مختلفة بناءً على تلك المعلومات. يسمح ذلك لموقع ما مثلًا بمعرفة أن مستخدمًا قد سجل الدخول مسبقًا وعرض روابطًا إلى رسائل بريده الإلكتروني، أو رتب السجل، أو حفظ حالة لعبة بسيطة بحيث يمكن للمستخدم الانتقال إلى الموقع مرةً أخرى والمتابعة من حيث تركه. ملاحظة: زُر موقع صحيفة يحتوي على نموذج اشتراك وافتح مجموعة من النوافذ مثل موقع The Age. استمر في زيارة الموقع على مدار بضع ساعات أو أيام، ثم سيُعاد توجيهك إلى صفحات تشرح كيفية الاشتراك، ولن تتمكن من الوصول إلى المقالات. تمثل هذه المعلومات مثالًا عن معلومات الجلسة المخزنة في ملفات تعريف الارتباط. الإشعارات والاتصالات يمكن للخوادم إرسال إشعارات عامة أو خاصة بالمستخدم من خلال موقع الويب نفسه، أو عبر البريد الإلكتروني، أو الرسائل القصيرة، أو الرسائل الفورية، أو محادثات الفيديو، أو خدمات الاتصالات الأخرى، ومن الأمثلة على ذلك ما يلي: يرسل فيسبوك وتويتر رسائل بريد إلكتروني ورسائل قصيرة لإعلامك بالاتصالات الجديدة. يرسل أمازون بانتظام رسائل بريد إلكتروني خاصة بالمنتجات بحيث ثقترح منتجات مشابهة لتلك التي اشتريتها أو شاهدتها مسبقًا والتي يمكن أن تكون مهتمًا بها. يمكن أن يرسل خادم الويب رسائل تحذير إلى مسؤولي الموقع لتنبيههم بانخفاض الذاكرة على الخادم أو نشاط مستخدم مريب. ملاحظة: أكثر أنواع الإشعارات شيوعًا هو "تأكيد التسجيل". اختر أيّ موقع كبير تهتم به مثل جوجل وأمازون وإنستغرام وأنشئ حسابًا جديدًا باستخدام عنوان بريدك الإلكتروني، وستتلقى بعدها بريدًا إلكترونيًا يؤكد تسجيلك أو يطلب تأكيدًا لتفعيل حسابك. تحليل البيانات يمكن أن يجمع موقع الويب الكثير من البيانات حول المستخدمين مثل ما الذي يبحثون عنه وماذا يشترون وما يوصون به ومدة بقائهم في كل صفحة. يمكن استخدام البرمجة من طرف الخادم لتحسين الاستجابات بناءً على تحليل هذه البيانات، فمثلًا تعلن كلًا من أمازون وجوجل عن منتجات بناءً على عمليات البحث السابقة وعمليات الشراء. ملاحظة: إذا كنت من مستخدمي فيسبوك، فانتقل إلى الصفحة الرئيسية وانظر إلى المنشورات. لاحظ كيف أن بعض المنشورات ليست مرتبةً عدديًا، إذ تكون في أغلب الأحيان المشاركات التي تحتوي على عدد أكبر من الإعجابات أعلى في القائمة من المشاركات الأحدث. ألقِ نظرةً على نوع الإعلانات المعروضة، إذ يمكن أن تشاهد إعلانات عن الأشياء التي اطّلعتَ عليها على مواقع أخرى. يمكن أن تكون خوارزمية فيسبوك لإظهار المحتوى والإعلانات غامضةً بعض الشيء، ولكنها تعتمد على إعجاباتك وعادات المشاهدة. الخلاصة تعلمت الآن أن الشيفرة البرمجية من طرف الخادم تعمل على خادم ويب وأن دورها الرئيسي هو التحكم في المعلومات المُرسَلة إلى المستخدم، بينما تتعامل الشيفرة البرمجية من طرف العميل مع بنية تلك البيانات وعرضها للمستخدم، كما يجب أن تفهم أن الشيفرة البرمجية من طرف الخادم مفيدةٌ، لأنها تتيح إنشاء مواقع الويب التي تقدم معلومات مُخصَّصة لكل مستخدم بكفاءة ولديها فكرةٌ جيدةٌ عن بعض الأشياء التي يمكن أن تكون قادرًا على تطبيقها عندما تكون مبرمجًا من طرف الخادم. أخيرًا، يجب أن تفهم أنه يمكن كتابة الشيفرة البرمجية من طرف الخادم باستخدام عدد من لغات البرمجة وأنه يجب عليك استخدام إطار عمل ويب لتسهيل تلك العملية. سنساعدك في المقال التالي على اختيار أفضل إطار عمل ويب لموقعك الأول، وسنأخذك في جولة حول التفاعلات الرئيسية بين العميل والخادم بمزيدٍ من التفاصيل. ترجمة -وبتصرُّف- للمقالين Server-side website programming first steps و Introduction to the server side. اقرأ أيضًا المقال السابق: إعداد البيئة للاختبارات الآلية في مشاريع الويب للتوافق مع المتصفحات المدخل الشامل لتعلم تطوير الويب وبرمجة المواقع أساسيات إنشاء موقع ويب باستخدام تعليمات HTML رفع ملفات موقع الويب إلى خادم على الإنترنت1 نقطة
-
عند الاتصال بخادوم ويب أو تطبيق، يتم الردّ على كلّ طلب HTTP يتمّ استقباله من طرف الخادوم برمز حالة HTTP أو “HTTP status codes”. رموز حالة HTTP هي عبارة عن رموز مكوّنة من 3 أرقام يتم تصنيفها إلى 5 أصناف مختلفة. يمكن أن يتمّ التعرّف على صنف رمز الحالة بسرعة عبر الرقم الأوّل منه: 1xx: معلومة 2xx: نجاح 3xx: إعادة توجيه 4xx: خطأ من طرف جهاز العميل 5xx: خطأ من طرف الخادوميركّز هذا الدرس على استكشاف أبرز رموز أخطاء HTTP التي قد تصادفك مثل 4xx و5xx وإصلاحها. من منظور مدير النظام، هناك العديد من الحالات التي قد تجعل خادوم الويب يجيب طلبًا معيّنًا برمز خطأ معيّن، سنقوم بتغطية أكثر الأسباب الشائعة التي تؤدي إلى ذلك بالإضافة إلى حلولها. لمحة عامة عن أخطاء العميل والخادومأخطاء العميل، أو رموز حالة HTTP من 400 إلى 499، هي نتيجة لطلبات HTTP تمّ إرسالها بواسطة جهاز مستخدم (مثل متصفح ويب أو أيّ عميل HTTP آخر), صحيح أنّ هذا النوع من الأخطاء مرتبط بالعميل، إلّا أنّه سيكون من المفيد معرفة رمز الخطأ الذي يصادف المستخدم للتحقق مما إذا كان يمكن إصلاح المشكلة من إعدادات الخادوم. يتم إرجاع أخطاء الخادوم أو بالأحرى رموز حالة HTTP من 500 إلى 599 بواسطة خادوم الويب عندما يكتشف حصول مشكلة، وإلّا فإنّه لن يكون قادرًا على معالجة الطلب. نصائح عامة عن اكتشاف الأخطاء وإصلاحهاعند استخدام متصفّح ويب لاختبار خادوم ويب، قم بتحديث المتصفّح بعد تطبيق التغييرات على الخادوم.تحقق من سجلات الخادوم للمزيد من التفاصيل عن كيفية قيام الخادوم بمعالجة الطلبات. كمثال، تُنتِج خواديم الويب مثل Apache وNginx ملفّين اثنين يدعيان access.log وerror.log يمكن أن يتم فحصهما للحصول على المعلومات منهما.تذكّر أنّ تعريفات رموز حالة HTTP هي جزء من معيار مُضمَّن من قبل التطبيق الذي يخدم الطلبات. هذا يعني أنّ رمز الحالة الذي يتم إرجاعه إليك يعتمد على كيفية معالجة برنامج الخادوم لخطأ معيّن. سيفيدك هذا الدرس عمومًا لتوجيهك في المسار الصحيح بخصوص ذلك.الآن وبعد أن امتلكت فهمًا جيدًا لرموز حالة HTTP، سنلقي نظرةً على الأخطاء الشائعة التي قد تصافدك. 400 Bad Requestرمز الحالة 400، أو خطأ Bad Request، يعني أنّ طلب الـHTTP الذي تمّ إرساله إلى الخادوم كان يحوي دوالًا ومُعامِلات غير صحيحة. إليك بعض الأمثلة التي قد يطرأ فيها خطأ Bad Request والذي رقمه 400: كعكة المستخدم (Cookie) المرتبطة بالموقع تالفة، مسح خبيئة المتصفّح والكعكات قد يحلّ هذه المشكلة. طلب تالف بسبب متصفّح ويب سيء وقديم مثلًا. طلب تالف بسبب خطأٍ بشري مثل عند تشكيل طلبات HTTP بشكلٍ يدوي (مثل استعمال curl بطريقة غير صحيحة).401 Unauthorizedرمز الحالة 401، أو خطأ Unauthorized أو عدم التصريح يعني أنّ المستخدم يحاول الوصول إلى صفحة أو مادّة غير مخوّل له بالوصول إليها أو لم يتم السماح له بذلك بشكلٍ صحيح. يعني هذا أنّه يجب على المستخدم توفير بيانات الدخول ليتمكّن من رؤية البيانات والموارد المحمية. كمثال، إذا حاول مستخدم الوصول إلى صفحة محمية باستيثاق HTTP، كما في درسنا كيفية إعداد استيثاق http مع nginx على 14.04 ubuntu، ففي هذه الحالة، سيتلقّى المستخدم رمز الحالة "401" إلى أن يقوم بتوفير اسم مستخدم وكلمة مرور (تلك الموجودة في ملفّ htpasswd.) لخادوم الويب. 403 Forbiddenرمز الحالة 403، أو خطأ Forbidden أو "محظور"، يعني أنّ المستخدم قام بطلبٍ خاطئ إلّا أنّ الخادوم يرفض تنفيذه على كلّ حال بسبب عدم توفّر الصلاحيات الكافية للوصول إلى الصفحة المطلوبة. إذا كنت تواجه خطأ 403 بشكلٍ غير متوقّع، فهناك بضع أسباب يمكن أن نشرحها هنا. صلاحيات الملفاتتطرأ أخطاء 403 عادةً عندما يكون المستخدم الذي يشغّل عملية خادوم الويب لا يمتلك الصلاحيات الكافية لقراءة الملفّ الذي تمّ طلبه. لإعطاء مثال عن الكشف عن هذا الخطأ وإصلاحه، افترض حصول الوضع التالي: يحاول المستخدم الوصول إلى ملفّ الفهرس الخاصّ بالخادوم من http://example.com/index.htmlعملية تشغيل خادوم الويب مملوكة للمستخدم www-dataيوجد ملفّ الفهرس على الخادوم بالمسار usr/share/nginx/html/index.html/إذا كان المستخدم يحصل على خطأ 403، فتأكّد أنّ المستخدم www-data يمتلك الصلاحيات الكافية لقراءة ذلك الملفّ. يعني هذا عادةً أنّه يجب ضبط صلاحيات "الآخرين" أو الـ"Others" إلى السماح بالقراءة ليتم حلّ المشكلة، هناك عدّة طرق لتنفيذ هذا، ولكنّ هذا الأمر سيعمل في هذه الحالة: sudo chmod o=r /usr/share/nginx/html/index.html htaccess.سببٌ آخر قد يكون وراء خطأ 403 وغالبًا ما يحصل عن غير قصد، هو الاستخدام الخاطئ لملفّ htaccess.، يمكن أن يتمّ استخدام ملفّ htaccess. لمنع الوصول إلى صفحاتٍ أو موارد معيّنة من قبل عناوين IP محددة أو نطاقات، استخدام هذا الملفّ بشكلٍ غير صحيح قد يكون المشكلة مثلًا. إذا كان المستخدم يحصل على خطأ 403 بشكلٍ غير متوقع، فتأكّد من أنّ ملفّ الـhtaccess. الخاصّ بك ليس المسؤول عن ذلك. ملف الفهرس غير موجودإذا كان المستخدم يحاول الوصول إلى مجلّد لا يمتلك بداخله ملفّ فهرس افتراضيًا، ولم يكن خيار السماح بسرد محتويات المجلّدات مفعّلًا، فإنّ خادوم الويب سيُرجع خطأ حظر 403. كمثال، إذا كان المستخدم يحاول الوصول إلى http://example.com/emptydir ولم يكن هناك ملفّ فهرس في المجلّد emptydir على الخادوم، فإنّه سيتم إرجاع رمز حالة 403. إذا كنت تريد تفعيل خيار سرد محتويات المجلّدات في حال عدم وجود ملفّ فهرس بداخلها، فيمكنك القيام بذلك من إعدادات خادوم الويب الخاصّ بك. 404 Not Foundرمز الحالة 404، أو خطأ Not Found، يعني أنّ المستخدم كان قادرًا على التواصل مع الخادوم إلّا أنّه لم يتمكن من إيجاد الملفّ المطلوب أو الصفحة المنشودة. يمكن أن تطرأ أخطاء 404 في الكثير من الحالات. إذا كان المستخدم يتلقّى خطأ 404 بشكلٍ غير متوقّع، فإليك بعض الأسئلة التي يجب أن تسألها للمساعدة في تفحّص المشكلة وإصلاحها: هل الرابط الذي وجّهَ المستخدم إلى خادمك يحتوي على خطأ بالكتابة؟ هل قام المستخدم بكتابة العنوان الخاطئ؟ هل الملفّ موجود في المسار الحالي للخادوم؟ وهل تمّ نقله أو نقل الصفحة المطلوبة إلى مكانٍ آخر أو حذفها من الخادوم؟ هل تمّ ضبط إعدادات الخادوم إلى مسار الجذر الرئيسي المطلوب؟ هل المستخدم الذي يملك العملية المُشغّلة لخادوم الويب يمتلك الصلاحيات اللازمة للوصول إلى المسار الذي يحوي الملفّ بداخله؟ (تلميح: تتطلب المجلّدات صلاحيات القراءة والتنفيذ لتستطيع الوصول إليها). هل يتمّ الوصول إلى الملفّ أو الصفحة عبر وصلة رمزية (symbolic link)؟ إذا كان الأمر كذلك، فتحقق من أن خادوم الويب مضبوط ليتبع الوصلات الرمزية.500 Internal Server Errorرمز الحالة 500، أو 500 Internal Server Error يعني أنّ الخادوم غير قادر على معالجة الطلب لسببٍ مجهول. أحيانًا سيظهر هذا الرمز عندما تكون أخطاء 5xx أكثر عرضةً لتكون هي سبب المشكلة. عادةً ما يكون أبرز سببٍ مسبب لهذا الخطأ هو وجود مشكلة في إعدادات الخادوم (مثل ملفّ htaccess. تالف) أو حزم ناقصة (مثل محاولة تنفيذ سكربت PHP دون وجود حزمة PHP مثبّتة بشكلٍ صحيح على الخادوم). 502 Bad Gatewayرمز الحالة 502، أو 502 Bad Gateway، يعني أنّ الخادوم هو عبارة عن خادوم بوّابة أو وسيط (proxy)، وأنّه لا يتلقّى ردًا صحيحًا من خواديم الواجهة الخلفية (backend servers) التي يجب أن تقوم بمعالجة الطلب. إذا كان الخادوم المطلوب هو عبارة عن خادوم وسيط عكسي (reverse proxy server)، مثل موازِن للحِمل، فإليك بعض الأمور التي يمكنك التحقق منها: أنّ خواديم الواجهة الخلفية (حيث يتم توجيه طلبات HTTP) تعمل بشكلٍ صحيح. أنّ الخادوم العكسي مضبوط بشكلٍ صحيح، مع تحديد الخواديم الصحيحة للواجهة الخلفية. أنّ اتصال الشبكة بين خواديم الواجهة الخلفية وبين خادوم الوسيط العكسي يعمل بشكلٍ جيّد. إذا كان بإمكان الخواديم أن تتواصل عن طريق منافذ أخرى، فتأكّد أنّ الجدار الناري يسمح بمرور التدفّق (Traffic) بينها. إذا كان تطبيق الويب الخاصّ بك مضبوطًا للاستماع إلى socket، فتأكّد أنّ الـsocket موجودة في المسار الحالي وأنّها تمتلك الصلاحيات الكافية.503 Service Unavailableرمز الحالة 503، أو خطأ Service Unavailable، يعني أنّ الخادوم قد تحمّل فوق طاقته أو أنّه تحت الصيانة، يوحي هذا الخطأ أنّ الخدمة يجب أن تعود إلى العمل في وقتٍ ما من الزمن. إذا لم يكن الخادوم تحت الصيانة، يمكن لهذا أن يشير إلى أنّ الخادوم لا يملك الموارد الكافية من المعالج والذاكرة العشوائية لمعالجة جميع الطلبات الواردة، أو أنّ خادوم الويب يحتاج إلى أنّ يتم إعداده ليسمح بالمزيد من المستخدمين والعمليات. 504 Gateway Timeoutرمز الحالة 504، أو خطأ Gateway Timeout، يعني أنّ الخادوم هو عبارة عن خادوم بوّابة أو خادوم وسيط (proxy)، وأنّه لا يتلقّى ردًا من خواديم الواجهة الخلفية في فترة الوقت المسموح بها. يمكن لهذا الخطأ عادةً أن يحصل في الحالات التالية: اتصال الشبكة بين الخواديم ضعيف. خواديم الواجهة الخلفية التي تقوم بتنفيذ الطلب بطيئة جدًا، بسبب الأداء الضعيف. فترة المهلة لخادوم البوابة أو الوسيط قصيرة جدًا.الخاتمةيجب أن تكون قد صرتَ الآن مُدركًا لأبرز رموز أخطاء HTTP وأبرز الحلول المتوفّرة لهذه الأخطاء، يجب أن تمتلك أساسياتٍ جيّدة لاكتشاف الأخطاء وإصلاحها على خواديم الويب الخاصّة بك أو تطبيقاتك. ترجمة -وبتصرف- للمقال How To Troubleshoot Common HTTP Error Codes لصاحبه Mitchell Anicas.1 نقطة