بعد فهم Routes في Laravel، يقع كثير من المبتدئين في خطأ شائع:
وهو كتابة منطق التطبيق مباشرة داخل Routes.
في البداية قد يبدو الأمر بسيطًا، لكن مع توسّع المشروع تتحول هذه الطريقة إلى عبء حقيقي.
لذلك، جاء مفهوم Controllers في Laravel ليحل مشكلة التنظيم، ويجعل الكود أوضح وأسهل في الصيانة.
في هذا المقال، سنفهم ما هي Controllers في Laravel، ولماذا نحتاجها، ومتى يجب استخدامها، وكيف تنظّم مشروعك بطريقة احترافية.
المشكلة: تكديس المنطق داخل Routes
كثير من المطورين المبتدئين يكتبون كودًا بهذا الشكل:
Route::get('/posts', function () {
$posts = Post::all();
return view('posts.index', compact('posts'));
});
في البداية يعمل الكود بشكل طبيعي، ولكن مع الوقت تظهر مشاكل واضحة، مثل:
- تضخّم ملف routes/web.php
- تكرار نفس المنطق في أكثر من Route
- صعوبة اختبار الكود
- ضعف تنظيم المشروع
- صعوبة فهم الكود من طرف مطور آخر
نتيجةً لذلك، يصبح المشروع معقّدًا وغير قابل للتوسّع.
الحل: استخدام Controllers في Laravel
Laravel يقدّم Controllers كحل مباشر لهذه المشكلة.
الفكرة بسيطة:
كل منطق التطبيق يجب أن يكون داخل Controller، وليس داخل Route.
بهذا الأسلوب:
- Routes تحدد المسار فقط
- Controllers تحتوي منطق التطبيق
- Views تعرض البيانات
نتيجة لذلك يصبح المشروع منظمًا وقابلًا للتطوير.
ما هو Controller في Laravel؟
يعتبر Controller هو كلاس (Class) يحتوي على مجموعة من الدوال (Methods)،
وكل دالة تمثل إجراءً معيّنًا داخل التطبيق.
عادةً، Controllers توجد داخل المسار:
app/Http/Controllers
إنشاء Controller في Laravel
يمكنك إنشاء Controller باستخدام Artisan:
php artisan make:controller PostController
ثم سينشئ Laravel ملفًا بهذا الشكل:
class PostController extends Controller
{
//
}
ربط Controller بـ Route
بدل كتابة منطق داخل Route، نربطه بـ Controller:
Route::get('/posts', [PostController::class, 'index']);
ثم داخل Controller:
class PostController extends Controller
{
public function index()
{
$posts = Post::all();
return view('posts.index', compact('posts'));
}
}
بهذا الشكل:
- Route نظيف
- Controller يحتوي المنطق
- View مخصص للعرض
متى يجب استخدام Controller؟
استخدم Controller دائمًا عندما:
- تتعامل مع قاعدة بيانات
- تمرّر بيانات إلى View
- تنفّذ منطقًا برمجيًا
- تبني CRUD
- تطوّر مشروعًا حقيقيًا وليس تجربة بسيطة
في المقابل، يمكن استخدام Closure داخل Route فقط في الحالات البسيطة جدًا أو المؤقتة.
Controller واحد أم عدة Controllers؟
خطأ شائع هو وضع كل شيء داخل Controller واحد.
الطريقة الصحيحة:
- Controller لكل كيان (Resource)
- مثال:
- PostController
- UserController
- ProductController
ذلك يسهّل الصيانة ويجعل الكود واضحًا.
Resource Controllers (أفضل تنظيم لـ CRUD)
Laravel يوفّر Resource Controllers لتنظيم عمليات CRUD.
إنشاء Resource Controller:
php artisan make:controller PostController --resource
ثم سينشئ Laravel دوال جاهزة مثل:
- index
- create
- store
- show
- edit
- update
- destroy
وربطه بالـ Routes:
Route::resource('posts', PostController::class);
نتيجة لذلك تصبح هذه الطريقة مثالية في المشاريع المتوسطة والكبيرة.
تنظيم Controllers في مشاريع كبيرة
عند كبر المشروع، يمكنك تنظيم Controllers داخل مجلدات:
app/Http/Controllers/Admin
على سبيل المثال:
use App\Http\Controllers\Admin\PostController;
وبذلك تحافظ على بنية واضحة ومنطقية.
أخطاء شائعة عند استخدام Controllers
وضع منطق كبير داخل Constructor
المشكلة: يصعّب الاختبار
الحل: ضع المنطق داخل methods مخصصة
تكرار نفس الكود في عدة Controllers
المشكلة: صعوبة الصيانة
الحل: استخدام Services أو Traits (سنشرحها لاحقًا)
استخدام Controller لكل شيء
المشكلة: تضخّم Controllers
الحل: فصل المنطق المعقّد في Classes مستقلة
العلاقة بين Routes و Controllers
يمكن تلخيص العلاقة كالتالي:
- Route: يستقبل الطلب
- Controller: يعالج الطلب
- View: يعرض النتيجة
فصل هذه الأدوار هو أساس أي تطبيق Laravel احترافي.
ماذا بعد Controllers؟
بعد فهم Controllers، الخطوة التالية هي:
- عرض البيانات بطريقة منظمة
- تجنب تكرار HTML
- بناء واجهات نظيفة
وهنا يأتي دور Blade Templates.
