< Summary

Information
Class: OzonOrdersWeb.Areas.Studio2.Controllers.OrderArchiveController
Assembly: OzonOrdersWeb
File(s): /home/runner/work/Studio2Prod/Studio2Prod/OzonOrdersWeb/Areas/Studio2/Controllers/OrderArchiveController.cs
Line coverage
0%
Covered lines: 0
Uncovered lines: 106
Coverable lines: 106
Total lines: 202
Line coverage: 0%
Branch coverage
0%
Covered branches: 0
Total branches: 32
Branch coverage: 0%
Method coverage

Feature is only available for sponsors

Upgrade to PRO version

Metrics

MethodBranch coverage Crap Score Cyclomatic complexity Line coverage
.ctor(...)100%210%
Index()100%210%
GridRows()0%4260%
GridFacets()0%4260%
RestoreOrder()100%210%
RestoreOrderToOrders()100%210%
ArchiveMultiple()0%210140%
ArchiveOrder()0%2040%

File(s)

/home/runner/work/Studio2Prod/Studio2Prod/OzonOrdersWeb/Areas/Studio2/Controllers/OrderArchiveController.cs

#LineLine coverage
 1using Microsoft.AspNetCore.Authorization;
 2using Microsoft.AspNetCore.Mvc;
 3using Newtonsoft.Json;
 4using OzonDomains.Models;
 5using Microsoft.EntityFrameworkCore;
 6using OzonDomains.Models.Authorization.Enums;
 7using OzonOrdersWeb.Authorization;
 8using OzonOrdersWeb.WebServices.Grid;
 9using OzonOrdersWeb.WebServices.Journals;
 10using OzonRepositories.Context;
 11using Services.DataServices;
 12
 13namespace OzonOrdersWeb.Areas.Studio2.Controllers
 14{
 15    [Area("Studio2")]
 16    [Authorize(Roles = "User,Admin")]
 17    public class OrderArchiveController : Controller
 18    {
 19        private readonly OrderArchiveDataService _orderArchiveService;
 20        private readonly ApplicationDbContext _context;
 21
 022        public OrderArchiveController(OrderArchiveDataService orderArchiveService, ApplicationDbContext context)
 23        {
 024            _orderArchiveService = orderArchiveService;
 025            _context = context;
 026        }
 27
 28        private const string PageCode = "Studio2.OrderArchive.Index";
 29
 30        /// <summary>Каркас страницы: строки архива грид подгружает блоками через <see cref="GridRows"/>.</summary>
 31        public async Task<IActionResult> Index(CancellationToken cancellationToken)
 32        {
 033            ViewBag.TotalCount = await _context.OrderArchives.CountAsync(cancellationToken);
 034            return View();
 035        }
 36
 37        [HttpPost("Studio2/OrderArchive/grid")]
 38        [ValidateAntiForgeryToken]
 39        [PageAuthorize(PageCode, AccessType.View)]
 40        public async Task<IActionResult> GridRows([FromBody] ServerGridRequest? request, CancellationToken cancellationT
 41        {
 042            var error = ServerGridQuery.Validate(request);
 043            if (error != null) return BadRequest(new { success = false, error });
 44
 045            var def = JournalGridDefinitions.OrderArchive;
 046            var filtered = ServerGridQuery.ApplyFilters(_context.OrderArchives.AsNoTracking(), def, request!);
 047            var total = await filtered.CountAsync(cancellationToken);
 048            var start = Math.Max(0, request!.StartRow);
 049            var take = Math.Clamp(request.EndRow - start, 1, ServerGridQuery.MaxBlockSize);
 050            var page = start >= total
 051                ? []
 052                : await ServerGridQuery.ApplySort(filtered, def, request.SortModel).Skip(start).Take(take)
 053                    .Select(a => new
 054                    {
 055                        a.Id, a.OrderId, a.ArchivedAt, a.ArchivedBy, a.ArchiveReason,
 056                        a.Order.ShipmentNumber, a.Order.ProcessingDate, a.Order.ProductName, a.Order.Article,
 057                        a.Order.Quantity, a.Order.ProductKey, a.Order.PurchasePrice,
 058                        AppStatus = a.Order.AppStatus != null ? a.Order.AppStatus.Name : null,
 059                        ClientStatus = a.Order.ClientStatus != null ? a.Order.ClientStatus.Name : null,
 060                        ClientName = a.Order.OzonClient != null ? a.Order.OzonClient.Name : null,
 061                        ImageUrl = a.Order.ProductInfo != null ? a.Order.ProductInfo.ImageUrl : null
 062                    })
 063                    .ToListAsync(cancellationToken);
 64            // Количество — с кратностью упаковки из ключа товара, как «Истинное количество» в заказах.
 065            var rows = page.Select(a => new
 066            {
 067                a.Id, a.OrderId, a.ArchivedAt, a.ArchivedBy, a.ArchiveReason, a.ShipmentNumber, a.ProcessingDate,
 068                a.ProductName, a.Article, a.Quantity,
 069                TrueQuantity = a.Quantity.HasValue ? Order.ApplyProductKeyMultiplier(a.Quantity.Value, a.ProductKey) : (
 070                a.PurchasePrice, a.AppStatus, a.ClientStatus, a.ClientName, a.ImageUrl
 071            }).ToList();
 072            var lastRow = start + rows.Count >= total ? total : -1;
 073            return Ok(new { success = true, rows, totalCount = total, lastRow });
 074        }
 75
 76        [HttpPost("Studio2/OrderArchive/grid/facets")]
 77        [ValidateAntiForgeryToken]
 78        [PageAuthorize(PageCode, AccessType.View)]
 79        public async Task<IActionResult> GridFacets([FromBody] ServerGridRequest? request, CancellationToken cancellatio
 80        {
 081            if (request is null || string.IsNullOrWhiteSpace(request.ColId)) return BadRequest(new { success = false, er
 082            request.StartRow = 0;
 083            request.EndRow = 1;
 084            var error = ServerGridQuery.Validate(request);
 085            if (error != null) return BadRequest(new { success = false, error });
 086            var values = await ServerGridQuery.FacetsAsync(_context.OrderArchives.AsNoTracking(), JournalGridDefinitions
 087            return Ok(new { success = true, values });
 088        }
 89
 90        // POST: Studio2/OrderArchive/RestoreOrder/5
 91        [HttpPost]
 92        public async Task<IActionResult> RestoreOrder(int id)
 93        {
 94            try
 95            {
 096                await _orderArchiveService.RestoreFromArchiveAsync(id);
 097                TempData["SuccessMessage"] = "Заказ успешно восстановлен из архива";
 098            }
 099            catch (Exception ex)
 100            {
 0101                TempData["ErrorMessage"] = $"Ошибка при восстановлении заказа: {ex.Message}";
 0102            }
 103
 0104            return RedirectToAction(nameof(Index));
 0105        }
 106
 107        // POST: Studio2/OrderArchive/RestoreOrderToOrders/5
 108        [HttpPost]
 109        public async Task<IActionResult> RestoreOrderToOrders(int id, int page = 1)
 110        {
 111            try
 112            {
 0113                await _orderArchiveService.RestoreFromArchiveAsync(id);
 0114                TempData["SuccessMessage"] = "Заказ успешно восстановлен из архива";
 0115            }
 0116            catch (Exception ex)
 117            {
 0118                TempData["ErrorMessage"] = $"Ошибка при восстановлении заказа: {ex.Message}";
 0119            }
 120
 0121            HttpContext.Session.SetString("selectedIds", JsonConvert.SerializeObject(new List<int>()));
 0122            return RedirectToAction(
 0123                "Index",
 0124                "Orders",
 0125                new { area = "Studio2", page = page }
 0126            );
 0127        }
 128
 129        // POST: Studio2/OrderArchive/ArchiveMultiple
 130        [HttpPost]
 131        public async Task<IActionResult> ArchiveMultiple(string orderIds, int page = 1)
 132        {
 0133            if (string.IsNullOrEmpty(orderIds))
 134            {
 0135                TempData["ErrorMessage"] = "Не выбраны заказы для архивации";
 0136                return RedirectToAction("Index", "Orders", new { page });
 137            }
 138
 139            // Парсим строку с ID в список
 0140            var orderIdList = orderIds.Split(',')
 0141                .Where(id => !string.IsNullOrEmpty(id))
 0142                .Select(id => int.Parse(id.Trim()))
 0143                .ToList();
 144
 0145            var successCount = 0;
 0146            var errorCount = 0;
 147
 0148            foreach (var orderId in orderIdList)
 149            {
 150                try
 151                {
 0152                    if (!await _orderArchiveService.IsOrderArchivedAsync(orderId))
 153                    {
 0154                        await _orderArchiveService.ArchiveOrderAsync(orderId, User.Identity?.Name ?? "System",
 0155                            "Массовая архивация");
 0156                        successCount++;
 157                    }
 0158                }
 0159                catch
 160                {
 0161                    errorCount++;
 0162                }
 163            }
 164
 0165            if (successCount > 0)
 166            {
 0167                TempData["SuccessMessage"] = $"Успешно архивировано заказов: {successCount}";
 168            }
 169
 0170            if (errorCount > 0)
 171            {
 0172                TempData["ErrorMessage"] = $"Не удалось архивировать заказов: {errorCount}";
 173            }
 174
 0175            HttpContext.Session.SetString("selectedIds", JsonConvert.SerializeObject(new List<int>()));
 0176            return RedirectToAction("Index", "Orders", new { area = "Studio2", page = page });
 0177        }
 178
 179        // POST: Studio2/OrderArchive/ArchiveOrder
 180        [HttpPost]
 181        public async Task<IActionResult> ArchiveOrder(int id, int page = 1)
 182        {
 183            try
 184            {
 0185                await _orderArchiveService.ArchiveOrderAsync(id, User.Identity?.Name ?? "System",
 0186                    "Одиночная архивация");
 0187                TempData["SuccessMessage"] = "Заказ успешно архивирован";
 0188            }
 0189            catch (Exception ex)
 190            {
 0191                TempData["ErrorMessage"] = $"Ошибка при архивации заказа: {ex.Message}";
 0192            }
 193
 0194            HttpContext.Session.SetString("selectedIds", JsonConvert.SerializeObject(new List<int>()));
 0195            return RedirectToAction(
 0196                "Index",
 0197                "Orders",
 0198                new { area = "Studio2", page = page }
 0199            );
 0200        }
 201    }
 202}