fix(ivy): copy top-level comments into generated factory shims (#29065)

When ngtsc generates a .ngfactory shim, it does so based on the contents of
an original file in the program. Occasionally these original files have
comments at the top which are load-bearing (e.g. they contain jsdoc
annotations which are significant to downstream bundling tools). The
generated factory shims should preserve this comment.

This commit adds a step to the ngfactory generator to preserve the top-level
comment from the original source file.

FW-1006 #resolve
FW-1095 #resolve

PR Close #29065
This commit is contained in:
Alex Rickabaugh 2019-03-01 15:17:26 -08:00 committed by Andrew Kushnir
parent 04cf4ef0c7
commit 866d500324
2 changed files with 29 additions and 2 deletions

View File

@ -56,14 +56,25 @@ export class FactoryGenerator implements ShimGenerator {
// Grab the symbol name.
.map(decl => decl.name !.text);
let sourceText = '';
// If there is a top-level comment in the original file, copy it over at the top of the
// generated factory file. This is important for preserving any load-bearing jsdoc comments.
let comment: string = '';
if (original.statements.length > 0) {
const firstStatement = original.statements[0];
if (firstStatement.getLeadingTriviaWidth() > 0) {
comment = firstStatement.getFullText().substr(0, firstStatement.getLeadingTriviaWidth());
}
}
let sourceText = comment;
if (symbolNames.length > 0) {
// For each symbol name, generate a constant export of the corresponding NgFactory.
// This will encompass a lot of symbols which don't need factories, but that's okay
// because it won't miss any that do.
const varLines = symbolNames.map(
name => `export const ${name}NgFactory = new i0.ɵNgModuleFactory(${name});`);
sourceText = [
sourceText += [
// This might be incorrect if the current package being compiled is Angular core, but it's
// okay to leave in at type checking time. TypeScript can handle this reference via its path
// mapping, but downstream bundlers can't. If the current package is core itself, this will

View File

@ -1694,6 +1694,22 @@ describe('ngtsc behavioral tests', () => {
expect(emptyFactory).toContain(`export var ɵNonEmptyModule = true;`);
});
it('should copy a top-level comment into a factory stub', () => {
env.tsconfig({'allowEmptyCodegenFiles': true});
env.write('test.ts', `/** I am a top-level comment. */
import {NgModule} from '@angular/core';
@NgModule({})
export class TestModule {}
`);
env.driveMain();
const factoryContents = env.getContents('test.ngfactory.js');
expect(factoryContents).toMatch(/^\/\*\* I am a top-level comment\. \*\//);
});
it('should be able to compile an app using the factory shim', () => {
env.tsconfig({'allowEmptyCodegenFiles': true});