给出以下TypeScript文件,
export = {};
tsc
("module": "amd"
)会发出:
define(["require", "exports"], function (require, exports) {
"use strict";
return {};
});
但是,我宁愿它发出
define([], function() {
"use strict";
return {};
});
...如果我明确导入它们,只包括require
或exports
,即
import relativeRequire = require("require");
有没有办法告诉TypeScript不要在发出的AMD模块中发出require
和exports
(即要求它不使用CommonJS simplified wrapping)?
注意:
2017年7月4日更新: 看起来这实际上是TypeScript GitHub仓库中的一个未解决的问题:https://github.com/Microsoft/TypeScript/issues/669
在实施之前,是否有任何实用的解决方法? (或者,实际上是否有某种方法可以使TypeScript执行此操作?)
答案 0 :(得分:3)
我认为你所做的事情没有实质性的优势。对于任何超过玩具应用程序的应用程序,通过删除未使用的依赖项而节省的执行时间将与应用程序其余部分的执行时间相比相形见绌。 require
和exports
都是虚拟模块,实例化成本非常低。 (“虚拟”是指它们完全是您使用的AMD加载程序的内部信息,不需要从网络或磁盘上的文件中获取任何内容。)我看到您提到的issue 669已于2014年9月开放并被视为自2015年4月以来“接受”。似乎没有人受到如此严重的伤害,以至于他们急于提出拉动请求。
我不知道TypeScript会以什么方式开箱即用。我最近研究过TypeScript如何发出define
调用,因为我需要将名为"module"
的虚拟模块添加到依赖项列表中。 (如果使用Angular,则希望使用module.id
将当前模块的id传递给Angular,以便它可以解析相对模板路径等问题。您可以使用module.id
而不会出现CommonJS问题默认情况下,依赖列表中不包括输出但是输出module
。)我在{{1}发射了它。它使用regexp修改依赖关系列表以添加tsc
,并修改回调以添加相应的参数。这对我有用,因为我正在添加。对于您要执行的操作,这不是一个很好的方法,因为您想要删除依赖项,但可能会出现删除它们会导致代码无效的情况。
对于解决方法,您可以使用Esprima检查tsc
生成的JavaScript以及模块"module"
和{{1}的值传递给tsc
的工厂函数中的代码不使用它,然后从依赖项列表中删除未使用的模块,并将参数列表中的相应参数传递给工厂函数。这将是最通用的解决方案。 (除此之外,它与使用AMD加载器在工厂函数中提供的异步"require"
调用(形式为"exports"
)兼容。)但编码此逻辑可能与它将产生一个拉请求,define
首先发出你想要的代码。
答案 1 :(得分:1)
你说:
..如果我明确导入它们,只包括require或exports,即
import relativeRequire = require("require");
除非已存在,否则您无法使用require
。它的好处就在那里。
exports
。如果您希望在export =
中进行根导出,则TypeScript会将其映射到return
。但是使用export const foo = 123
时,需要使用exports
。
在那里没有任何伤害,任何对性能的影响都是微乎其微的。