comment 0
/ wsakaren

Dependency Injection without the noise

So everyone in Magento 2 land is going on about Dependency Injection. For many PHP Magento developers this will be a new concept. So what does it mean, in lamens terms.

I’m going to leave the Alan Storm’s of this world to give you the technical definition, here is what it means to me.

Injecting Code

With DI you inject code into a class.  So if we think in terms of a car, its like having a car class and then passing in the wheels, engine and seats to the car.  The car doesn’t go get these items, they are passed to it.  Therefore if you wish to change the wheels you just pass in different ones, the car itself is agnostic.

VW Syncro crew cab transporter 4WD Type 2 (T3)

Example

In Magento terms I believe that any calls you had to GetModel in your methods now have to be replaced with DI via the constructor.

So something like this:

Mage::getModel('vendor_module/foo')->processBar()

becomes

public function __construct(\Vendor\Module\Model\Foo $foo) {
$this->foo = $foo;
}

then later you can do:

$this->foo->processBar();

On top of doing this you need to setup your di.xml file so that it injects the class you need.  And really you need to inject interfaces or factories, not models but thats another discussion. Let’s keep it simple.

Why oh Why?

Because Magento says so! Okay, so the great thing about doing this is that the class now is loosely coupled to the other classes it uses. It makes it much better for unit testing, and for switching out components for maybe a more intelligent or different implementation. A good example here might be that you switch out the logger. The interface doesn’t change, you just inject a different Logger implementation in its place. As long as it conforms to the interface you are fine.

What is an Interface

Just in case you didn’t know an interface is basically an agreement that a class will implement certain methods. Its not an implementation. So a Shape interface might say something like I support methods to return area and perimeter. In Magento interfaces have Interface at the end of the class name.

My View

I’ve used (and continue to use) Dependency Injection in Java, I understand its benefits. Personally in Magento I find it a pain to inject every single thing. Maybe I’m misunderstanding its usage but it seems like hard work, especially when you add in all the namespace definitions. And its error prone, PHP Storm really does not help stop you from making mistakes here, especially around mistyping the resulting class based variables that you assign. It makes reading Magento code an exercise in navigating classes.

I think we are writing Magento 2 code to make it easier to test, which I get, I just wonder if in doing so we are losing the ability to write code that is readable and that can be written fast (which after all is a key reason why people choose PHP). Do we really need to inject Data.php files from the same module for instance? Maybe, but I think thats a choice we should make. It seems from what I’ve seen M2 core code injects the lot.

Leave a Reply

Your email address will not be published. Required fields are marked *