C# 错误-INSERT语句与外键约束冲突

C# 错误-INSERT语句与外键约束冲突,c#,sql-server,asp.net-mvc,entity-framework,sql-insert,C#,Sql Server,Asp.net Mvc,Entity Framework,Sql Insert,使用EF Code First迁移时,在数据库中创建包含代码的项时出错 我已经回顾了stackoverflow上与我的问题类似的几个QA,但它们不能帮助我解决问题。我没有使用自动迁移 我遵循本教程,为主要类别/子类别创建级联下拉列表,在我的列表中效果很好,但当我去创建项目时,出现以下错误: INSERT语句与外键约束“FK_dbo.Fabrics_dbo.maincegories_MainCategoryId”冲突。冲突发生在数据库“MyFabricStashAppDb”、表“dbo.mainC

使用EF Code First迁移时,在数据库中创建包含代码的项时出错

我已经回顾了stackoverflow上与我的问题类似的几个QA,但它们不能帮助我解决问题。我没有使用自动迁移

我遵循本教程,为主要类别/子类别创建级联下拉列表,在我的列表中效果很好,但当我去创建项目时,出现以下错误:

INSERT语句与外键约束“FK_dbo.Fabrics_dbo.maincegories_MainCategoryId”冲突。冲突发生在数据库“MyFabricStashAppDb”、表“dbo.mainContegories”、列“MainCategorid”中。声明已终止

我的模型如下: 我的MainCategory.cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;

namespace MyFabricStashApp.Models
{
    public class MainCategory
    {
        public int MainCategoryId { get; set; }
        public string Name { get; set; }
        public List<SubCategory1> SubCategories1 { get; set; }

    }
}
My Fabric.cs(项目类别)

My FabricListViewModel.cs-我创建它是为了让视图能够访问我所有类中需要的所有属性

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;

namespace MyFabricStashApp.Models
{
    public class FabricListViewModel
    {
        public int FabricId { get; set; } //Item Number

        public int MainCategoryId { get; set; }
        public string MainCategoryName { get; set; }

        public int SubCategory1Id { get; set; }
        public string SubCategory1Name { get; set; }

        public string Name { get; set; }
        public string ImagePath { get; set; }
        public string Location { get; set; }
        public string Type { get; set; } //Knit, Woven, Voile, Interfacing, Denim, Suiting, etc.
        public string Weight { get; set; }//Lightweight, Medium, Heavy
        public string Content { get; set; }//Cotton, Polyester, Nylon, etc.
        public string Design { get; set; }//Marvel Comics, Amy Butler, etc.
        public string Brand { get; set; } //Springs Creative Products, Free Spirit, Robert Kaufman, etc.
        public double Quantity { get; set; }//.25 yd, .50 yd, .75 yd, 1.0 yd, etc.
        public int Width { get; set; }// in inches, ie. 44", 54", etc.
        public string Source { get; set; }//Joann
        public string Notes { get; set; }
        public int ItemsSold { get; set; }
        public int PurchaseCount { get; set; }

    }
}
在我的控制器FabricController中,您可以看到我在列表中包括MainCategory和SubCategory 1模型,因此我可以访问它们的属性。为了简洁起见,我加入了索引操作和创建后操作

