I'm designing a larger enterprise architecture and I'm in a doubt about how to separate the models and design those. There are several points I'd like suggestions for: - models to define - way to define models
Currently my idea is to define:
- Core (domain) model
- Repositories to get data to that domain model from a database or other store
- Business logic model that would contain business logic, validation logic and more specific versions of forms of data retrieval methods
- View models prepared for specifically formated data output that would be parsed by views of different kind (web, silverlight, etc).
For the first model I'm puzzled at what to use and how to define the mode. Should this model entities contain collections and in what form? IList, IEnumerable or IQueryable collections? - I'm thinking of immutable collections which IEnumerable is, but I'd like to avoid huge data collections and to offer my Business logic layer access with LINQ expressions so that query trees get executed at Data level and retrieve only really required data for situations like the one when I'm retrieving a very specific subset of elements amongst thousands or hundreds of thousands.
What if I have an item with several thousands of bids? I can't just make an IEnumerable collection of those on the model and then retrieve an item list in some Repository method or even Business model method. Should it be IQueryable so that I actually pass my queries to Repository all the way from the Business logic model layer? Should I just avoid collections in my domain model? Should I void only some collections?
Should I separate Domain model and BusinessLogic model or integrate those?
Data would be dealt trough repositories which would use Domain model classes. Should repositories be used directly using only classes from domain model like data containers?
This is an example of what I had in mind:
So, my Domain objects would look like (e.g.)
public class Item
{
public string ItemName { get; set; }
public int Price { get; set; }
public bool Available { get; set; }
private IList<Bid> _bids;
public IQueryable<Bid> Bids
{
get { return _bids.AsQueryable(); }
private set { _bids = value; }
}
public AddNewBid(Bid newBid)
{
_bids.Add(new Bid {....
}
}
Where Bid would be defined as a normal class.
Repositories would be defined as data retrieval factories and used to get data into another (Business logic) model which would again be used to get data to ViewModels which would then be rendered by different consumers.
I would define IQueryable interfaces for all aggregating collections to get flexibility and minimize data retrieved from real data store.
Or should I make Domain Model "anemic" with pure data store entities and all collections define for business logic model?
One of the most important questions is, where to have IQueryable typed collections? - All the way from Repositories to Business model or not at all and expose only solid IList and IEnumerable from Repositories and deal with more specific queries inside Business model, but have more finer grained methods for data retrieval within Repositories.
So, what do you think? Have any suggestions?