A factory method may violate the Law Of Demeter? A factory method may violate the Law Of Demeter? php php

A factory method may violate the Law Of Demeter?


I don't think so.

Especially this:

Any objects created/instantiated within m

I would apply that to the factory as well. Even though strictly the object's constructor is called in the factory, the object is still constructed by, and especially for m. I would interpret the factory as a special kind of constructor, and look past the fact that you don't see a new keyword there.

Given the various important roles that factories play in software design (inversion of control is one of them), I think they are too valuable to let go. It's better to change your interpretation of this law, or of what a constructor is and use those factories when you want.


Shouldn't too strict follow to rules which originate from the law of Demeter. There is a need to understand the sense and purpose of this law.Abidance of the law of Demeter helps us avoid excess dependencies of code on external classes and components. One of the principles of this law tells us the following:

Each unit should have only limited knowledge about other units: only units "closely" related to the current unit

In your example, O class knows C class in any case. Usage of a factory doesn't affect this fact. Somehow or another O class depends on C class and that dependency is unavoidable. It means that dependency is not excess. In fact dependency between C class and O class is a dependency between "closely" related units, therefore there isn't the violation of the law of Demeter if you use a factory.

As an example, let's imagine the following instance of code:

class O{   public function m()   {      $c = new C();      $c->a();   }}

As you can see O class knows C class and has the dependency on it. The law of Demeter is not violated in this code. If you'll modify this example like:

class O{   protected function build()   {      return new C();   }   public function m()   {      $c = $this->build();      $c->a();   }}

class O still will know C class and depend on it, the law of Demeter won't be violated in this code. In fact, we delegated the responsibility of object making to the factory method. If you'll modify this example like:

class Factory{   public function build()   {      return new C();   }}class O{   /**    * @var Factory    */   protected $factory;   public function m()   {      $c = $this->factory->build();      $c->a();   }}

We delegated the responsibility of object making to the factory object, but this fact had violated the law of Demeter because nothing will change in dependencies between O class and C class. As prev instances, O class knows C class and has the dependency on it.We have same dependencies in all of three instances.