eitaa logo
پروژه ASP.Net Core MVC (وب و سی شارپ)
119 دنبال‌کننده
168 عکس
38 ویدیو
376 فایل
❁﷽❁ آموزش 📖 برنامه نویسی ASP.Net Core MVC (وب و سی شارپ) Admin: @alialirezapanahi برنامه نویسی برنامه نویسی سی شارپ eitaa.com/sisharpapp برنامه نویسی وب eitaa.com/aspdatnet ویراستی virasty.com/alialirezapanahi آپارات aparat.com/alialirezapanahi
مشاهده در ایتا
دانلود
CProduct.zip
حجم: 24.9M
این پروژه یک سیستم ساده مدیریت محصولات و دسته‌بندی‌هاست
پروژه ASP.Net Core MVC (وب و سی شارپ)
این پروژه یک سیستم ساده مدیریت محصولات و دسته‌بندی‌هاست
در ادامه، پروژه‌ات رو فقط به‌صورت لیست توضیح می‌دم که چه کارهایی انجام می‌ده و چرا تصمیم گرفتی از Select() به‌جای Include() استفاده کنی: ✅ عملکردهای پروژه - نمایش دسته‌بندی‌ها با محصولات اخیر هر دسته - صفحه‌بندی پویا برای دسته‌بندی‌ها و محصولات - نمایش جزئیات محصولات هر دسته‌بندی - افزودن، ویرایش و حذف محصولات - افزودن، ویرایش و حذف دسته‌بندی‌ها - نمایش تعداد محصولات مرتبط با هر دسته - استفاده از ViewModel برای ارسال داده ترکیبی - طراحی ساده و واکنش‌گرا با لیست‌های Bootstrap - لینک‌دهی بین صفحات با asp-controller و asp-action - جلوگیری از خطاهای dynamic با تعریف دقیق مدل‌ها 🎯 هدف آموزشی پروژه - آموزش Entity Framework Core و رابطه‌ها - تمرین معماری MVC در ASP.NET Core - یادگیری صفحه‌بندی و ارسال داده به ویو - تمرین طراحی رابط کاربری ساده و قابل فهم - ساخت پروژه قابل توسعه برای کلاس، آموزشگاه یا گیت‌هاب 🔍 چرا از Select() به‌جای Include() استفاده کردی - کنترل دقیق روی فیلدهای مورد نیاز - کاهش حجم داده‌های دریافتی از دیتابیس - جلوگیری از بارگذاری اضافی موجودیت‌های مرتبط - افزایش سرعت و بهینه‌سازی کوئری‌ها - ساده‌سازی داده‌ها برای ارسال به ویو - سازگاری بهتر با ViewModel و ساختار آموزشی پروژه
بهینه_سازی_کار_با_داده_در_ASP.mp3
زمان: حجم: 19.6M
بهینه سازی کار با داده در ASP.Net Core MVC ساخته شده از هوش مصنوعی نکته: شاید پادکست تکراری باشد ولی نکته مهمی گفته شده
پروژه ASP.Net Core MVC (وب و سی شارپ)
بهینه سازی کار با داده در ASP.Net Core MVC ساخته شده از هوش مصنوعی نکته: شاید پادکست تکراری باشد و
بیا این رو به شکل یک اسکریپت پادکست آموزشی آماده کنیم که هم شنیدنی باشه، هم پر از مثال عملی. این متن رو می‌تونی هم برای ضبط صدا استفاده کنی، هم بعداً به عنوان یادداشت آموزشی نگه داری. --- 🎧 عنوان پادکست: «سه روش بارگذاری داده در EF Core + Select برای لیست کردن آیتم‌ها + صفحه‌بندی در ASP.NET Core MVC» --- 🎙️سلام امروز می‌خوایم با هم سه روش بارگذاری داده در EF Core رو یاد بگیریم، بعد با Select فقط فیلدهای لازم رو بگیریم، و در نهایت با صفحه‌بندی (Pagination) حجم داده رو کنترل کنیم تا پروژه‌هامون سریع‌تر و بهینه‌تر بشه. --- 🧩 بخش اول: سه روش بارگذاری داده در EF Core 1️⃣ Eager Loading – بارگذاری پیش‌گیرانه - با Include() داده‌های مرتبط رو هم‌زمان با داده اصلی می‌آریم. - مثال:
csharp
var products = _context.Products
    .Include(p => p.Category)
    .ToList();
