I'm having a couple of problems with circular reference/dependency that I've been sitting on all day. Something must be wrong with my thought process, I just don't get it.
Here are my projects:
Flip.Main (ASP.NET MVC)
Flip.Domain (C# DLL)
Flip.Services (C# DLL)
Flip.Utility (C# DLL)
Current References/Dependencies:
Flip.Main -> Flip.Domain, Flip.Services, Flip.Utility
Flip.Services -> Flip.Domain, Flip.Utility
Flip.Domain -> Flip.Utility
I wanted to structure my project in a way that my services project has all services, my domain project the model, repository and 'fluent' extensions to query the model, and the main and utility project are pretty much self explanatory.
Problems encountered:
1) I have an EmailService in my Flip.Services project, which needs to send out localized emails. All localization is done in Flip.Main's App_GlobalResources. No idea how to get the strongly typed emails and other localized resources now to my service layer as Flip.Main already depends on the service layer and therefore I can have it depend back to the Main project.
2) I have business classes, e.g. CustomerSearchFilter which represents a strongly typed search query. I want those business classes outside of the Flip.Domain project because they are not part of the domain model. However, in my CustomerSearchFilter class I have domain class instances (e.g. CustomerGroup) so it needs to know about domain classes. At the same time my Fluent interface in my Flip.Domain project needs to know what CustomerSearchFilter is so I can apply it to my IQueryable interface. Circular reference again.
3) I have a custom [AuthorizeSessionState] attribute which I use to decorate specific controller actions in my ASP.NET MVC Flip.Main project. This is an ActionFilterAttribute which needs to instantiate my SessionService who resides in my Flip.Services project. I can't put this into my Utility class though (because Flip.Services already references Flip.Utility). I don't think they should be in Flip.Main either - do I have to make another project for this!?
(20 more)
I feel like I'm making a mistake somewhere down the line, especially when I read that others usually don't encounter circular reference problems. Help?
Use interfaces for all non-trivial classes. Place interfaces in a different assembly from implementation.
The question comes down to what you separate by namespace and what you separate by DLL. If you have a good reason to keep EVERYTHING modular, you have to work really hard. But if each of these dlls only have a class or two in them, perhaps you could merge them together?
Take a few minutes and sort out the procedures ... create an identifier for each project (FM, FS, FD, FU). List each publicly accessible procedure on a page and then add an identifier for a project, if that project uses the procedure ...
Then you can see which procedure needs to be in (or accessible to) which project.
Hope that helps!
You can put your localized email strings in Flip.Services. The downside is that you have two places to maintain localized resources. You can also have a separate dll for all your resources to minimize the place to edit resources.
You have to move the fluent interface to an other dll or make CustomerSearchFilter part of the domain.
You will need to add more projects or rearrange your structure and use namespaces to create the separation.
It sounds like your building on concrete implementations instead of interfaces/contracts. As Ima suggests define interfaces that describe what a certain class should be able to do. Use this interface when you declare properties, parameters and the like. Keep the interfaces separate from the implementaion and both the implementation and the projects that uses the interface can reference the interface project.
You then get the nice option of using dependency injection making your code easier to test as an a side
In the "tiers" of a domain, repositories and services live at the same logical level, above the domain in an infrastructure role. I would suggest moving your repository implementations (queries, etc.) outside of the domain itself. That solves #2 at least.
Related
I currently have all my common utility function methods in a base controller, which all of my controllers inherits from. These are methods for functionality like uploading files, resizing pictures, deleting files, sending e-mails, generating random passwords, hashing passwords, etc.
What is the recommended structure for these kinds of things?
In that case you shouldn't put all these utility functions inside your base controller. You will face a lot of problems if your project grows. Changes and testing of these methods can become difficult, all your inherited classes need to use the same utility methods, etc. Have a look at Composition over inheritance to see another approach.
Somethimes I tend to organize my projects in the following manner if that might help you:
Simple helper methods: Create a folder and a namespace (e.g. namespace [...].Common") inside your web project and put one or more public static classes inside it (e.g. class "FileHelper.cs", "StringHelper.cs", etc). If you need one of these methods in a controller action simply put a "using ...Common" statement at the top of your controller class and call e.g. FileHelper.MethodName.
If I can define a closed subject area with a group of methods I try to encapsulate these methods in a service class (maybe even outside the web project if I have a feeling that I might need this functionality in other projects too), define an interface for that class and plug that functionality into controller classes by using dependency injection. If you don't know about that concept you should definitely read Dependency injection in ASP.NET Core. Dependency injection is a vastly used major concept in ASP.NET Core projects that brings you a lot of advantages and - if used correctly - stears your work into well-organized projects.
More complex organizations are always possible depending on your needs. Have a look at multitier, hexagonal or onion architecture if your projects grow.
We would like to create a new project with a clean architecture. So our team decided to have:
Repository pattern
Data Access Layer
Business Access Layer
Common Layer (Abstractions such as IPersonRepository, IPersonService, ICSVExport)
Some Core services such as create CSV files.
UnitTests
Now what we have is:
PersonsApp.Solution
--PersonsApp.WebUI
-- Controllers (PersonController)
--PersonApp.Persistence
--Core folder
-IGenericRepository.cs (Abstraction)
-IUnitOfWork.cs (Abstraction)
--Infrastructure folder
-DbDactory.cs (Implementation)
-Disposable.cs (Implementation)
-IDbFactory.cs (Abstraction)
-RepositoryBase.cs (Abstraction)
--Models folder
- Here we DbContext, EF models (Implementation)
--Repositories
- PersonRepository.cs (Implementation)
--PersonApp.Service
--Core folder
-IPersonService.cs (Abstraction)
-ICSVService.cs (Abstraction)
--Business
-PersonService.cs (Abstraction)
--System
-CSVService.cs (Abstraction)
--PersonApp.Test
In my view, our structure is a little bit messy.
The first problem is:
PersonApp.Service has abstractions(interfaces) and implementations
in one class library.
The second problem is:
PersonApp.Persistence has abstractions(RepositoryBase) and
implementations in one class library. But if I move RepositoryBase,
IGenericRepository, IUnitOfWork in a class library called
PersonApp.Abstractions, then I will circular reference errors
between PersonApp.Abstractions and PersonApp.Persistence
What is the best way to organize our solution?
This is probably not a good S.O. question given it's asking something that is opinion-based. When planning out project structure I aim to keep things simple. If an abstraction is for polymorphism I will consider moving interfaces into a separate "common" assembly. For example if I want to provide several possible implementations of a thing, I will have a common assembly that declares the interface, then separate assemblies for the specific implementations. In most cases I use interfaces as contracts so that I can substitute the real with mocks. In these cases I keep the interfaces nested beneath the concrete implementation. I use a VS add-in called NestIn to provide nesting support. This keeps the project structure nice and compact. However, a caveat, if you are using .Net Standard libraries, file nesting doesn't appear to be supported. (Hopefully this changes / has changed)
So for a SomeService, my folder project structure would look like:
Services [folder]
SomeService.cs [concrete]
SomeService.dependencies.cs [partial] [nested]
ISomeService [nested]
the .dependencies.cs file is a partial class where I put all dependencies and the constructor. This keeps them tucked out of the way while I'm working on implementation. I used to rely on #regions way back, but frankly I cannot stand them now. Partial classes are much better IMO.
My repositories live alongside my entities in a Domain assembly.
Entities [folder]
Configuration [folder]
OrderConfiguration.cs
Order.cs
Repositories [folder]
OrderManagementRepository.cs
OrderManagementRepository.dependencies.cs
IOrderManagementRepository.cs
MySystemDbContext.cs
I don't use Generic repositories, rather repositories are designed to pair up with Controllers or Services that they serve. I might have some general purpose repositories that service more than one consumer. (stuff like lookups, etc.) This pattern evolved for me from wanting to satisfy SRP. The biggest issue with things like generic repositories is that they need to serve multiple masters. While an OrderRepository might serve a single responsibility in being worried solely about Orders, the problem I see is that many different places will need access to Order information. This means different criteria, and wanting different amounts of data. So instead, if I have an OrderManagementService that deals with orders, order lines, etc. and touches on Products and other bits and bobs in the process of placing orders, I will use an OrderManagementRepository to serve virtually all data needed by the service, and manage the wrapping of supported operations for managing an order. This means my service only typically needs 1 repository dependency (rather than an OrderRepository, ProductRepository, etc. etc. etc.) and my OrderManagemmentRepository has only 1 reason to change. (But that's getting off topic. :)
I started relying on Nesting a while ago back when you needed ReSharper or the like to get access to "Go to Implementation" for interfaces. Go to Definition would take you to the interfaces, which when in a separate namespace or assembly made navigating around dependencies a pain. By nesting interfaces under their concrete implementations, it's a quick click through from the interface to it's concrete implementation and back. I make use of tracking the current code file in the solution manager so as I navigate through code my project view highlights/expands to the currently viewed file.
Ultimately, your project structure should reflect how you prefer to navigate through the code to make it as intuitive and easy to get around to find the bits you need. That will be different for different people, so partial classes and nesting works really well for me, as I am a very visual person that uses the project view a lot. It might not serve any benefit for people that are hotkey navigation wizards. Ultimately though I'd say keep it simple, and adaptable. Trying to plan it out too much in the early stages is like premature optimization. Don't be afraid to move things around as a project grows. A project that grows simply by adding code will invariably turn into a unstable, confusing tangled mess, no matter how well you try to plan ahead. Good code comes from constant re-factoring which is moving things around and deleting as well as adding. When your style is adaptable and you are building in a way that is constantly refining and code is getting better through natural selection, the structure is free to evolve.
Hopefully that might give some food for thought. Good luck in the green fields!
Edit: Regarding polymorphic interfaces vs. contract interfaces. With polymorphic interfaces where I want to have multiple, substitute-able concrete implementations, this is a case where the interface (and any applicable base class) would reside in a separate assembly. The nesting solution applies for cases where the only substitution is for mocking purposes. (unit testing) A recent example of a polymorphic instance was when I needed to replace an in-built SMS service wrapper to support a new SMS provider. This resulted in re-factoring a hard-coded concrete class from the original code into a SMSCore assembly containing the ISMSProvider interface and some general common definitions, then two assemblies for the implementations: SMSByMessageMedia and SMSBySoprano.
Other cases that come up might be around customizations. For instance I have a number of personal libraries and such for general purpose code, and when implementing them for a client there might be some client-specific "isms" that I want to make. These cases are typically resolved by extending the general purpose implementation (Open-Closed Principle) by overriding, or implementing a provided interface for the custom dependency that the general purpose code can consume. In both of these cases, the client project is going to have a reference to the concrete implementation(s) anyways, so having extendable classes and dependency interfaces in that assembly/namespace doesn't pose any issues. This saves needing to add several different namespaces & assembly references.
I am pretty new to MVC and I am currently working on an MVC 3 project in visual studio and I want to create a method or variable that is accessible globally. When I say globally I mean available in my web project, service layer project, and data layer project.
I guess when I say global I mean global to the entire solution.
I tried creating a class in the solution items folder and referencing in my web project but its not letting me add a reference to the class since it is not a DLL.
I am a little confused with how to do this. Any suggestion would be appreciated. Also keep in mind that though I am a programmer I am still somewhat new to MVC and programming.
Edit: I have also tried adding a method in the global.asax file but was unable to call it
You should create a shared assembly where you define the class. You can then add a reference to the shared assembly from all projects that need the feature.
The class that you want to be "global" sounds like some sort of service. I suppose this is the kind of thing you may want to do with a logging service for example.
Using a logging service as an example it is generally best practice for the interface to the logging service be defined in a lightweight contracts type assembly. Then any of your assemblies that require an implementation of ILoggingService should inject the necessary implementation using an IoC container such as Autofac or MEF.
This pattern is pretty common and allows you to share common services while keeping implementations loosely coupled. Also this pattern will lead to highly testable code as fake implementations can be injected with Moq
just finished one of my projects and about to start another. This is never taught in my university so i dont even know if it exists. Lets say for example you have the code...
MessageBox.Show("Hi");
Now i know i can call it in Form1.
I also know i can call it in another form providing it is in a public class / void or something?
My question is, is there a library system where i can add 30-40 code snippits each to do their own job. So when i want to update sql or run calculations i just call a code file from a library?
Sorry if im missing something obvious google is driving me insane, i know what i want to ask, just not how to ask it! Hope you understand my question..
Thanks, Regards..
Of course. In your solution in Visual Studio you can add a Class Library project and fill it with all of the re-usable code that you want. Then any project in the solution can reference it by adding a Project Reference to that project.
Note that it's very easy to go overboard on something like this. Take, for example, your example:
MessageBox.Show("Hi");
The MessageBox class is tightly coupled to the user interface. So it belongs in the user interface objects. (The forms in this case.) This is because if you try to use it in your class library then you would need to add user interface libraries to that class library, making it more tightly coupled with that specific user interface implementation. This makes the class library much less portable and less re-usable because it can only be used by projects of that same user interface technology. (Can't be used by web projects, for example.)
So you'll want to think about each common utility that you encapsulate into its own re-usable code. Does it belong in the UI, in the business objects, in the data access, etc.? If it's tightly coupled with a specific periphery technology (user interface technology, data access technology, etc.) then it probably belongs there.
One approach to this would be to have multiple "common utilities" libraries. Using a contrived naming scheme, a larger enterprise domain solution might have projects like this:
Domain.BusinessLogic (class library, referenced by everything)
Application.Forms.AdminPanel (forms application)
Application.Forms.OperationsPanel (forms application)
Application.Forms.Common (class library, referenced by other Forms apps)
Application.Web.PublicWebsite (web application)
Application.Web.Common (class library, referenced by other Web apps)
Infrastructure.DataAccess.SQLServer (class library, dependency-injected into the Domain)
Infrastructure.Vendor.SomeService (class library, dependency-injected into the Domain)
etc.
So you have a core business logic project, which contains anything that's universal to the entire business domain in which you're working. It should have no dependencies. (Not rely on user interfaces, databases, frameworks, etc.) Then you have applications of various technologies, into which are mixed class libraries which have application-coupled common functionality. And finally you have the other periphery of the domain, the back-end dependencies. These could be your data access layer, integrations into 3rd party systems and services, etc.
As any given piece of functionality is abstracted into a common utility to reduce duplication and increase re-use, take care to keep your code-coupling low so the "common utilities" aren't tightly bound to "uncommon dependencies." All too often in the industry there's an increase in tight coupling with code re-use. (See the Single Responsibility Principle.) So exercise good judgement to avoid that.
There's nothing inherently wrong with writing the same piece of code ("same" by keystrokes alone, not necessarily by conceptual purpose) more than once if it serves more than one responsibility and those responsibilities should not be mixed.
It sounds like you want to use static methods. Group your routines by what they do, and put them in a static class, .e.g
internal static class Utility
{
public static void Method1(int whatever)
{
// do stuff
}
public static void Method2(string another)
{
// do other stuff
}
}
You can then call them like:
Utility.Method1(7);
Utility.Method2("thingy");
The simple solution is create a new project and select the "Class Library" option. This will create a class which is compiled into a DLL (dynamically linked library). Everywhere you want to use this common code you add can add a reference to the assembly, then in the specific files you use it, you'll have to add a using statement for it.
If you're required to turn in multiple projects you could put all of them under a single solution. If you right click the solution and select the properties option for the drop down menu it will open a new window with a "Configuration Properties" option in the left nav bar. Select it, then you can specify build dependencies. So if you have projects A and B which use methods in project C (the class library) then you can set that as a build dependency meaning whenever you build project A, B or the solution as a whole, it will first build project C.
This is commonly how enterprise software is structured; some dll's or exe's that are the application level code, then many other projects which build common code that is often shared by multiple projects. All of this is usually put under the umbrella of a single solution.
If you go this route there are more details (like which exe runs by default when you debug) that I can update with. It's probably nothing you'll be taught in university but you'll most likely see as soon as you start your first job.
I'm working on WPF MVVM project which contains following projects,
Domain,
ViewModels,
Infrastructure,
Views
and for example I need IFileService that provide some operations with file and doesn't contains any business logic, I'm sure that the implementation of this interface FileService will be in Infrastructure project, but I have question where to put the IFileService interface
I need to use this interface in ViewModels project, if I will put it in this projects its mean that Infrastructure will have reference on ViewModels that is not good I think, if I will put it in Domain which contains business related classes the same.
Help me what is the best to organize structure and references between projects and where to put interfaces like IFileService?
Hmm, why not creating an additional project like DAL or DataLayer? It provides the model classes, which I'm also missing in your listing. You could also put the interface IFileService there although I would prefer working with DataProviders or Repositories (that's my prefered option), so that the VMs are not aware from where the data was loaded.
IMHO The project Infrastructure shouldn't not contain any sofisticated logic. I would put some useful methods and classes there and keep it as simple and clean as possible, so that it could be referenced everywhere. Probably, you won't even need it.
The unique rule I use for my MVVM project is, all projects have a reference to my Infrastructure project and my Infrastructure project has no reference to my other project.
So IMHO, IFileService, and interfaces in general, should be in the Infrastructure project. Then it is up to you decide where to put the implementation. The Infrastructure project usually has very basic logic implementation and final implementation goes to a dedicated project.
The only exception I sometimes add to this rule is when I base my development on an existing MVVM framework, then Infrastructure might reference it too but I try to avoid this approach.
You should put the IFileService interface to Infrastructure project. because this will make it available to every project as this is the core project right. and you might have diffrent implemantations e.g. syncronious file reader and asyncronius file reader. so the implemantation could go into your modules or ViewModels.