public class FabricController : Controller
    {
        private MyFabricStashDb db = new MyFabricStashDb();

        // GET: Fabric
        public ActionResult Index(string searchTerm = null)
        {
            var model = db.Fabrics.Include(f => f.MainCategory).Include(f => f.SubCategory1)
                .OrderByDescending(f => f.ItemsSold)
                .Where(f => searchTerm == null || f.Name.StartsWith(searchTerm))
                .Select(f => new FabricListViewModel
                {
                    FabricId = f.FabricId,
                    Name = f.Name,
                    MainCategoryId = f.MainCategoryId,
                    MainCategoryName = f.MainCategory.Name,
                    SubCategory1Id = f.SubCategory1Id,
                    SubCategory1Name = f.SubCategory1.Name,
                    ImagePath = f.ImagePath,
                    Location = f.Location,
                    Type = f.Type,
                    Weight = f.Weight,
                    Content = f.Content,
                    Design = f.Design,
                    Brand = f.Brand,
                    Quantity = f.Quantity,
                    Width = f.Width,
                    Source = f.Source,
                    Notes = f.Notes,
                    ItemsSold = f.ItemsSold,
                    PurchaseCount = f.Purchases.Count()
                });
            return View(model);
        }
// POST: Fabric/Create
        // 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]
        public ActionResult Create([Bind(Include = "FabricId,MainCategory,SubCategory1,SubCategory2,Name,ImagePath,Location,Type,Weight,Content,Design,Brand,Quantity,Width,Source,Notes,ItemsSold")] Fabric fabric, HttpPostedFileBase file)
        {
            if (ModelState.IsValid)
            {
                var filename = Path.GetFileName(file.FileName);
                string fabricId = fabric.FabricId.ToString();
                string myfile = fabricId + "_" + filename;
                var path = Path.Combine(Server.MapPath("~/images"), myfile);
                fabric.ImagePath = myfile;
                file.SaveAs(path);
                db.Fabrics.Add(fabric);
                db.SaveChanges();
                return RedirectToAction("Index");
            }

            return View(fabric);
        }
是否需要在POST Create方法中绑定MainCategory和SubCategory 1类中的属性?这就是INSERT语句失败的原因吗?创建后操作方法中的“db.SaveChanges();”行失败


当我注释掉Fabric类中的行
public virtual maincography maincography{get;set;}
属性时,它可以工作,并且我可以创建一个新项,但是我不能在Fabric控制器中包括这些类,因为这些属性在Fabric类中不存在,因此我无法访问它们的属性

问题是,这里有一种简化数据的方法。每个子类别都有一个唯一的id。要链接到主类别,可以通过结构所属的子类别。这给了我们

public class Fabric
    {
        public int FabricId { get; set; } //Item Number

        // public int MainCategoryId { get; set; }
        // public virtual MainCategory MainCategory { get; set; }

        public int SubCategory1Id { get; set; }
        public virtual SubCategory1 SubCategory1 { get; set; }
        public string Name { get; set; }
        public string ImagePath { get; set; }
        public string Location { get; set; }
        public string Type { get; set; } //Knit, Woven, Voile, Interfacing, Denim, Suiting, etc.
        public string Weight { get; set; }//Lightweight, Medium, Heavy
        public string Content { get; set; }//Cotton, Polyester, Nylon, etc.
        public string Design { get; set; }//Marvel Comics, Amy Butler, etc.
        public string Brand { get; set; } //Springs Creative Products, Free Spirit, Robert Kaufman, etc.
        public double Quantity { get; set; }//.25 yd, .50 yd, .75 yd, 1.0 yd, etc.
        public int Width { get; set; }// in inches, ie. 44", 54", etc.
        public string Source { get; set; }//Joann
        public string Notes { get; set; }
        public List<string> Tags { get; set; }
        public int ItemsSold { get; set; }
        public virtual ICollection<Purchase> Purchases { get; set; }
    }
公共类结构
{
public int FabricId{get;set;}//项目编号
//公共int MainCategoryId{get;set;}
//公共虚拟MainCategory MainCategory{get;set;}
公共int子类别1id{get;set;}
公共虚拟子类别1子类别1{get;set;}
公共字符串名称{get;set;}
公共字符串ImagePath{get;set;}
公共字符串位置{get;set;}
公共线类型{get;set;}//针织、机织、纱、衬布、牛仔布、西装等。
公共字符串权重{get;set;}//轻、中、重
公共字符串内容{get;set;}//棉、聚酯、尼龙等。
公共字符串设计{get;set;}//惊奇漫画、艾米·巴特勒等。
公共字符串品牌{get;set;}//弹簧创意产品、自由精神、罗伯特·考夫曼等。
公共双码{get;set;}/.25码、50码、75码、1.0码等。
公共整数宽度{get;set;}//以英寸为单位,即44英寸、54英寸等。
公共字符串源{get;set;}//Joann
公共字符串注释{get;set;}
公共列表标记{get;set;}
public int ItemsSold{get;set;}
公共虚拟ICollection{get;set;}
}
只要你能通过

db.Fabrics.Include("SubCategory1").Include("SubCategory1.MainCategory").FirstOrDefault(p => p.FabricId == <something>);
db.Fabrics.Include(“子类别1”).Include(“子类别1.MainCategory”).FirstOrDefault(p=>p.FabricId==);
您可以引用Fabric.subcategory 1.maincegory.Name


使用MainCategory/SubCategory 1填充下拉列表,并确保在创建时将SubCategory 1键放入结构记录中。应该简化你的生活。下拉列表将绑定到MainCategory的临时字段和SubCategory 1.SubCategory ID的listmodel。对于显示,您可以从Fabric.SubCategory1.maincegory.maincegoryId字段填充临时字段。ymmv.

我在这里发布问题的解决方案。上面@juharr和@user1011627在评论中回答了这个问题,但我想发布解决方案,以防有人遇到同样的问题

我只是在POST-Create操作方法的BIND语句中添加了“MainCategoryId”和“SubCategory1Id”属性。请参见下面的FabricController中:

// POST: Fabric/Create
        // 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]
        public ActionResult Create([Bind(Include = "FabricId,MainCategory,MainCategoryId, SubCategory1Id,SubCategory1,SubCategory2,Name,ImagePath,Location,Type,Weight,Content,Design,Brand,Quantity,Width,Source,Notes,ItemsSold")] Fabric fabric, HttpPostedFileBase file)
        {
            if (ModelState.IsValid)
            {
                var filename = Path.GetFileName(file.FileName);
                string fabricId = fabric.FabricId.ToString();
                string myfile = fabricId + "_" + filename;
                var path = Path.Combine(Server.MapPath("~/images"), myfile);
                fabric.ImagePath = myfile;
                file.SaveAs(path);
                db.Fabrics.Add(fabric);
                db.SaveChanges();
                return RedirectToAction("Index");
            }

            return View(fabric);
        }

我相信还有其他方法可以做到这一点,但这是最简单、最快捷的解决方案,可以让它与应用程序中的其他代码一起工作

长柱;简短问题:您是否知道,通常是什么原因导致此错误
INSERT语句与外键约束冲突
?问题似乎是您创建了一个
Fabric
实体,该实体的
MainCategoryId
maincegory
表中不存在。如果是,请在
public ActionResult Create
中的某个位置设置断点。使用调试器检查
Fabric
的所有必需属性是否已填充。其中一个字段可能未正确填充。如果你发现了瓶颈,你可以把你的问题更多地集中在这个细节上。我从来没有用这个Bind属性为MVC做过模型绑定,但我突然想到的一件事是:“[Bind(Include=“FabricId,MainCategory,SubCategory 1…”。。。"您的MainCategory和SubCategory看起来类似于对象引用,而其他包含的字段看起来类似于字段引用……这意味着,MainCategory应该是MainCategoryId而不仅仅是MainCategory。juharr和Stefan都是正确的,因为您试图存储在DB中的MainCategoryId字段不正确y填写…这可能是他们没有被正确发送的原因吗?有可能,你对绑定过程不太了解吗?(无意冒犯:)我真的建议你读几分钟关于它的内容,这有助于理解它是如何工作的以及为什么它是必要的。只需阅读,你生成的代码中的链接指向=>没有冒犯,但这就是为什么我在这里发布问题,这样我可以更好地理解
public class Fabric
    {
        public int FabricId { get; set; } //Item Number

        // public int MainCategoryId { get; set; }
        // public virtual MainCategory MainCategory { get; set; }

        public int SubCategory1Id { get; set; }
        public virtual SubCategory1 SubCategory1 { get; set; }
        public string Name { get; set; }
        public string ImagePath { get; set; }
        public string Location { get; set; }
        public string Type { get; set; } //Knit, Woven, Voile, Interfacing, Denim, Suiting, etc.
        public string Weight { get; set; }//Lightweight, Medium, Heavy
        public string Content { get; set; }//Cotton, Polyester, Nylon, etc.
        public string Design { get; set; }//Marvel Comics, Amy Butler, etc.
        public string Brand { get; set; } //Springs Creative Products, Free Spirit, Robert Kaufman, etc.
        public double Quantity { get; set; }//.25 yd, .50 yd, .75 yd, 1.0 yd, etc.
        public int Width { get; set; }// in inches, ie. 44", 54", etc.
        public string Source { get; set; }//Joann
        public string Notes { get; set; }
        public List<string> Tags { get; set; }
        public int ItemsSold { get; set; }
        public virtual ICollection<Purchase> Purchases { get; set; }
    }
db.Fabrics.Include("SubCategory1").Include("SubCategory1.MainCategory").FirstOrDefault(p => p.FabricId == <something>);
// POST: Fabric/Create
        // 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]
        public ActionResult Create([Bind(Include = "FabricId,MainCategory,MainCategoryId, SubCategory1Id,SubCategory1,SubCategory2,Name,ImagePath,Location,Type,Weight,Content,Design,Brand,Quantity,Width,Source,Notes,ItemsSold")] Fabric fabric, HttpPostedFileBase file)
        {
            if (ModelState.IsValid)
            {
                var filename = Path.GetFileName(file.FileName);
                string fabricId = fabric.FabricId.ToString();
                string myfile = fabricId + "_" + filename;
                var path = Path.Combine(Server.MapPath("~/images"), myfile);
                fabric.ImagePath = myfile;
                file.SaveAs(path);
                db.Fabrics.Add(fabric);
                db.SaveChanges();
                return RedirectToAction("Index");
            }

            return View(fabric);
        }