Skip to content
This repository was archived by the owner on Apr 4, 2025. It is now read-only.

Commit db5469f

Browse files
committed
test: never use subscribe with done callbacks in jasmine
Using subscribe with done callbacks in Jasmine leads to `afterEach` being called before the observable is unsubscribed from. This in turn leads to teardown logic inside observables to only happen after `afterEach` runs. This can be problematic when the teardown logic in observables interacts with logic in `afterEach`. For instance, for webpack builders in watch mode, `afterEach` deletes source file folder while the teardown logic closes file watchers. Trying to delete files while they are still being watched leads to errors on Windows.
1 parent 0be99d3 commit db5469f

File tree

58 files changed

+276
-279
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

58 files changed

+276
-279
lines changed

packages/angular_devkit/architect/src/architect_spec.ts

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -61,7 +61,7 @@ describe('Architect', () => {
6161
beforeAll((done) => workspace.loadWorkspaceFromJson(workspaceJson).pipe(
6262
concatMap(ws => new Architect(ws).loadArchitect()),
6363
tap(arch => architect = arch),
64-
).subscribe(undefined, done.fail, done));
64+
).toPromise().then(done, done.fail));
6565

6666
it('works', () => {
6767
const targetSpec = { project: 'app', target: 'browser', configuration: 'prod' };
@@ -101,24 +101,24 @@ describe('Architect', () => {
101101
expect(events[1].success).toBe(false);
102102
expect(events[2].success).toBe(true);
103103
}),
104-
).subscribe(undefined, done.fail, done);
104+
).toPromise().then(done, done.fail);
105105
});
106106

107107
it('errors when builder cannot be resolved', (done) => {
108108
const targetSpec = { project: 'app', target: 'karma' };
109109
const builderConfig = architect.getBuilderConfiguration<BrowserTargetOptions>(targetSpec);
110-
architect.run(builderConfig).subscribe(undefined, (err: Error) => {
110+
architect.run(builderConfig).toPromise().then(() => done.fail(), (err: Error) => {
111111
expect(err).toEqual(jasmine.any(BuilderCannotBeResolvedException));
112112
done();
113-
}, done.fail);
113+
});
114114
});
115115

116116
it('errors when builder options fail validation', (done) => {
117117
const targetSpec = { project: 'app', target: 'badBrowser' };
118118
const builderConfig = architect.getBuilderConfiguration<BrowserTargetOptions>(targetSpec);
119-
architect.run(builderConfig).subscribe(undefined, (err: Error) => {
119+
architect.run(builderConfig).toPromise().then(() => done.fail(), (err: Error) => {
120120
expect(err).toEqual(jasmine.any(schema.SchemaValidationException));
121121
done();
122-
}, done.fail);
122+
});
123123
});
124124
});

packages/angular_devkit/build_angular/test/app-shell/app-shell_spec_large.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,8 +11,8 @@ import { Timeout, host, runTargetSpec } from '../utils';
1111

1212

