The first wave of DDD actual combat advanced (8): Develop a direct sales system for the general business of the big health industry (best practice for business logic condition judgment)

This article is actually an extra part of the direct sales system in the big health industry. It mainly tells you how to effectively deal with the best practice of business logic condition judgment in domain logic.

As we all know, domain objects such as aggregate roots, entities, and value objects handle their own business logic. In the process of business processing, there are usually some conditional judgments. When these conditions are met, different follow-up processing will be performed. In the traditional implementation, it can be judged by the If Else conditional statement, but the If Else statement is used in complex fields to check whether some business conditions are met, there are the following problems:

1. The business conditions themselves cannot be well displayed.

2. It is impossible to flexibly combine multiple conditions in different places.

 

In order to better organize the judgment of business conditions in business logic, the best practice is to split the business conditions into sufficient detail and express them in a semantic manner. In this way, domain objects in the current context can use a combination of one or more business conditions.

 

For example: in the hotel business, the room domain object will handle the domain logic of booking a room and the domain logic of checking out. When booking a room, we need to ensure that the room is not reserved by others and the room is not being maintained. These two business conditions are at the same time. Satisfied; upon check-out, we need to ensure that there are no items in the room damaged or that damages have been paid for either of these two business conditions.

To achieve the above requirements, we can make four business condition rules respectively, and then make flexible combinations in any place where the bounded context is to be used.

1. In order to achieve the above purpose, we must first develop the definition of the combination of the interface of the business condition and the condition.

public interface ISpecification<T>
    {
        bool IsSatisfied(T entity);
    }

The protocol interface defines a method to pass in a domain object to determine whether the conditions are met.

 

public class AndSpecification<T> : ISpecification<T>
    {
        private ISpecification<T> left;
        private ISpecification<T> right;
        public AndSpecification(ISpecification<T> left,ISpecification<T> right)
        {
            this.left = left;
            this.right = right;
        }
        public bool IsSatisfied(T entity)
        {
            return this.left.IsSatisfied(entity) 
                && this.right.IsSatisfied(entity);
        }
}

This class implements an AND relationship of two business conditions.

 

public class OrSpecification<T> : ISpecification<T>
    {
        private ISpecification<T> left;
        private ISpecification<T> right;
        public OrSpecification(ISpecification<T> left, ISpecification<T> right)
        {
            this.left = left;
            this.right = right;
        }
        public bool IsSatisfied(T entity)
        {
            return this.left.IsSatisfied(entity)
                || this.right.IsSatisfied(entity);
        }
}

This class implements an OR relationship of two business conditions.

 

2. In the context of room business boundaries, implement four business condition rules respectively.

// The room is not judged by other people's booking business conditions 
    public  class RoomIsNotConfirmedByOtherSpecification : ISpecification<Room>
    {
        public bool IsSatisfied(Room entity)
        {
            return !entity.OtherConfirmed;
        }
    }
    // The room is not judged by the maintenance business condition 
    public  class RoomIsNotMaintenanceSpecification : ISpecification<Room>
    {
        public bool IsSatisfied(Room entity)
        {
            return !entity.Maintenancing;
        }
    }
    // The room has no item damage condition judgment 
    public  class RoomIsNotAnythingBrokenSpecification : ISpecification<Room>
    {
        public bool IsSatisfied(Room entity)
        {
            return !entity.AnythingBroken;
        }
    }
    // The room has no item damage condition judgment 
    public  class RoomHasBeenBrokenCompensateSpecification : ISpecification<Room>
    {
        public bool IsSatisfied(Room entity)
        {
            return entity.HasBeenCompensated;
        }
    }

 

3. In the domain logic of room reservation and check-out of the room domain object, use the above four conditional rules in combination

// Book a room 
    public Room Reservation()
    {
        var roomisnotconfirmedspec = new RoomIsNotConfirmedByOtherSpecification();
        var roomisnotmaintenancespec = new RoomIsNotMaintenanceSpecification();
        var researvationrulespec = new AndSpecification<Room>(roomisnotconfirmedspec, roomisnotconfirmedspec);
        if (researvationrulespec)
        {
            // Carry out subsequent business processing 
        }
         return  this ;
    }

    // Check out 
    public Room CheckOut()
    {
        var roomisnotanythingbrokenspec = new RoomIsNotAnythingBrokenSpecification();
        var roomhasbeenbrokenspec = new RoomHasBeenBrokenCompensateSpecification();
        var checkrulespec = new OrSpecification<Room>(roomisnotanythingbrokenspec, roomhasbeenbrokenspec);
        if (checkrulespec)
        {
            // Carry out subsequent business processing 
        }
         return  this ;
}

Of course, if you want to combine multiple AND or business conditions arbitrarily, you need to implement the Or and And methods on the protocol to form a chain call. How to implement it? With the above ideas, try to write the code yourself.

QQ discussion group: 309287205

Please pay attention to the WeChat public account for the advanced video of DDD actual combat:

Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=324955620&siteId=291194637
Recommended