构建 rxjs/Observable 时出错

Error constructing an rxjs/Observable

为什么下面的 TypeScript 代码可以编译,但是 systemjs 在运行时无法正确加载依赖项?

import { Observable } from 'rxjs';
let temp123 = new Observable<String>();

但是,这有效:

import { Observable } from 'rxjs/Observable';
let temp123 = new Observable<String>();

具体来说,第一个代码生成包含以下代码的 .js 文件:

var Observable_1 = require('rxjs');
var temp123 = new Observable_1.Observable();

但是第二个代码生成这个:

var Observable_1 = require('rxjs/Observable');
var temp123 = new Observable_1.Observable();

require('rxjs') 行因 404 错误而失败,因为那里没有文件。为什么typescript编译器可以解决这个问题,而systemjs在运行时加载不出来?

还值得注意:只有当我对 Observable 做某些事情时才会出现这个问题。例如,以下代码有效:

import { Observable } from 'rxjs';
let temp123: Observable<String> = null;
let xyz = temp123.first();

我可以使用 Observable,并在其上调用方法,无需 TypeScript 编译器生成 require('rxjs')。但是我不能构造一个,我也不能扩展它。

版本:TypeScript 2.0.3、Systemjs 0.19.27、rxjs 5.0.0-beta.12

Why is the typescript compiler able to resolve this, but systemjs cannot load it at runtime?

这就是它的工作方式:

当你写 import { Observable } from 'rxjs'; 时,打字稿会在 node_modules 中找到 rxjs 文件夹,里面有 package.json,其中有

 "typings": "Rx.d.ts"

这是 rxjs 的类型声明文件,该文件包含

  export { Observable } from './Observable';

这使得打字稿在同一文件夹中找到另一个类型声明文件,Observable.d.ts,它导出了 Observable class.

的声明

这足以让您的代码编译无误。

如果您的代码实际上没有尝试使用 Observable 作为值,它会起作用,因为 typescript 会 unused reference elision - 如果 Observable 仅用于类型检查,如在您的第二个示例中,生成的 javascrpt.

中不会有 require('rxjs') 调用

现在,SystemJS。

SystemJS 没有任何默认位置来查找模块 - 它甚至不识别 node_modules 关于 package.json 文件与 main 属性.[=48 的约定=]

因此,您示例中的 SystemJS 很可能是这样配置的:

    SystemJS.config({
        paths: {'npm:': 'node_modules/'},
        map: {'rxjs': 'npm:rxjs'},
        packages: {
            rxjs: {
            }
        }
    });

因此,此行导入的模块rxjs/Observable

import { Observable } from 'rxjs/Observable';

映射到

node_modules/rxjs/Observable.js

因为 rxjs 前缀匹配 map 条目,它与 paths 一起映射到 node_modules/rxjs

Observable 部分按原样通过

添加

.js 扩展名是因为 rxjs 与 systemjs 配置中的 rxjs 包匹配,对于属于包的任何模块,SystemJS 会自动添加 .js 扩展名除非 defaultExtension 在该包配置中设置为其他内容。

它有效,因为文件 node_modules/rxjs/Observable.js 存在。

并且该导入也适用于打字稿,因为 node_modules/rxjs/Observable.d.ts 也存在。

最后,这在运行时不起作用

import { Observable } from 'rxjs';

因为它映射到 node_modules/rxjs url,并且那里没有实际文件。

您可以通过在 SystemJS 包配置中使用 main 属性 来修复它:

        packages: {
            rxjs: {
                main: 'Rx.js'
            }
        }

现在它映射到 node_modules/rxjs/Rx.js,并且该文件实际存在并导出名为 Observable 的内容,因此它应该可以工作。

已使用 SystemJS 0.19.43、rxjs 5.0.3、typescript 2.1.5 进行检查。