You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
iot/projects/Infrastructure/Web/Mvc/CrudController.cs

321 lines
10 KiB

using Infrastructure.Application;
using Infrastructure.Data;
using Infrastructure.Domain;
using Infrastructure.Extensions;
using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.Mvc.Controllers;
using Microsoft.AspNetCore.Mvc.Filters;
using Microsoft.EntityFrameworkCore;
using System;
using System.Collections.Generic;
using System.Linq;
namespace Infrastructure.Web.Mvc
{
[ApiExplorerSettings(IgnoreApi = false)]
[ApiController]
[Route("Admin/[controller]/[action]")]
public class CrudController<TEntity, TSearchModel, TDisplayModel, TEditModel> : BaseController
where TEntity : BaseEntity
where TSearchModel : PagedListModel<TDisplayModel>
{
protected readonly IRepository<TEntity> _repo;
public CrudController(IRepository<TEntity> repo)
{
this._repo = repo;
}
[HttpGet]
public virtual IActionResult Index(TSearchModel model)
{
if (model == null)
{
throw new ArgumentNullException(nameof(model));
}
var query = this._repo.ReadOnlyTable();
if (model is ISoftDeleteEntity && !model.IsDeleted)
{
query = query.Where(o => o.IsDeleted == null);
}
query = this.Include(query);
query = this.Query(model, query);
model.TotalCount = query.Count();
model.List.AddRange(query.Skip(model.PageSize * (model.PageIndex - 1))
.Take(model.PageSize)
.ToList()
.Select(o =>
{
var m = o.To<TDisplayModel>();
this.ToDisplayModel(o, m);
return m;
})
.ToList());
ViewData["EntityTypeExt"] = typeof(TEntity);
ViewData["ModelTypeExt"] = typeof(TDisplayModel);
return this.Result(model);
}
[HttpGet]
public virtual IActionResult Details(Guid id)
{
var query = this._repo.ReadOnlyTable();
query = this.Include(query);
var entity = query.FirstOrDefault(o => o.Id == id);
var model = entity.To<TDisplayModel>();
this.ToDisplayModel(entity, model);
return Result(model);
}
[HttpGet]
public virtual IActionResult Add()
{
var model = Activator.CreateInstance<TEditModel>();
this.ToEditModel(null, model);
return View(model);
}
[HttpPost]
public virtual IActionResult Add(TEditModel model)
{
if (ModelState.IsValid)
{
try
{
var entity = Activator.CreateInstance<TEntity>();
entity.From(model);
this.ToEntity(model, entity);
this._repo.Add(entity);
if (this._repo.SaveChanges() > 0)
{
this.OnInserted(entity);
}
return RedirectTo();
}
catch (DbUpdateException ex)
{
ex.PrintStack();
ModelState.AddModelError("", ex.Message);
}
}
this.ToEditModel(null, model);
return View(model);
}
[HttpGet]
public virtual IActionResult Edit(Guid id)
{
var query = this._repo.ReadOnlyTable();
query = this.Include(query);
var entity = query.FirstOrDefault(o => o.Id == id);
var model = entity.To<TEditModel>();
this.ToEditModel(entity, model);
return View(model);
}
[HttpPost]
public virtual IActionResult Edit(TEditModel model)
{
var id = (Guid)model.GetType().GetProperty("Id").GetValue(model);
var query = this._repo.Table();
query = this.Include(query);
var entity = query.FirstOrDefault(o => o.Id == id);
if (ModelState.IsValid)
{
try
{
this.OnEdit(entity, model);
entity.From(model);
this.ToEntity(model, entity);
if (this._repo.SaveChanges() > 0)
{
this.OnUpdated(entity);
}
return RedirectTo();
}
catch (DbUpdateException ex)
{
ex.PrintStack();
ModelState.AddModelError("", ex.Message);
}
}
this.ToEditModel(entity, model);
return View(model);
}
[HttpPost]
public virtual IActionResult Remove(List<Guid> list)
{
if (list == null)
{
throw new ArgumentNullException(nameof(list));
}
try
{
foreach (var id in list)
{
var query = this._repo.Table();
var entity = query.FirstOrDefault(o => o.Id == id);
entity.IsDeleted = Guid.NewGuid().ToString();
this._repo.SaveChanges();
}
return RedirectTo();
}
catch (DbUpdateException ex)
{
ex.PrintStack();
return RedirectTo(rawMesage: ex.Message);
}
}
[HttpPost]
public IActionResult Restore(List<Guid> list)
{
if (list == null)
{
throw new ArgumentNullException(nameof(list));
}
try
{
foreach (var id in list)
{
var query = this._repo.Table();
var entity = query.FirstOrDefault(o => o.Id == id);
entity.IsDeleted = null;
this._repo.SaveChanges();
}
return RedirectTo();
}
catch (DbUpdateException ex)
{
ex.PrintStack();
return RedirectTo(rawMesage: ex.Message);
}
}
[HttpPost]
public virtual IActionResult Delete(List<Guid> list)
{
if (list == null)
{
throw new ArgumentNullException(nameof(list));
}
try
{
foreach (var id in list)
{
var query = this._repo.Table();
var entity = query.FirstOrDefault(o => o.Id == id);
this._repo.Delete(entity);
if (this._repo.SaveChanges() > 0)
{
this.OnDeleted(entity);
}
}
return RedirectTo();
}
catch (DbUpdateException ex)
{
ex.PrintStack();
return RedirectTo(rawMesage: ex.Message);
}
}
[ApiExplorerSettings(IgnoreApi = true)]
public virtual IQueryable<TEntity> Include(IQueryable<TEntity> query)
{
return query;
}
[ApiExplorerSettings(IgnoreApi = true)]
public virtual IQueryable<TEntity> Query(TSearchModel model, IQueryable<TEntity> query)
{
return query;
}
[ApiExplorerSettings(IgnoreApi = true)]
public virtual void ToEditModel(TEntity entity, TEditModel model)
{
}
[ApiExplorerSettings(IgnoreApi = true)]
public virtual void ToDisplayModel(TEntity entity, TDisplayModel model)
{
}
[ApiExplorerSettings(IgnoreApi = true)]
public virtual void ToEntity(TEditModel model, TEntity entity)
{
}
[ApiExplorerSettings(IgnoreApi = true)]
public virtual void OnEdit(TEntity entity, TEditModel model)
{
}
[ApiExplorerSettings(IgnoreApi = true)]
public virtual void OnInserted(TEntity entity)
{
}
[ApiExplorerSettings(IgnoreApi = true)]
public virtual void OnUpdated(TEntity entity)
{
}
[ApiExplorerSettings(IgnoreApi = true)]
public virtual void OnDeleted(TEntity entity)
{
}
[ApiExplorerSettings(IgnoreApi = true)]
public override void OnActionExecuting(ActionExecutingContext context)
{
if (context == null)
{
throw new ArgumentNullException(nameof(context));
}
var name = (context.ActionDescriptor as ControllerActionDescriptor).ActionName;
var permission = string.Empty;
if (name == "Index")
{
permission = $"Read-{typeof(TEntity).Name}";
}
else if (name == "Details")
{
permission = $"Read-{typeof(TEntity).Name}";
}
else if (name == "Add")
{
permission = $"Add-{typeof(TEntity).Name}";
}
else if (name == "Edit" || name == "Remove" || name == "Restore")
{
permission = $"Edit-{typeof(TEntity).Name}";
}
else if (name == "Delete")
{
permission = $"Delete-{typeof(TEntity).Name}";
}
if (!string.IsNullOrEmpty(permission))
{
var returnUrl = context.HttpContext.Request.GetUrl();
if (!context.HttpContext.User.Identity.IsAuthenticated)
{
context.Result = new RedirectToActionResult("Login", "Account", new { area = "", returnUrl }); ;
}
else if (!context.HttpContext.User.IsInRole(permission))
{
context.Result = new RedirectToActionResult("AccessDenied", "Account", new { area = "", returnUrl });
}
}
}
[ApiExplorerSettings(IgnoreApi = true)]
private IActionResult Result(object model)
{
return this.Request.Headers["accept"].ToString().Contains("json") ? Json(model) as IActionResult : View(model);
}
}
}