Abstract

MVC is a software design pattern, first proposed by Trygve Reenskaug in 1978. He effectively solved the problem of mixing the codes of the presentation layer, controller layer and logic layer, and achieved a good separation of responsibilities. However, in the process of actual coding practice, you will find that with the expansion of business, this mode becomes logic disorder and code coincidence is very high. A new engineering structure based on DDD is proposed

The problem of MVC

For a system with separate front and back ends, the back-end engineering system structure diagram usually looks like this

1. The four levels of the controller/service/manager/mapper 2. 3. The higher level can know the lower level, but the lower level cannot know the higher level, that is, the bean transformation is placed at the higher levelCopy the code

This hierarchical structure divides responsibilities vertically

1. Repository is db-oriented programming; 2. Service is front-end page-oriented programming.Copy the code

That is, instead of abstracting the logic together for a particular piece of business, he simply slices a request vertically. There is no horizontal business segmentation. This will lead to decentralized responsibility and high logic repetition

  • Bean creation is arbitrary, basically a requirement corresponding to some DTO, VO, and Query beans
  • Different developers have different beans for the same domain, the same developer for the same logic of the bean, a few months later, define a similar bean

No boundary

  • There is no concept of context/boundary at all. For example, stores will interact with users, orders will interact with users. Usually, when DB is stored, only the association ID will be stored, and then the corresponding name and other attribute information need to be retrieved. Some of this information is acquired at the Manager level, and then attributes are defined in store-specific Dtos. Some are done in the Service layer. The controller/service/manager at all levels, can be called without any constraint.

The evolution of the MVC

As described above, serious problems can occur in a single service as the business iterates over time.

Let me give you some real examples

An example of a separate table

Entity A is A basic and important entity in our business, corresponding to the data table tableA. At the beginning, the business was very simple with only one service, which was called in this service. Then the business expanded, and there were a dozen services, and then a dozen services just looked at tableA. TableA expands to tableA,tableB,tableC. Some people feel that the code is too repetitive and split the Mapper/Manager layer into common parts into a JAR package, which is then introduced into each microservice. The business has become more complex, the service has expanded to dozens of tableA data has tens of millions, this time to do sub-database sub-table, how to whole.

In the end, it took almost a year and a dozen teams to get rid of the Mapper/Manager call and make the repository and table.

One might think that this is just a matter of avoiding direct calls when a service is split, but let’s take another example.

User-level examples

The user hierarchy, the user hierarchy is very complex, different business phases have different definitions. Let’s say we start with a field called grade that represents the user level. Then, each business looked up the field grade in this table to judge, and the product needed to be changed, adding judgment to determine what conditions must be met at the same time to be called grade X. Now you have to change all over the world.

DDD engineering architecture

The core idea: encapsulate the logic in the domain, unify the entrance to external exposure, and prevent the leakage of business logic.

  • On the basis of MVC vertical shard, add a layer of domain horizontal shard
  • Within the same project, calls between domains can only be made through domainService, which can mask how databases in domains are persisted, how business logic is determined, and how algorithms are implemented. Services can be called directly between services.
  • The domain is still segmented vertically, with MVC hierarchies installed.

The above is just a sketch, but our actual structure is a little more complicated than that. Domain objects, domain services, and infrastructure layers are distinguished within domains. In this way, accusations are separated in the field. However, considering the details in the field in the actual implementation process, the ROI is relatively low. It is recommended that you follow this method first.

Voiceover: Some programmers might chuckle at this structural change and think it’s not worth it.

The structural division of the project took about eight months from the time it was proposed to the time it was accepted by our team members. There are several reasons

  1. Introducing new layers, which are too complex, increases code complexity
  2. My part of the business is very simple, CRUD is ok, there is no interaction between services. Direct MVC a path to black can be.

If this is how you feel about reading this article, take a moment to look at the code for your business and see how repetitive and messy the logic is. You’ll see.

DDD engineering evolution

The evolution of DDD engineering is also called service unassembly, which will be covered in the next installment.

conclusion

A lot of DDD articles say that traditional programming is database programming, resulting in getters, setters, anaemic models that have no business logic, process oriented design, and do not conform to object-oriented design principles.

I agree with the conclusion, but I don’t quite agree with the cause. Personally, I think the main reason for this is that the LONG-STANDING MVC model is only caused by vertical segmentation. If you combine horizontal shards, DDD doesn’t matter. Again, the driver approach doesn’t change anything, if you understand responsibility, encapsulation. And constantly refactor your code as the business iterates, so you don’t need DDD, or any other methodology.

Use responsibility, encapsulation and composition; Think in terms of interfaces, that is, “How do people use my components?” ; Write code well using relevant techniques, including readability, informality, brevity, self-description, and avoiding explicit use of patterns. Ability to answer the “essence” of a particular business; “Essence” is a model, but it doesn’t mean classes and methods, it means answering the question “How does this business really work?”

Because these constraints are forcing you to think, to do the thinking of responsibility, to do the encapsulation of modules. If you/your team members have already figured it out and are using it well, why do you need these rules?

Next up, the domain and microservices division. To see what happens next, listen to the next section.

reading

Landable DDD(1)- Objective discussion

Pay attention to [Abbot’s Temple], receive the update of the article as soon as possible, and start the road of technical practice together with the abbot