TypeScript中的条件编译

时间:2014-02-24 18:05:18

标签: typescript

有没有办法在TypeScript中使用#if,#endif指令进行条件编译?我希望我能够启用/禁用跟踪。

5 个答案:

答案 0 :(得分:4)

你不能做编译时指令。最好的选择是定义一个跟踪方法,包括对它的所有调用,并将其打开,将其定义为实数,并将其关闭,将该方法定义为空操作(function () {})。你仍然会在运行时调用方法调用的开销,但它调用一个空方法的方法 - 开销很小。

答案 1 :(得分:3)

TL; DR:否,使用MSBuild conditions作为手动解决方法

打字稿中没有条件,但是如果你像我一样,你可以使用一种丑陋(但稳定)的解决方法来实现编译时条件。

如果您正在开发visual studio之外的typescript,您可以在typescript编译器运行之前在构建步骤中使用类似C预处理器的东西。你可能知道这一点。

如果你在视觉工作室,它不是那么简单(可以做,但它很麻烦)。 相反,您可以在项目中使用MSBuild conditional constructs并使用一些javascript滥用来实现类似的效果。

以下代码段假设您具有DebugRelease配置以及Config.Release.tsConfig.Debug.ts两个文件。

  • 包含它,卸载您的项目(right click - > Unload project
  • 然后将其打开为xml(right click - > Edit foo.csproj)。
  • 从无条件项目组
  • 中删除条件项(Config.(Release|Debug).ts
  • 在无条件项目组
  • 下添加代码段
<Choose>
  <When Condition=" '$(Configuration)'=='Debug' ">
    <ItemGroup>
      <TypeScriptCompile Include="Config.Debug.ts" />
    </ItemGroup>
  </When>
  <Otherwise>
    <ItemGroup>
      <None Include="Config.Debug.ts" />
    </ItemGroup>
  </Otherwise>
</Choose>
<Choose>
  <When Condition=" '$(Configuration)'=='Release' ">
    <ItemGroup>
      <TypeScriptCompile Include="Config.Release.ts" />
    </ItemGroup>
  </When>
  <Otherwise>
    <ItemGroup>
      <None Include="Config.Release.ts" />
    </ItemGroup>
  </Otherwise>
</Choose>

这将根据您使用的配置编译一个文件或另一个文件,因此您可以有条件地修补&#39;跟踪行为(或禁用它)。

// Config.Release.ts
/// <reference "Trace.ts" />
module Config {
    import TraceService = Trace.TraceService;
    TraceService.trace = function(msg: string) {}
}

// Config.Debug.ts
/// <reference "Trace.ts" />
module Config {
    import TraceService = Trace.TraceService;
    TraceService.trace = function(msg: string) { console.log(msg); }
}

这种技术很麻烦,需要手动修补proj文件,但它很稳定,只有在TypeScript开发人员满足大众需求或者Visual Studio决定添加一个有效的预编译器之前它才能正常工作以及MSBuild。

更新

自从我创建这个hack以来已经过了一年多,但情况并没有改变。 TypeScript仍然不愿意引入条件编译,并且不太可能改变。 请注意,此解决方法不适用于tsconfig.json的项目。 如果项目的根目录中有tsconfig.json,则忽略所有<TypeScriptCompile/>指令,只有tsconfig.json定义编译的内容和不会编译的内容。 当然,该问题的解决方案是多个tsconfig.json文件和更多MSBuild voodoo

如果您需要并且无法自己弄清楚如何操作,请发表评论。

答案 2 :(得分:2)

没有。由于在编译期间保留了注释,因此您可以在构建过程中使用单独的工具来模拟它。

答案 3 :(得分:2)

目前没有,但投票给feature request,以便它在某一天出现!

答案 4 :(得分:2)

您可以使用UglifyJs的global_defenitions选项执行此操作。例如,如果您通过:

global_defs: {
    DEBUG: false
}

压缩器将假定这是一个常量定义,并将无法访问的此类代码丢弃:

if (DEBUG) {
   ...
}

文档: http://lisperator.net/uglifyjs/compress