InterestApp.zip
حجم:
23.2M
پروژه با یک جدول ساخته شده ولی جالب اینجاست که با یک ستون دیتابیس چند داده ذخیره کنید
پروژه ASP.Net Core MVC (وب و سی شارپ)
پروژه با یک جدول ساخته شده ولی جالب اینجاست که با یک ستون دیتابیس چند داده ذخیره کنید
بذار یک توضیح کامل و آماده برای انتشار دربارهی پروژهای که با یک جدول و CheckBox ساختهای بنویسم. این متن میتونه بهعنوان معرفی پروژه در وبلاگ یا شبکههای اجتماعی استفاده بشه:
---
## 📌 معرفی پروژه CRUD علاقهمندیها با یک جدول و CheckBox
### 🔹 ساختار پروژه
این پروژه با استفاده از ASP.NET Core MVC طراحی شده و هدف آن مدیریت علاقهمندیهای کاربران است. دادهها در یک جدول ساده ذخیره میشوند و کاربر میتواند چند علاقهمندی را همزمان انتخاب کند.
### 🔹 مدل داده
مدل اصلی پروژه شامل یک جدول به نام Interests است که دارای ستونهای زیر میباشد:
-
Id→ شناسه یکتا -
Name→ نام کاربر یا آیتم -
SelectedInterests→ علاقهمندیهای انتخابشده (به صورت رشته ذخیره میشوند، مثلاً
"Music,Sport,Travel") ### 🔹 امکانات پروژه 1. افزودن علاقهمندیها (Create) - کاربر میتواند نام خود را وارد کند. - چند علاقهمندی را با CheckBox انتخاب کند (موسیقی، ورزش، سفر، مطالعه). - انتخابها در ستون
SelectedInterestsذخیره میشوند. 2. ویرایش علاقهمندیها (Edit) - کاربر میتواند رکورد موجود را باز کند. - CheckBoxها بر اساس انتخابهای قبلی پر میشوند (Checked). - تغییرات ذخیره میشوند و رشتهی جدید جایگزین قبلی میشود. 3. نمایش لیست (Index) - همه رکوردها در قالب جدول نمایش داده میشوند. - علاقهمندیها به صورت فارسی و جداشده با "،" نمایش داده میشوند. 4. جزئیات (Details) - نمایش اطلاعات کامل یک رکورد شامل نام و علاقهمندیهای انتخابشده. - علاقهمندیها با نگاشت به فارسی نمایش داده میشوند. 5. حذف (Delete) - امکان حذف رکورد از جدول وجود دارد. --- ### 🔹 نحوه ذخیرهسازی - وقتی کاربر چند CheckBox انتخاب میکند، مقادیر انتخابی در یک رشته با جداکنندهی کاما ذخیره میشوند. - مثال: اگر کاربر موسیقی و سفر را انتخاب کند، در دیتابیس اینطور ذخیره میشود:
Music,Travel- در نمایش (Index و Details)، این رشته به لیست تبدیل شده و با نگاشت به فارسی نمایش داده میشود:
موسیقی، سفر--- ## 🎯 نتیجه این پروژه یک نمونهی ساده و کاربردی از CRUD با یک جدول و CheckBox است که امکانات زیر را فراهم میکند: - مدیریت علاقهمندیها (افزودن، ویرایش، حذف، جزئیات) - انتخاب چند گزینه با CheckBox - ذخیره دادهها در یک ستون رشتهای - نمایش علاقهمندیها به صورت فارسی در لیست و جزئیات --- وقتی پروژه رو معرفی کردی (CRUD علاقهمندیها با یک جدول و CheckBox)، برای بخش ادامه توضیحات میتونی روی دو محور تمرکز کنی: --- ## 🔹 اصولی بودن پروژه - سادگی و آموزشمحور بودن: پروژه با یک جدول ساخته شده تا مفاهیم پایهی CRUD (افزودن، ویرایش، حذف، جزئیات) به شکل ساده و قابل فهم تمرین بشه. - استفاده از CheckBox: این انتخاب باعث میشه کاربر بتونه چند گزینه رو همزمان انتخاب کنه و درک بهتری از نحوهی کار فرمها و ارسال دادهها داشته باشه. - ذخیرهسازی رشتهای: علاقهمندیها در یک ستون رشتهای ذخیره میشن. این روش برای پروژههای آموزشی سریع و ساده است، هرچند در پروژههای بزرگتر محدودیتهایی داره. - نمایش فارسی: دادهها به صورت انگلیسی ذخیره میشن ولی در رابط کاربری به فارسی نمایش داده میشن، که هم استاندارد دیتابیس رعایت میشه و هم تجربه کاربری بهتره. --- ## 🔹 مسیر توسعه و ارتقا - جدول واسط (Many-to-Many): در نسخهی پیشرفته میتونی علاقهمندیها رو در یک جدول جدا ذخیره کنی و با جدول واسط به کاربر وصل کنی. این کار جستجو و گزارشگیری رو خیلی راحتتر میکنه. - مدیریت پویا: علاقهمندیها به جای اینکه ثابت باشن (Music, Sport, Travel)، میتونن از دیتابیس خوانده بشن و کاربر یا مدیر سیستم بتونه گزینههای جدید اضافه کنه. - فیلتر و جستجو: میتونی صفحهای بسازی که کاربرها رو بر اساس علاقهمندیها فیلتر کنه (مثلاً همه کسانی که علاقهمند به ورزش هستن). - رابط کاربری بهتر: استفاده از TagHelper یا Component برای نمایش CheckBoxها به صورت پویا و زیباتر. - اعتبارسنجی و امنیت: اضافه کردن Validation برای اطمینان از اینکه کاربر حتماً یک یا چند علاقهمندی انتخاب کرده و دادهها درست ذخیره میشن. ---
پروژه ASP.Net Core MVC (وب و سی شارپ)
پروژه با یک جدول ساخته شده ولی جالب اینجاست که با یک ستون دیتابیس چند داده ذخیره کنید
## 🎯 متن آماده برای انتشار
«این پروژه یک نمونهی آموزشی CRUD با ASP.NET Core MVC است که با یک جدول ساده ساخته شده و علاقهمندیهای کاربران را مدیریت میکند. کاربر میتواند چند علاقهمندی را با CheckBox انتخاب کند و دادهها در یک ستون رشتهای ذخیره میشوند. در رابط کاربری، علاقهمندیها به صورت فارسی نمایش داده میشوند. این پروژه برای یادگیری اصولی CRUD و کار با فرمها بسیار مناسب است. در نسخههای توسعهیافته میتوان از جدول واسط برای ذخیرهسازی استاندارد، مدیریت پویا علاقهمندیها، فیلتر و جستجو بر اساس علاقهمندیها و رابط کاربری پیشرفتهتر استفاده کرد.»
بلاخره من موفق شدم ویدئو ضبط کنم و این دفعه اولمه کامل و بدونه صدا ضبط کنم
نمیدونم چرا برای من ویدئو ضبط کردن سخته؟
NameApp2.zip
حجم:
23.3M
لاگ نویسی پروژه فرقی نمیکنه چی باشه این پروژه برای پروژه های بزرگ هم کار میکند
پروژه ASP.Net Core MVC (وب و سی شارپ)
لاگ نویسی پروژه فرقی نمیکنه چی باشه این پروژه برای پروژه های بزرگ هم کار میکند
// مسیر پوشه لاگها را مشخص میکنیم (داخل wwwroot/logs)
var folderPath = Path.Combine(Directory.GetCurrentDirectory(), "wwwroot", "logs");
// اگر پوشه وجود نداشت، ساخته میشود
Directory.CreateDirectory(folderPath);
// نام فایل لاگ را با تاریخ و ساعت جاری میسازیم (هر بار اجرا یک فایل جدید)
var logFilePath = Path.Combine(folderPath, $"eflog_{DateTime.Now:yyyyMMdd_HHmmss}.txt");
// فایل را باز میکنیم با اجازهی اشتراکگذاری (FileShare.ReadWrite)
// تا چند پروسه بتوانند همزمان به آن دسترسی داشته باشند
var fileStream = new FileStream(logFilePath, FileMode.Append, FileAccess.Write, FileShare.ReadWrite);
// یک StreamWriter روی فایل ایجاد میکنیم و AutoFlush را فعال میکنیم
// تا هر خط بلافاصله نوشته شود و نیازی به Close دستی نباشد
var writer = new StreamWriter(fileStream) { AutoFlush = true };
// ثبت DbContext در DI Container (Dependency Injection)
// اینجا EF Core را تنظیم میکنیم تا:
// 1. از ConnectionString موجود در appsettings.json استفاده کند
// 2. SensitiveDataLogging فعال باشد (پارامترهای کوئری هم نمایش داده شوند)
// 3. همهی کوئریها در فایل لاگ نوشته شوند
builder.Services.AddDbContext<AppDbContext>(options =>
options.UseSqlServer(builder.Configuration.GetConnectionString("DefaultConnection"))
.EnableSensitiveDataLogging()
.LogTo(writer.WriteLine, LogLevel.Information));
پروژه ASP.Net Core MVC (وب و سی شارپ)
لاگ نویسی پروژه فرقی نمیکنه چی باشه این پروژه برای پروژه های بزرگ هم کار میکند
## 📌 معرفی پروژه لاگنویسی EF Core در پروژه NameApp2
### 🔹 هدف پروژه
این پروژه با استفاده از ASP.NET Core MVC و Entity Framework Core طراحی شده تا تمام کوئریهای اجرا شده توسط EF Core را در فایل متنی ذخیره کند. هدف اصلی، مانیتورینگ و بررسی کوئریها برای یادگیری و تحلیل عملکرد دیتابیس است.
---
### 🔹 ساختار پروژه
- Program
به گونهای تنظیم شده که هنگام اجرای برنامه، یک فایل جدید در مسیر
wwwroot/logsساخته میشود. - نام فایل شامل تاریخ و ساعت اجراست (مثلاً
eflog_20260101_220000.txt). - همهی کوئریهای EF Core در این فایل ثبت میشوند. --- ### 🔹 امکانات پروژه 1. ایجاد فایل لاگ جدید در هر اجرا - هر بار پروژه اجرا شود، یک فایل جدید ساخته میشود. - این فایل شامل تمام کوئریهای SQL تولید شده توسط EF Core است. 2. ذخیره کوئریها با جزئیات کامل - متن کامل کوئریها (SELECT, INSERT, UPDATE, DELETE) ثبت میشود. - با فعال بودن `EnableSensitiveDataLogging`، پارامترهای کوئری نیز نمایش داده میشوند. 3. مدیریت پوشه لاگها - اگر پوشهی
wwwroot/logsوجود نداشته باشد، به صورت خودکار ساخته میشود. - فایلها به صورت مرتب و قابل دسترسی ذخیره میشوند. 4. قابلیت توسعه - میتوان لاگها را به جای فایل، در دیتابیس یا سرویسهای مانیتورینگ (مثل Seq یا ELK) ذخیره کرد. - امکان استفاده از کتابخانههای حرفهای مثل Serilog یا NLog برای مدیریت بهتر لاگها وجود دارد. --- ### 🔹 نمونه کاربرد - بررسی کوئریهای تولید شده توسط EF Core برای یادگیری. - تحلیل عملکرد دیتابیس و پیدا کردن کوئریهای سنگین. - مستندسازی کوئریها برای آموزش یا انتشار. --- ## 🎯 نتیجه این پروژه یک نمونهی ساده و آموزشی است که نشان میدهد چگونه میتوان کوئریهای EF Core را در فایل متنی ذخیره کرد. کاربرد اصلی آن برای یادگیری، مانیتورینگ و تحلیل کوئریها است و میتواند پایهای برای پروژههای بزرگتر با سیستم لاگ حرفهای باشد.
PictureApp.zip
حجم:
23.4M
اینکه دو پروژهی جدا (CRUD تصویر و CRUD فایل) رو در یک پروژه ترکیب کردی، یعنی الان دو کنترلر داری که هر کدوم مسئولیت متفاوتی دارن. بذار مرحلهبهمرحله توضیح بدم:
پروژه ASP.Net Core MVC (وب و سی شارپ)
اینکه دو پروژهی جدا (CRUD تصویر و CRUD فایل) رو در یک پروژه ترکیب کردی، یعنی الان دو کنترلر داری که
## 🔹 کنترلر اول: PicturesController
این کنترلر مخصوص مدیریت تصاویر هست:
- Index
→ لیست همه تصاویر ذخیرهشده در دیتابیس رو نمایش میده.
- Create (GET/POST)
→ کاربر میتونه یک تصویر آپلود کنه. تصویر در پوشهی
wwwroot/imagesذخیره میشه و مسیرش در دیتابیس ثبت میشه. - Edit (GET/POST) → کاربر میتونه توضیحات تصویر رو تغییر بده یا تصویر جدید جایگزین کنه. اگر تصویر جدید آپلود بشه، تصویر قبلی حذف میشه. - Delete → تصویر از دیتابیس و فایل فیزیکی از پوشه حذف میشه. - نمایش در ویو → تصاویر با
<img src="~/images/...">نمایش داده میشن. 👉 این کنترلر بیشتر برای گالری عکس، پروفایل کاربری یا نمایش بصری استفاده میشه. --- ## 🔹 کنترلر دوم: DocumentsController این کنترلر مخصوص مدیریت فایلهای عمومی (PDF، Word، ZIP و …) هست: - Index → لیست همه فایلها رو نمایش میده همراه با توضیحات. - Create (GET/POST) → کاربر میتونه یک فایل آپلود کنه. فایل در پوشهی
wwwroot/filesذخیره میشه و نام اصلی + مسیر ذخیره در دیتابیس ثبت میشه. - Edit (GET/POST) → کاربر میتونه توضیحات فایل رو تغییر بده یا فایل جدید جایگزین کنه. فایل قبلی حذف و فایل جدید ذخیره میشه. - Download → کاربر میتونه فایل رو دانلود کنه. اینجا کنترلر فایل رو از پوشه میخونه و با متد
File()به کاربر برمیگردونه. - Delete → فایل از دیتابیس و پوشه حذف میشه. 👉 این کنترلر بیشتر برای مدیریت اسناد، فایلهای آموزشی یا دانلودی استفاده میشه. --- ## 🔹 تفاوت اصلی دو کنترلر - PicturesController → تمرکز روی نمایش بصری (
<img>). - DocumentsController → تمرکز روی دانلود فایل (
File()در کنترلر). - هر دو از یک الگو استفاده میکنن: - آپلود → ذخیره در پوشه + ثبت در دیتابیس - ویرایش → تغییر توضیحات یا جایگزینی فایل - حذف → پاک کردن رکورد + فایل فیزیکی --- ## 🎯 جمعبندی الان پروژهات دو بخش داره: - بخش مدیریت تصاویر (نمایش مستقیم در صفحه) - بخش مدیریت فایلها (دانلود توسط کاربر) هر دو کنترلر ساختار مشابه دارن، فقط فرقشون در نوع نمایش خروجی هست: - تصاویر با
<img>نمایش داده میشن. - فایلها با لینک دانلود برگردونده میشن.
// مسیر پوشه لاگها را مشخص میکنیم (داخل wwwroot/logs)
var folderPath = Path.Combine(Directory.GetCurrentDirectory(), "wwwroot", "logs");
// اگر پوشه وجود نداشت، ساخته میشود
Directory.CreateDirectory(folderPath);
// نام فایل لاگ را با تاریخ و ساعت جاری میسازیم (هر بار اجرا یک فایل جدید)
var logFilePath = Path.Combine(folderPath, $"eflog_{DateTime.Now:yyyyMMdd_HHmmss}.txt");
// فایل را باز میکنیم با اجازهی اشتراکگذاری (FileShare.ReadWrite)
// تا چند پروسه بتوانند همزمان به آن دسترسی داشته باشند
var fileStream = new FileStream(logFilePath, FileMode.Append, FileAccess.Write, FileShare.ReadWrite);
// یک StreamWriter روی فایل ایجاد میکنیم و AutoFlush را فعال میکنیم
// تا هر خط بلافاصله نوشته شود و نیازی به Close دستی نباشد
var writer = new StreamWriter(fileStream) { AutoFlush = true };
// ثبت DbContext در DI Container (Dependency Injection)
// اینجا EF Core را تنظیم میکنیم تا:
// 1. از ConnectionString موجود در appsettings.json استفاده کند
// 2. SensitiveDataLogging فعال باشد (پارامترهای کوئری هم نمایش داده شوند)
// 3. همهی کوئریها در فایل لاگ نوشته شوند
builder.Services.AddDbContext<AppDbContext>(options =>
options.UseSqlServer(builder.Configuration.GetConnectionString("DefaultConnection"))
.EnableSensitiveDataLogging()
.LogTo(writer.WriteLine, LogLevel.Information));
و
if (file != null)
{
// مسیر پوشه wwwroot/images
var folder = Path.Combine(_env.WebRootPath, "images");
Directory.CreateDirectory(folder);
// نام فایل یکتا
var fileName = Guid.NewGuid() + Path.GetExtension(file.FileName);
var filePath = Path.Combine(folder, fileName);
// ذخیره فایل
using (var stream = new FileStream(filePath, FileMode.Create))
{
file.CopyTo(stream);
}
// ذخیره رکورد در دیتابیس
var pc = new Picture { FileName = fileName , Description = description};
_db.Pictures.Add(pc);
_db.SaveChanges();
return RedirectToAction("Index");
}
شباهت و تفاوت
این دو قطعه کد از نظر ساختار خیلی شبیه هم هستند، اما از نظر هدف کاملاً متفاوتند. بذار دقیق توضیح بدم:
---
## 🔹 شباهتها
1. ساخت پوشه
هر دو با Directory.CreateDirectory(...) مطمئن میشوند که پوشه وجود دارد و اگر نبود ساخته میشود.
- اولی:
wwwroot/logs- دومی:
wwwroot/images2. ساخت نام فایل یکتا هر دو نام فایل را با Guid.NewGuid() و پسوند مناسب میسازند تا فایلها تکراری نشوند. 3. کار با FileStream هر دو از
FileStreamاستفاده میکنند تا روی فایل بنویسند. - اولی: برای نوشتن لاگها (متن کوئریهای EF Core). - دومی: برای ذخیره کردن محتوای آپلود شده (تصویر). 4. ارتباط با دیتابیس هر دو در نهایت یک رکورد در دیتابیس ثبت میکنند: - اولی: EF Core کوئریها را لاگ میکند. - دومی: مسیر و توضیحات تصویر را ذخیره میکند. --- ## 🔹 تفاوتها 1. هدف اصلی - کد اول: مخصوص لاگنویسی EF Core است. یعنی کوئریهای دیتابیس در فایل متنی ذخیره میشوند. - کد دوم: مخصوص آپلود تصویر است. یعنی فایل واقعی (jpg, png و …) در پوشه ذخیره میشود. 2. نوع داده ورودی - کد اول: هیچ ورودی از کاربر نمیگیرد، خودش فایل لاگ میسازد. - کد دوم: ورودی از کاربر (
IFormFile file) میگیرد و آن را ذخیره میکند. 3. نحوه نوشتن در فایل - کد اول: از
StreamWriterاستفاده میکند تا متن (کوئریها) را خطبهخط بنویسد. - کد دوم: از file.CopyTo(stream) استفاده میکند تا کل محتوای فایل آپلود شده کپی شود. 4. محل استفاده - کد اول: در Program.cs یا هنگام تنظیم DbContext استفاده میشود. - کد دوم: در Controller (اکشن Create) استفاده میشود. 5. نوع خروجی - کد اول: خروجیاش یک فایل متنی لاگ است. - کد دوم: خروجیاش یک فایل تصویر است که بعداً در ویو با
<img>نمایش داده میشود. --- ## 🎯 جمعبندی - شباهتها: ساخت پوشه، نام یکتا، کار با FileStream، ثبت در دیتابیس. - تفاوتها: هدف (لاگنویسی vs آپلود تصویر)، نوع داده (متن vs فایل)، محل استفاده (Program.cs vs Controller)، و نوع خروجی (فایل متنی vs تصویر).
برای اینکه ورودی <input type="file"> فقط فرمتهای تصویر رو قبول کنه، باید از ویژگی accept استفاده کنی. این ویژگی مشخص میکنه چه نوع فایلهایی قابل انتخاب باشن.
---
🔹 نمونه کد HTML
html
<form asp-action="Create" enctype="multipart/form-data" method="post">
<div class="form-group">
<label>انتخاب تصویر</label>
<input type="file" name="file" class="form-control"
accept="image/*" /> <!-- فقط همه فرمتهای تصویر -->
</div>
<div class="form-group">
<label>توضیحات</label>
<input type="text" name="description" class="form-control" />
</div>
<button type="submit" class="btn btn-success">ذخیره</button>
</form>
---
🔹 توضیح
- accept="image/*" → یعنی فقط فایلهایی که نوع MIME آنها تصویر است (jpg, png, gif, bmp, webp, svg و …) قابل انتخاب هستند.
- اگر بخوای دقیقتر باشی و فقط چند فرمت خاص رو قبول کنی، میتونی اینطوری بنویسی:
html
<input type="file" name="file"
accept=".jpg,.jpeg,.png,.gif,.bmp,.webp" />
---
🎯 جمعبندی
- برای همهی فرمتهای تصویر → accept="image/*"
- برای فرمتهای خاص → accept=".jpg,.png,.gif"