وقتی برای اولین بار لیست محصولات یا کاربران رو توی API میسازی، همه چیز به ظاهر درسته : GET /products/ رو صدا میزنی و ۱۰ تا محصول تستی که ساختی رو میبینی. کلی هم ذوق میکنی! اما صبر کن... یک نکته ی خیلی ترسناک اینجا هست. تصور کن سایتت بزرگ شده و حالا ۱۰۰,۰۰۰ تا محصول داری. اگر کاربر درخواست بده "محصولات رو بده" و تو همه ی ۱۰۰ هزار تا رو یکجا بفرستی سمتش، چه اتفاقی می افته؟ دقیقاً مثل اینه که بری توی یک کتابخونه بزرگ و به کتابدار بگی "کتاب می خوام" و اونم یهو ۵ کامیون کتاب خالی کنه روی سرت! نه سرور تو زنده می مونه، نه اینترنت کاربر، و نه اپلیکیشن موبایلی که قراره این همه داده رو پردازش کنه.
اینجاست که فیلترینگ (Filtering) وارد بازی میشه. فیلترینگ یعنی اون کتابدار هوشمندی که به جای همه کتاب ها، ازت میپرسه: "چه ژانری؟ چه نویسنده ای؟ سال انتشارش کی باشه؟" و دقیقاً همون چیزی رو میاره که لازم داری. توی جنگو رست فریمورک، ما این هوشمندی رو با پکیج django-filter پیاده میکنیم.
تفاوت "جستجو" و "فیلترینگ"
۱. فیلترینگ (Filtering): یعنی "غربال کردن". من دقیقاً میدونم چی میخوام. مثلاً: "گوشی های برند سامسونگ که موجود باشن". داده ها ساختار مشخص دارن. ۲. جستجو (Search): یعنی "دنبال گشتن". من دقیقاً نمیدونم چی میخوام، فقط یه کلمه تو ذهنمه. مثلاً: "هر چیزی که توش کلمه 'لباس' داره".
نصب و راهاندازی
این پکیج به صورت پیش فرض روی DRF نیست، پس باید نصبش کنی (pip install django-filter) و توی settings.py معرفیش کنی. حالا دو راه داری برای استفاده ازش:
۱. روش تنبلها (Quick & Easy): فقط کافیه توی ویو (View) بگی که کدوم فیلد ها قابلیت فیلتر شدن دارن.
filterset_fields = ['category', 'is_active']
با همین یک خط، جنگو رست خودش میفهمه که اگر کاربر زد ?category=tech، باید بره فقط تکنولوژی ها رو بیاره. مثل اینه که روی قفسه ها برچسب بزنی و بگی "فقط قفسه تکنولوژی رو نشون بده".
روش حرفهای ها (Custom FilterSet): روش قبلی خوبه، اما محدودیت داره. فرض کن کاربر بگه "محصولاتی رو میخوام که قیمتشون بیشتر از ۵ میلیون تومن باشه". روش قبلی فقط تساوی (=) رو میفهمه. اینجاست که باید FilterSet بسازیم. این یعنی خودت منطق غربالگری رو بنویسی. یک کلاس میسازی و میگی:
min_price: برو توی دیتابیس بگرد دنبال اونایی که قیمت (Price) بزرگتر یا مساوی (gte) این عدد هستن.
name: بگرد دنبال اونایی که اسمشون شامل (icontains) این کلمه میشه.
انواع فیلترهای پرکاربرد (Lookup Expressions)
توی جنگو ما یه سری کلمات کلیدی داریم که کار رو راحت میکنن:
exact: یعنی دقیقاً همین باشه (مثلاً id=5).
icontains: یعنی شامل این کلمه باشه (حساس به حروف بزرگ و کوچیک هم نباشه). برای سرچ اسم عالیه.
gte / lte: مخفف
Greater Than Equal و Less Than Equal. خوراک فیلتر کردن بازه قیمت یا تاریخ تولده (مثلاً از تاریخ X تا تاریخ Y)
چرا باید حتماً از django-filter استفاده کنیم؟
شاید بگی "خب. من خودم دستی توی get_queryset کوئری مینویسم و با if چک میکنم". ۱. خداحافظی با کد های اسپاگتی: اگر بخوای برای ۵ تا فیلد مختلف (قیمت، رنگ، سایز، برند، موجودی) دستی شرط if بذاری، ویو (View) شما تبدیل میشه به یک جنگل تو در تو که هیچکس نمیتونه بخونتش. ۲. استاندارد بودن: این پکیج خودش مدیریت میکنه که اگر کاربر یه چیز عجیب غریب فرستاد، ارور مناسب بده و کوئری دیتابیس خراب نشه. ۳. سرعت توسعه: کاری که دستی ۳ ساعت طول میکشه، اینجا با ۳ خط کد انجام میشه.
جمع بندی
در دنیای واقعی داده ها طلا هستن، اما دیتای زیاد و فیلتر نشده مثل زباله هست. هیچ کاربری دوست نداره بین هزاران محصول اسکرول کنه تا چیزی که میخواد رو پیدا کنه. با استفاده از django-filter شما به کاربرتون احترام میزارید و بهش اجازه میدید دقیقا همون بخش دیتابیس رو ببینه که بهش نیاز داره. این یعنی :
فشار کمتر روی سرور ، سرعت بیشتر برای کلاینت کاربر ، کد تمیز تر
نظرات کاربران (0)