Reputation:
Assume a web project by ASP.NET MVC 5 and OWIN/Identity membership. The IoC is done with Unity. Everything is within one project now. Question: Does it make any sense to separate MVC, Idenity and IoC to isolated projects and encapsulate Identity into some IAccountService to be resolved by Unity in MVC project? The question seems to be quite silly, but my rubber duck keeps silence for unknown reasons, any guess?
The goal I want to achieve looks like this
ASP.NET MVC (OWIN) --> IoC (Unity) --> AccountServiceImpl --> Identity
Both MVC, IoC --> Contracts (IAccountService)
where --> is a project reference
I need it to be able to change IoC container and also I need Identity data to be accessed from another projects through an interface
Upvotes: 5
Views: 1602
Reputation: 35106
I'll add my 0.02¢ to the excellent answer from Rowan. I'll say more about actual Identity implementation.
As far as ASP.Net Identity framework goes - it might be slightly tricky to move it out of MVC project into higher (or lower, depends how you place it) sitting layer. I'm pretty sure you'd want to have ApplicationUser
object in your domain layer. But ApplicationUser
depends on IdentityUser
which depends on Identity.EntityFramework
, depending on EntityFramework
. And adding EF to your domain project might go slightly against the rules of Onion Architecture.
Also ApplicationUserManager
from Identity framework is massive (in terms of number of methods) and also depends on EF. So hiding it behind an interface can be tricky.
So really you have 2 options:
ApplicationUser
and ApplicationUserManager
classes in your Domain layer. And don't wrap UserManager
in an interface for multiple reasons.ApplicationUserManager
.I have tried both and both approaches in different projects and both work equally well. I have tried adding interface on top of ApplicationUserManager
and failed - mostly because of the size of the class, also it is aimed to work in async manner and there are sync-wrappers. Sync wrappers will not work with your interface - because strong-typing.
I've written a blog-post about applying DI to Identity framework and there is a discussion in the comments about layers separating - have a look for ideas.
Upvotes: 2
Reputation: 16358
Yes, it is safe to separate your solution into smaller projects such as MVC, Identity and IoC.
At least, that's my short answer.
Does it make sense? The long answer is a little bit more complicated. I've answered some similar questions before where I address solution and project architecture:
In the answer above, I explained
[...] I have a typical structure like this:
- MyProject.Core
- MyProject.Domain
- MyProject.DependencyInjection
- MyProject.Infrastructure
- MyProject.Web
- MyProject.Tests
Jeffrey Palermo encourages the use of Onion Architecture. In part 4 of his article on Onion Architecture, Jeffrey provides an example solution with the following structure
However, Jimmy Bogard somewhat disagrees with me and my approach.
In Evolutionary Project Structure, Jimmy explains:
I used to care quite a bit about project structure in applications. Trying to enforce logical layering through physical projects, I would start off a project by defaulting to building an app with at least two projects, if not more.
Indeed, Jimmy describes his previously-preferred solution architecture style as being similar to the style that I've mentioned above.
Jimmy goes further to say that "deciding about project structure is a waste of time and energy". He actually prefers a simpler solution structure. That is, very little.
Although Jimmy does clarify his position by saying:
I have absolutely nothing against layered software design. Using project structure to do so is a waste of time if you only have 1 app you're deploying [...]
(Emphasis mine)
If you have other applications needing to reference aspects of your MVC solution, it may very well make sense to split them out into their own projects so that you can easily reference them.
I think what we should conclude is that:
Solution architecture isn't a rule or a law. Separate projects out where it makes sense.
Make sure your solution is easy to maintain and easily understood by others. Don't over-complicate your solution.
Upvotes: 5