📌 مزیت: فقط یک کوئری به دیتابیس 📌 عیب: ممکنه داده زیادی بیاد که لازم نداشته باشیم --- 2️⃣ Lazy Loading – بارگذاری تنبل - داده‌های مرتبط فقط وقتی لود می‌شن که بهشون دسترسی پیدا کنیم. - نیاز به virtual و فعال‌سازی UseLazyLoadingProxies():
csharp
var product = _context.Products.First();
var categoryName = product.Category.Name; // اینجا کوئری جدا اجرا میشه
📌 مزیت: فقط داده لازم لود میشه 📌 عیب: خطر N+1 Query --- 3️⃣ Explicit Loading – بارگذاری صریح - خودمون به صورت دستی و در زمان دلخواه داده مرتبط رو لود می‌کنیم:
csharp
var category = _context.Categories.First();
_context.Entry(category)
    .Collection(c => c.Products)
    .Load();
📌 مزیت: کنترل کامل روی زمان و نوع بارگذاری 📌 عیب: نیاز به کدنویسی بیشتر --- 🧩 بخش دوم: استفاده از Select برای لیست کردن آیتم‌ها گاهی همه‌ی ستون‌ها رو لازم نداریم. با Select فقط فیلدهای موردنیاز رو می‌گیریم:
csharp
var productList = _context.Products
    .Select(p => new { p.Title, p.Price })
    .ToList();
📌 مزیت: حجم داده کمتر → سرعت بیشتر --- 🧩 بخش سوم: صفحه‌بندی برای کنترل حجم داده فرمول اصلی:
csharp
int pageSize = 10;
int pageNumber = 2;
int skipCount = (pageNumber - 1) * pageSize;
کوئری:
csharp
var products = _context.Products
    .AsNoTracking()
    .Include(p => p.Category)
    .OrderBy(p => p.Title)
    .Skip(skipCount)
    .Take(pageSize)
    .ToList();
📌 اینطوری مثلاً صفحه دوم رو می‌گیریم: آیتم‌های ۱۱ تا ۲۰. --- 🧠 نکات پایانی: - همیشه قبل از Skip() مرتب‌سازی (OrderBy) انجام بده - برای داده‌های فقط خواندنی از AsNoTracking() استفاده کن - با ToQueryString() می‌تونی SQL نهایی رو ببینی و بهینه کنی - انتخاب روش بارگذاری بستگی به نیاز پروژه و حجم داده داره --- 🎯 جمع‌بندی پادکست: با شناخت سه روش بارگذاری داده، استفاده از Select برای کم کردن حجم، و پیاده‌سازی صفحه‌بندی، می‌تونی پروژه‌های ASP.NET Core MVC رو سریع‌تر و بهینه‌تر بسازی.
پروژه ASP.Net Core MVC (وب و سی شارپ)
بهینه سازی کار با داده در ASP.Net Core MVC ساخته شده از هوش مصنوعی نکته: شاید پادکست تکراری باشد و
در EF Core وقتی از Select استفاده می‌کنی، می‌تونی هم داده‌های اصلی و هم داده‌های مرتبط (Navigation Properties) رو انتخاب کنی—و حتی روی همون نتیجه صفحه‌بندی (Skip و Take) انجام بدی. --- 🧩 ایده کلی Select بهت اجازه می‌ده فقط فیلدهایی که لازم داری رو از چند جدول مرتبط بگیری، بدون اینکه کل موجودیت‌ها رو لود کنی. این کار باعث می‌شه حجم داده کمتر بشه و سرعت بیشتر. --- 🔹 مثال: لیست کردن همه آیتم‌های مرتبط فرض کن دو جدول داری: Product و Category (یک محصول یک دسته‌بندی دارد).
csharp
var products = _context.Products
    .Select(p => new 
    {
        p.Title,
        p.Price,
        CategoryName = p.Category.Name
    })
    .ToList();
