首页 > 解决方案 > 禁用删除具有依赖关系的记录

问题描述

我只想从我的数据库中删除没有任何依赖关系的记录。

例如:-Company表有Company Pk主键,它是department表和location表的外键。因此,如果公司与和company有依赖关系,则系统不应允许用户从中删除公司。departmentlocation

可以删除没有任何依赖关系的记录。我该怎么做

using System;
using System.Collections.Generic;
using System.Data;
using System.Data.Entity;
using System.Linq;
using System.Threading.Tasks;
using System.Net;
using System.Web;
using System.Web.Mvc;
using Payroll.Core.Domain;
using Payroll.Infrastructure.Data;
using AutoMapper;
using Payroll.Web.Dto;
using Payroll.Core.Interfaces;
using Payroll.Infrastructure.Validators;

namespace Payroll.Web.Controllers
{
    [RoutePrefix("Company")]
    public class CompanyController : Controller
    {
        private readonly IMapper _mapper = null;
        private readonly IUnitOfWork _work = null;

        public CompanyController(IUnitOfWork work, IMapper mapper)
        {
            _work = work;
            _mapper = mapper;
        }

        // GET: Company
        public async Task<ActionResult> Index()
        {
            var companies = await _work.Companies.GetAllAsync();
            var companyDtos = _mapper.Map<List<CompanyDto>>(companies);

            return View(companyDtos);
        }

        // GET: Company/5
        [Route("{companyPk:int}")]
        public async Task<ActionResult> Details(int? companyPk)
        {
            //Validate parameters
            if (companyPk == null)
            {
                return new HttpStatusCodeResult(HttpStatusCode.BadRequest, "Company identifier is missing.");
            }

            //Get model from db
            Company company = await _work.Companies.GetAsync(companyPk);
            if (company == null)
            {
                return HttpNotFound();
            }

            //Convert model to dto
            CompanyDto companyDto = _mapper.Map<CompanyDto>(company);

            return View(companyDto);
        }

        // GET: Company/New
        [Route("New")]
        public ActionResult New()
        {
            var dto = new CompanyDto();
            return View(dto);
        }

        // POST: Company/New
        // To protect from overposting attacks, please enable the specific properties you want to bind to, for 
        // more details see https://go.microsoft.com/fwlink/?LinkId=317598.
        [HttpPost]
        [ValidateAntiForgeryToken]
        [Route("New")]
        public async Task<ActionResult> New(CompanyDto companyDto)
        {
            //Validate Dto state
            if (ModelState.IsValid)
            {
                //Convert dto to model
                Company company = _mapper.Map<Company>(companyDto);

                //Assign model properties
                company.CompanyPk = new Random().Next(1, 10);

                Utilities.Instance.SetEntityProperties(company);

                //Validate model
                var validator = new CompanyValidator();
                var validation = await validator.ValidateAsync(company);

                if (validation.IsValid)
                {
                    //Save model to db
                    _work.Companies.Add(company);
                    await _work.CompleteAsync();

                    return RedirectToAction("Index");
                }
                else
                {
                    foreach (var error in validation.Errors)
                    {
                        ModelState.AddModelError(error.PropertyName, error.ErrorMessage);
                    }
                }
            }

            return View(companyDto);
        }

        // GET: Company/5/Edit
        [Route("{companyPk:int}/Edit")]
        public async Task<ActionResult> Edit(int? companyPk)
        {
            //Validate parameters
            if (companyPk == null)
            {
                return new HttpStatusCodeResult(HttpStatusCode.BadRequest, "Company identifier is missing.");
            }

            //Get the model from db
            Company company = await _work.Companies.GetAsync(companyPk);
            if (company == null)
            {
                return HttpNotFound();
            }

            //Convert model to dto
            CompanyDto companyDto = _mapper.Map<CompanyDto>(company);

            return View(companyDto);
        }

