Apollo-angular: ng add apollo-angular not working correctly

Created on 28 Mar 2020  路  4Comments  路  Source: kamilkisiela/apollo-angular

Intended outcome:
use ng add apollo-angular command to start an Angular project with Apollo

Actual outcome:
I get the following error:

We couln't find 'esnext.asynciterable' in the list of library files to be included in the compilation.
It's required by 'apollo-client' package so please add it to your tsconfig.

Could not find /src/src/app/app.module.ts!

(Aside: Note the couln't typo)

How to reproduce the issue:
Use the following tsconfig.json in the root of the project and run ng add apollo-angular:

{
    "compileOnSave": false,
    "compilerOptions": {
        "module": "esnext",
        "outDir": "./dist/out-tsc",
        "strictNullChecks": true,
        "noImplicitAny": false,
        "noImplicitThis": true,
        "alwaysStrict": false,
        "forceConsistentCasingInFileNames": true,
        "noImplicitReturns": true,
        "noUnusedLocals": true,
        "skipLibCheck": true,
        "sourceMap": true,
        "declaration": false,
        "moduleResolution": "node",
        "emitDecoratorMetadata": true,
        "experimentalDecorators": true,
        "allowJs": true,
        "resolveJsonModule": true,
        "esModuleInterop": true,
        "target": "es2015",
        "types": [
            "node",
            "jest"
        ],
        "typeRoots": [
            "node_modules/@types"
        ],
        "lib": [
            "es2018",
            "dom",
            "esnext.asynciterable"
        ],
        "baseUrl": "./",
        "paths": {
            "core-js/es6/*": [
                "node_modules/core-js/es/*"
            ],
            "core-js/es7/reflect": [
                "node_modules/core-js/proposals/reflect-metadata"
            ],
            "@core/*": [
                "src/app/core/*"
            ],
            "@shared/*": [
                "src/app/shared/*"
            ],
            "@feature/*": [
                "src/app/feature/*"
            ],
            "@test/*": [
                "src/test/*"
            ],
            "@/*": [
                "src/*"
            ]
        }
    },
    "exclude": [
        "**/node_modules/*",
        "**/dist/*"
    ],
    "angularCompilerOptions": {
        "fullTemplateTypeCheck": true,
        "strictInjectionParameters": true
    }
}

Versions
Nothing installed yet on Apollo side.

Angular:

Angular CLI: 9.0.7
Node: 13.9.0
OS: win32 x64

Angular: 9.0.7
... animations, cli, common, compiler, compiler-cli, core, forms
... language-service, localize, platform-browser
... platform-browser-dynamic, router, service-worker
Ivy Workspace: Yes

Package                           Version
-----------------------------------------------------------
@angular-devkit/architect         0.900.4
@angular-devkit/build-angular     0.900.7
@angular-devkit/build-optimizer   0.900.7
@angular-devkit/build-webpack     0.900.7
@angular-devkit/core              9.0.4
@angular-devkit/schematics        9.0.7
@angular/cdk                      9.1.3
@angular/material                 9.1.3
@ngtools/webpack                  9.0.7
@schematics/angular               9.0.7
@schematics/update                0.900.7
rxjs                              6.5.4
typescript                        3.7.5
webpack                           4.41.2

When analyzing the code here https://github.com/apollographql/apollo-angular/blob/master/packages/apollo-angular/schematics/install/index.ts it appears that there is incorrect logic on line 135:

    if (
      compilerOptions &&
      compilerOptions.lib &&
      !compilerOptions.lib.find(lib => lib.toLowerCase() === requiredLib)
    ) {
      compilerOptions.lib.push(requiredLib);
      host.overwrite(tsconfigPath, JSON.stringify(tsconfig, null, 2));
    } else {
      console.error(
        terminal.yellow(
          '\n' +
            tags.stripIndent`
              We couln't find '${requiredLib}' in the list of library files to be included in the compilation.
              It's required by 'apollo-client' package so please add it to your tsconfig.
            ` +
            '\n',
        ),
      );
    }

If esnext.asynciterable is a required library, then you would want to error if it is not found, not if it is found, so !compilerOptions.lib.find(lib => lib.toLowerCase() === requiredLib) should be compilerOptions.lib.find(lib => lib.toLowerCase() === requiredLib) in the conditional statement. I have verified that if I remove esnext.asynciterable from my tsconfig.json, I only get the error:

Could not find /src/src/app/app.module.ts!

And this error appears to be happening because an extra src is being added into the path somewhere, but I'm not sure where or why.

Most helpful comment

I had the same issue. Solved it by temporary changing the AppModule import URL in my src/main.ts file from this:

import { AppModule } from 'src/app/app.module';
to this (only while the schematic was running):
import { AppModule } from 'app/app.module';
The problem was with the function `getAppModulePath` in this file: [https://github.com/kamilkisiela/apollo-angular/blob/master/packages/apollo-angular/schematics/install/index.ts](https://github.com/kamilkisiela/apollo-angular/blob/master/packages/apollo-angular/schematics/install/index.ts#L159), line 159:
function addSetupFiles(options: Schema) {
  return (host: Tree) => {
    const mainPath = getMainPath(host, options.project);
    const appModulePath = getAppModulePath(host, mainPath);
    const appModuleDirectory = dirname(appModulePath);
...

It's looking the AppModule import URL in the main.ts file, found in the build.options.main property in the angular.json file.

All 4 comments

I did:

# 9.1.1
yarn global add @angular/cli
# 9.1.1.
ng --version

yarn ng new test-app
cd test-app
yarn ng add apollo-angular

And it works

Please provide an example project / reproduction so I will reopen the issue

I've hit the same problem.
angular.json has "tsConfig": "src/client/tsconfig.app.json",

src/client/tsconfig.app.json has "extends": "./tsconfig.json",

./tsconfig.json has "lib": ["es2018", "dom", "esnext.asynciterable"],

ng add gives

We couln't find 'esnext.asynciterable'

I had the same issue. Solved it by temporary changing the AppModule import URL in my src/main.ts file from this:

import { AppModule } from 'src/app/app.module';
to this (only while the schematic was running):
import { AppModule } from 'app/app.module';
The problem was with the function `getAppModulePath` in this file: [https://github.com/kamilkisiela/apollo-angular/blob/master/packages/apollo-angular/schematics/install/index.ts](https://github.com/kamilkisiela/apollo-angular/blob/master/packages/apollo-angular/schematics/install/index.ts#L159), line 159:
function addSetupFiles(options: Schema) {
  return (host: Tree) => {
    const mainPath = getMainPath(host, options.project);
    const appModulePath = getAppModulePath(host, mainPath);
    const appModuleDirectory = dirname(appModulePath);
...

It's looking the AppModule import URL in the main.ts file, found in the build.options.main property in the angular.json file.

Was this page helpful?
0 / 5 - 0 ratings