2011-01-21 28 views
5

Tôi đang làm việc trên một dự án ASP.NET MVC nhỏ vào lúc này.
Tôi đang cố gắng triển khai Nhibernate để tồn tại trên cơ sở dữ liệu MS Sql Server. Đã dành nhiều thời gian nghiên cứu DDD và các dự án khác được tìm thấy trên Internet, tôi đã quyết định chuyển sang mẫu kho lưu trữ. Bây giờ tôi phải đối mặt với một tình huống khó xử.
Tôi có thực sự cần một kho lưu trữ khi sử dụng Nhinbernate không?
Nó sẽ không thể tốt hơn để có một lớp dịch vụ (Tôi không có một lớp dịch vụ tại thời điểm này) mà tương tác với Nhinbernate tránh phải viết nhiều lần một cái gì đó như thế:ASP.NET MVC, Nhibernate và kho lưu trữ cho các dự án vừa và nhỏ

public Domain.Reminder GetById(Guid Code) 
{ 
    return (_session.Get<Domain.Reminder>(Code)); 
} 

public Domain.Reminder LoadById(Guid Code) 
{ 
    return (_session.Load<Domain.Reminder>(Code)); 
} 

public bool Save(Domain.Reminder Reminder) 
{ 
    _session.SaveOrUpdate(Reminder); 
    return (true); 
} 

public bool Delete(Domain.Reminder Reminder) 
{ 
    _session.Delete(Reminder); 
    return (true); 
} 

Tôi tìm thấy một cũ Bài đăng của Ayende chống lại kho.
Tôi biết có một cuộc tranh luận lớn về những chủ đề này và câu trả lời luôn là ... phụ thuộc, nhưng có vẻ như với quá nhiều lớp trừu tượng, mọi thứ trở nên phức tạp và khó theo dõi hơn.
Tôi có sai không?

+0

Chỉ cần một ghi chú nhỏ. Không có dự án vừa và nhỏ, bây giờ nó có thể nhỏ, nhưng ngày mai người quản lý của bạn sẽ hỏi bạn một tính năng khác, và cái khác, và cái khác, và cuối cùng bạn sẽ có một dự án lớn với kiến ​​trúc vừa và nhỏ . Tôi thực sự không giống như Big Design Up Front, nhưng đôi khi bạn cần phải suy nghĩ trước một chút. – goenning

+0

Tôi đồng ý với bạn hoàn toàn nhưng, thực sự, tôi không thể thấy lợi ích trong việc sử dụng kho lưu trữ nếu không thực tế là tôi có thể không sử dụng nihbernate trong tương lai. Nó tạo ra rất nhiều công việc mà tôi không thể biện minh vào lúc này. – LeftyX

Trả lời

7

Ayende chống lại viết một kho lưu trữ theo cách bạn đã làm vì lý do bạn hỏi câu hỏi này, đó là mã lặp đi lặp lại và NH có thể xử lý tất cả mọi thứ. Ông chủ trương chỉ cần gọi NH trực tiếp như bạn sẽ là một kho lưu trữ, và ngừng lo lắng về nó.

Tôi khá đồng ý với anh ấy. Có thực sự không phải là nhiều để đạt được ngoại trừ cho công việc nhiều hơn nữa.

+0

Tôi phải thú nhận rằng đây là câu trả lời tôi muốn nghe :-) – LeftyX

0

Tôi đã tìm thấy một số lý do tại sao bạn nên sử dụng Kho lưu trữ/DAO/Dù.

  1. Kiểm tra đơn vị. Tôi không bao giờ cố gắng để giả/stub một ISession, nhưng tôi sẽ nói rằng nó phải là một LOT phức tạp hơn so với chế nhạo hoặc stubbing một Repository/DAO Interface.
  2. Sử dụng lại mã. Nếu bạn viết truy vấn của mình trực tiếp vào Dịch vụ/Bộ điều khiển, bạn sẽ kết thúc sao chép nó khi bạn cần sử dụng lại một truy vấn cụ thể. Nếu bạn có nó wrapper vào một Repository, chỉ cần gọi nó là phương pháp.
  3. Single Responsibility Principle. Việc lan truyền các truy vấn của bạn xung quanh Bộ điều khiển của bạn khiến bạn phá vỡ nguyên tắc này.
  4. NHibernate Dependency. Ok, điều này là khó xảy ra, nhưng nếu bạn cần thay đổi ORM của bạn, các kho lưu trữ làm cho nó dễ dàng hơn (nhìn, nó dễ dàng hơn, không dễ dàng :)). Hoặc ngay cả khi bạn cần thay đổi DataSource của người dùng từ Cơ sở dữ liệu sang Microsoft Active Directory, nó sẽ dễ dàng hơn.