📌 اینجا EF Core خودش Join می‌زنه و اسم دسته‌بندی رو هم میاره، بدون نیاز به Include(). --- 🔹 مثال: صفحه‌بندی روی داده‌های انتخاب‌شده
csharp
int pageSize = 10;
int pageNumber = 2;

var products = _context.Products
    .Where(p => p.IsActive)
    .OrderBy(p => p.Title)
    .Select(p => new 
    {
        p.Title,
        p.Price,
        CategoryName = p.Category.Name
    })
    .Skip((pageNumber - 1) * pageSize)
    .Take(pageSize)
    .ToList();
✅ این کوئری: - فقط فیلدهای لازم رو میاره (Title, Price, CategoryName) - صفحه‌بندی رو روی همون داده‌ها انجام می‌ده - بهینه‌تر از Include هست وقتی کل موجودیت رو لازم نداری --- 🧠 نکات حرفه‌ای - وقتی فقط چند فیلد لازم داری، Select بهتر از Include هست چون حجم داده کمتره - Select می‌تونه چند سطح رابطه رو هم بیاره، مثلاً:
csharp
  .Select(o => new {
      o.Id,
      o.Customer.Name,
      City = o.Customer.Address.City
  })
  
- صفحه‌بندی (Skip/Take) رو می‌تونی بعد از Select یا قبلش بزنی، ولی معمولاً بعد از OrderBy و قبل از ToList() میاد
وقتی می‌خوای داده‌ای رو از دیتابیس بارگذاری کنی (مثلاً لیست کتاب‌ها یا محصولات)، چند مرحله مهم وجود داره که هر کد حرفه‌ای باید رعایت کنه. این مراحل نه‌تنها باعث می‌شن کدت بهینه باشه، بلکه قابل توسعه، قابل تست و قابل فهم هم می‌شه. بذار این مراحل رو خیلی واضح و قابل استفاده برات لیست کنم، طوری که همیشه بتونی بهش رجوع کنی و ترتیب اجرای کوئری‌ها در EF Core رو اصولی یاد بگیری. --- ✅ مراحل استاندارد بارگذاری داده در EF Core 1️⃣ AsNoTracking() - کاربرد: حذف ردیابی تغییرات توسط EF - هدف: سبک‌سازی کوئری‌های فقط خواندنی - مثال:
csharp
  context.Books.AsNoTracking()
  
--- 2️⃣ Where() - کاربرد: فیلتر کردن داده‌ها بر اساس شرط - هدف: حذف رکوردهای غیرضروری - مثال:
csharp
  .Where(b => b.IsAvailable == true)
  
--- 3️⃣ جستجو (Search) - کاربرد: جستجو در متن یا فیلدهای خاص - هدف: پیدا کردن رکوردهای مرتبط با عبارت کاربر - مثال:
csharp
  .Where(b => b.Title.Contains(search) || b.Author.FullName.Contains(search))
  
--- 4️⃣ OrderBy() / OrderByDescending() - کاربرد: مرتب‌سازی داده‌ها - هدف: تعیین ترتیب نمایش در لیست - مثال:
csharp
  .OrderBy(b => b.Title)
  
--- 5️⃣ Skip() و Take() - کاربرد: صفحه‌بندی داده‌ها - هدف: گرفتن فقط رکوردهای صفحه فعلی - مثال:
csharp
  .Skip((page - 1) * pageSize).Take(pageSize)
  
--- 6️⃣ Select() - کاربرد: انتخاب فقط فیلدهای مورد نیاز - هدف: کاهش حجم خروجی و کنترل نمایش - مثال:
csharp
  .Select(b => new { b.Id, b.Title, b.IsAvailable })
  
--- 7️⃣ ToList() یا ToListAsync() - کاربرد: اجرای کوئری و گرفتن داده‌ها - هدف: انتقال داده‌ها به حافظه برنامه - مثال:
csharp
  .ToList()
  
--- 8️⃣ ارسال به View - کاربرد: نمایش داده‌ها در Razor یا API - هدف: ارائه خروجی به کاربر - مثال:
csharp
  return View(books);
  
--- 📌ترتیب استاندارد نوشتن کوئری در EF Core
csharp
var query = context.TableName
    .AsNoTracking()                         