1313
describe('AppShell Builder', () => {
14-
beforeEach(done => host.initialize().subscribe(undefined, done.fail, done));
15-
afterEach(done => host.restore().subscribe(undefined, done.fail, done));
14+
beforeEach(done => host.initialize().toPromise().then(done, done.fail));
15+
afterEach(done => host.restore().toPromise().then(done, done.fail));
1616

1717
it('works (basic)', done => {
1818
host.replaceInFile('src/app/app.module.ts', / BrowserModule/, `
@@ -44,7 +44,7 @@ describe('AppShell Builder', () => {
4444
const content = virtualFs.fileBufferToString(host.scopedSync().read(normalize(fileName)));
4545
expect(content).toMatch(/Welcome to app!/);
4646
}),
47-
).subscribe(undefined, done.fail, done);
47+
).toPromise().then(done, done.fail);
4848

4949
}, Timeout.Complex);
5050
});

packages/angular_devkit/build_angular/test/browser/allow-js_spec_large.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -11,8 +11,8 @@ import { Timeout, browserTargetSpec, host, runTargetSpec } from '../utils';
1111

1212

1313
describe('Browser Builder allow js', () => {
14-
beforeEach(done => host.initialize().subscribe(undefined, done.fail, done));
15-
afterEach(done => host.restore().subscribe(undefined, done.fail, done));
14+
beforeEach(done => host.initialize().toPromise().then(done, done.fail));
15+
afterEach(done => host.restore().toPromise().then(done, done.fail));
1616

1717
it('works', (done) => {
1818
host.writeMultipleFiles({
@@ -25,7 +25,7 @@ describe('Browser Builder allow js', () => {
2525

2626
runTargetSpec(host, browserTargetSpec).pipe(
2727
tap((buildEvent) => expect(buildEvent.success).toBe(true)),
28-
).subscribe(undefined, done.fail, done);
28+
).toPromise().then(done, done.fail);
2929
}, Timeout.Basic);
3030

3131
it('works with aot', (done) => {
@@ -38,6 +38,6 @@ describe('Browser Builder allow js', () => {
3838

3939
runTargetSpec(host, browserTargetSpec, overrides).pipe(
4040
tap((buildEvent) => expect(buildEvent.success).toBe(true)),
41-
).subscribe(undefined, done.fail, done);
41+
).toPromise().then(done, done.fail);
4242
}, Timeout.Basic);
4343
});

packages/angular_devkit/build_angular/test/browser/aot_spec_large.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -14,8 +14,8 @@ import { Timeout, browserTargetSpec, host, runTargetSpec } from '../utils';
1414
describe('Browser Builder AOT', () => {
1515
const outputPath = normalize('dist');
1616

17-
beforeEach(done => host.initialize().subscribe(undefined, done.fail, done));
18-
afterEach(done => host.restore().subscribe(undefined, done.fail, done));
17+
beforeEach(done => host.initialize().toPromise().then(done, done.fail));
18+
afterEach(done => host.restore().toPromise().then(done, done.fail));
1919

2020
it('works', (done) => {
2121
const overrides = { aot: true };
@@ -27,6 +27,6 @@ describe('Browser Builder AOT', () => {
2727
const content = virtualFs.fileBufferToString(host.scopedSync().read(normalize(fileName)));
2828
expect(content).toMatch(/platformBrowser.*bootstrapModuleFactory.*AppModuleNgFactory/);
2929
}),
30-
).subscribe(undefined, done.fail, done);
30+
).toPromise().then(done, done.fail);
3131
}, Timeout.Standard);
3232
});

packages/angular_devkit/build_angular/test/browser/assets_spec_large.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -12,8 +12,8 @@ import { Timeout, browserTargetSpec, host, runTargetSpec } from '../utils';
1212

1313

1414
describe('Browser Builder assets', () => {
15-
beforeEach(done => host.initialize().subscribe(undefined, done.fail, done));
16-
afterEach(done => host.restore().subscribe(undefined, done.fail, done));
15+
beforeEach(done => host.initialize().toPromise().then(done, done.fail));
16+
afterEach(done => host.restore().toPromise().then(done, done.fail));
1717

1818
it('works', (done) => {
1919
const assets: { [path: string]: string } = {
@@ -55,7 +55,7 @@ describe('Browser Builder assets', () => {
5555
// .gitkeep should not be there.
5656
expect(host.scopedSync().exists(normalize('./dist/folder/.gitkeep'))).toBe(false);
5757
}),
58-
).subscribe(undefined, done.fail, done);
58+
).toPromise().then(done, done.fail);
5959
}, Timeout.Basic);
6060

6161
it('fails with non-absolute output path', (done) => {
@@ -100,6 +100,6 @@ describe('Browser Builder assets', () => {
100100
runTargetSpec(host, browserTargetSpec, overrides).pipe(
101101
toArray(),
102102
tap((buildEvents) => expect(buildEvents.length).toBe(1)),
103-
).subscribe(undefined, done.fail, done);
103+
).toPromise().then(done, done.fail);
104104
}, Timeout.Basic);
105105
});

packages/angular_devkit/build_angular/test/browser/base-href_spec_large.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -14,8 +14,8 @@ import { Timeout, browserTargetSpec, host, runTargetSpec } from '../utils';
1414
describe('Browser Builder base href', () => {
1515
const outputPath = normalize('dist');
1616

17-
beforeEach(done => host.initialize().subscribe(undefined, done.fail, done));
18-
afterEach(done => host.restore().subscribe(undefined, done.fail, done));
17+
beforeEach(done => host.initialize().toPromise().then(done, done.fail));
18+
afterEach(done => host.restore().toPromise().then(done, done.fail));
1919

2020
it('works', (done) => {
2121
host.writeMultipleFiles({
@@ -32,6 +32,6 @@ describe('Browser Builder base href', () => {
3232
const content = virtualFs.fileBufferToString(host.scopedSync().read(fileName));
3333
expect(content).toMatch(/<base href="\/myUrl">/);
3434
}),
35-
).subscribe(undefined, done.fail, done);
35+
).toPromise().then(done, done.fail);
3636
}, Timeout.Basic);
3737
});

packages/angular_devkit/build_angular/test/browser/build-optimizer_spec_large.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -14,8 +14,8 @@ import { Timeout, browserTargetSpec, host, runTargetSpec } from '../utils';
1414
describe('Browser Builder build optimizer', () => {
1515
const outputPath = normalize('dist');
1616

17-
beforeEach(done => host.initialize().subscribe(undefined, done.fail, done));
18-
afterEach(done => host.restore().subscribe(undefined, done.fail, done));
17+
beforeEach(done => host.initialize().toPromise().then(done, done.fail));
18+
afterEach(done => host.restore().toPromise().then(done, done.fail));
1919

2020
it('works', (done) => {
2121
const overrides = { aot: true, buildOptimizer: true };
@@ -26,6 +26,6 @@ describe('Browser Builder build optimizer', () => {
2626
const content = virtualFs.fileBufferToString(host.scopedSync().read(normalize(fileName)));
2727
expect(content).not.toMatch(/\.decorators =/);
2828
}),
29-
).subscribe(undefined, done.fail, done);
29+
).toPromise().then(done, done.fail);
3030
}, Timeout.Basic);
3131
});

packages/angular_devkit/build_angular/test/browser/bundle-budgets_spec_large.ts

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -12,8 +12,8 @@ import { TestLogger, Timeout, browserTargetSpec, host, runTargetSpec } from '../
1212

1313
describe('Browser Builder bundle budgets', () => {
1414

15-
beforeEach(done => host.initialize().subscribe(undefined, done.fail, done));
16-
afterEach(done => host.restore().subscribe(undefined, done.fail, done));
15+
beforeEach(done => host.initialize().toPromise().then(done, done.fail));
16+
afterEach(done => host.restore().toPromise().then(done, done.fail));
1717

1818
it('accepts valid bundles', (done) => {
1919
const overrides = {
@@ -26,7 +26,7 @@ describe('Browser Builder bundle budgets', () => {
2626
runTargetSpec(host, browserTargetSpec, overrides, logger).pipe(
2727
tap((buildEvent) => expect(buildEvent.success).toBe(true)),
2828
tap(() => expect(logger.includes('WARNING')).toBe(false)),
29-
).subscribe(undefined, done.fail, done);
29+
).toPromise().then(done, done.fail);
3030
}, Timeout.Complex);
3131

3232
it('shows errors', (done) => {
@@ -37,7 +37,7 @@ describe('Browser Builder bundle budgets', () => {
3737

3838
runTargetSpec(host, browserTargetSpec, overrides).pipe(
3939
tap((buildEvent) => expect(buildEvent.success).toBe(false)),
40-
).subscribe(undefined, done.fail, done);
40+
).toPromise().then(done, done.fail);
4141
}, Timeout.Complex);
4242

4343
it('shows warnings', (done) => {
@@ -51,6 +51,6 @@ describe('Browser Builder bundle budgets', () => {
5151
runTargetSpec(host, browserTargetSpec, overrides, logger).pipe(
5252
tap((buildEvent) => expect(buildEvent.success).toBe(true)),
5353
tap(() => expect(logger.includes('WARNING')).toBe(true)),
54-
).subscribe(undefined, done.fail, done);
54+
).toPromise().then(done, done.fail);
5555
}, Timeout.Complex);
5656
});

packages/angular_devkit/build_angular/test/browser/circular-dependency_spec_large.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,8 +11,8 @@ import { TestLogger, Timeout, browserTargetSpec, host, runTargetSpec } from '../
1111

1212

1313
describe('Browser Builder circular dependency detection', () => {
14-
beforeEach(done => host.initialize().subscribe(undefined, done.fail, done));
15-
afterEach(done => host.restore().subscribe(undefined, done.fail, done));
14+
beforeEach(done => host.initialize().toPromise().then(done, done.fail));
15+
afterEach(done => host.restore().toPromise().then(done, done.fail));
1616

1717
it('works', (done) => {
1818
host.appendToFile('src/app/app.component.ts',
@@ -24,6 +24,6 @@ describe('Browser Builder circular dependency detection', () => {
2424
runTargetSpec(host, browserTargetSpec, overrides, logger).pipe(
2525
tap((buildEvent) => expect(buildEvent.success).toBe(true)),
2626
tap(() => expect(logger.includes('Circular dependency detected')).toBe(true)),
27-
).subscribe(undefined, done.fail, done);
27+
).toPromise().then(done, done.fail);
2828
}, Timeout.Basic);
2929
});

packages/angular_devkit/build_angular/test/browser/deploy-url_spec_large.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -14,8 +14,8 @@ import { Timeout, browserTargetSpec, host, runTargetSpec } from '../utils';
1414
describe('Browser Builder deploy url', () => {
1515
const outputPath = normalize('dist');
1616

17-
beforeEach(done => host.initialize().subscribe(undefined, done.fail, done));
18-
afterEach(done => host.restore().subscribe(undefined, done.fail, done));
17+
beforeEach(done => host.initialize().toPromise().then(done, done.fail));
18+
afterEach(done => host.restore().toPromise().then(done, done.fail));
1919

2020
it('uses deploy url for bundles urls', (done) => {
2121
const overrides = { deployUrl: 'deployUrl/' };
@@ -35,7 +35,7 @@ describe('Browser Builder deploy url', () => {
3535
const content = virtualFs.fileBufferToString(host.scopedSync().read(normalize(fileName)));
3636
expect(content).toContain('http://example.com/some/path/main.js');
3737
}),
38-
).subscribe(undefined, done.fail, done);
38+
).toPromise().then(done, done.fail);
3939
}, Timeout.Basic);
4040

4141
it('uses deploy url for in webpack runtime', (done) => {
@@ -48,7 +48,7 @@ describe('Browser Builder deploy url', () => {
4848
const content = virtualFs.fileBufferToString(host.scopedSync().read(normalize(fileName)));
4949
expect(content).toContain('deployUrl/');
5050
}),
51-
).subscribe(undefined, done.fail, done);
51+
).toPromise().then(done, done.fail);
5252
}, Timeout.Basic);
5353

5454
});

packages/angular_devkit/build_angular/test/browser/errors_spec_large.ts

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -11,8 +11,8 @@ import { TestLogger, Timeout, browserTargetSpec, host, runTargetSpec } from '../
1111

1212

1313
describe('Browser Builder errors', () => {
14-
beforeEach(done => host.initialize().subscribe(undefined, done.fail, done));
15-
afterEach(done => host.restore().subscribe(undefined, done.fail, done));
14+
beforeEach(done => host.initialize().toPromise().then(done, done.fail));
15+
afterEach(done => host.restore().toPromise().then(done, done.fail));
1616

1717
it('shows error when files are not part of the compilation', (done) => {
1818
host.replaceInFile('src/tsconfig.app.json', '"compilerOptions": {', `
@@ -26,7 +26,7 @@ describe('Browser Builder errors', () => {
2626
expect(buildEvent.success).toBe(false);
2727
expect(logger.includes('polyfills.ts is missing from the TypeScript')).toBe(true);
2828
}),
29-
).subscribe(undefined, done.fail, done);
29+
).toPromise().then(done, done.fail);
3030
}, Timeout.Basic);
3131

3232
it('shows TS syntax errors', (done) => {
@@ -38,7 +38,7 @@ describe('Browser Builder errors', () => {
3838
expect(buildEvent.success).toBe(false);
3939
expect(logger.includes('Declaration or statement expected.')).toBe(true);
4040
}),
41-
).subscribe(undefined, done.fail, done);
41+
).toPromise().then(done, done.fail);
4242
}, Timeout.Basic);
4343

