C# – Confused about layered application development

clayers

So, for the first big project that I'm getting paid for, I decided I'd do things right.

To that end, I've created several projects in my Solution. Some of these projects are generic and handle common elements that can be used in any project (stuff like logging and such), but that's not where the focus of my question is.

The projects I'm concerning myself with in this case are mostly to do with the database and the actual web application that will use it.

So I have an Ortund.Objects Class Library Project and an Ortund.DBContext Class Library Project.

Ortund.Objects
This project defines the classes, setting properties and default values that makes up the database.
For example, the Users class defines properties such as Username, EmailAddress, Password

Ortund.DBContext
This project uses Entity Framework and the Objects project to build the database. DbSets of the classes in the Objects project and various other components explicitly define the structure of the database.

Obviously, given this structure, I would have the DBContext project referencing the Objects project. This means that, while somewhere in my head, it makes sense to put all my methods and functions that the web app will use into the Objects project, I wouldn't actually be able to do anything because I won't have the DbContext. To reference the DBContext project would create a circular reference.

So, in order for my application to interact with the database now, the only option I can see is to create a 4th project to act as the data layer, effectively becoming a "middle-man" between the web application and the other 2 projects.

When I suggested this on IRC, someone answered with the following:

No, the application layer uses the database layer to provide persistence to the domain layer.

I don't understand what this means. Can someone help me to understand how best to structure this application?

Best Answer

A typical full-tier application can be composed in many different ways. One of those ways is very similar to what you have come up with so far. The layers go somewhat like this (feel free to tweak and extend as per your use case):

  1. A Models layer, which contains your database objects. These classes map directly to your database.

  2. A Data Access layer, which contains your entity framework code and uses (1) to provide CRUD operations, etc.

  3. A Business Logic or Domain layer, which uses (2) and adds business logic, domain-specific rules and functions to the mix

  4. Sometimes, this business tier defines its own Domain Objects. These are also model objects, but they are in the context of the end-user rather than that of the database. A single business-tier object may be a logical composition/transformation of multiple database model objects.

  5. Finally, an Application layer, which exposes a specific UI for a specific consumer. It uses the underlying business tier functions to do the actual work.

It is not necessary for these layers to be in separate packages. It all depends on the complexity and size of your application. The loose coupling helps to separate out the layers into independent modules as and when the need arises.