PositionController.cs 4.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131
  1. using System.Diagnostics;
  2. using bitforum.Models;
  3. using bitforum.Models.Page.Banner;
  4. using Microsoft.AspNetCore.Authorization;
  5. using Microsoft.AspNetCore.Mvc;
  6. using Microsoft.EntityFrameworkCore;
  7. namespace bitforum.Controllers.Page
  8. {
  9. [Authorize]
  10. [Route("Page")]
  11. public class PositionController : Controller
  12. {
  13. private readonly ILogger<PositionController> _logger;
  14. private readonly DefaultDbContext _db;
  15. private readonly string _ViewPath = "~/Views/Page/Banner/Position/Index.cshtml";
  16. public PositionController(ILogger<PositionController> logger, DefaultDbContext db)
  17. {
  18. _logger = logger;
  19. _db = db;
  20. }
  21. [ResponseCache(Duration = 0, Location = ResponseCacheLocation.None, NoStore = true)]
  22. public IActionResult Error()
  23. {
  24. return View(new ErrorViewModel { RequestId = Activity.Current?.Id ?? HttpContext.TraceIdentifier });
  25. }
  26. [HttpGet("Banner")]
  27. public IActionResult Index()
  28. {
  29. ViewBag.BannerPositions = _db.BannerPosition.Include(c => c.BannerItem).ToList();
  30. return View(_ViewPath);
  31. }
  32. [HttpPost("Banner")]
  33. public async Task<IActionResult> Save([FromForm] List<BannerPosition> request)
  34. {
  35. using var transaction = await _db.Database.BeginTransactionAsync();
  36. try
  37. {
  38. if (request == null || !request.Any())
  39. {
  40. // 전체 삭제
  41. var bannerPositions = await _db.BannerPosition.ToListAsync();
  42. if (bannerPositions.Any())
  43. {
  44. _db.BannerPosition.RemoveRange(bannerPositions);
  45. await _db.SaveChangesAsync();
  46. }
  47. await transaction.CommitAsync();
  48. return RedirectToAction("Index");
  49. }
  50. if (!ModelState.IsValid)
  51. {
  52. throw new Exception("유효성 검사에 실패하였습니다.");
  53. }
  54. var requestIds = request.Select(x => x.ID).ToList(); // 요청 데이터의 ID 목록
  55. var existingIds = await _db.BannerPosition.Select(c => c.ID).ToListAsync(); // 데이터베이스에 존재하는 ID 목록
  56. var idsToDelete = existingIds.Except(requestIds).ToList(); // 삭제 대상 ID: 요청 데이터에 없는 항목
  57. // 삭제 대상 항목 제거
  58. if (idsToDelete.Any())
  59. {
  60. var selectedRows = await _db.BannerPosition.Where(c => idsToDelete.Contains(c.ID) && !c.BannerItem.Any()).ToListAsync();
  61. _db.BannerPosition.RemoveRange(selectedRows);
  62. }
  63. foreach (var row in request)
  64. {
  65. // 중복 확인
  66. if (await _db.BannerPosition.AnyAsync(c => c.Code == row.Code && c.ID != row.ID))
  67. {
  68. throw new Exception($"이미 존재하는 배너 위치입니다: {row.Code}");
  69. }
  70. if (row.ID == 0)
  71. {
  72. row.UpdatedAt = null;
  73. row.CreatedAt = DateTime.Now;
  74. await _db.BannerPosition.AddAsync(row);
  75. }
  76. else
  77. {
  78. var existing = await _db.BannerPosition.FirstOrDefaultAsync(c => c.ID == row.ID);
  79. if (existing == null)
  80. {
  81. throw new Exception($"ID {row.ID}에 해당하는 데이터가 없습니다.");
  82. }
  83. existing.Code = row.Code;
  84. existing.Subject = row.Subject;
  85. existing.IsActive = row.IsActive;
  86. existing.UpdatedAt = DateTime.Now;
  87. _db.BannerPosition.Update(existing);
  88. }
  89. }
  90. await transaction.CommitAsync();
  91. int affectedRows = await _db.SaveChangesAsync();
  92. if (affectedRows <= 0)
  93. {
  94. throw new Exception("배너 위치 저장 중 오류가 발생했습니다.");
  95. }
  96. string message = "배너 위치가 정상적으로 저장되었습니다.";
  97. TempData["SuccessMessage"] = message;
  98. _logger.LogInformation(message);
  99. return RedirectToAction("Index");
  100. }
  101. catch (Exception e)
  102. {
  103. await transaction.RollbackAsync();
  104. _logger.LogError(e, e.Message);
  105. TempData["ErrorMessages"] = e.Message;
  106. ViewBag.BannerPositions = _db.BannerPosition.Include(c => c.BannerItem).ToList();
  107. return View(_ViewPath, request);
  108. }
  109. }
  110. }
  111. }