4444
it('shows static analysis errors', (done) => {
@@ -50,7 +50,7 @@ describe('Browser Builder errors', () => {
5050
expect(buildEvent.success).toBe(false);
5151
expect(logger.includes('Function expressions are not supported in')).toBe(true);
5252
}),
53-
).subscribe(undefined, done.fail, done);
53+
).toPromise().then(done, done.fail);
5454
}, Timeout.Basic);
5555

5656
});

packages/angular_devkit/build_angular/test/browser/i18n_spec_large.ts

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -22,8 +22,8 @@ describe('Browser Builder i18n', () => {
2222
</file>
2323
</xliff>`;
2424

25-
beforeEach(done => host.initialize().subscribe(undefined, done.fail, done));
26-
afterEach(done => host.restore().subscribe(undefined, done.fail, done));
25+
beforeEach(done => host.initialize().toPromise().then(done, done.fail));
26+
afterEach(done => host.restore().toPromise().then(done, done.fail));
2727

2828
it('uses translations', (done) => {
2929
host.writeMultipleFiles({
@@ -60,7 +60,7 @@ describe('Browser Builder i18n', () => {
6060
const content = virtualFs.fileBufferToString(host.scopedSync().read(normalize(fileName)));
6161
expect(content).toMatch(/Bonjour i18n!/);
6262
}),
63-
).subscribe(undefined, done.fail, done);
63+
).toPromise().then(done, done.fail);
6464
}, Timeout.Basic);
6565

6666
it('ignores missing translations', (done) => {
@@ -82,7 +82,7 @@ describe('Browser Builder i18n', () => {
8282
const content = virtualFs.fileBufferToString(host.scopedSync().read(normalize(fileName)));
8383
expect(content).toMatch(/Other content/);
8484
}),
85-
).subscribe(undefined, done.fail, done);
85+
).toPromise().then(done, done.fail);
8686
}, Timeout.Basic);
8787

8888
it('reports errors for missing translations', (done) => {
@@ -99,7 +99,7 @@ describe('Browser Builder i18n', () => {
9999

100100
runTargetSpec(host, browserTargetSpec, overrides).pipe(
101101
tap((buildEvent) => expect(buildEvent.success).toBe(false)),
102-
).subscribe(undefined, done.fail, done);
102+
).toPromise().then(done, done.fail);
103103
}, Timeout.Basic);
104104

105105
it('register locales', (done) => {
@@ -113,6 +113,6 @@ describe('Browser Builder i18n', () => {
113113
expect(content).toMatch(/registerLocaleData/);
114114
expect(content).toMatch(/angular_common_locales_fr/);
115115
}),
116-
).subscribe(undefined, done.fail, done);
116+
).toPromise().then(done, done.fail);
117117
}, Timeout.Basic);
118118
});

packages/angular_devkit/build_angular/test/browser/index_spec_large.ts

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -14,8 +14,8 @@ import { Timeout, browserTargetSpec, host, runTargetSpec } from '../utils';
1414
describe('Browser Builder works with BOM index.html', () => {
1515
const outputPath = normalize('dist');
1616

17-
beforeEach(done => host.initialize().subscribe(undefined, done.fail, done));
18-
afterEach(done => host.restore().subscribe(undefined, done.fail, done));
17+
beforeEach(done => host.initialize().toPromise().then(done, done.fail));
18+
afterEach(done => host.restore().toPromise().then(done, done.fail));
1919

2020
it('works with UTF-8 BOM', (done) => {
2121
host.writeMultipleFiles({
@@ -32,7 +32,7 @@ describe('Browser Builder works with BOM index.html', () => {
3232
// tslint:disable-next-line:max-line-length
3333
expect(content).toBe(`<html><head><base href="/"></head><body><app-root></app-root><script type="text/javascript" src="runtime.js"></script><script type="text/javascript" src="polyfills.js"></script><script type="text/javascript" src="styles.js"></script><script type="text/javascript" src="vendor.js"></script><script type="text/javascript" src="main.js"></script></body></html>`);
3434
}),
35-
).subscribe(undefined, done.fail, done);
35+
).toPromise().then(done, done.fail);
3636
}, Timeout.Basic);
3737

3838
it('works with UTF16 LE BOM', (done) => {
@@ -50,7 +50,7 @@ describe('Browser Builder works with BOM index.html', () => {
5050
// tslint:disable-next-line:max-line-length
5151
expect(content).toBe(`<html><head><base href="/"></head><body><app-root></app-root><script type="text/javascript" src="runtime.js"></script><script type="text/javascript" src="polyfills.js"></script><script type="text/javascript" src="styles.js"></script><script type="text/javascript" src="vendor.js"></script><script type="text/javascript" src="main.js"></script></body></html>`);
5252
}),
53-
).subscribe(undefined, done.fail, done);
53+
).toPromise().then(done, done.fail);
5454
}, Timeout.Basic);
5555

5656
it('keeps escaped charaters', (done) => {
@@ -69,7 +69,7 @@ describe('Browser Builder works with BOM index.html', () => {
6969
// tslint:disable-next-line:max-line-length
7070
expect(content).toBe(`<html><head><title>&iacute;</title><base href="/"></head> <body><app-root></app-root><script type="text/javascript" src="runtime.js"></script><script type="text/javascript" src="polyfills.js"></script><script type="text/javascript" src="styles.js"></script><script type="text/javascript" src="vendor.js"></script><script type="text/javascript" src="main.js"></script></body></html>`);
7171
}),
72-
).subscribe(undefined, done.fail, done);
72+
).toPromise().then(done, done.fail);
7373
}, Timeout.Basic);
7474

7575
it('keeps custom template charaters', (done) => {
@@ -88,6 +88,6 @@ describe('Browser Builder works with BOM index.html', () => {
8888
// tslint:disable-next-line:max-line-length
8989
expect(content).toBe(`<html><head><base href="/"><%= csrf_meta_tags %></head> <body><app-root></app-root><script type="text/javascript" src="runtime.js"></script><script type="text/javascript" src="polyfills.js"></script><script type="text/javascript" src="styles.js"></script><script type="text/javascript" src="vendor.js"></script><script type="text/javascript" src="main.js"></script></body></html>`);
9090
}),
91-
).subscribe(undefined, done.fail, done);
91+
).toPromise().then(done, done.fail);
9292
}, Timeout.Basic);
9393
});

0 commit comments

Comments
 (0)