in src/ts_migration_exports_shim.ts [141:241]
private extractTsmesStatement(): undefined|TsmesCallBreakdown {
const startDiagnosticsCount = this.diagnostics.length;
let tsmesCallStatement: ts.ExpressionStatement|undefined = undefined;
for (const statement of this.src.statements) {
if (!ts.isExpressionStatement(statement) ||
!isAnyTsmesCall(statement.expression)) {
this.checkNonTopLevelTsmesCalls(statement);
continue;
}
if (tsmesCallStatement) {
this.report(
tsmesCallStatement,
'at most one call to any of goog.tsMigrationExportsShim, ' +
'goog.tsMigrationDefaultExportsShim, ' +
'goog.tsMigrationNamedExportsShim is allowed per file');
} else {
tsmesCallStatement = statement;
}
}
if (!tsmesCallStatement) {
return undefined;
} else if (!this.host.generateTsMigrationExportsShim) {
this.report(
tsmesCallStatement,
'calls to goog.tsMigration*ExportsShim are not enabled. Did you' +
' remember to set generate_ts_migration_exports_shim?');
return undefined;
}
const tsmesCall = tsmesCallStatement.expression as ts.CallExpression;
if (isGoogCallExpressionOf(tsmesCall, 'tsMigrationExportsShim') &&
tsmesCall.arguments.length !== 2) {
this.report(
tsmesCall, 'goog.tsMigrationExportsShim requires 2 arguments');
return undefined;
}
if (isTsmesShorthandCall(tsmesCall) && tsmesCall.arguments.length !== 1) {
this.report(
tsmesCall,
`goog.${
getGoogFunctionName(tsmesCall)} requires exactly one argument`);
return undefined;
}
if (isGoogCallExpressionOf(tsmesCall, 'tsMigrationDefaultExportsShim') &&
this.mainExports.length !== 1) {
this.report(
tsmesCall,
'can only call goog.tsMigrationDefaultExportsShim when there is' +
' exactly one export.');
return undefined;
}
const [moduleId, exportsExpr] = tsmesCall.arguments;
if (!ts.isStringLiteral(moduleId)) {
this.report(
moduleId,
`goog.${getGoogFunctionName(tsmesCall)} ID must be a string literal`);
return undefined;
}
let googExports: GoogExports|undefined = undefined;
const fnName = getGoogFunctionName(tsmesCall);
switch (fnName) {
case 'tsMigrationDefaultExportsShim':
// Export the one and only export as an unnamed export.
// vis. export = foo;
googExports = this.mainExports[0].name;
break;
case 'tsMigrationNamedExportsShim':
// Export all exports as named exports
// vis. export.a = a;
// export.b = b;
googExports = new Map<string, string>();
for (const mainExport of this.mainExports) {
googExports.set(mainExport.name, mainExport.name);
}
break;
case 'tsMigrationExportsShim':
// Export the structure described by exportsExpr
googExports = this.extractGoogExports(exportsExpr);
break;
default:
throw new Error(`encountered unhandled goog.$fnName: ${fnName}`);
}
if (googExports === undefined) {
if (startDiagnosticsCount >= this.diagnostics.length) {
throw new Error(
'googExports should be defined unless some diagnostic is reported.');
}
return undefined;
}
return {
callStatement: tsmesCallStatement,
googModuleId: moduleId,
googExports,
};
}