2013-03-21 14 views
9

Tôi đang di chuyển từ Linq-to-SQL sang Entity Framework (4.4), sử dụng Database First với DbContext. Tôi đang tự hỏi liệu các hành vi sau đây là chuyện bình thường:Tôi có phải đặt thuộc tính khóa ngoài bằng tay khi tôi thay đổi liên kết không?

using (var e = new AgendaEntities()) { 
    var store = e.Stores.First(); 
    var office = e.Offices.Create(); 
    office.Store = store; // Set association 
    Console.WriteLine(office.StoreID); // shows Guid.Empty, expected store.ID! 
} 

Trong L2S, thiết lập các hiệp hội Store đến một thực thể cũng sẽ cập nhật các chính StoreID. Ở EF, điều này dường như không xảy ra. Điều này là bất kể các thực thể là mới hay được nạp từ ngữ cảnh.

Khi tôi SaveChanges, nó tiết kiệm một cách chính xác và StoreID được cập nhật để phù hợp với office.ID, nhưng tại sao điều này chỉ xảy ra sau khi tiết kiệm?

Có điều gì tôi thiếu hay bây giờ tôi có phải giữ đồng thời các khóa ngoại theo cách thủ công không?


Giải pháp Edit: này được gọi là fixup bất động sản, và thường được thực hiện tự động bởi các proxy được tạo ra. Tuy nhiên, với DbContext điều này không còn là trường hợp. Theo this Connect issue, đây là theo thiết kế.

Xin chào, Mẫu DbContext thực sự không tạo lớp sẽ được sử dụng làm proxy theo dõi thay đổi - chỉ cần tải proxy chậm (không sửa). Chúng tôi đưa ra quyết định này bởi vì thay đổi theo dõi proxy rất phức tạp và có rất nhiều sắc thái có thể rất khó hiểu đối với các nhà phát triển. Nếu bạn muốn sửa chữa xảy ra trước khi SaveChanges bạn có thể gọi myContext.ChangeTracker.DetectChanges. ~ EF Team

Cách khác là gọi DbContext.Entry(entity), sẽ đồng bộ hóa pháp nhân. Điều này được mô tả trong bài viết này: Relationships and Navigation Properties bên dưới "Đồng bộ hóa các thay đổi giữa các thuộc tính Điều hướng và FK và" Điều hướng "

+0

Thật khó để hiểu được không có nhiều người đánh giá cao giải pháp này. Không ai làm việc với dbcontext theo cách này? – danihp

+0

Cá nhân, tôi bây giờ chỉ cần đặt các phím theo cách thủ công bất cứ khi nào tôi thay đổi liên kết. Việc sửa chữa là một điều tốt đẹp, nhưng sau một vài suy nghĩ, không có ý nghĩa gì khi mong đợi POCO làm điều đó. Bất kỳ hoạt động nào thay đổi các liên kết phải được tóm tắt trong một số phương thức lớp miền nào đó, vì vậy cuối cùng nó không phải là sự căm thù như tôi nghĩ. –

+0

Tôi là thực thể 'mù' thông qua dbEntityValidations với tất cả các quy tắc kinh doanh của tôi để có thể trưng ra các thực thể cho lớp UI, ít nhất là đối với các thực thể 'đơn giản'. Tôi đối phó với lazyloading thực thể liên quan với 'entry.related' nhưng detectChanges phương pháp tiếp cận. Cảm ơn về bài đăng và giải pháp của bạn. – danihp

Trả lời

6

No. Khuôn khổ thực thể thực hiện điều này cho bạn. Đọc Relationships and Navigation Properties để biết thêm thông tin.

Bằng cách gán một đối tượng mới cho thuộc tính điều hướng. Mã sau tạo mối quan hệ giữa khóa học và department. Nếu các đối tượng được gắn với bối cảnh, các course cũng bổ sung vào bộ sưu tập department.Courses và tương ứng sở hữu nước ngoài chủ chốt trên đối tượng dĩ nhiên được thiết lập để các giá trị tài sản quan trọng của department.

  • course.Department = department;

Nhưng khi bạn quan sát, điều này chỉ xảy ra sau khi bạn gọi SaveChanges hoặc một trong các hành động khác được đề cập trong "Đồng bộ hóa những thay đổi giữa FKs và tài sản Navigation" phần của tài liệu được liên kết ở trên.

Nếu bạn đang sử dụng các đối tượng POCO không cần proxy, bạn phải chắc chắn rằng phương pháp DetectChanges được gọi để đồng bộ hóa các liên quan đối tượng trong bối cảnh. Lưu ý rằng các API sau tự động kích hoạt cuộc gọi DetectChanges.

  • DbSet.Add
  • DbSet.Find
  • DbSet.Remove
  • DbSet.Local
  • DbContext.SaveChanges
  • DbSet.Attach
  • DbContext.GetValidationErrors
  • DbContext. Nhập
  • DbChangeTracke r.Entries
  • Thực thi một truy vấn LINQ chống lại một DbSet

Nếu điều này không xảy ra ở tất cả các , tôi đoán là bạn chưa đúng định nghĩa StoreID là chìa khóa đối ngoại của bất động sản chuyển hướng Store.

+1

Tôi nghĩ rằng những gì đang xảy ra được mô tả trong "Đồng bộ hóa các thay đổi giữa các FK và các thuộc tính Điều hướng", ở cuối bài viết bạn đã liên kết. Gọi 'e.Entry (office)' đồng bộ hóa các ID. Tuy nhiên, tôi có thể thấy trong trình gỡ rối proxy đang được tạo, vì vậy nó * nên * hoạt động ... –

+0

@IliaJerebtsov ahh chính xác. Tôi đã đọc sai câu hỏi của bạn ban đầu. Tôi nghĩ rằng bạn đang nói rằng nó đã không xảy ra ở tất cả. –

+0

Cảm ơn, tôi đã tìm ra nó, dường như việc thiếu sửa lỗi là do thiết kế trong API DbContext. –