簡體   English   中英

Entity Framework Core 無法更新包含相關對象的 object

[英]Entity Framework Core fail to update object with related objects included

我正在嘗試使用 Entity Framework Core 實現 WebApi。 我已經建模了一個隱式的多對多關系,並基於DbContext搭建了控制器。

但這不允許將 object 與其鏈接對象保持一致。

演示我的問題的簡化版本:

using Microsoft.EntityFrameworkCore;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using System.Collections.Generic;
using System.Linq;

namespace Tests
{
    public class Author
    {
        public long Id { get; set; }
        public string Name { get; set; }
        public ICollection<Book> Books { get; set; }
    }

    public class Book
    {
        public long Id { get; set; }
        public string Title { get; set; }
        public ICollection<Author> Authors { get; set; }
    }

    public class LibraryDbContext : DbContext
    {
        public DbSet<Book> Books { get; set; }
        public DbSet<Author> Authors { get; set; }

        protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
        {
            optionsBuilder.UseSqlServer(@"Server=localhost\mssqlserver01;Database=Library;Trusted_Connection=True;MultipleActiveResultSets=true");
        }
    }

    [TestClass]
    public class Test
    {
        [TestMethod]
        public void TestMethod1()
        {
            // Assign
            Author author_buzz = new Author()
            {
                Name = "Buzz",
                Books = new List<Book>()
                {
                    new Book()
                    {
                        Title = "Book 1",
                    },
                    new Book()
                    {
                        Title = "Book 2",
                    }
                }
            };

            using (LibraryDbContext context = new LibraryDbContext())
            {
                context.Database.EnsureDeleted();
                context.Database.EnsureCreated();

                context.Authors.Add(author_buzz);
                context.SaveChanges();
            }

            // Act
            author_buzz.Name = "Buzz Lightyear";
            //author_buzz.Books = null; // Uncommenting this will make the test pass.

            using (LibraryDbContext context = new LibraryDbContext())
            {
                context.Entry(author_buzz).State = EntityState.Modified;
                //context.Update(author_buzz); // Using this way of updating doesn't work either.

                context.SaveChanges();
            }

            // Assert
            using (LibraryDbContext context = new LibraryDbContext())
            {
                author_buzz = context.Authors
                    .Include(author => author.Books)
                    .Single();

                Assert.AreEqual("Buzz Lightyear", author_buzz.Name);
                Assert.AreEqual(2, author_buzz.Books.Count);
            }
        }
    }
}

在最后一個 SaveChanges() 上運行此測試會導致以下異常:

SqlException:違反主鍵約束“PK_AuthorBook”。 無法在 object 'dbo.AuthorBook' 中插入重復密鑰。 重復鍵值為 (1, 1)。

但是,當我將屬性 Books 設置為 null 時,測試通過了。

在我看來,Entity Framework 並沒有認識到作者和書籍之間的關系是現有關系這一事實,並試圖再次添加它。 然后它會失敗,因為該鏈接已經存在於實體 AuthorBook 中。

如何在不清除其關系屬性的情況下更新實體? 在更復雜的領域,這是我不想 go 低谷的東西,我覺得應該有更簡單的方法。

(這與 Visual Studio 基於實體框架搭建的 controller 中的 PUT 方法的實現相同。此外,使用 context.Update() 似乎也不起作用。)

問題是實體不再附加到上下文中。 通過調用context.Attach(author_buzz);解決了它在將 State 設置為已修改之前。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM