无法导入自定义组件 - Angular2和TypeScript

时间:2016-01-19 14:03:23

标签: typescript angular systemjs

我尝试在app.ts中导入自定义组件,但收到错误" TS2307:找不到模块' MyComponent' &# 34;我已经看过了,找不到任何可以帮助我的东西。

有些人写道:使用" moduleResolution":" classic" ,但如果我这样做,那么我得到TS2307错误的其他一切(所有angular2 / ...)除了MyComponent。

其他人写了"运行tsc --declaration MyComponent.ts" - 它会生成一个MyComponent.d.ts文件(同时在控制台中抛出错误,例如"除非提供了--module标志,否则无法编译" - 在tsconfig中作为选项提供 - 或&# 34;找不到模块' angular2 / common'"对于我在MyComponent.ts中导入的任何内容 - 但它确实会生成.d.ts文件),但在尝试编译app.ts时仍然给出相同的TS2307错误。 Nohting我找到了工作。

这是我的项目结构:

| /app
|     /resources
|         /dev
|             /ts
|                 app.ts
|                 MyComponent.ts
|         /dist
|             /js
|                 app.js          // transcompiled app.ts
|                 MyComponent.js  // transcompiled MyComponent.ts
|             /modules            // files copied from the /node_modules/**/ folders (because node_modules is outside versioning and also outside public root (public root is the /app folder)
|                 es6-shim.js
|                 angular2-polyfills.js
|                 system.src.js
|                 Rx.js
|                 http.dev.js
|                 angular2.dev.js
|     index.html
|
| /node_modules
|     /angular2            // 2.0.0-beta.1
|     /es6-promise         // 3.0.2
|     /es6-shim            // 0.33.3
|     /rxjs                // 5.0.0-beta.0
|     /reflect-metadata    // 0.1.2
|     /systemjs            // 0.19.6
|     /zone.js             // 0.5.10
| 

这是我的 tsconfig.json

{
    "compilerOptions": {
        "target": "ES5",
        "module": "system",
        "moduleResolution": "node",
        "sourceMap": true,
        "emitDecoratorMetadata": true,
        "experimentalDecorators": true,
        "removeComments": true,
        "noImplicitAny": false,
        "outDir": "app/resources/dist/js"
    },
    "files": [
        "app/resources/dev/ts/app.ts"
    ]
}

我的 app.ts

import { bootstrap } from "angular2/platform/browser";
import { Component, View } from "angular2/core";
import { HTTP_PROVIDERS, Http, Response } from "angular2/http";

//My Custom Components:
import { MyComponent } from 'MyComponent';

/**
 * APP
 */
@Component({
    selector: 'my-app'
})
@View({
    directives: [MyComponent],
    template: `
        <my-component></my-component>
        plus other html
    `
})
class MyApp {
    public whatever;

    constructor(public http: Http) {
        // initialize this.whatever
    }

    makeRequest(): void {
        this.http.request('/_http/response.json')
            .subscribe((res:Response) => {
                this.whatever = res.json();
            });
    }
}

bootstrap(MyApp, [ HTTP_PROVIDERS ]);

这是 MyComponent.ts

import { Component } from 'angular2/core';
import { NgFor, NgIf } from 'angular2/common';

@Component({
    selector: 'my-component',
    template: `
        <div>MY IMPORTED COMPONENT</div>
    `
})
export class MyComponent {

    constructor() {}

    doSomething(): void {
        console.log('Doing something');
    }
}

我的 app.ts MyComponent.ts 都在同一个文件夹中。无论如何,我还试过这样的路径:从&#34; / app / resources / dev / ts / MyComponent&#34;导入{MyComponent}。 另外,我已经尝试将它添加到tsconfig中的文件数组中(有些人写道我应该这样做)......还是......没有用!我也检查了js输出,因为有些人写道,即使它抛出错误,它仍然可能被编译......没有运气!

====================

编辑:

好吧,正如inoabrian在第一条评论中所说的那样......我以为我尝试了所有的东西,但似乎我没有尝试过#34; ./ MyComponent&#34;对于进口部分。

import { MyComponent } from './MyComponent';

现在,转编译器完成了它的工作。谢谢inoabrian,但现在我有另一个问题。当我尝试在浏览器中运行时,我检查我的控制台,并且systemjs和angular2-pollyfills都尖叫:

http://my-app/resources/dist/js/MyComponent 404 (Not Found)

分别为:

XHR error (404 Not Found) loading  http://my-app/resources/dist/js/MyComponent(…)

不要被路径抛弃(与我的项目文件夹结构比较时),当我访问http://my-app时,我的本地服务器指向/ app

这是我的 index.html ,包含系统配置和所有包含的js文件:

<!DOCTYPE html>
<html lang="en">
<head>
    <!-- ... Meta tags & CSS assets -->

    <script src="resources/dist/modules/es6-shim.js"></script>
    <script src="resources/dist/modules/angular2-polyfills.js"></script>
    <script src="resources/dist/modules/system.src.js"></script>
    <script src="resources/dist/modules/Rx.js"></script>
    <script src="resources/dist/modules/http.dev.js"></script>
    <script src="resources/dist/modules/angular2.dev.js"></script>
</head>
<body>
<script>
    System.config({
        packages: {
            app: {
                format: 'register',
                defaultExtension: 'js'
            }
        }
    });
    System.import('resources/dist/js/app.js')
            .then(null, console.error.bind(console));
</script>

<my-app></my-app>

</body>
</html>

我觉得我应该对转换后的文件&#34; MyComponent.js&#34;再做一件事,但不知道是什么(我已经尝试将它添加到System。导入,希望它会接受一个数组...但似乎它没有。接下来我该怎么办?

PS 但令人失望的是,我希望将MyComponent导入app.ts就可以了,而且我会找到MyComponent类+来自MyComponent.ts +我的反编译app.ts文件的所有内容ALL IN ONE app.js文件,没有另外的js文件:(

3 个答案:

答案 0 :(得分:8)

我知道它已经姗姗来迟,但也许其他人可能会从答案中受益。 我确实意识到最后的问题是什么(除了我在原始问题中已经编辑过的内容)。这里是: 我确实提到我有一个自定义文件夹结构,并且不愿意改变它。如果我有,它只需按照角度2快速启动即可。但是在我的具体案例中我不会意识到这个问题,我也不会理解System.js的工作原理。

问题出在我的System.config()中 - 在packages部分。 这是糟糕的代码:

System.config({
    packages: {
        app: {
            format: 'register',
            defaultExtension: 'js'
        }
    }
});
System.import('my/path/to/app_main_file');

我的错误是认为关键&#34; app&#34;只是一个通用的密钥,来自单词&#34; application&#34;。事实证明,在packages对象中,每个键实际上代表一个路径(该包的位置 - 它的文件 - 驻留在您的应用程序中)。因此,假设我的转换文件所在的文件夹将是&#34; my / app / public&#34;和&#34; app_main_file&#34;是我的应用程序的主要js文件,那么我应该实际上有这样的东西:

System.config({
    packages: {
        'my/app/public': {
            format: 'register',
            defaultExtension: 'js'
        }
    }
});
System.import('my/app/public/app_main_file')
    .then(null, console.error.bind(console));

或者,您可以更好地编写配置部分,如下所示:

System.config({
    packages: {
        'my-app': {
            format: 'register',
            defaultExtension: 'js'
        }
    },
    map: {
        'my-app': 'my/app/public'
    }
});

我认为它很明显是什么&#34; map&#34;做和如何使用它。

P.S。我知道在我的回答中我并没有像原始问题那样遵循完全相同的文件夹结构,但我认为这样解释它更有意义。如果重要,只需替换&#34; my / app / public&#34;以上是我最初在问题中所拥有的:&#34; resources / dist / js /&#34;,它也是一样的。

答案 1 :(得分:1)

我相信你错过了系统配置中的正确参数。 像这样添加:

System.config({
   defaultJSExtensions: true
})

答案 2 :(得分:0)

有点奇怪的是,MyComponent.js与同一文件夹中没有app.jsoutDir。就我而言,当我在tsconfig.json文件中添加tsconfig.json时,我的所有TypeScript文件都会在此文件夹中编译为JavaScript。

以下是我在{ "compilerOptions": { "target": "ES5", "module": "system", "moduleResolution": "node", "sourceMap": true, "emitDecoratorMetadata": true, "experimentalDecorators": true, "removeComments": false, "noImplicitAny": false, "outDir": "app/resources/dist/js" }, "exclude": [ "node_modules" ] } 文件中的配置:

tsc -w

我使用以下命令运行编译阶段:function coversWeekend($start, $end) { $weekend = [0, 6]; // 0 for Sunday, 6 for Saturday. // Loop over the date period. while ($start < $end) { if (in_array($start->format('w'), $weekend)) { return true; } $start->modify('+1 day'); } return false; }

希望它可以帮到你, 亨利