typescript - angular-cli 25.5 Modul gagal dibangun


Masalah

Setelah memperbarui angular-cli dari 22.1 ke 25.5 (menginstal angular-cli@latest) dan dari angular 2.2.3 ke 2.3.1, saya mengalami masalah ini:

ERROR in ./src/app/app.module.ts
Module build failed: TypeError: Cannot read property 'text' of undefined
    at IdentifierObject.TokenOrIdentifierObject.getText (~/projects/MyProject/node_modules/typescript/lib/typescript.js:53644:56)
    at ~/projects/MyProject/node_modules/@ngtools/webpack/src/loader.js:83:72
    at Array.some (native)
    at ~/projects/MyProject/node_modules/@ngtools/webpack/src/loader.js:83:32
    at Array.filter (native)
    at _removeModuleId (~/projects/MyProject/node_modules/@ngtools/webpack/src/loader.js:82:10)
    at ~/projects/MyProject/node_modules/@ngtools/webpack/src/loader.js:167:48
 @ ./src/main.ts 5:0-45
 @ multi main

Tapi saya tidak bisa mencari tahu apa masalahnya, main.ts terlihat normal:

import './polyfills.ts';
import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
import { enableProdMode } from '@angular/core';
import { environment } from './environments/environment';
import { AppModule } from './app/app.module';

if (environment.production) {
  enableProdMode();
}

platformBrowserDynamic().bootstrapModule(AppModule);

Ada dua file lain yang juga gagal dengan pesan kesalahan yang sama persis seperti di atas, pertama environment.ts tanpa ada yang istimewa di dalamnya dan kedua sebuah sub modul yang gagal dengan tambahan:

 @ ./src async
 @ ./~/@angular/core/src/linker/system_js_ng_module_factory_loader.js
 @ ./~/@angular/core/src/linker.js
 @ ./~/@angular/core/src/core.js
 @ ./~/@angular/core/index.js
 @ ./src/main.ts
 @ multi main

Kode Sumber NodeModules

Kode typescript.js:53644:56 yang dimaksud terlihat seperti ini:

[53643] TokenOrIdentifierObject.prototype.getText = function (sourceFile) {
[53644]     return (sourceFile || this.getSourceFile()).text.substring(this.getStart(), this.getEnd());
[53645] };

dan loader.js:83:72 & 83:32 merujuk pada webpack dan potongan kode ini:

[078] exports.removeModuleIdOnlyForTesting = removeModuleIdOnlyForTesting;
[...] function _removeModuleId(refactor) {
[...]   var sourceFile = refactor.sourceFile;
[...]   refactor.findAstNodes(sourceFile, ts.SyntaxKind.ObjectLiteralExpression, true)
[...]       .filter(function (node) {
[083]       return node.properties.some(function (prop) { return prop.name.getText() == 'moduleId'; });
[...]   })
[...]       .forEach(function (node) {
[...]       var moduleIdProp = node.properties.filter(function (prop, idx) {
[...]           return prop.name.getText() == 'moduleId';
[...]       })[0];
[...]       // get the trailing comma
[...]       var moduleIdCommaProp = moduleIdProp.parent.getChildAt(1).getChildren()[1];
[...]       refactor.removeNodes(moduleIdProp, moduleIdCommaProp);
[...]   });
[093] }

dan loader.js:167:48