// 1️⃣ سبک‌سازی
    .Where(...)                             
// 2️⃣ فیلتر
    .Where(searchCondition)               
// 3️⃣ جستجو
    .OrderBy(...)                          
// 4️⃣ مرتب‌سازی
    .Skip((page - 1) * pageSize)            
// 5️⃣ صفحه‌بندی
    .Take(pageSize)                        
// 6️⃣ محدودسازی
    .Select(x => new { ... })               
// 7️⃣ انتخاب فیلدها
    .ToList();                             
// 8️⃣ اجرا
✅ اکشن Index برای پروژه کتابخانه (نسخه آموزشی و مرحله‌به‌مرحله)
csharp
public IActionResult Index(int page = 1, int pageSize = 10, string search = "", string statusFilter = "", string sort = "")
{
    // 1️⃣ شروع کوئری با سبک‌سازی
    var query = _context.Books
        .AsNoTracking();

    // 2️⃣ فیلتر وضعیت کتاب (موجود یا فروخته‌شده)
    if (statusFilter == "available")
        query = query.Where(b => b.IsAvailable == true);
    else if (statusFilter == "sold")
        query = query.Where(b => b.IsAvailable == false);

    // 3️⃣ جستجو در عنوان یا نام نویسنده
    if (!string.IsNullOrEmpty(search))
        query = query.Where(b => b.Title.Contains(search) || b.Author.FullName.Contains(search));

    // 4️⃣ مرتب‌سازی بر اساس فیلد انتخاب‌شده
    switch (sort)
    {
        case "title":
            query = query.OrderBy(b => b.Title);
            break;
        case "status":
            query = query.OrderByDescending(b => b.IsAvailable);
            break;
        default:
            query = query.OrderBy(b => b.Id); // مرتب‌سازی پیش‌فرض
            break;
    }

    // 5️⃣ محاسبه تعداد کل رکوردها برای صفحه‌بندی
    int totalCount = query.Count();
    int totalPages = (int)Math.Ceiling((double)totalCount / pageSize);

    // 6️⃣ اعمال صفحه‌بندی
    query = query
        .Skip((page - 1) * pageSize)
        .Take(pageSize);

    // 7️⃣ انتخاب فیلدهای مورد نیاز
    var books = query
        .Select(b => new
        {
            b.Id,
            b.Title,
            b.IsAvailable,
            AuthorName = b.Author.FullName
        })
        .ToList();

    // 8️⃣ ارسال داده‌ها به View
    ViewBag.CurrentPage = page;
    ViewBag.TotalPages = totalPages;
    ViewBag.TotalCount = totalCount;
    ViewBag.PageSize = pageSize;
    ViewBag.Search = search;
    ViewBag.StatusFilter = statusFilter;
    ViewBag.Sort = sort;

    return View(books);
}
--- 🎯 ویژگی‌های این اکشن | مرحله | توضیح | |-------|--------| ۱ـ| AsNoTracking() | سبک‌سازی کوئری فقط خواندنی | ۲ـ| Where() | فیلتر وضعیت و جستجو | ۳ـ| switch | مرتب‌سازی بر اساس انتخاب کاربر | ۴ـ| Count() | محاسبه تعداد کل رکوردها | ۵ـ| Skip/Take | صفحه‌بندی واقعی | ۶ـ| Select() | خروجی سبک و قابل کنترل | ۷ـ| ViewBag | ارسال اطلاعات به View برای نمایش صفحه‌بندی و فیلترها 🧩 بخش‌های قابل حذف یا اختیاری در اکشن Index | بخش | کاربرد | آیا می‌تونی حذفش کنی؟ | |------|--------|------------------------| ۱ـ| AsNoTracking() | سبک‌سازی کوئری فقط خواندنی | ✅ اگر نیاز به ویرایش نداری، بهتره باشه | ۲ـ| فیلتر statusFilter | نمایش فقط کتاب‌های موجود یا فروخته‌شده | ✅ اگر همه کتاب‌ها رو می‌خوای، می‌تونی حذفش کنی | ۳ـ| جستجو search | پیدا کردن کتاب یا نویسنده با متن واردشده | ✅ اگر صفحه‌ات جستجو نداره، حذفش مشکلی نداره | ۴ـ| مرتب‌سازی sort | نمایش بر اساس عنوان یا وضعیت یا تاریخ | ✅ اگر ترتیب خاصی نمی‌خوای، می‌تونی حذفش کنی یا فقط یه OrderBy ساده بذاری | ۵ـ| صفحه‌بندی Skip/Take | نمایش فقط بخشی از داده‌ها در هر صفحه | ✅ اگر تعداد داده‌ها کم باشه، می‌تونی حذفش کنی و همه رو نشون بدی | ۶ـ| Select() | انتخاب فیلدهای مورد نیاز | ✅ اگر کل مدل رو می‌خوای، می‌تونی حذفش کنی و فقط ToList() بزنی | ۷ـ| ViewBag | ارسال داده‌ها به View برای نمایش فیلتر و صفحه‌بندی | ✅ اگر View ساده‌ست و این اطلاعات رو نمی‌خوای، حذفش مشکلی نداره --- 🎯 مثال ساده‌شده بدون فیلتر و صفحه‌بندی
csharp
var books = _context.Books
    .AsNoTracking()
    .OrderBy(b => b.Title)
    .Select(b => new
    {
        b.Id,
        b.Title,
        AuthorName = b.Author.FullName
    })
    .ToList();

