Tác động hiệu năng của Entity Framework Core 3.0 bao gồm các thuộc tính điều hướng bộ sưu tập (vụ nổ cartesian)


8

Chúng tôi đang đối mặt với một vấn đề hiệu năng lớn sau khi nâng cấp EF Core 2.2 lên EF Core 3.0. Hãy tưởng tượng một mô hình dữ liệu đơn giản với một thuộc tính điều hướng bộ sưu tập duy nhất và hàng trăm trường (thực tế trông còn tối hơn):

public class Item
{
  [Key]
  public int ItemID {get;set;}

  public ICollection<AddInfo> AddInfos {get;set;}
  ...  // consisting of another 100+ properties!
}

public class AddInfo
{
  [Key]
  public int AddInfoID {get;set;}
  public int? ItemID {get;set;}
  public string SomePayload {get;set;}
}

Trong quá trình truy xuất mục, chúng tôi truy vấn như sau:

...
var myQueryable = this._context.Items.Include(i => i.AddInfos).Where(**some filter**);
... // moar filters
var result = myQueryable.ToList();

Thẳng về phía trước, cho đến thời điểm này.

Trong EF 2.2, tìm nạp kết quả có thể truy vấn đó trong hai truy vấn riêng biệt, một cho Itemvà một cho AddInfocấp -. Các truy vấn này thường lấy 10.000 itemsvà khoảng 250.000 AddInfos.

Trong EF Lõi 3.0 tuy nhiên, một truy vấn duy nhất đã được tạo ra, trái tham gia AddInfođể Item mà trên xuất hiện cái nhìn đầu tiên là lựa chọn tốt hơn. ItemTuy nhiên, chúng tôi cần phải tìm nạp tất cả hơn 100 trường, đó là lý do tại sao chiếu đến một lớp nhỏ hơn hoặc loại ẩn danh (thêm một cuộc gọi vào phương thức .Select (...) - không khả thi. Do đó, tập kết quả có quá nhiều sự dư thừa trong đó (mỗi lần Itemxấp xỉ 25 lần) mà bản thân truy vấn mất quá nhiều thời gian để chạy trong thời gian chấp nhận được.

Có phải EF-Core 3.0 cung cấp bất kỳ tùy chọn nào cho phép chúng tôi quay lại hành vi truy vấn của EF Core cũ 2.2 tốt mà không cần thay đổi nhiều đối với mô hình dữ liệu của chúng tôi không? Chúng tôi đã thu được lợi nhuận từ sự thay đổi này trong các phần khác của ứng dụng, nhưng không phải trong kịch bản cụ thể này.

Rất cám ơn trước!

Cập nhật

Sau khi điều tra thêm, tôi thấy rằng vấn đề này đã được xử lý với Microsoft ở đây và ngoài hộp, dường như không có cách nào để định cấu hình thực thi truy vấn phân tách.


Là truy vấn qua kết nối web (http)? Các tiêu đề mặc định có thể khác nhau trong Core 2.2 và Core 3.0 (như http phiên bản 1.0 và http phiên bản 1.1). Bạn có thể muốn sử dụng một trình thám thính như wireshark hoặc fiddler và kiểm tra yêu cầu đầu tiên để xác minh các tiêu đề giống nhau.
jdweng

1
Đọc cảnh báo này . Bạn đã đúng hành vi được thay đổi, nó phù hợp với hành vi cũ EF 6.x. Điều tôi không thể hiểu Làm thế nào mà EF 2.2 đã dịch nó thành 2 truy vấn. Bạn có mẫu cho điều đó?
Eldar

@Eldar, cảm ơn bạn đã cung cấp liên kết. Việc dịch sang hai truy vấn đã được thực hiện, bởi vì cùng một bộ lọc (-> WHERE-Article) đã được sử dụng để tìm nạp dữ liệu từ bảng Item và AddInfo, tất nhiên sau đó có một liên kết trở lại chính bảng mục. EF đã khâu các mục và thuộc tính điều hướng bộ sưu tập của chúng lại với nhau trong bộ nhớ.
TheSchmu

Câu trả lời:


3

Theo cập nhật của câu hỏi ban đầu của tôi, những hiểu biết đã đi xa để đảm bảo với bản thân rằng hiện tại, trên thực tế không có cấu hình được xây dựng để quay lại thực hiện truy vấn phân tách.

Tuy nhiên, MS đã cung cấp các mẫu mã về cách thực hiện việc này với các thay đổi mã tối thiểu (đối với trường hợp sử dụng của chúng tôi!) Tại đây .

Chúng tôi chỉ đơn giản là xóa các lệnh gọi .Include (...) đến các thuộc tính điều hướng bộ sưu tập (quan hệ 1: n trong trường hợp của chúng tôi, quan hệ 1: 1 không bị ảnh hưởng!). Sau khi tìm nạp các mục, chúng tôi chỉ cần thực hiện một cuộc gọi khác bằng cách sử dụng:

...
var myQueryable = this._context.Items.Where(**some filter**);
... // moar filters
var result = myQueryable.ToList();
...
var addInfos = myQueryable.Include(x => x.AddInfos).SelectMany(x => x.AddInfos).Select(x => new {x.ItemID, x}).ToList();

Điều này tìm nạp các thực thể thuộc tính điều hướng bộ sưu tập và - nếu tính năng theo dõi thay đổi được bật - sẽ tự động điền vào các bộ sưu tập trên các mục riêng lẻ trong resultbiến.


Bạn có thể chia sẻ đầu ra (truy vấn sql được tạo) của truy vấn thứ hai không.
Eldar
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.