2010-03-09 37 views
5

Có thể thực hiện tìm kiếm toàn cục được tìm thấy trên các đối tượng được quản lý NHibernate không?Tìm tham chiếu đối tượng toàn cầu trong NHibernate

Cụ thể, tôi có một lớp liên tục được gọi là "Io". Có một số lượng lớn các trường trên nhiều bảng có khả năng chứa đối tượng thuộc loại đó. Có cách nào (cho một trường hợp cụ thể của một đối tượng Io), để lấy một danh sách các đối tượng (của bất kỳ loại nào) mà thực sự tham chiếu đến đối tượng cụ thể đó? (Điểm thưởng nếu nó có thể xác định các trường cụ thể thực sự chứa tham chiếu, nhưng điều đó không quan trọng.)

Vì ánh xạ NHibernate xác định tất cả các liên kết (và cơ sở dữ liệu bên dưới có liên kết khóa ngoài tương ứng), nên có một số cách để làm điều đó.

Hãy tưởng tượng điều này loại cấu trúc:

class Io 
{ 
    public int Id { get; set; } 
    // other fields specific to the Io type 
} 

class ThingOne 
{ 
    public int Id { get; set; } 
    public Io SensorInput { get; set; } 
    public Io SolenoidOutput { get; set; } 
    // other stuff 
} 

class ThingTwo 
{ 
    public int Id { get; set; } 
    public Io SensorInput1 { get; set; } 
    public Io SensorInput2 { get; set; } 
    public SubThing Doohickey { get; set; } 
    // ... 
} 

class SubThing 
{ 
    public int Id { get; set; } 
    public Io ControlOutput1 { get; set; } 
    // ... 
} 

Cho một ví dụ cụ thể của Io, tôi muốn khám phá ra rằng nó được tham chiếu bởi ThingTwo với id 12. Hoặc rằng nó được tham chiếu bởi điều đó và cũng bởi ThingOne với id 16. Nếu có thể, ví dụ, tham chiếu đầu tiên là thông qua SensorInput2, ví dụ.

Trả lời

3

Các ánh xạ cấu hình dường như không để lộ mối quan hệ FK, do đó trong thời gian này, một số phản ánh có thể tìm thấy đối tượng loại nào tham chiếu đến điều này. Lưu ý rằng mã bên dưới giả định rằng bạn có tất cả các lớp ánh xạ nhibernate vào một assembly đơn và cũng sử dụng C# 3.0 trở lên để hỗ trợ LINQ.

IO toSearch = nhSession.Get<IO>(5); 
var assembly = Assembly.Load("EntityAssembly"); 
IList<Type> assemblyTypes = assembly.GetTypes(); 
var searchType = toSearch.GetType(); 
var typesThatContainedSearchTypeProperty = 
    assemblyTypes.Where(
    ast => ast.GetProperties().Count() > 0 && 
    ast.GetProperties().Where(
     astp => astp.PropertyType != null && astp.PropertyType == searchType).Count() > 0); 

Bây giờ nếu bạn cũng muốn nhận các đối tượng chứa trường hợp cụ thể này, bạn có thể có một tiêu chí tốt để thực hiện nó trong một chuyến đi khứ hồi.

var multiCrit = nhSession.CreateMultiCriteria(); 

foreach (var type in typesThatContainedSearchTypeProperty) 
{ 
    //maybe this class has multiple properties of the same Type 
    foreach (PropertyInfo pi in type.GetProperties().Where(astp => astp.PropertyType == toSearch.GetType())) 
     multiCrit.Add(nhSession.CreateCriteria(type).Add(Restrictions.Eq(pi.Name, toSearch))); 
} 
IList results = multiCrit.List(); 

như bạn có thể đoán, vì chúng tôi bắt đầu với sự phản chiếu, chúng tôi chỉ có thể kết thúc bằng sự phản chiếu. Danh sách kết quả là một mảng với mỗi mục nhập là kết quả của mỗi tiêu chí, trong đó mỗi tiêu chí tìm kiếm có thể là một kết quả duy nhất hoặc một danh sách kết quả.

+0

Lúc đầu, điều này đã cho tôi một số rắc rối, nhưng điều đó hóa ra lại là một lỗi trong ánh xạ hbm của tôi. Sau khi san bằng kết quả vào một danh sách duy nhất, điều này thực hiện chính xác những gì tôi đã sau. Cảm ơn! – Miral

+0

Rất đẹp nhưng bạn nên biết ** toSearch.GetType() **. Nó có thể trả về đối tượng proxy thay vì đối tượng thực. –

+0

@ S.M.Amin bạn đang trộn Get() với Load().Get() sẽ không trả về proxy, Load() sẽ – Jaguar

0

Lớp "lo" của bạn có chứa tham chiếu đến (các) đối tượng có chứa đối tượng "lo" không?

tức là nếu "Lo" là tài liệu tham khảo của một số số "Hi" đối tượng:

public class Lo 
{ 
    List<Hi> hiObjects; 
} 

Bây giờ nếu bạn có một thể hiện của "Lo":

Lo lo = new Lo(); 
List<Hi> hiObjects = lo.hiObjects; 

Nếu bạn không có các loại tài liệu tham khảo này, bạn có thể thêm chúng.

+0

Chỉ khi có cách để NHibernate điền thông tin đó vào cho tôi. Nó chắc chắn không thuộc về trạng thái tồn tại - đây là thông tin được phục hồi như là một phần của việc xây dựng đồ thị đối tượng. Tôi đã mở rộng câu hỏi của mình bằng một ví dụ hy vọng giải thích mọi thứ tốt hơn. – Miral

+0

Ngoài ra, hiện tại có khoảng 20 loại khác nhau có thể chứa Io. Vì vậy, tôi thực sự không muốn phải liệt kê chúng một cách rõ ràng ở bất cứ đâu. – Miral

Các vấn đề liên quan