TypeScript中的module.exports

107

有人知道如何使用module.exports吗?

我尝试了一些不同的方法,最终得到了:

export class Greeter {}

将编译为

exports.Greeter = Greeter;

但是我真正想要的是这个:

exports = Greeter;

这样我就可以像这样使用它:

import { Greeter } from "greeter";

const greeter = new Greeter();

不是

import { Greeter } from "greeter";

const greeter = new Greeter.Greeter();

使用Typescript是否可能实现这个功能?

4个回答

102

在TypeScript中,您可以通过以下方式导出单个类:

class Person {

  private firstName: string;
  private lastName: string;

  constructor(firstName: string, lastName: string) {
    this.firstName = firstName;
    this.lastName = lastName;
  }

  public getFullName() {
    return `${this.firstName} ${this.lastName}`;
  }
}

export = Person;

现在来介绍如何使用它:

var Person = require('./dist/commonjs/Person.js');

var homer = new Person('Homer', 'Simpson');
var name = homer.getFullName();

console.log(name); // Homer Simpson

为了完整起见,这是我的 tsconfig.json 文件(我正在使用 TypeScript v2.0.3):

{
  "compilerOptions": {
    "module": "commonjs",
    "moduleResolution": "node",
    "outDir": "dist/commonjs",
    "rootDir": "src/ts",
    "target": "es5"
  },
  "exclude": [
    "dist",
    "node_modules"
  ]
}

1
非常感谢!我想知道为什么TypeScript没有实现导出Person ... 哔哩哔哩?我认为这是很合理的,不是吗?还是我漏掉了什么? - Arsen Mkrtchyan
1
是否仍然可以从文件中导出一些类型呢?您可能希望从文件中获取类型以编写测试,但最终仍希望有一个 module.exports - Eric Burel
确实有些令人困惑,因此我创建了一个视频来解释导出的差异:https://www.youtube.com/watch?v=XoOgNRQEYws - Benny Code

23

这个功能现在已经实现了,并且在TypeScript 0.9中已经准备就绪 :)


10
为了澄清(因为我不得不去查找这个),0.9版本中的语法在此处可用:http://blogs.msdn.com/b/typescript/archive/2013/06/18/announcing-typescript-0-9.aspx(在“Export =”下)。 - Dan
4
为了进一步说明,对于未来读者,它已经被实现得几乎与提问者所期望的完全相同...... 但是我真正想要的是 export = Greeter;,这正是你所做的 :) - Binary Worrier
1
我想从config/db.ts中仅公开一个配置对象,并在应用程序中使用该配置。这是我在TypeScript 1.4中成功实现的方法:在config/db.ts中编写var config = {connStr:'postgres://user:pass@host/dbname'}; export = config;,并在app.ts中引用它,如import dbConfig = require('./config/db'); dbConnect(dbConfig.connStr); - Gurjeet Singh

10

所以我想我已经找到了一个变通方法。只需要在你的 .ts 文件中,用括号将关键字 'module' 包起来:

所以我认为我已经找到了一种解决方法。只需在您的 .ts 文件中,使用括号将关键字 'module' 包含起来:

declare var module: any;
(module).exports = MyClass;
生成的 JavaScript 文件将完全相同:
(module).exports = MyClass;

注意,比起自己声明变量,更好的方法是下载node.d.ts定义文件,并将其放在与你的typescript文件相同的目录中。这里是一个完整的express node.js路由文件示例,假设node.d.ts文件在同一目录中:

/// <reference path="node.d.ts" />
var SheetController = function () {
    this.view = function (req, res) {
        res.render('view-sheet');
    };
};
(module).exports = SheetController;
我可以新建一个SheetController,然后(使用express)分配视图方法:
var sheetController = new SheetController();
app.get('/sheet/view', sheetController.view);

我想任何关键字都可以使用这种模式进行转义:

declare var reservedkeyword: any;
(reservedkeyword).anything = something;

2

这不太美观,也有点繁琐,但你仍然可以:

class Greeter {}
declare var exports:any;
exports = Greeter;

编译后的结果为:

var Greeter = (function () {
    function Greeter() { }
    return Greeter;
})();
exports = Greeter;

1
不幸的是,TypeScript编译器似乎处理这个问题不太好。例如,当您这样做时,无法从该类派生。 - dcstraw
这个怎么运作?这不是 CommonJs vs. AMD 的整个争论吗?因为 Common 不支持直接将内容返回到 exports 变量中? - George Mauer

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接