Open al-the-x opened 10 years ago
instantiate
method appeared in c925f8a6578e05
.
The instantiation of a new object happens in two phases:
instantiate
, a new object is created with an empty constructor, but the constructor’s prototype is set to be equal to Type
’s prototype, so the prototype chain is correctly maintained.invoke
, the Type
function is simply called via apply
, but bound to the correct object (the one created in instantiate
, and with correct arguments (services that the injector supplies and locals (like $scope
).
If we called new Type(...)
inside instantiate
, we would have to duplicate the dependency-injection code there, which is why we’re piggybacking on invoke
.Now, instantiate
ends with this line: return isObject(returnedValue) || isFunction(returnedValue) ? returnedValue : instance
.
Which says: if the Type
function returned something that is either an object or a function, return it. Otherwise, return the newly created instance.
According to the commit message to c22adbf160
, this mimics the behavior of the native new
operator.
In your Directive assignment (#5), you identified the return value for the
controller
property as replacing the instantiated object:Which is generally true in JavaScript when using the
new
operator:prototype
assigned to theprototype
of the Constructornew
statement; otherwise the original Object is returned.However, Angular isn't just using the
new
statement to instantiate an Injectable, as we saw. There's some "magic" at work ininvoke()
that's worth investigating. Trace through the lifecycle of theConstructor
andType
variables to determine what is actually returned by$injector.invoke
.