In all examples i found about repository pattern and service layers the Service always has a unique dependency wich is the correponding model entity(ProductService is injected with ProductRepository). supose this service has a method Add(string name, int
typeID, int productFamily).
In real world inserting an entity almost always means associating related existing model entities , much like Product type, family and so on.
So ProductRepository isnt enough to query database by id of type or productFamily and associate to product.
How does repository pattern resolves this question?
I think it is at repository implementation level where we can query the database because we have acces to DbContext or any other abstraction. So we extend the usually generated repository for Product(in this case).
If i am thinking ritgh this doesn´t violate the single responsability principle because Product is an aggregate root and has to be traeted like that.
I like Architecture questions. It is here that we are truly thinking about what makes good software. There's rarely a right or wrong answer, it is more philisophical in nature, and I tend to learn the most here.
Repository Pattern is about abstracting data access from the business layer so you can use simple methods like ListWidgets() or AddWidget(), etc. Like you, I have found that this can get a little more convoluted when working with a relational database since
you may need to consider related tables as well. When I first got into this, it took me a while to understand why my repositories were failing until I realized they each had their own data context reference. There are a number of ways you could resolve this,
and it is ultimately going to depend on your architecture.
One method is to have a "BaseRepository". This will have the data context reference in it and any standard methods like Save(), etc. The rest of your repositories could then extend this repository, but you would still need to have the business layer maintain
the datacontext and pass it through constructor injection, which doesn't sound ideal.
You could also group your repositories by functional area of your application. This could solve your business layer problems, but now your data model is rather convoluted.
For me, I have found I can get away with keeping them separate in most cases and just ensuring that the repository is responsible for maintaining any strict relationships. For instance, say you have a 1-1 relationship UserAccount to UserProfile where a
UserAccount must always have 1 and only 1 UserProfile. We could discuss the pros and cons of actually splitting the two tables, but say this is a design decision you have come up with. In this case, I don't even implement a UserProfile repository. So if,
in the business layer, I enter just enough data to create a UserAccount, then the repository will automatically create a UserProfile and populate it with empty strings where appropriate.
"Dream as if you'll live forever, live as if you'll die today." --James Dean
And you absolutly right when you talking about relational databases and related objects.
One of my approaches to it is to use the following:
1.Generic Repository pattern with standard CRUD operations that separates data layer from BL
2.Repository factory that creates the repository instances regarding the model than passed into the generic type and DbContext instance that passed to the constructor
3.Unit Of Work pattern that implements all required repositories with single/mutual DbContext instance and has a single method of SaveChanges that actually calls to DbContext to save all the enity changes in one operation against database.
Just google the unit of work and repository patterns and maybe you can find the better answer on it.
JorgeVinagre
Member
5 Points
15 Posts
Repository and Single Responsability
Jan 24, 2013 10:27 AM|LINK
Hi
I have this question:
In all examples i found about repository pattern and service layers the Service always has a unique dependency wich is the correponding model entity(ProductService is injected with ProductRepository). supose this service has a method Add(string name, int typeID, int productFamily).
In real world inserting an entity almost always means associating related existing model entities , much like Product type, family and so on.
So ProductRepository isnt enough to query database by id of type or productFamily and associate to product.
How does repository pattern resolves this question?
I think it is at repository implementation level where we can query the database because we have acces to DbContext or any other abstraction. So we extend the usually generated repository for Product(in this case).
If i am thinking ritgh this doesn´t violate the single responsability principle because Product is an aggregate root and has to be traeted like that.
Im i right?
Thanks
AceCorban
Star
12318 Points
2269 Posts
Re: Repository and Single Responsability
Jan 24, 2013 03:32 PM|LINK
I like Architecture questions. It is here that we are truly thinking about what makes good software. There's rarely a right or wrong answer, it is more philisophical in nature, and I tend to learn the most here.
Repository Pattern is about abstracting data access from the business layer so you can use simple methods like ListWidgets() or AddWidget(), etc. Like you, I have found that this can get a little more convoluted when working with a relational database since you may need to consider related tables as well. When I first got into this, it took me a while to understand why my repositories were failing until I realized they each had their own data context reference. There are a number of ways you could resolve this, and it is ultimately going to depend on your architecture.
One method is to have a "BaseRepository". This will have the data context reference in it and any standard methods like Save(), etc. The rest of your repositories could then extend this repository, but you would still need to have the business layer maintain the datacontext and pass it through constructor injection, which doesn't sound ideal.
You could also group your repositories by functional area of your application. This could solve your business layer problems, but now your data model is rather convoluted.
For me, I have found I can get away with keeping them separate in most cases and just ensuring that the repository is responsible for maintaining any strict relationships. For instance, say you have a 1-1 relationship UserAccount to UserProfile where a UserAccount must always have 1 and only 1 UserProfile. We could discuss the pros and cons of actually splitting the two tables, but say this is a design decision you have come up with. In this case, I don't even implement a UserProfile repository. So if, in the business layer, I enter just enough data to create a UserAccount, then the repository will automatically create a UserProfile and populate it with empty strings where appropriate.
iluxa.v
Member
215 Points
47 Posts
Re: Repository and Single Responsability
Jan 29, 2013 06:16 AM|LINK
This is excelent question.
And you absolutly right when you talking about relational databases and related objects.
One of my approaches to it is to use the following:
1.Generic Repository pattern with standard CRUD operations that separates data layer from BL
2.Repository factory that creates the repository instances regarding the model than passed into the generic type and DbContext instance that passed to the constructor
3.Unit Of Work pattern that implements all required repositories with single/mutual DbContext instance and has a single method of SaveChanges that actually calls to DbContext to save all the enity changes in one operation against database.
Just google the unit of work and repository patterns and maybe you can find the better answer on it.