Đó là điều cần biết, không thể nhớ bất cứ điều gì khác.

+0

Cảm ơn Oenning. Tôi không muốn viết truy vấn trong bộ điều khiển của tôi nhưng trong một lớp dịch vụ. Tôi nghĩ rằng đó là một nơi tốt để đặt một số logic kinh doanh quá. Nó sẽ không có trong giao diện người dùng và nó sẽ được tái sử dụng nếu tôi muốn cắm lớp dịch vụ của tôi ở một nơi khác. Nhibernate phụ thuộc. Vâng, vâng, tôi có thể đồng ý nhưng tôi không nghĩ rằng nó sẽ xảy ra sớm và tôi không nghĩ rằng đó là khác nhau từ việc thay đổi một kho lưu trữ. Dù sao cũng cảm ơn bạn. – LeftyX

+0

1. Nếu bạn thử repo, bạn đang sử dụng mẫu thử nghiệm "đã biết lịch thi đấu". 2. Không có gì nói rằng bạn không thể tạo ra các trừu tượng trong lớp dịch vụ của bạn. Điều này hoàn toàn sai. 3. Không hề. Bạn sẽ gọi db ở đâu đó. Cho dù của nó trong một dịch vụ hoặc gọi lại phương thức repo hoặc một phần của bộ điều khiển không quan trọng. Vẫn là cùng một mã. Bộ điều khiển vẫn chịu trách nhiệm truy vấn db. – jfar

+0

@jfar 1. Mô hình chống thử nghiệm "được biết đến" là gì? Chưa bao giờ nghe về nó. Tôi luôn giả lập kho của tôi. 2. Nếu tôi có những gì bạn nói đúng, bạn sẽ kết thúc thiết kế giống như một Kho lưu trữ nhưng bạn sẽ gọi nó là cái gì khác. Có ví dụ nào về điều này không? Tôi muốn xem một số mã trên cái này. 3. Bộ điều khiển không chịu trách nhiệm truy vấn db, anh ta cần phải nhờ người khác làm điều đó. Anh ta nhận được yêu cầu và dựa trên nó ủy nhiệm nhiệm vụ cho các lớp khác và chọn khung nhìn tiếp theo. – goenning

4

Sử dụng một kho lưu trữ chung để thay thế. Một kho lưu trữ cho mỗi lớp có thể dễ dàng bị quá mức.

Tôi sử dụng một kho lưu trữ với phương thức Get, Load, Save và các phương thức Đối sánh khác nhau (một cho LINQ và một cho các truy vấn miền của tôi).

Phương pháp cuối cùng chấp nhận triển khai ICreateCritiera. Dưới đây là giao diện và một thực hiện của nó.

public interface ICreateCriteria<T> : ICreateCriteria 
{ 
    DetachedCriteria GetCriteria(); 
} 

public class ChallengesAvailableToRound : ICreateCriteria<Challenge> 
{ 
    private readonly Guid _roundId; 

    public ChallengesAvailableToRound(Round round) 
    { 
     _roundId = round.Id; 
    } 

    public DetachedCriteria GetCriteria() 
    { 
     var criteria = DetachedCriteria.For<Challenge>(). 
      CreateAlias("Event", "e"). 
      CreateAlias("e.Rounds", "rounds"). 
      Add(Restrictions.Eq("rounds.Id", _roundId)); 

     return criteria; 
    } 
} 

Điều này cho phép tôi chia nhỏ các truy vấn cho các lớp của riêng mình và sử dụng lại chúng dễ dàng hơn dự án của tôi.

+0

Tôi thích ý tưởng của bạn Kenny. Tôi sẽ cố gắng để làm việc trên nó. Cảm ơn – LeftyX

+0

Kenny, tôi nghĩ giải pháp của bạn đủ tốt cho tôi. Cảm ơn. – LeftyX

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