7

We were taught that objects are self contained things with data and behaviour and therefore they should have methods that act on their attributes. But there are several situations when this coupling between entities and their behaviour is not observed:

  • Entity frameworks (like .NET with POCO and Enterprise Java with POJO entities) stipulate that CRUD/persistence/search operations should be done by external entity managers (and repositories) and not by the entities themselves, i.e. we have code entityManager.save(entity) and not entity.save();
  • Business rule engines are the most visible examples of separating business logic from the entities - business rules form completely different code (even in different languages) from entities. E.g. JBoss Drools or IBM ILOG or other rule engines. Business rule paradigm can be used for the extrapolation of OO programming - in OO we consider data and methods, but in semantic web we can consider ontologies and logical/business rules that are acting on the ABox or TBox of ontologies - two completely different languages and reasoning systems.
  • Distributed computing stipulates use of serialization and deserialization of objects and communication of those objects across network - we have XML, native binary formats or JSON for this. Usually only data are communicated over network and business logic is kept in one layer and there is not technology for moving business logic across network and platforms, e.g. there is no automatic translation and communication of business logic when Java entities are translated into JSON objects and exposed through REST API to Angular 2 frontend. Business logic usually is kept in one side (e.g. in Java).
  • It is said that OO domain model should reflect/model real world. And sometimes the real world objects do not have business logic inside them. E.g. there are concepts about calculators, e.g. tax calculators, salary calculators etc. Therefore we write calculator.recalcTaxes(invoice) and not invoice.recalcTaxes. The former approach allow us to apply different calculators in different cases = e.g. across legislations. We are not forced to build complex inheritance hierarchy simply beacuse there are different business methods, we simply apply different business services/calculators to the same data.

Considering those arguments pro separating business logic from data/entities - how acceptable is to make this separation as the general rule of design for my project of business software? What are the arguments against separating business logic from data?

  • 1
    There's no "one size fits all" rule. You separate logic from data when it makes sense to do so. – Robert Harvey Dec 28 '16 at 21:45
  • 1
    Also look for MVC to see that's it's actually desired to split up things at certain boundaries. – Thomas Kilian Dec 28 '16 at 22:01
  • I find that coupling behavior with the entity is usually a very non maintainable method of design. I always like to separate the logic out of the models/entities. – The Muffin Man Dec 29 '16 at 0:41
5

I believe that the problem you referring to is connected to single class characteristics and level of class decomposition established for a considered problem. Each of your examples sounds reasonable taking into account class characteristics. On the other hand, there are plenty of scenarios that data is bound to logic. In such case it's called rather class behaviour than business logic.

Each of these should be considered separately taking into account at least following:

  • does business logic represent external logic or internal class behaviour?
  • does class represent model?
  • what is level of logic complexity?
  • what is probability that business logic will change?
  • what is probability that there will be new business logic rules applied to object?
  • is class exposed to external environment?
  • is class logic spread over tiers in n-tier approach?

Uncle Bob introduced some Object-Oriented Design principles called SOLID. One of the principles, Single Responsibility Principle (SRP) describes exactly what you are referring to:

a class should have only a single responsibility (i.e. only one potential change in the software's specification should be able to affect the specification of the class)

That's the general rule. What's important (also recommended by Martin), the principle should be used only in scenarios that the class is considered in change chain / has a reason to change. In other case, use of the principle may increase code complexity...

Just short example: you create (or use) one class called List which contains model (Items) and behaviour (Add, Edit, Delete) rather than two classes (ListContainer and ListManager). That because of unnecessary complexity introduced to the problem which is 'internal' class behaviour. Moreover, the way how list will manage objects will never change.

4

If you are literally talking about business logic as in, it's for a business and not domain logic in general, I find most entities have logic imposed on them by outside influencers or because of the context (We give you a discount if ...). That's why business programming can be so frustrating because things can appear to be arbitrary. Entities don't always match the real world, but the world as the business perceives it under different circumstances. There's only one customer called "Acme, Inc." but we have to have two entries because our system only allows one sales person to be assigned to them, and we need them to have two because of yadda-yadda-yadda someone's cousin. Don't worry, you don't have to do this all the time (as if that matters), so I'm sure you can program the computer to make this one exception when calculating their total purchases.

In the U.S., if you hire a contractor, you're suppose to give them a 1099 tax form if they bill you for over $400. This rule isn't part of the contractor or even a particular invoice, but an external government tax rule that looks at the aggregate of bills for a given tax year. This rule could even fluctuate from one year to the next. Dealing with non-profits may present another concern. You really need some sort of tax.calculator for this.

When you don't separate your logic properly, users may start to use your entities in ways you hadn't planned, because the business logic is too closely tied to the entity. Client address data entry should be so straight-forward, but have you ever seen: AddressLine3 = "c/o John Smith" because the app doesn't differentiate business deliveries from private residences? Since you don't have separate logic for printing mailing labels, users do all sorts of things to work-around the lack of separate address info from address printout logic.

Business rules tend to be a combination of factors and are rarely cut-and-dried for a given entity. You can put logic in a business entity, but I think you'll find yourself refactoring this away when everyone finally identifies how things are really done or will be done.

1

how acceptable is to make this separation as the general rule of design for my project of business software?

Depends on which paradigm you want to follow. You are basically describing procedural programming (a set of instructions acts upon data) vs object orientated programming (an object carries out a unit of behaviour via requesting other objects also carry out units of behaviour).

As Alan Kay likes to point out, there are hardly any actual true object orientated languages/systems. So it is not surprising that procedural programming paradigms sneak into "OO" languages as you listed. I would not take that though to mean that procedural paradigm is necessary, only that often procedural thinking (as Dave West calls it) is easier when you are writing code. There is an awful lot of so called "object orientated" code that isn't in fact object orientated.

Personally I'm a subscriber to the idea that if you are going to follow a procedural paradigm you should use a procedural language (or the procedural features of a language that supports both procedural and OO). Trying to shoe horn procedural code into code you are also trying to make as object orientated as possible, can create a bit of a mess.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.