        // POST: Company/5/Edit
        // To protect from overposting attacks, please enable the specific properties you want to bind to, for 
        // more details see https://go.microsoft.com/fwlink/?LinkId=317598.
        [HttpPost]
        [ValidateAntiForgeryToken]
        [Route("{companyPk:int}/Edit")]
        public async Task<ActionResult> Edit(int? companyPk, CompanyDto companyDto)
        {
            //Validate parameters
            if (companyPk == null)
            {
                return new HttpStatusCodeResult(HttpStatusCode.BadRequest, "Company identifier is missing.");
            }

            //Validate Dto state
            if (ModelState.IsValid)
            {
                //Get the model from db
                //Because the record now being edited can be changed by another process
                var company = await _work.Companies.GetAsync(companyPk);

                if (company == null)
                {
                    return HttpNotFound();
                }

                //Map the previous state of the model to log
                var logCompany = _mapper.Map<LogCompany>(company);

                //Convert dto to model
                //This is a specific mapping which modifies the original model from only bound properties of Dto
                _mapper.Map(companyDto, company);

                //Validate model
                var validator = new CompanyValidator();
                var validation = await validator.ValidateAsync(company);

                if (validation.IsValid)
                {
                    //Assign log model properties
                    logCompany.RecordId = 0;
                    Utilities.Instance.SetLogEntityProperties(logCompany, "E");

                    //Save model to db
                    _work.LogCompanies.Add(logCompany);
                    _work.Companies.Update(company);

                    await _work.CompleteAsync();

                    return RedirectToAction("Index");
                }
                else
                {
                    foreach (var error in validation.Errors)
                    {
                        ModelState.AddModelError(error.PropertyName, error.ErrorMessage);
                    }
                }
            }

            return View(companyDto);
        }

        // GET: Company/5/Delete
        [Route("{companyPk:int}/Delete")]
        public async Task<ActionResult> Delete(int? companyPk)
        {
            //Validate parameters
            if (companyPk == null)
            {
                return new HttpStatusCodeResult(HttpStatusCode.BadRequest, "Company identifier is missing.");
            }

            //Get the model from db
            Company company = await _work.Companies.GetAsync(companyPk);
            if (company == null)
            {
                return HttpNotFound();
            }

            //Convert model to dto
            CompanyDto companyDto = _mapper.Map<CompanyDto>(company);

            return View(companyDto);
        }

        // POST: Company/5/Delete
        [HttpPost, ActionName("Delete")]
        [ValidateAntiForgeryToken]
        [Route("{companyPk:int}/Delete")]
        public async Task<ActionResult> DeleteConfirmed(int companyPk)
        {
            //Get the model from db
            Company company = await _work.Companies.GetAsync(companyPk);

            //Prepare log model
            var logCompany = _mapper.Map<LogCompany>(company);
            logCompany.RecordId = 0;
            Utilities.Instance.SetLogEntityProperties(logCompany, "D");

            //Save model to db
            _work.LogCompanies.Add(logCompany);
            _work.Companies.Remove(company);
            await _work.CompleteAsync();

            return RedirectToAction("Index");
        }

        protected override void Dispose(bool disposing)
        {
            if (disposing)
            {
                _work.Dispose();
            }
            base.Dispose(disposing);
        }
    }
}

标签: c#model-view-controllerentity-framework-6dto

解决方案


如果您的实体中有导航属性,那么您可以检查它们的键是否不为空:

company.LocationId !=null && company.DepartmentId!=null

如果您没有 Id 属性(EF 可以按照惯例创建它们),请阅读此文档并加载实体。假设这不会增加太多开销。

var company = _work.Companies.Where(b => b.CompanyPk == companyPk)
                       .Include(b => b.Location)
                       .Include(b => b.Department)
                       .FirstOrDefault();
company.Location !=null && company.Department!=null

希望这不是生产代码:

company.CompanyPk = new Random().Next(1, 10);

并且永远不会破坏注入的依赖项。这是一个危险信号,因为您无法控制它的生命周期,如果有池怎么办?规则是 - 你没有创造它,你没有责任摧毁它。如果您想明确控制生命周期 - 然后注入工厂,创建服务,使用和销毁。

_work.Dispose();

推荐阅读