avatartarun bhatt

Summary

The article discusses the Open-Closed Principle (OCP) and its implementation through the Rule Engine design pattern, using C# as an example.

Abstract

The article delves into the Open-Closed Principle (OCP), one of the SOLID principles of object-oriented design, which advocates for software entities to be open for extension but closed for modification. The author illustrates the benefits of OCP using a hypothetical scenario where WhatsApp extends its chat service to Facebook messenger, emphasizing the importance of being able to add new features without altering existing code. The Rule Engine design pattern is presented as a method to adhere to OCP, allowing for the independent addition, removal, or disabling of business rules in complex systems such as a Tax Calculator application. The author provides a step-by-step guide on implementing the Rule Engine pattern, including writing all rules in one place, creating classes for each rule, and building the Rule Engine itself. The article concludes by summarizing the advantages of using the Rule Engine design pattern, such as independent testability of business rules and the ability to enable or disable rules without affecting the Rule Engine or other rules.

Opinions

  • The author believes that following the Open-Closed Principle is crucial for software that requires frequent updates or extensions, such as chat services or tax calculation systems.
  • The Rule Engine design pattern is favored by the author as an effective way to implement OCP, particularly for systems with complex and frequently changing business rules.
  • The author suggests that using the Rule Engine pattern leads to better maintainability and testability of software, as it allows for modular updates and independent rule validation.
  • The article implies that the Rule Engine design pattern is superior for handling evolving business logic, as it decouples the rules from the code that executes them, thus reducing the risk of introducing bugs when updating the system.

Open Closed principle and Rule engine design pattern

Respect the privacy.

Photo by Tim Mossholder on Unsplash

The SOLID principle is a subset of the many tenets promoted by American software engineer and instructor Robert C Martin, known as “Uncle Rob.” In this article, I would be talking about one of the S{O}LID principles, i.e., Open-Closed Principle(OCP).

I would use C# for demonstrating code, but OCP is language-agnostic.

The official definition of OCP is:

software entities (classes, modules, functions, etc.) should be open for extension, but closed for modification

Benefits of OCP

OCP recommends practices that make it easy to upgrade software applications. Imagine a use case where WhatsApp wants to extend the chat service to send messages to Facebook messenger.

The developers would like to re-use relevant components of the chat service. There are two ways of doing it.

  1. Modify existing chat service to support the new requirement. It will expose the chat service code to bugs. The complexity of chat service will increase, and automated test cases might fail.
  2. Extend the chat service code by using relevant components. The code written to support new features will be in the form of new classes but will benefit from the core functionality of the chat service. The benefit of this approach is that new features can be deployed and tested independently.

Rule Engine design pattern is one of the many ways to obey OCP. Many other design patterns allow us to follow OCP, but I am limiting this session to the Rule Engine design pattern, which is one of the easiest ways to demonstrate the power of OCP.

Rule Engine

One of the popular design patterns to help developers follow OCP is the Rule Engine design pattern. It is an efficient design pattern to develop software applications with multiple and complex business rules processing the same entity.

Business rules could be correlated and complex. There could be a lot of complicated branching and conditional logic involved. Following OCP will enable the developers to add, remove or disable business results independently.

There are two components of a Rule Engine:

  1. Rule Engine — An Engine that executes all rules on an entity to produce a result.
  2. Business Rule — A Rule defines a processing logic or a condition.

A Tax Calculator

Let’s try and implement Rule Engine design pattern for a Tax Calculator application. Tax Calculation is a complex process and depends on many factors like Age, Gross Income, Residency status, etc. A lot of business rules evaluate these factors to determine Tax amount. Government policies drive these business rules and can change them frequently. I will use the Rule Engine design pattern to keep these business rules independent in this use case.

Steps to implement Rule Engine Design pattern

Complete code can be found at https://github.com/tarunbhatt9784/TaxCalculator.git

Step 1 — Write all the rules in one place

Write all rules in one method using if-then-else conditional statements.

Step 2: Create classes for each rule.

Create separate classes for each rule. Add a ShouldRun() method in each class file to determine whether the business rule has to be executed or not.

Each class has two methods — Evaluate() and ShouldRun().

Hence we can create an Interface and let all these Rule specific classes implement this interface. Let’s class this interface ITaxCalculatorRule.

Step 3: Create Rule Engine

Once we have the contract of each rule in the form of an interface and the concrete rule classes, it’s time to process them with the help of a Rule Engine. The Rule Engine will be responsible for evaluating these rules. It’s a two-step process:

  • Find all implementations of the Rule Interface — ITaxCalculatorRule
  • Check ShouldRun() for each rule, and if it returns true, run the Evaluate() method

Complete code can be found at https://github.com/tarunbhatt9784/TaxCalculator.git

Conclusion

Let’s summarize and re-iterate the advantages of using the Rule Engine design pattern

  1. Independent testability of Business Rules
  2. Rule Engine does not need to change with the addition or removal of each business rule.
  3. Business Rules can be enabled or disabled separately without changing other rules or Rule Engine

Thanks

P.S — Medium is an excellent platform to read, write and learn from fellow authors. If you want to join me in this journey, Join medium today.

Glossary

Open–closed principle — Wikipedia

Open–closed principle — Wikipedia

SOLID — Wikipedia

Robert C. Martin — Wikipedia

SOLID Principles for C# Developers | Pluralsight

C# Design Patterns: Rules Engine Pattern | Pluralsight

Open Closed Principle
Solid Principles
C Sharp Programming
Net Core
Recommended from ReadMedium