< Summary

Information
Class: OzonOrdersWeb.Areas.Studio2.Controllers.Directories.StatusTransitionController
Assembly: OzonOrdersWeb
File(s): /home/runner/work/Studio2Prod/Studio2Prod/OzonOrdersWeb/Areas/Studio2/Controllers/Directories/StatusTransitionController.cs
Line coverage
0%
Covered lines: 0
Uncovered lines: 113
Coverable lines: 113
Total lines: 196
Line coverage: 0%
Branch coverage
0%
Covered branches: 0
Total branches: 68
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()0%2040%
Create()100%210%
Create()0%1190340%
Edit()0%620%
Edit()0%272160%
Delete()0%620%
DeleteConfirmed()0%620%
SetStatusSelectLists()0%110100%

File(s)

/home/runner/work/Studio2Prod/Studio2Prod/OzonOrdersWeb/Areas/Studio2/Controllers/Directories/StatusTransitionController.cs

#LineLine coverage
 1using Microsoft.AspNetCore.Authorization;
 2using Microsoft.AspNetCore.Mvc;
 3using Microsoft.AspNetCore.Mvc.Rendering;
 4using OzonDomains;
 5using OzonDomains.Models;
 6using OzonOrdersWeb.WebServices;
 7using Services.DataServices;
 8
 9namespace OzonOrdersWeb.Areas.Studio2.Controllers.Directories
 10{
 11    [Authorize(Roles = "Admin")]
 12    [Area("Studio2")]
 13    public class StatusTransitionController : Controller
 14    {
 15        private readonly StatusTransitionDataServices _statusTransitionServices;
 16        private readonly AppStatusDataServices _appStatusServices;
 17        private readonly TransactionTooltipService _transactionTooltipService;
 18        private readonly TransactionTransitionRuleService _transactionTransitionRuleService;
 19
 020        public StatusTransitionController(
 021            StatusTransitionDataServices statusTransitionServices,
 022            AppStatusDataServices appStatusServices,
 023            TransactionTooltipService transactionTooltipService,
 024            TransactionTransitionRuleService transactionTransitionRuleService)
 25        {
 026            _statusTransitionServices = statusTransitionServices;
 027            _appStatusServices = appStatusServices;
 028            _transactionTooltipService = transactionTooltipService;
 029            _transactionTransitionRuleService = transactionTransitionRuleService;
 030        }
 31
 32        /// <summary>Граф и весь список переходов: фильтры по статусам, типу и активности — в гриде AG Grid.</summary>
 33        public async Task<IActionResult> Index()
 34        {
 035            var list = await _statusTransitionServices.Get();
 36
 037            ViewBag.Statuses = await _appStatusServices.GetAppStatuses();
 038            ViewBag.TransactionTypes = TransactionTypeExtensions.GetTransactionTypes().Where(t => t != TransactionType.A
 39
 040            return View(list);
 041        }
 42
 43        public async Task<IActionResult> Create()
 44        {
 045            await SetStatusSelectLists();
 046            return View(new StatusTransition { IsActive = true });
 047        }
 48
 49        [HttpPost]
 50        [ValidateAntiForgeryToken]
 51        public async Task<IActionResult> Create([Bind("FromStatusId,ToStatusId,DisplayName,Description,DisplayOrder,IsAc
 52        {
 053            var transactionTypeStr = Request.Form["TransactionType"].FirstOrDefault()
 054                ?? Request.Form["StatusTransition.TransactionType"].FirstOrDefault();
 055            if (string.IsNullOrEmpty(transactionTypeStr))
 056                ModelState.AddModelError("TransactionType", "Выберите тип транзакции.");
 057            else if (int.TryParse(transactionTypeStr, out var ttVal) && Enum.IsDefined(typeof(OzonDomains.TransactionTyp
 058                model.TransactionType = (OzonDomains.TransactionType)ttVal;
 59            else
 060                ModelState.AddModelError("TransactionType", "Недопустимый тип транзакции.");
 061            if (model.FromStatusId == 0)
 062                ModelState.AddModelError("FromStatusId", "Выберите исходный статус.");
 063            if (model.ToStatusId == 0)
 064                ModelState.AddModelError("ToStatusId", "Выберите целевой статус.");
 065            if (model.FromStatusId != 0 && model.ToStatusId != 0 && model.FromStatusId == model.ToStatusId && !model.IsR
 066                ModelState.AddModelError("", "Исходный и целевой статус не должны совпадать (кроме повторяемых переходов
 67
 68            // Для одного типа транзакции допускается только один конечный статус (ToStatus); начальных может быть неско
 069            if (model.ToStatusId != 0 && ModelState.IsValid)
 70            {
 071                var existingForType = (await _statusTransitionServices.Get())
 072                    .Where(t => t.TransactionType == model.TransactionType)
 073                    .ToList();
 074                var requiredToStatusId = existingForType.FirstOrDefault()?.ToStatusId;
 075                if (requiredToStatusId.HasValue && requiredToStatusId.Value != model.ToStatusId)
 076                    ModelState.AddModelError("ToStatusId", "Для данного типа транзакции уже задан другой конечный статус
 77            }
 78
 079            if (ModelState.IsValid)
 80            {
 081                var existing = await _statusTransitionServices.GetAsync(model);
 082                if (existing != null)
 83                {
 084                    ModelState.AddModelError("", "Такой переход уже существует (та же пара статусов и тип транзакции).")
 85                }
 86                else
 87                {
 088                    await _statusTransitionServices.Add(model);
 089                    _transactionTooltipService.InvalidateCache();
 090                    _transactionTransitionRuleService.InvalidateCache();
 091                    TempData["StatusResult"] = "Переход добавлен.";
 092                    return RedirectToAction(nameof(Index));
 93                }
 94            }
 95
 096            await SetStatusSelectLists(model.FromStatusId, model.ToStatusId, model.TransactionType);
 097            return View(model);
 098        }
 99
 100        public async Task<IActionResult> Edit(int id)
 101        {
 0102            var item = await _statusTransitionServices.GetAsync(id);
 0103            if (item == null)
 0104                return NotFound();
 105
 0106            await SetStatusSelectLists(item.FromStatusId, item.ToStatusId, item.TransactionType);
 0107            return View(item);
 0108        }
 109
 110        [HttpPost]
 111        [ValidateAntiForgeryToken]
 112        public async Task<IActionResult> Edit(int id, [Bind("Id,FromStatusId,ToStatusId,TransactionType,DisplayName,Desc
 113        {
 0114            if (id != model.Id)
 0115                return NotFound();
 116
 0117            if (model.FromStatusId == model.ToStatusId && !model.IsRepeatable)
 118            {
 0119                ModelState.AddModelError("", "Исходный и целевой статус не должны совпадать (кроме повторяемых переходов
 120            }
 121
 122            // Для одного типа транзакции допускается только один конечный статус (ToStatus)
 0123            var othersForType = (await _statusTransitionServices.Get())
 0124                .Where(t => t.TransactionType == model.TransactionType && t.Id != id)
 0125                .ToList();
 0126            var requiredToStatusId = othersForType.FirstOrDefault()?.ToStatusId;
 0127            if (requiredToStatusId.HasValue && requiredToStatusId.Value != model.ToStatusId)
 0128                ModelState.AddModelError("ToStatusId", "Для данного типа транзакции уже задан другой конечный статус. У 
 129
 0130            if (ModelState.IsValid)
 131            {
 0132                var existing = await _statusTransitionServices.GetAsync(id);
 0133                if (existing == null)
 0134                    return NotFound();
 135
 0136                existing.FromStatusId = model.FromStatusId;
 0137                existing.ToStatusId = model.ToStatusId;
 0138                existing.TransactionType = model.TransactionType;
 0139                existing.DisplayName = model.DisplayName;
 0140                existing.Description = model.Description;
 0141                existing.DisplayOrder = model.DisplayOrder ?? 0;
 0142                existing.IsActive = model.IsActive;
 0143                existing.IsRepeatable = model.IsRepeatable;
 0144                existing.Conditions = model.Conditions;
 0145                existing.SystemName = model.SystemName;
 146
 0147                await _statusTransitionServices.Update(existing);
 0148                _transactionTooltipService.InvalidateCache();
 0149                _transactionTransitionRuleService.InvalidateCache();
 0150                TempData["StatusResult"] = "Переход обновлён.";
 0151                return RedirectToAction(nameof(Index));
 152            }
 153
 0154            await SetStatusSelectLists(model.FromStatusId, model.ToStatusId, model.TransactionType);
 0155            return View(model);
 0156        }
 157
 158        public async Task<IActionResult> Delete(int id)
 159        {
 0160            var item = await _statusTransitionServices.GetAsync(id);
 0161            if (item == null)
 0162                return NotFound();
 163
 0164            return View(item);
 0165        }
 166
 167        [HttpPost, ActionName("Delete")]
 168        [ValidateAntiForgeryToken]
 169        public async Task<IActionResult> DeleteConfirmed(int id)
 170        {
 0171            var item = await _statusTransitionServices.GetAsync(id);
 0172            if (item == null)
 0173                return NotFound();
 174
 0175            await _statusTransitionServices.Delete(item);
 0176            _transactionTooltipService.InvalidateCache();
 0177            _transactionTransitionRuleService.InvalidateCache();
 0178            TempData["StatusResult"] = "Переход удалён.";
 0179            return RedirectToAction(nameof(Index));
 0180        }
 181
 182        private async Task SetStatusSelectLists(int? selectedFromId = null, int? selectedToId = null, TransactionType? s
 183        {
 0184            var statuses = await _appStatusServices.GetAppStatuses();
 0185            ViewBag.FromStatusId = new SelectList(statuses, "Id", "Name", selectedFromId);
 0186            ViewBag.ToStatusId = new SelectList(statuses, "Id", "Name", selectedToId);
 0187            ViewBag.StatusList = statuses;
 0188            var types = TransactionTypeExtensions.GetTransactionTypes()
 0189                .Where(t => t != TransactionType.All)
 0190                .Select(t => new SelectListItem(t.GetDisplayName(), ((int)t).ToString(), selectedTransactionType == t))
 0191                .ToList();
 0192            ViewBag.TransactionTypeList = types;
 0193            ViewBag.TransactionTypes = TransactionTypeExtensions.GetTransactionTypes().Where(t => t != TransactionType.A
 0194        }
 195    }
 196}