feat(core): properly support inheritance

## Inheritance Semantics:

Decorators:
1) list the decorators of the class and its parents in the ancestor first order
2) only use the last decorator of each kind (e.g. @Component / ...)

Constructor parameters:
If a class inherits from a parent class and does not declare
a constructor, it inherits the parent class constructor,
and with it the parameter metadata of that parent class.

Lifecycle hooks:
Follow the normal class inheritance model,
i.e. lifecycle hooks of parent classes will be called
even if the method is not overwritten in the child class.

## Example

E.g. the following is a valid use of inheritance and it will
also inherit all metadata:

```
@Directive({selector: 'someDir'})
class ParentDirective {
  constructor(someDep: SomeDep) {}

  ngOnInit() {}
}

class ChildDirective extends ParentDirective {}
```

Closes #11606
Closes #12892
This commit is contained in:
Tobias Bosch
2016-11-18 15:17:44 -08:00
committed by vsavkin
parent 4a09251921
commit f5c8e0989d
19 changed files with 1102 additions and 260 deletions

View File

@ -8,6 +8,7 @@
import {Injectable, NgModule, Type} from '@angular/core';
import {ListWrapper} from './facade/collection';
import {isPresent, stringify} from './facade/lang';
import {ReflectorReader, reflector} from './private_import_core';
@ -25,7 +26,8 @@ export class NgModuleResolver {
isNgModule(type: any) { return this._reflector.annotations(type).some(_isNgModuleMetadata); }
resolve(type: Type<any>, throwIfNotFound = true): NgModule {
const ngModuleMeta: NgModule = this._reflector.annotations(type).find(_isNgModuleMetadata);
const ngModuleMeta: NgModule =
ListWrapper.findLast(this._reflector.annotations(type), _isNgModuleMetadata);
if (isPresent(ngModuleMeta)) {
return ngModuleMeta;