return View(books);
✅ این نسخه برای لیست ساده کتاب‌ها بدون جستجو، فیلتر، یا صفحه‌بندی مناسبه
پروژه ASP.Net Core MVC (وب و سی شارپ)
صفر تا صد بهینه سازی کوئری در EF Core ساخته شده از هوش مصنوعی
چرا ترتیب مراحل کوئری در EF Core مهمه، باید بدونی که این ترتیب فقط برای زیبایی نیست—بلکه مستقیماً روی عملکرد، بهینه‌سازی، امنیت و خوانایی کد تأثیر می‌ذاره. بیا با هم یه پادکست آموزشی طراحی کنیم که هم شنیدنی باشه، هم کاربردی، و هم پر از مثال واقعی. --- 🎧 عنوان پادکست: «چرا ترتیب مراحل کوئری در EF Core مهمه؟ از AsNoTracking تا ToList» --- 🎙️ امروز می‌خوایم درباره‌ی یکی از مهم‌ترین اصول EF Core صحبت کنیم: ترتیب نوشتن کوئری‌ها. شاید فکر کنی ترتیب مهم نیست، ولی در واقع این ترتیب می‌تونه تفاوت بین یه کوئری سریع و یه کوئری کند باشه. پس با من همراه باش تا مرحله‌به‌مرحله بررسی کنیم. --- 🧩 مرحله 1: AsNoTracking() – سبک‌سازی از ابتدا وقتی می‌دونی داده فقط برای نمایش هست و قرار نیست تغییرش بدی، بهتره از همون اول بگی EF Core ردیابی نکنه. اگر بذاری آخر کوئری، EF از قبل ردیابی کرده و دیگه فایده‌ای نداره. 📌 پس باید اول بیاد تا کل کوئری سبک بشه. --- 🧩 مرحله 2 و 3: Where() و جستجو – حذف داده‌های اضافی قبل از هر چیز اگه اول Include یا Select بزنی و بعد Where، ممکنه کلی داده بیاد که اصلاً لازم نداری. مثل اینه که اول همه کتاب‌ها رو بیاری، بعد بگی فقط اونایی که موجودن رو نگه دار. 📌 پس اول فیلتر کن، بعد ادامه بده. --- 🧩 مرحله 4: OrderBy() – مرتب‌سازی قبل از صفحه‌بندی اگه قبل از Skip مرتب‌سازی نکنی، صفحه‌بندی بی‌معنی می‌شه. چون ترتیب مشخص نیست و هر بار داده‌ها جابه‌جا می‌شن. 📌 پس اول مرتب کن، بعد صفحه‌بندی کن. --- 🧩 مرحله 5 و 6: Skip() و Take() – کنترل حجم داده اینجا مشخص می‌کنی چند رکورد رد بشه و چند تا گرفته بشه. اگه اینو بعد از ToList() بزنی، کل داده‌ها لود می‌شن و فقط در حافظه فیلتر می‌شن—که خیلی سنگینه. 📌 پس قبل از ToList() باید باشه تا در سطح دیتابیس اجرا بشه. --- 🧩 مرحله 7: Select() – فقط فیلدهای لازم اگه کل موجودیت رو بیاری (Product یا Book) ولی فقط Title و Price رو لازم داشته باشی، داری حافظه رو بی‌خود پر می‌کنی. با Select فقط اون چیزی که لازم داری رو می‌گیری. 📌 بهتره بعد از فیلتر و صفحه‌بندی باشه، چون روی داده‌های نهایی اعمال می‌شه. --- 🧩 مرحله 8: ToList() – اجرای نهایی تا اینجا فقط کوئری ساخته شده. با ToList() یا ToListAsync() کوئری اجرا می‌شه و داده‌ها وارد حافظه می‌شن. اگه زودتر بزنی، همه چیز در حافظه انجام می‌شه و بهینه نیست. 📌 پس همیشه آخر باشه. --- 🎯 جمع‌بندی پادکست ترتیب مراحل کوئری در EF Core فقط یه توصیه نیست—یه اصل مهمه برای: - بهینه‌سازی عملکرد - کاهش مصرف حافظه - جلوگیری از بارگذاری غیرضروری - افزایش خوانایی و تست‌پذیری کد
✅ کوئری کامل و بهینه برای پروژه کتابخانه با همه ویژگی‌هایی که گفتی
csharp
var query = _context.Books
    .AsNoTracking() // 1️⃣ سبک‌سازی کوئری فقط خواندنی

    // 2️⃣ فیلتر وضعیت کتاب (موجود یا فروخته‌شده)
    .Where(b => statusFilter == "available" ? b.IsAvailable :
                statusFilter == "sold" ? !b.IsAvailable : true)

    // 3️⃣ جستجو در عنوان کتاب یا نام نویسنده
    .Where(b => string.IsNullOrEmpty(search) ||
                b.Title.Contains(search) ||
                b.Author.FullName.Contains(search))

    // 4️⃣ مرتب‌سازی بر اساس تاریخ ثبت (جدیدترین یا قدیمی‌ترین)
    .OrderByDescending(b => sort == "new" ? b.Id : 0)
    .ThenBy(b => sort == "old" ? b.Id : 0)

    // 5️⃣ صفحه‌بندی بر اساس تعداد کل رکوردها و صفحه فعلی
    .Skip((page - 1) * pageSize)
    .Take(pageSize)

    // 6️⃣ انتخاب فیلدهای مورد نیاز برای نمایش
    .Select(b => new
    {
        b.Id,
        b.Title,
        b.IsAvailable,
        AuthorName = b.Author.FullName
    })

    // 7️⃣ اجرای کوئری و گرفتن داده‌ها
    .ToList();