[148] // Super simple TS transpiler loader for testing / isolated usage. does not type check!
[...] function ngcLoader(source) {
[...]   this.cacheable();
[...]   var cb = this.async();
[...]   var sourceFileName = this.resourcePath;
[...]   var plugin = this._compilation._ngToolsWebpackPluginInstance;
[...]   // We must verify that AotPlugin is an instance of the right class.
[...]   if (plugin && plugin instanceof plugin_1.AotPlugin) {
[...]       var refactor_2 = new refactor_1.TypeScriptFileRefactor(sourceFileName, plugin.compilerHost, plugin.program);
[...]       Promise.resolve()
[...]           .then(function () {
[...]           if (!plugin.skipCodeGeneration) {
[...]               return Promise.resolve()
[...]                   .then(function () { return _removeDecorators(refactor_2); })
[...]                   .then(function () { return _replaceBootstrap(plugin, refactor_2); });
[...]           }
[...]           else {
[...]               return Promise.resolve()
[...]                   .then(function () { return _replaceResources(refactor_2); })
[167]                   .then(function () { return _removeModuleId(refactor_2); });
[...]           }
[169]       })
[...]  ...

Pertanyaan

Apakah ada yang mengalami masalah yang sama atau bisa mengetahui kenapa webpack(?) gagal - atau bisa menjelaskan kepada saya apa yang sedang dicoba oleh compiler dan mengapa itu gagal?

Sunting

angular-cli.json:

{
  "project": {
    "version": "1.0.0-beta.25.5",
    "name": "myproject"
  },
  "apps": [
    {
      "root": "src",
      "outDir": "dist",
      "assets": [
        "assets",
        "favicon.ico"
      ],
      "index": "index.html",
      "main": "main.ts",
      "test": "test.ts",
      "tsconfig": "tsconfig.json",
      "prefix": "app",
      "mobile": false,
      "styles": [
        "assets/css/main.css"
      ],
      "scripts": [
        "assets/lib/stomp.min.js"
      ],
      "environments": {
        "source": "environments/environment.ts",
        "dev":    "environments/environment.ts",
        "live": "environments/environment.live.ts"
      }
    }
  ],
  "addons": [],
  "packages": [],
  "e2e": {
    "protractor": {
      "config": "./protractor.conf.js"
    }
  },
  "test": {
    "karma": {
      "config": "./karma.conf.js"
    }
  },
  "defaults": {
    "styleExt": "css",
    "prefixInterfaces": false,
    "inline": {
      "style": false,
      "template": false
    },
    "spec": {
      "class": false,
      "component": true,
      "directive": true,
      "module": false,
      "pipe": true,
      "service": true
    }
  }
}

tsconfig.json:

{
  "compilerOptions": {
    "baseUrl": "",
    "declaration": false,
    "emitDecoratorMetadata": true,
    "experimentalDecorators": true,
    "lib": [
      "es6",
      "dom"
    ],
    "mapRoot": "./",
    "module": "es6",
    "moduleResolution": "node",
    "outDir": "../dist/out-tsc",
    "sourceMap": true,
    "target": "es5",
    "typeRoots": [
      "../node_modules/@types"
    ]
  },
  "files": [
    "typings/index.d.ts"
  ]
}

Jawaban #1

Perbarui :

Seperti yang dicatat @stewdebaker: angular-cli: 1.0.0-beta.26 sekarang telah dirilis dan tampaknya memperbaiki masalah ini.

Seperti yang disebutkan oleh @stewdebaker, ada pertanyaan serupa yaitu Build error di frontend angular2 menggunakan angular-cli - solusinya di sana adalah dengan hanya mengembalikan ke angular-cli: 1.0.0-beta.21.

Lihat juga https://github.com/angular/angular-cli/issues/4072 untuk informasi lebih lanjut tentang masalah di pelacak masalah angular-cli.

Saya tidak bisa memperbaiki proyek saya dan juga saya tidak bisa kembali ke versi angular-cli saya sebelumnya 1.0.0-beta.22-1 (dan saya tidak melihat pertanyaan lain yang diajukan di Stack Overflow, kalau tidak saya mungkin sudah mencoba kembali ke 1.0.0-beta.21).

Entah kenapa sebelum memperbarui ke 1.0.0-beta.25.5 perintah ng serve berjalan, tetapi setelah kembali ke 1.0.0-beta.22-1 tetap muncul kesalahan yang sama seperti setelah pembaruan.

Solusi yang Membutuhkan Waktu

Jadi saya memutuskan untuk membuat proyek Angular2 baru dengan angular-cli dan membangun kembali seluruh proyek dengan CLI sambil menyalin kode dari repositori lama dan memperbaiki bug.

Bug yang saya temui adalah masalah kecil (saya pikir ini akibat dari perubahan tslint.json karena angular-cli yang diperbarui) tetapi tidak ada perubahan besar pada proyek dan sekarang proyek ini berjalan.

File sumber yang disebutkan dalam pesan kesalahan:

  • app.module.ts
  • tsconfig.json
  • angular-cli.json

tidak berubah sama sekali tetapi angular-cli bisa digunakan lagi, ng serve sekarang berjalan tanpa mengalami kesalahan.

Saya tidak berpikir ini adalah solusi yang ideal (dan menurunkan versi ke 1.0.0-beta.21 juga bukan) - tapi itu satu-satunya hal yang bisa saya temukan.