Following this question
So Python doesn't need IoC/DI because it's dynamic scripting language already.
Javascript is also a dynamic scripting langauge, why does angularjs need DI then?
Is it because JSON <-> DOM is static? Could someone give me a minimal example?
Following this question
https://stackoverflow.com/a/2465052/41948
So Python doesn't need IoC/DI because it's dynamic scripting language already.
Javascript is also a dynamic scripting langauge, why does angularjs need DI then?
Is it because JSON <-> DOM is static? Could someone give me a minimal example?
Share Improve this question edited May 23, 2017 at 12:33 CommunityBot 11 silver badge asked Sep 25, 2013 at 8:00 estest 11.9k15 gold badges73 silver badges124 bronze badges 3- 1 To my knowledge (some talk on youtube by misko and the other guys) DI in angular was a deliberate decission not a need. Primarily to make testing easier/possible. – Yoshi Commented Sep 25, 2013 at 8:53
- 1 I wouldn't say angular needs DI. It's more of an additional tool to structure your application. – David Commented Sep 25, 2013 at 8:53
- In facgt is very smart and usefule to have a DI. Because AngularJS can mange the two data-binding the runtime of factories, controllers, runtime with it via _invokeQueue. Without it, and just with dynamic language how to structure correctly your app ? – Thomas Pons Commented Sep 25, 2013 at 9:10
4 Answers
Reset to default 11Dependency Injection (DI) in Angular wasn't a necessary decision. Most other JavaScript frameworks don't have it built in. (Although look at Marionette, a framework built on top of Backbone.js... it includes an optional DI layer). Angular.js comes with a set of architectural opinions that help you separate your code. It was built in as a design decision, not a necessity.
The biggest reason it is necessary for YOU to use DI in Angular is because that is the way Angular works. The angular team could have decided to use an Asynchronous Module Definition (AMD) library like Require.js. Instead they chose a DI pattern and baked it in for convenience.
The link you posted suggests that DI might be an anti-pattern in dynamic languages. I disagree with that. I'd just say that DI is less necessary in dynamic languages. In the case of Angular, however, it works well. They allow you to compose your system of parts and inject only what you need, when you need it. When you look at the way other frameworks do it, they (often) just namespace their Model/View/Controller/Template/Router parts in the global space (Like App.Models.Person in Backbone.js).
I find DI in Angular to be like "When in Rome, do as the Romans do". Embrace the architectural decision. It feels good.
The best use case for the DI is when you are building an extremely large application with testing. In that case you will likely be very modular and have dozens of components that can come together to form a page. The classic issue with JavaScript is timing and when to include the scripts, check to see if they are already loaded, etc. The DI eliminates that. As long as you get the script included - however you like, whether it's a direct include or an asynchronous module load or a bundle or a combination - AngularJS will handle the rest. You don't have to worry about order because AngularJS will walk the dependency tree for you and assemble the components in the correct order, and you don't have to worry about lifetime management because AngularJS will maintain the appropriate instances for you.
Well, first thing, IoC and DI are two different things (DI is a type of IoC, very popular in static languages). DI isn't very popular in python, but other IoC paradigms are popular, such as Service Locator. Django serve partly as a service locator (for services such as settings, caching, storage, etc..).
You need to remember that Javascript doesn't have any import capabilities (html does, but javascript itself doesn't, though it is planned for ES6), and unlike python, if you want to build modular applications with intricate inner dependencies, you don't have any way in code to describe your dependencies (or get them).
If you don't use somekind of dependency management framework (such as require.js), you are forced to use the global object (or an object inside the global object) as a service locator (which is what other frameworks and plugins do).
The choice of DI instead of service locator in angular is a design decision, which I'm guessing was decided because of two main reasons - the first is unit testing, DI is very amendable to unit testing. The second is probably future proofing for things like ES6 modules.
I know this is an old question but since there is still lot of people finding this confusing I guess that it is worth to mention that everything that can be done with the DI approach can be done with plain CommonJS. Or at least the following:
- Inject test doubles during testing (overloading the require function like proxyquire or karma-commonjs-plus
- Replace services in runtime (using browserify
exports
andrequire
options)
I haven't yet found an instance of something provided by Dependency Injection approach that cannot be done Simpler with just plain commonJS.
For sure if you're not using commonJS
, AMD
or other modular approach you only have the angular one, in that case you should evaluate at least start using one, it will make your life insanely easy without requiring DI.
That said, DI is a very powerful concept, one that cannot be underestimated, only not that needed in Javascript as in other languages.