🔍 تفاوت‌های اصلی بین دو روش | تفاوت | روش اول (if و switch) | روش دوم (شرط داخل Where و OrderBy) | |-------|-----------------------------|----------------------------------------| | سبک نوشتن | مرحله‌مرحله با شرط‌های جدا | همه‌چیز در یک زنجیره‌ی متصل | | خوانایی | ✅ واضح‌تر برای مبتدی‌ها | کمی فشرده‌تر ولی حرفه‌ای‌تر | | انعطاف‌پذیری | راحت‌تر برای شرط‌های پیچیده | مناسب برای کوئری‌های ساده و مستقیم | | قابل تست بودن | می‌تونی هر مرحله رو جدا تست بزنی | سخت‌تر برای دیباگ مرحله‌ای | | کنترل منطق | شرط‌ها جدا و قابل تغییر | شرط‌ها داخل کوئری، کمتر قابل تغییر در لحظه | | مناسب برای پروژه‌های بزرگ | ✅ بهتر برای منطق پیچیده | مناسب برای لیست‌های سبک و سریع | | تعداد متغیرها | از query چند بار استفاده می‌شه | فقط یک بار تعریف و استفاده می‌شه |
BookSelect.zip
حجم: 17.6M
پروژه مدیریت نویسنده و کتاب