TL; DR:赶快来吧,不会在GSoC正式截止日期之前及时完成,我会继续努力。
对于今年的Google Summer of Code,我正在努力为Ceylon JavaScript后端添加TypeScript支持。 目标是要有一个工具,给定TypeScript模块(一个或多个文件),该工具可为JavaScript后端生成Ceylon模块。 该模块的JS代码只是TypeScript编译器的输出(可能还包含一些元模型的东西),但是该工具还将添加模型信息,使您可以像其他Ceylon模块一样使用Ceylon的TypeScript模块,而无需使用dynamic
块或必须声明自己的动态接口。
实际上,我在今年1月GSoC推出之前的几个月就开始使用此工具。 我用TypeScript编写了程序的第一次迭代,以便能够与TypeScript编译器(也用TypeScript编写)进行交互。 第一次迭代的目的只是为了能够加载TypeScript编译器本身,这样我就可以使用Ceylon的模块( tsc
)并在Ceylon中编写程序的第二次(可能是最终的)迭代。
在GSoC工作期正式开始后不久,该程序的第一次迭代已基本完成,至少足以使我能够开始编写第二次迭代。 我曾希望从GSoC的开始就开始第二次迭代,但是尽管我自己的简单测试模块取得了不错的进展,但tsc
了一些我没想到的令人讨厌的惊喜,而且我必须解决。 事实证明,我很早就做出了几个非常糟糕的决定:
-
我选择对解析的语法树进行操作,而不是对typechecker模型进行操作。 我不知道该如何工作,但我不知道,但是问题很快变得很明显:
- 当我看到类型引用(例如
Element
,我必须知道它是引用类型参数,来自同一模块的类型还是来自另一个模块的类型。
- 当我看到类型引用(例如
为了快速发布第一个版本,我直接写了
-model.js
文件。 该模型主要是JSON,因此这意味着要进行一些丑陋的手动逗号管理,结果是有些声明中我没有发出任何东西(例如索引签名)。
git日志中有一些可爱的提交消息,包括“完全hacky”,“现在应该足够”,“这一切都破灭了”,“添加虚假支持”,“可怕的hack”和“我怎么可能认为完全不基于AST的情况下就可以编写这种加载器而无需访问tsc的模型?” 我很高兴能在第二次迭代中从这些错误中学习:)
现在,编写第二个迭代也比我想象的要难。 我有(仍然有)TypeScript编译器的Ceylon版本的tsc
模块,但是在Ceylon上很难使用。 主要有两个问题使我沮丧:
- TypeScript支持可选成员:
{ name?: string }
是值的类型,该值可能具有成员name
(包含string
),但也可能没有这样的成员(undefined
)。 Ceylon运行时根本不喜欢这种方式,并以许多不同且难以调试的方式中断。 我发现的唯一解决方案是根本不发出此类成员。 要访问它们而不会出现“属性不存在”类型检查器错误,我在dynamic
块内使用了eval
,这导致我们遇到第二个问题。 - 每当将动态值(例如
eval
调用的返回值)分配给Ceylon类型时,运行时就会将该值“分配”给分配给它的类型(添加RTTI)。 如果这不是最精确的值类型(例如,您将值用Node
,后来又想将其用作VariableDeclaration
),则必须跳过一些箍以解决此问题–一个简单的assert (is VariableDeclaration node)
由于锡兰不喜欢缩小这些穿衣类型,因此将无法使用。
我现在有解决这两个问题的方法,但是找到它们花了一些时间,当然我一开始就不必解决这些问题,因此我必须教Ceylon JS后端“做正确的事”。最终。 (在许多其他情况下,我也必须这样做,因为Ceylon JS“ ABI”与普通JS显着不同– Ceylon类未使用new
实例化,顶级值编译为函数,数组不是数组,等等。 )
现在,第二个迭代支持:
- 顶级价值,
- 顶级函数(无参数),以及
-
string
类型。
而已。 但是 ,与第一次迭代不同,它无需添加任何JS代码即可支持此功能(我已经教过编译器以值而不是函数的形式访问顶级值)。 当前,添加了一些JS代码(元模型的东西),但是我不确定是否会真正保留它。 我们可以说,您疯了么,为什么TypeScript模块支持元模型?然后JS文件将只是未tsc
输出,而该工具只会添加-model.js
文件。 这可能会使声明文件的使用更加容易(JS不是由tsc
生成的,这是我什至尚未开始考虑的许多问题之一)。
我非常有信心,我将能够添加对大多数“基本”功能的支持-类型引用和其他原始类型,类型参数和参数,参数,类,接口,方法,属性-不会有太多麻烦。 在那之后,所有的赌注都关闭了。 TypeScript支持一些疯狂的功能,例如字符串类型( "foo" | "bar" | "baz"
是有效类型)和类型卫士( pet is Fish
是有效的返回类型,Ceylon的怪异反转is Fish pet
条件),我不知道我们能为他们提供多好的支持。 我还需要对JS后端和运行时进行更多更改,而且我不知道这些更改会有多困难。
在正式的GSoC截止日期之前,大约还有四个星期,我将在其中一个假期中休假。 我希望“基本”支持能够在此之前完成,但是该项目处于可交付状态的可能性为零。 我不是太担心的是-我对这个项目工作过编程之夏开始,我会继续编程之夏结束后在其上工作,就像我做ceylon.ast
两年前。 而且,就像两年前一样,我应该在GSoC结束后有更多的时间,因为GSoC实际上对我来说安排得很奇怪,我在那儿仍然有很多讲座,而且与学期几乎没有重叠。 我应该在8月,9月和10月上半月的大部分时间里都可以自由地从事这个项目,并希望在此期间结束之前达成一些可以实际发布的东西。
翻译自: https://www.javacodegeeks.com/2016/07/status-report-ceylon-typescript-loader-gsoc-project.html