fix(testing): add an explicit doAsyncPrecompilation step (#10015)
This removes the magic from the `inject` test helper that would inspect the current zone and would only work with our `async` test helper. Now, `inject` is always synchronous, and if you are using a module that requires async precompilation, you're required to call `doAsyncPrecompilation` in your tests. This is part of the breaking changes introduced with the swap to each test having an AppModule. Closes #9975 Closes #9593 BREAKING CHANGE: `TestInjector` is now renamed to `TestBed` Before: ```js import {TestInjector, getTestInjector} from '@angular/core/testing'; ``` After: ```js import {TestBed, getTestBed} from '@angular/core/testing'; ```
This commit is contained in:
parent
450f61d384
commit
b43f95435b
@ -7,7 +7,7 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
import {beforeEach, ddescribe, xdescribe, describe, expect, iit, inject, beforeEachProviders, it, xit,} from '@angular/core/testing/testing_internal';
|
import {beforeEach, ddescribe, xdescribe, describe, expect, iit, inject, beforeEachProviders, it, xit,} from '@angular/core/testing/testing_internal';
|
||||||
import {TestComponentBuilder, ComponentFixtureAutoDetect, ComponentFixtureNoNgZone} from '@angular/core/testing';
|
import {TestComponentBuilder, ComponentFixtureAutoDetect, ComponentFixtureNoNgZone, withProviders} from '@angular/core/testing';
|
||||||
import {AsyncTestCompleter} from '@angular/core/testing/testing_internal';
|
import {AsyncTestCompleter} from '@angular/core/testing/testing_internal';
|
||||||
import {Injectable, Component, Input, ViewMetadata} from '@angular/core';
|
import {Injectable, Component, Input, ViewMetadata} from '@angular/core';
|
||||||
import {NgIf} from '@angular/common';
|
import {NgIf} from '@angular/common';
|
||||||
@ -15,7 +15,6 @@ import {TimerWrapper} from '../src/facade/async';
|
|||||||
import {IS_DART} from '../src/facade/lang';
|
import {IS_DART} from '../src/facade/lang';
|
||||||
import {PromiseWrapper} from '../src/facade/promise';
|
import {PromiseWrapper} from '../src/facade/promise';
|
||||||
import {dispatchEvent} from '@angular/platform-browser/testing/browser_util';
|
import {dispatchEvent} from '@angular/platform-browser/testing/browser_util';
|
||||||
import {withProviders} from '@angular/core/testing/test_injector';
|
|
||||||
|
|
||||||
@Component(
|
@Component(
|
||||||
{selector: 'child-comp', template: `<span>Original {{childBinding}}</span>`, directives: []})
|
{selector: 'child-comp', template: `<span>Original {{childBinding}}</span>`, directives: []})
|
||||||
|
@ -7,12 +7,13 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
import {AnimationEntryMetadata, Compiler, ComponentFactory, Inject, Injectable, Injector, NgZone, ViewMetadata} from '@angular/core';
|
import {AnimationEntryMetadata, Compiler, ComponentFactory, Inject, Injectable, Injector, NgZone, ViewMetadata} from '@angular/core';
|
||||||
import {ComponentFixture, ComponentFixtureNoNgZone, TestComponentBuilder, TestInjector} from '@angular/core/testing';
|
import {ComponentFixture, ComponentFixtureNoNgZone, TestBed, TestComponentBuilder} from '@angular/core/testing';
|
||||||
|
|
||||||
import {DirectiveResolver, ViewResolver} from '../index';
|
import {DirectiveResolver, ViewResolver} from '../index';
|
||||||
import {MapWrapper} from '../src/facade/collection';
|
import {MapWrapper} from '../src/facade/collection';
|
||||||
import {ConcreteType, IS_DART, Type, isPresent} from '../src/facade/lang';
|
import {ConcreteType, IS_DART, Type, isPresent} from '../src/facade/lang';
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A TestComponentBuilder that allows overriding based on the compiler.
|
* A TestComponentBuilder that allows overriding based on the compiler.
|
||||||
*/
|
*/
|
||||||
@ -31,7 +32,7 @@ export class OverridingTestComponentBuilder extends TestComponentBuilder {
|
|||||||
/** @internal */
|
/** @internal */
|
||||||
_viewOverrides = new Map<Type, ViewMetadata>();
|
_viewOverrides = new Map<Type, ViewMetadata>();
|
||||||
|
|
||||||
constructor(@Inject(TestInjector) injector: Injector) { super(injector); }
|
constructor(@Inject(TestBed) injector: Injector) { super(injector); }
|
||||||
|
|
||||||
/** @internal */
|
/** @internal */
|
||||||
_clone(): OverridingTestComponentBuilder {
|
_clone(): OverridingTestComponentBuilder {
|
||||||
|
@ -10,5 +10,5 @@ export * from './testing/async';
|
|||||||
export * from './testing/component_fixture';
|
export * from './testing/component_fixture';
|
||||||
export * from './testing/fake_async';
|
export * from './testing/fake_async';
|
||||||
export * from './testing/test_component_builder';
|
export * from './testing/test_component_builder';
|
||||||
export * from './testing/test_injector';
|
export * from './testing/test_bed';
|
||||||
export * from './testing/testing';
|
export * from './testing/testing';
|
||||||
|
@ -18,11 +18,12 @@ const UNDEFINED = new Object();
|
|||||||
/**
|
/**
|
||||||
* @experimental
|
* @experimental
|
||||||
*/
|
*/
|
||||||
export class TestInjector implements Injector {
|
export class TestBed implements Injector {
|
||||||
private _instantiated: boolean = false;
|
private _instantiated: boolean = false;
|
||||||
|
|
||||||
private _compiler: Compiler = null;
|
private _compiler: Compiler = null;
|
||||||
private _moduleRef: AppModuleRef<any> = null;
|
private _moduleRef: AppModuleRef<any> = null;
|
||||||
|
private _appModuleFactory: AppModuleFactory<any> = null;
|
||||||
|
|
||||||
private _compilerProviders: Array<Type|Provider|any[]|any> = [];
|
private _compilerProviders: Array<Type|Provider|any[]|any> = [];
|
||||||
private _compilerUseJit: boolean = true;
|
private _compilerUseJit: boolean = true;
|
||||||
@ -36,6 +37,7 @@ export class TestInjector implements Injector {
|
|||||||
reset() {
|
reset() {
|
||||||
this._compiler = null;
|
this._compiler = null;
|
||||||
this._moduleRef = null;
|
this._moduleRef = null;
|
||||||
|
this._appModuleFactory = null;
|
||||||
this._compilerProviders = [];
|
this._compilerProviders = [];
|
||||||
this._compilerUseJit = true;
|
this._compilerUseJit = true;
|
||||||
this._providers = [];
|
this._providers = [];
|
||||||
@ -89,16 +91,43 @@ export class TestInjector implements Injector {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
createInjectorSync(): Injector {
|
createAppModuleFactory(): Promise<AppModuleFactory<any>> {
|
||||||
if (this._instantiated) {
|
if (this._instantiated) {
|
||||||
return this;
|
throw new BaseException(
|
||||||
|
'Cannot run precompilation when the test AppModule has already been instantiated. ' +
|
||||||
|
'Make sure you are not using `inject` before `doAsyncPrecompilation`.');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (this._appModuleFactory) {
|
||||||
|
return Promise.resolve(this._appModuleFactory);
|
||||||
|
}
|
||||||
|
|
||||||
let moduleMeta = this._createCompilerAndModuleMeta();
|
let moduleMeta = this._createCompilerAndModuleMeta();
|
||||||
return this._createFromModuleFactory(
|
|
||||||
this._compiler.compileAppModuleSync(_NoopModule, moduleMeta));
|
return this._compiler.compileAppModuleAsync(_NoopModule, moduleMeta)
|
||||||
|
.then((appModuleFactory) => {
|
||||||
|
this._appModuleFactory = appModuleFactory;
|
||||||
|
return appModuleFactory;
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
createInjectorAsync(): Promise<Injector> {
|
initTestAppModule() {
|
||||||
|
if (this._instantiated) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this._appModuleFactory) {
|
||||||
|
this._createFromModuleFactory(this._appModuleFactory);
|
||||||
|
} else {
|
||||||
|
let moduleMeta = this._createCompilerAndModuleMeta();
|
||||||
|
this._createFromModuleFactory(this._compiler.compileAppModuleSync(_NoopModule, moduleMeta));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @internal
|
||||||
|
*/
|
||||||
|
_createInjectorAsync(): Promise<Injector> {
|
||||||
if (this._instantiated) {
|
if (this._instantiated) {
|
||||||
return Promise.resolve(this);
|
return Promise.resolve(this);
|
||||||
}
|
}
|
||||||
@ -115,7 +144,7 @@ export class TestInjector implements Injector {
|
|||||||
deprecatedAppProviders: this._providers
|
deprecatedAppProviders: this._providers
|
||||||
});
|
});
|
||||||
const moduleMeta = new AppModuleMetadata({
|
const moduleMeta = new AppModuleMetadata({
|
||||||
providers: this._providers.concat([{provide: TestInjector, useValue: this}]),
|
providers: this._providers.concat([{provide: TestBed, useValue: this}]),
|
||||||
modules: this._modules.concat([this.appModule]),
|
modules: this._modules.concat([this.appModule]),
|
||||||
directives: this._directives,
|
directives: this._directives,
|
||||||
pipes: this._pipes,
|
pipes: this._pipes,
|
||||||
@ -134,9 +163,9 @@ export class TestInjector implements Injector {
|
|||||||
get(token: any, notFoundValue: any = Injector.THROW_IF_NOT_FOUND) {
|
get(token: any, notFoundValue: any = Injector.THROW_IF_NOT_FOUND) {
|
||||||
if (!this._instantiated) {
|
if (!this._instantiated) {
|
||||||
throw new BaseException(
|
throw new BaseException(
|
||||||
'Illegal state: The TestInjector has not yet been created. Call createInjectorSync/Async first!');
|
'Illegal state: The test bed\'s injector has not yet been created. Call initTestAppModule first!');
|
||||||
}
|
}
|
||||||
if (token === TestInjector) {
|
if (token === TestBed) {
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
// Tests can inject things from the app module and from the compiler,
|
// Tests can inject things from the app module and from the compiler,
|
||||||
@ -148,23 +177,30 @@ export class TestInjector implements Injector {
|
|||||||
execute(tokens: any[], fn: Function): any {
|
execute(tokens: any[], fn: Function): any {
|
||||||
if (!this._instantiated) {
|
if (!this._instantiated) {
|
||||||
throw new BaseException(
|
throw new BaseException(
|
||||||
'Illegal state: The TestInjector has not yet been created. Call createInjectorSync/Async first!');
|
'Illegal state: The test bed\'s injector has not yet been created. Call initTestAppModule first!');
|
||||||
}
|
}
|
||||||
var params = tokens.map(t => this.get(t));
|
var params = tokens.map(t => this.get(t));
|
||||||
return FunctionWrapper.apply(fn, params);
|
return FunctionWrapper.apply(fn, params);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
var _testInjector: TestInjector = null;
|
var _testBed: TestBed = null;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @experimental
|
* @experimental
|
||||||
*/
|
*/
|
||||||
export function getTestInjector() {
|
export function getTestBed() {
|
||||||
if (_testInjector == null) {
|
if (_testBed == null) {
|
||||||
_testInjector = new TestInjector();
|
_testBed = new TestBed();
|
||||||
}
|
}
|
||||||
return _testInjector;
|
return _testBed;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @deprecated use getTestBed instead.
|
||||||
|
*/
|
||||||
|
export function getTestInjector() {
|
||||||
|
return getTestBed();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -208,12 +244,12 @@ export function setBaseTestProviders(
|
|||||||
* @experimental
|
* @experimental
|
||||||
*/
|
*/
|
||||||
export function initTestEnvironment(appModule: Type, platform: PlatformRef) {
|
export function initTestEnvironment(appModule: Type, platform: PlatformRef) {
|
||||||
var testInjector = getTestInjector();
|
var testBed = getTestBed();
|
||||||
if (testInjector.platform || testInjector.appModule) {
|
if (testBed.platform || testBed.appModule) {
|
||||||
throw new BaseException('Cannot set base providers because it has already been called');
|
throw new BaseException('Cannot set base providers because it has already been called');
|
||||||
}
|
}
|
||||||
testInjector.platform = platform;
|
testBed.platform = platform;
|
||||||
testInjector.appModule = appModule;
|
testBed.appModule = appModule;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -231,10 +267,22 @@ export function resetBaseTestProviders() {
|
|||||||
* @experimental
|
* @experimental
|
||||||
*/
|
*/
|
||||||
export function resetTestEnvironment() {
|
export function resetTestEnvironment() {
|
||||||
var testInjector = getTestInjector();
|
var testBed = getTestBed();
|
||||||
testInjector.platform = null;
|
testBed.platform = null;
|
||||||
testInjector.appModule = null;
|
testBed.appModule = null;
|
||||||
testInjector.reset();
|
testBed.reset();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Run asynchronous precompilation for the test's AppModule. It is necessary to call this function
|
||||||
|
* if your test is using an AppModule which has precompiled components that require an asynchronous
|
||||||
|
* call, such as an XHR. Should be called once before the test case.
|
||||||
|
*
|
||||||
|
* @experimental
|
||||||
|
*/
|
||||||
|
export function doAsyncPrecompilation(): Promise<any> {
|
||||||
|
let testBed = getTestBed();
|
||||||
|
return testBed.createAppModuleFactory();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -262,39 +310,31 @@ export function resetTestEnvironment() {
|
|||||||
* @stable
|
* @stable
|
||||||
*/
|
*/
|
||||||
export function inject(tokens: any[], fn: Function): () => any {
|
export function inject(tokens: any[], fn: Function): () => any {
|
||||||
let testInjector = getTestInjector();
|
let testBed = getTestBed();
|
||||||
if (tokens.indexOf(AsyncTestCompleter) >= 0) {
|
if (tokens.indexOf(AsyncTestCompleter) >= 0) {
|
||||||
return () => {
|
return () => {
|
||||||
// Return an async test method that returns a Promise if AsyncTestCompleter is one of the
|
// Return an async test method that returns a Promise if AsyncTestCompleter is one of the
|
||||||
// injected tokens.
|
// injected tokens.
|
||||||
return testInjector.createInjectorAsync().then(() => {
|
return testBed._createInjectorAsync().then(() => {
|
||||||
let completer: AsyncTestCompleter = testInjector.get(AsyncTestCompleter);
|
let completer: AsyncTestCompleter = testBed.get(AsyncTestCompleter);
|
||||||
testInjector.execute(tokens, fn);
|
testBed.execute(tokens, fn);
|
||||||
return completer.promise;
|
return completer.promise;
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
} else {
|
} else {
|
||||||
return () => {
|
return () => {
|
||||||
// Return a asynchronous test method with the injected tokens.
|
try {
|
||||||
// TODO(tbosch): Right now, we can only detect the AsyncTestZoneSpec via its name.
|
testBed.initTestAppModule();
|
||||||
// (see https://github.com/angular/zone.js/issues/370)
|
} catch (e) {
|
||||||
if (Zone.current.name.toLowerCase().indexOf('asynctestzone') >= 0) {
|
if (e instanceof ComponentStillLoadingError) {
|
||||||
return testInjector.createInjectorAsync().then(() => testInjector.execute(tokens, fn));
|
throw new Error(
|
||||||
} else {
|
`This test module precompiles the component ${stringify(e.compType)} which is using a "templateUrl", but precompilation was never done. ` +
|
||||||
// Return a synchronous test method with the injected tokens.
|
`Please call "doAsyncPrecompilation" before "inject".`);
|
||||||
try {
|
} else {
|
||||||
testInjector.createInjectorSync();
|
throw e;
|
||||||
} catch (e) {
|
|
||||||
if (e instanceof ComponentStillLoadingError) {
|
|
||||||
throw new Error(
|
|
||||||
`This test module precompiles the component ${stringify(e.compType)} which is using a "templateUrl", but the test is synchronous. ` +
|
|
||||||
`Please use the "async(...)" or "fakeAsync(...)" helper functions to make the test asynchronous.`);
|
|
||||||
} else {
|
|
||||||
throw e;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
return testInjector.execute(tokens, fn);
|
|
||||||
}
|
}
|
||||||
|
return testBed.execute(tokens, fn);
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -314,14 +354,14 @@ export class InjectSetupWrapper {
|
|||||||
private _addModule() {
|
private _addModule() {
|
||||||
var moduleDef = this._moduleDef();
|
var moduleDef = this._moduleDef();
|
||||||
if (moduleDef) {
|
if (moduleDef) {
|
||||||
getTestInjector().configureModule(moduleDef);
|
getTestBed().configureModule(moduleDef);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
inject(tokens: any[], fn: Function): () => any {
|
inject(tokens: any[], fn: Function): () => any {
|
||||||
return () => {
|
return () => {
|
||||||
this._addModule();
|
this._addModule();
|
||||||
return inject_impl(tokens, fn)();
|
return inject(tokens, fn)();
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -346,9 +386,4 @@ export function withModule(moduleDef: () => {
|
|||||||
return new InjectSetupWrapper(moduleDef);
|
return new InjectSetupWrapper(moduleDef);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// This is to ensure inject(Async) within InjectSetupWrapper doesn't call itself
|
|
||||||
// when transpiled to Dart.
|
|
||||||
var inject_impl = inject;
|
|
||||||
|
|
||||||
class _NoopModule {}
|
class _NoopModule {}
|
@ -12,17 +12,17 @@
|
|||||||
* allows tests to be asynchronous by either returning a promise or using a 'done' parameter.
|
* allows tests to be asynchronous by either returning a promise or using a 'done' parameter.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import {TestInjector, getTestInjector} from './test_injector';
|
import {TestBed, getTestBed} from './test_bed';
|
||||||
|
|
||||||
declare var global: any;
|
declare var global: any;
|
||||||
|
|
||||||
var _global = <any>(typeof window === 'undefined' ? global : window);
|
var _global = <any>(typeof window === 'undefined' ? global : window);
|
||||||
|
|
||||||
var testInjector: TestInjector = getTestInjector();
|
var testBed: TestBed = getTestBed();
|
||||||
|
|
||||||
// Reset the test providers before each test.
|
// Reset the test providers before each test.
|
||||||
if (_global.beforeEach) {
|
if (_global.beforeEach) {
|
||||||
_global.beforeEach(() => { testInjector.reset(); });
|
_global.beforeEach(() => { testBed.reset(); });
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -34,7 +34,7 @@ if (_global.beforeEach) {
|
|||||||
export function addProviders(providers: Array<any>): void {
|
export function addProviders(providers: Array<any>): void {
|
||||||
if (!providers) return;
|
if (!providers) return;
|
||||||
try {
|
try {
|
||||||
testInjector.configureModule({providers: providers});
|
testBed.configureModule({providers: providers});
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
throw new Error(
|
throw new Error(
|
||||||
'addProviders can\'t be called after the injector has been already created for this test. ' +
|
'addProviders can\'t be called after the injector has been already created for this test. ' +
|
||||||
@ -58,7 +58,7 @@ export function configureModule(moduleDef: {
|
|||||||
}): void {
|
}): void {
|
||||||
if (!moduleDef) return;
|
if (!moduleDef) return;
|
||||||
try {
|
try {
|
||||||
testInjector.configureModule(moduleDef);
|
testBed.configureModule(moduleDef);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
throw new Error(
|
throw new Error(
|
||||||
'configureModule can\'t be called after the injector has been already created for this test. ' +
|
'configureModule can\'t be called after the injector has been already created for this test. ' +
|
||||||
@ -76,7 +76,7 @@ export function configureModule(moduleDef: {
|
|||||||
export function configureCompiler(config: {providers?: any[], useJit?: boolean}): void {
|
export function configureCompiler(config: {providers?: any[], useJit?: boolean}): void {
|
||||||
if (!config) return;
|
if (!config) return;
|
||||||
try {
|
try {
|
||||||
testInjector.configureCompiler(config);
|
testBed.configureCompiler(config);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
throw new Error(
|
throw new Error(
|
||||||
'configureCompiler can\'t be called after the injector has been already created for this test. ' +
|
'configureCompiler can\'t be called after the injector has been already created for this test. ' +
|
||||||
|
@ -11,11 +11,11 @@ import {StringMapWrapper} from '../src/facade/collection';
|
|||||||
import {Math, global, isFunction, isPromise} from '../src/facade/lang';
|
import {Math, global, isFunction, isPromise} from '../src/facade/lang';
|
||||||
|
|
||||||
import {AsyncTestCompleter} from './async_test_completer';
|
import {AsyncTestCompleter} from './async_test_completer';
|
||||||
import {getTestInjector, inject} from './test_injector';
|
import {getTestBed, inject} from './test_bed';
|
||||||
|
|
||||||
export {AsyncTestCompleter} from './async_test_completer';
|
export {AsyncTestCompleter} from './async_test_completer';
|
||||||
export {MockAnimationPlayer} from './mock_animation_player';
|
export {MockAnimationPlayer} from './mock_animation_player';
|
||||||
export {inject} from './test_injector';
|
export {inject} from './test_bed';
|
||||||
export * from './logger';
|
export * from './logger';
|
||||||
export * from './ng_zone_mock';
|
export * from './ng_zone_mock';
|
||||||
export * from './mock_application_ref';
|
export * from './mock_application_ref';
|
||||||
@ -40,7 +40,7 @@ var inIt = false;
|
|||||||
jasmine.DEFAULT_TIMEOUT_INTERVAL = 3000;
|
jasmine.DEFAULT_TIMEOUT_INTERVAL = 3000;
|
||||||
var globalTimeOut = jasmine.DEFAULT_TIMEOUT_INTERVAL;
|
var globalTimeOut = jasmine.DEFAULT_TIMEOUT_INTERVAL;
|
||||||
|
|
||||||
var testInjector = getTestInjector();
|
var testBed = getTestBed();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Mechanism to run `beforeEach()` functions of Angular tests.
|
* Mechanism to run `beforeEach()` functions of Angular tests.
|
||||||
@ -61,7 +61,7 @@ class BeforeEachRunner {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Reset the test providers before each test
|
// Reset the test providers before each test
|
||||||
jsmBeforeEach(() => { testInjector.reset(); });
|
jsmBeforeEach(() => { testBed.reset(); });
|
||||||
|
|
||||||
function _describe(jsmFn: any /** TODO #9100 */, ...args: any[] /** TODO #9100 */) {
|
function _describe(jsmFn: any /** TODO #9100 */, ...args: any[] /** TODO #9100 */) {
|
||||||
var parentRunner = runnerStack.length === 0 ? null : runnerStack[runnerStack.length - 1];
|
var parentRunner = runnerStack.length === 0 ? null : runnerStack[runnerStack.length - 1];
|
||||||
@ -110,7 +110,7 @@ export function beforeEachProviders(fn: any /** TODO #9100 */): void {
|
|||||||
jsmBeforeEach(() => {
|
jsmBeforeEach(() => {
|
||||||
var providers = fn();
|
var providers = fn();
|
||||||
if (!providers) return;
|
if (!providers) return;
|
||||||
testInjector.configureModule({providers: providers});
|
testBed.configureModule({providers: providers});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -138,7 +138,7 @@ function _it(jsmFn: Function, name: string, testFn: Function, testTimeOut: numbe
|
|||||||
return new AsyncTestCompleter();
|
return new AsyncTestCompleter();
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
testInjector.configureModule({providers: [completerProvider]});
|
testBed.configureModule({providers: [completerProvider]});
|
||||||
runner.run();
|
runner.run();
|
||||||
|
|
||||||
inIt = true;
|
inIt = true;
|
||||||
|
@ -9,7 +9,7 @@
|
|||||||
import {NgIf} from '@angular/common';
|
import {NgIf} from '@angular/common';
|
||||||
import {CompilerConfig, XHR} from '@angular/compiler';
|
import {CompilerConfig, XHR} from '@angular/compiler';
|
||||||
import {AppModule, Component, ComponentFactoryResolver, Directive, Injectable, Input, Pipe, ViewMetadata, provide} from '@angular/core';
|
import {AppModule, Component, ComponentFactoryResolver, Directive, Injectable, Input, Pipe, ViewMetadata, provide} from '@angular/core';
|
||||||
import {TestComponentBuilder, addProviders, async, configureCompiler, configureModule, fakeAsync, inject, tick, withModule, withProviders} from '@angular/core/testing';
|
import {TestComponentBuilder, addProviders, async, configureCompiler, configureModule, doAsyncPrecompilation, fakeAsync, inject, tick, withModule, withProviders} from '@angular/core/testing';
|
||||||
import {expect} from '@angular/platform-browser/testing/matchers';
|
import {expect} from '@angular/platform-browser/testing/matchers';
|
||||||
|
|
||||||
import {stringify} from '../../http/src/facade/lang';
|
import {stringify} from '../../http/src/facade/lang';
|
||||||
@ -115,7 +115,10 @@ class CompUsingModuleDirectiveAndPipe {
|
|||||||
class SomeNestedModule {
|
class SomeNestedModule {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Component({selector: 'comp', templateUrl: 'someTemplate.html'})
|
@Component({
|
||||||
|
selector: 'comp',
|
||||||
|
templateUrl: '/base/modules/@angular/platform-browser/test/static_assets/test.html'
|
||||||
|
})
|
||||||
class CompWithUrlTemplate {
|
class CompWithUrlTemplate {
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -296,27 +299,16 @@ export function main() {
|
|||||||
});
|
});
|
||||||
|
|
||||||
describe('precompile components with template url', () => {
|
describe('precompile components with template url', () => {
|
||||||
let xhrGet: jasmine.Spy;
|
beforeEach(async(() => {
|
||||||
beforeEach(() => {
|
configureModule({precompile: [CompWithUrlTemplate]});
|
||||||
xhrGet = jasmine.createSpy('xhrGet').and.returnValue(Promise.resolve('Hello world!'));
|
doAsyncPrecompilation();
|
||||||
configureCompiler({providers: [{provide: XHR, useValue: {get: xhrGet}}]});
|
}));
|
||||||
});
|
|
||||||
|
|
||||||
it('should allow to precompile components with templateUrl using the async helper',
|
it('should allow to createSync components with templateUrl after async precompilation',
|
||||||
async(withModule(() => {
|
inject([TestComponentBuilder], (builder: TestComponentBuilder) => {
|
||||||
return {precompile: [CompWithUrlTemplate]};
|
let fixture = builder.createSync(CompWithUrlTemplate);
|
||||||
}).inject([ComponentFactoryResolver], (resolver: ComponentFactoryResolver) => {
|
expect(fixture.nativeElement).toHaveText('from external template\n');
|
||||||
expect(resolver.resolveComponentFactory(CompWithUrlTemplate).componentType)
|
}));
|
||||||
.toBe(CompWithUrlTemplate);
|
|
||||||
})));
|
|
||||||
|
|
||||||
it('should allow to precompile components with templateUrl using the fakeAsync helper',
|
|
||||||
fakeAsync(withModule(() => {
|
|
||||||
return {precompile: [CompWithUrlTemplate]};
|
|
||||||
}).inject([ComponentFactoryResolver], (resolver: ComponentFactoryResolver) => {
|
|
||||||
expect(resolver.resolveComponentFactory(CompWithUrlTemplate).componentType)
|
|
||||||
.toBe(CompWithUrlTemplate);
|
|
||||||
})));
|
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('setting up the compiler', () => {
|
describe('setting up the compiler', () => {
|
||||||
@ -450,26 +442,27 @@ export function main() {
|
|||||||
configureCompiler({providers: [{provide: XHR, useValue: {get: xhrGet}}]});
|
configureCompiler({providers: [{provide: XHR, useValue: {get: xhrGet}}]});
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should report an error for precompile components with templateUrl and sync tests', () => {
|
it('should report an error for precompile components with templateUrl which never call doAsyncPrecompile',
|
||||||
var itPromise = patchJasmineIt();
|
() => {
|
||||||
|
var itPromise = patchJasmineIt();
|
||||||
|
|
||||||
expect(
|
expect(
|
||||||
() => it(
|
() =>
|
||||||
'should fail',
|
it('should fail',
|
||||||
withModule(() => { return {precompile: [CompWithUrlTemplate]}; })
|
withModule(() => { return {precompile: [CompWithUrlTemplate]}; })
|
||||||
.inject(
|
.inject(
|
||||||
[ComponentFactoryResolver],
|
[ComponentFactoryResolver],
|
||||||
(resolver: ComponentFactoryResolver) => {
|
(resolver: ComponentFactoryResolver) => {
|
||||||
expect(
|
expect(resolver.resolveComponentFactory(CompWithUrlTemplate)
|
||||||
resolver.resolveComponentFactory(CompWithUrlTemplate).componentType)
|
.componentType)
|
||||||
.toBe(CompWithUrlTemplate);
|
.toBe(CompWithUrlTemplate);
|
||||||
})))
|
})))
|
||||||
.toThrowError(
|
.toThrowError(
|
||||||
`This test module precompiles the component ${stringify(CompWithUrlTemplate)} which is using a "templateUrl", but the test is synchronous. ` +
|
`This test module precompiles the component ${stringify(CompWithUrlTemplate)} which is using a "templateUrl", but precompilation was never done. ` +
|
||||||
'Please use the "async(...)" or "fakeAsync(...)" helper functions to make the test asynchronous.');
|
'Please call "doAsyncPrecompilation" before "inject".');
|
||||||
|
|
||||||
restoreJasmineIt();
|
restoreJasmineIt();
|
||||||
});
|
});
|
||||||
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -7,7 +7,7 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
import {NgZone, provide} from '@angular/core';
|
import {NgZone, provide} from '@angular/core';
|
||||||
import {withProviders} from '@angular/core/testing/test_injector';
|
import {withProviders} from '@angular/core/testing/test_bed';
|
||||||
import {MockNgZone, beforeEach, beforeEachProviders, describe, expect, inject, it} from '@angular/core/testing/testing_internal';
|
import {MockNgZone, beforeEach, beforeEachProviders, describe, expect, inject, it} from '@angular/core/testing/testing_internal';
|
||||||
import {AsyncTestCompleter} from '@angular/core/testing/testing_internal';
|
import {AsyncTestCompleter} from '@angular/core/testing/testing_internal';
|
||||||
import {MessageBus} from '@angular/platform-browser/src/web_workers/shared/message_bus';
|
import {MessageBus} from '@angular/platform-browser/src/web_workers/shared/message_bus';
|
||||||
|
@ -8,7 +8,7 @@
|
|||||||
|
|
||||||
import {inject, ddescribe, describe, it, iit, expect, beforeEach, beforeEachProviders,} from '@angular/core/testing/testing_internal';
|
import {inject, ddescribe, describe, it, iit, expect, beforeEach, beforeEachProviders,} from '@angular/core/testing/testing_internal';
|
||||||
import {AsyncTestCompleter} from '@angular/core/testing/testing_internal';
|
import {AsyncTestCompleter} from '@angular/core/testing/testing_internal';
|
||||||
import {TestInjector, TestComponentBuilder, configureModule} from '@angular/core/testing';
|
import {TestBed, TestComponentBuilder, configureModule} from '@angular/core/testing';
|
||||||
import {getDOM} from '@angular/platform-browser/src/dom/dom_adapter';
|
import {getDOM} from '@angular/platform-browser/src/dom/dom_adapter';
|
||||||
import {provide, Injector, ViewMetadata, Component, Injectable, ComponentRef, ReflectiveInjector, getPlatform} from '@angular/core';
|
import {provide, Injector, ViewMetadata, Component, Injectable, ComponentRef, ReflectiveInjector, getPlatform} from '@angular/core';
|
||||||
import {NgIf} from '@angular/common';
|
import {NgIf} from '@angular/common';
|
||||||
@ -67,7 +67,7 @@ export function main() {
|
|||||||
|
|
||||||
beforeEach(() => {
|
beforeEach(() => {
|
||||||
uiRenderStore = new RenderStore();
|
uiRenderStore = new RenderStore();
|
||||||
var testUiInjector = new TestInjector();
|
var testUiInjector = new TestBed();
|
||||||
testUiInjector.platform = browserDynamicTestPlatform();
|
testUiInjector.platform = browserDynamicTestPlatform();
|
||||||
testUiInjector.appModule = BrowserTestModule;
|
testUiInjector.appModule = BrowserTestModule;
|
||||||
testUiInjector.configureModule({
|
testUiInjector.configureModule({
|
||||||
@ -77,9 +77,9 @@ export function main() {
|
|||||||
{provide: RootRenderer, useExisting: DomRootRenderer}
|
{provide: RootRenderer, useExisting: DomRootRenderer}
|
||||||
]
|
]
|
||||||
});
|
});
|
||||||
uiInjector = testUiInjector.createInjectorSync();
|
testUiInjector.initTestAppModule();
|
||||||
var uiSerializer = uiInjector.get(Serializer);
|
var uiSerializer = testUiInjector.get(Serializer);
|
||||||
var domRootRenderer = uiInjector.get(DomRootRenderer);
|
var domRootRenderer = testUiInjector.get(DomRootRenderer);
|
||||||
workerRenderStore = new RenderStore();
|
workerRenderStore = new RenderStore();
|
||||||
|
|
||||||
configureModule({
|
configureModule({
|
||||||
|
52
tools/public_api_guard/core/testing.d.ts
vendored
52
tools/public_api_guard/core/testing.d.ts
vendored
@ -46,6 +46,9 @@ export declare function configureModule(moduleDef: {
|
|||||||
/** @experimental */
|
/** @experimental */
|
||||||
export declare function discardPeriodicTasks(): void;
|
export declare function discardPeriodicTasks(): void;
|
||||||
|
|
||||||
|
/** @experimental */
|
||||||
|
export declare function doAsyncPrecompilation(): Promise<any>;
|
||||||
|
|
||||||
/** @experimental */
|
/** @experimental */
|
||||||
export declare function fakeAsync(fn: Function): (...args: any[]) => any;
|
export declare function fakeAsync(fn: Function): (...args: any[]) => any;
|
||||||
|
|
||||||
@ -53,7 +56,10 @@ export declare function fakeAsync(fn: Function): (...args: any[]) => any;
|
|||||||
export declare function flushMicrotasks(): void;
|
export declare function flushMicrotasks(): void;
|
||||||
|
|
||||||
/** @experimental */
|
/** @experimental */
|
||||||
export declare function getTestInjector(): TestInjector;
|
export declare function getTestBed(): TestBed;
|
||||||
|
|
||||||
|
/** @deprecated */
|
||||||
|
export declare function getTestInjector(): TestBed;
|
||||||
|
|
||||||
/** @experimental */
|
/** @experimental */
|
||||||
export declare function initTestEnvironment(appModule: Type, platform: PlatformRef): void;
|
export declare function initTestEnvironment(appModule: Type, platform: PlatformRef): void;
|
||||||
@ -82,6 +88,28 @@ export declare function resetTestEnvironment(): void;
|
|||||||
/** @deprecated */
|
/** @deprecated */
|
||||||
export declare function setBaseTestProviders(platformProviders: Array<Type | Provider | any[]>, applicationProviders: Array<Type | Provider | any[]>): void;
|
export declare function setBaseTestProviders(platformProviders: Array<Type | Provider | any[]>, applicationProviders: Array<Type | Provider | any[]>): void;
|
||||||
|
|
||||||
|
/** @experimental */
|
||||||
|
export declare class TestBed implements Injector {
|
||||||
|
appModule: Type;
|
||||||
|
platform: PlatformRef;
|
||||||
|
configureCompiler(config: {
|
||||||
|
providers?: any[];
|
||||||
|
useJit?: boolean;
|
||||||
|
}): void;
|
||||||
|
configureModule(moduleDef: {
|
||||||
|
providers?: any[];
|
||||||
|
directives?: any[];
|
||||||
|
pipes?: any[];
|
||||||
|
precompile?: any[];
|
||||||
|
modules?: any[];
|
||||||
|
}): void;
|
||||||
|
createAppModuleFactory(): Promise<AppModuleFactory<any>>;
|
||||||
|
execute(tokens: any[], fn: Function): any;
|
||||||
|
get(token: any, notFoundValue?: any): any;
|
||||||
|
initTestAppModule(): void;
|
||||||
|
reset(): void;
|
||||||
|
}
|
||||||
|
|
||||||
/** @stable */
|
/** @stable */
|
||||||
export declare class TestComponentBuilder {
|
export declare class TestComponentBuilder {
|
||||||
protected _injector: Injector;
|
protected _injector: Injector;
|
||||||
@ -103,28 +131,6 @@ export declare class TestComponentRenderer {
|
|||||||
insertRootElement(rootElementId: string): void;
|
insertRootElement(rootElementId: string): void;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @experimental */
|
|
||||||
export declare class TestInjector implements Injector {
|
|
||||||
appModule: Type;
|
|
||||||
platform: PlatformRef;
|
|
||||||
configureCompiler(config: {
|
|
||||||
providers?: any[];
|
|
||||||
useJit?: boolean;
|
|
||||||
}): void;
|
|
||||||
configureModule(moduleDef: {
|
|
||||||
providers?: any[];
|
|
||||||
directives?: any[];
|
|
||||||
pipes?: any[];
|
|
||||||
precompile?: any[];
|
|
||||||
modules?: any[];
|
|
||||||
}): void;
|
|
||||||
createInjectorAsync(): Promise<Injector>;
|
|
||||||
createInjectorSync(): Injector;
|
|
||||||
execute(tokens: any[], fn: Function): any;
|
|
||||||
get(token: any, notFoundValue?: any): any;
|
|
||||||
reset(): void;
|
|
||||||
}
|
|
||||||
|
|
||||||
/** @experimental */
|
/** @experimental */
|
||||||
export declare function tick(millis?: number): void;
|
export declare function tick(millis?: number): void;
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user