angularjs - 在導入 C3 和 D3 時的 Typescript 編譯錯誤
我正在一個 Ionic2/Angular2 TypeScript 專案中使用圖表庫 C3。我已經透過 npm 安裝了 C3,並透過 tsd 安裝了型別定義。
我已經將 when 匯入到我自己的 ts 文件中,方式如下..
import {Component} from '@angular/core';
import {NavController} from 'ionic-angular';
import * as C3 from 'c3';
import * as D3 from 'd3';
@Component({
templateUrl: 'build/pages/graphs-page/graphs-page.html'
....
})
一切看起來都很好。我可以看到 C3(以及依賴的 D3)的型別定義,而且當我運行時似乎一切都正常。
然而,當應用程式構建時(當我運行 ionic serve),我總是收到以下 TypeScript 編譯錯誤…
TypeScript error: D:/dev/ionic2/testcomonents/app/pages/graphs-page/graphs-page.ts(3,21): Error TS2307: Cannot find module 'c3'.
TypeScript error: D:/dev/ionic2/testcomonents/app/pages/graphs-page/graphs-page.ts(4,21): Error TS2307: Cannot find module 'd3'.
有人知道為什麼我在編譯時會出現這些錯誤,而在 IDE 中卻沒有錯誤(我使用的是 vscode),而且一切似乎都正常運作嗎?
[編輯]
我之後已經安裝了 typescipt 2 並使用 --traceResolution 標誌運行。我可以看到 tsc 似乎只會查看各層級的 node_modules,而從不查看 typings 資料夾,而 vscode 則是在那裡查找。
對我來說更令人困惑的是,c3.js 的源碼是如何被包含的,當它位於 node_modules/c3 資料夾下。我並沒有特別加入任何對 c3.js 的引用,但圖表仍然會顯示出來。
tsconfig.json 中的設定是
{
"compilerOptions": {
"target": "es5",
"module": "commonjs",
"emitDecoratorMetadata": true,
"experimentalDecorators": true
},
"filesGlob": [
"**/*.ts",
"!node_modules/**/*"
],
"exclude": [
"node_modules",
"typings/main",
"typings/main.d.ts"
],
"compileOnSave": false,
"atom": {
"rewriteTsconfig": false
}
}
我已經在上面的 tsconfig.json 嘗試了各種修改,但仍無法讓它在 typings 資料夾中尋找。
所以我現在的問題變成
- 如何讓 TypeScript 在 typings 資料夾中查找
- 實際位於 node_modules\c3\c3.js 的 c3.js 檔案是如何被包含在 Ionic 打包中的(因為我沒有在任何地方添加對它的引用)
答案#1
我想我現在知道這個問題的答案了,但如果我錯了,請指正我!
在 Ionic 檔案 D:\dev\ionic2\testcomponents\node_modules\ionic-gulp-browserify-typescript\index.js 中查看,有以下的 src 屬性
var defaultOptions = {
watch: false,
src: ['./app/app.ts', './typings/main.d.ts'],
所以如果我將以下內容加入到 main.d.ts
/// <reference path="globals/c3/index.d.ts" />
/// <reference path="globals/d3/index.d.ts" />
錯誤消失了。
如果我執行 tsc --traceResolution 我仍然看到錯誤,但我猜這裡的情況是,從命令列執行 tsc 並不會包含查看上述的 Ionic 腳本或 main.d.ts。
為了在使用 tsc --traceResolution 時消除錯誤,我嘗試將以下內容添加到檔案 D:\dev\ionic2\testcomponents\node_modules\c3\package.json
"typings": "../../typings/globals/c3/index.d.ts",
然後對 d3 做同樣的操作。但這在我執行 Ionic 建置時會導致以下錯誤
TypeScript error: d:/dev/ionic2/testcomponents/app/pages/graphs-page/graphs-page.ts(3,21): Error TS2656: Exported external package
typings file 'd:/dev/ionic2/testcomponents/typings/globals/c3/index.d.ts' is not a module. Please contact the package author to update the package definition.
所以,我認為在 Ionic 的情境下,正確的做法是將 /// 路徑加入 main.d.ts 檔案。
我有的另一個問題是,也就是說 c3.js 等文件是如何被包含的,這都是 Browserify/gulp 構建的一部分,它會檢查 nodes_modules 文件夾下的所有東西。它們都有 package.json 文件,而在 c3 的情況下,我們有這行 "main": "c3.js"。
