Hello, are you also considering Flow support or will this only support TypeScript?
I'm not currently considering Flow support. I've never used Flow myself and I had the (perhaps incorrect) impression that the web development community was gradually moving away from Flow to TypeScript. My goal for esbuild is to build a bundler that solves for a sweet spot of common use cases, not to build a bundler that works for any codebase.
That said, I could consider it. To get an idea of the scope of work that this would require (since I'm completely unfamiliar with Flow):
enum
and namespace
) that would need to be converted to JavaScript?As @rtsao says, Flow does not add any new language constructs. All Flow syntax can simply be stripped to get working JS code.
The Flow project contains multiple packages, one of which is the flow-remove-types
package with a test file featuring all the added syntax and multiple possible outputs which are valid JS.
Please look at this material to see if it can help. The package itself (published on NPM as flow-remove-types
) could be used directly. (It is not written in Go though.)
Thanks for the pointers! That's very helpful. I'm currently focused on building some other features first (code splitting and tree shaking) but I would like to do this at some point.
I'd like to see this as well. The flow syntax is extremely similar to TypeScript, really just a handful of differences. So hopefully this wouldn't be very hard to add.
I've scraped relevant test cases from from https://github.com/facebook/flow/tree/master/src/parser/test/flow/types and https://github.com/babel/babel/tree/main/packages/babel-parser/test/fixtures/flow and generated esbuild unit test cases.
In doing this, I learned that Flow actually supports enum syntax, which isn't really documented anywhere. Support for parsing Flow enums was also added to Babel, but interestingly it appears Babel does not transform them to anything when using @babel/plugin-strip-flow-types
. It's worth noting enums are gated behind configuration with both Flow and Babel. It might not be worth supporting in esbuild at all since it doesn't seem clear how they get converted to standard JS. Or I guess esbuild could just passthrough like Babel does.
Unfortunately, no special file extension is used for Flow syntax, so there's no way to know if a .js
file uses Flow syntax.
I can think of two ways of handling this:
options.TS.Parse = true
.// @flow
or /* @flow */
pragma.I think Flow pragma comments aren't strictly required, but I imagine the first option could introduce some overhead.
I need to clean up the test cases a bit more, but at some point I'd be interested in working on Flow support. My initial thought would be something like this:
parser_ts.go
into parser_flow.go
and make adjustments as needed. There'd be a lot of overlap, but I'm not sure it'd be worth trying to DRY things up (at least initially).Some quick thoughts:
If this is to be integrated into esbuild itself, it should be off by default and only enabled with --loader=flow
since Flow is not JavaScript.
It looks like Flow perhaps doesn't support enums? There's an open issue debating the addition of enums here and the AST generated on https://flow.org/try for enum foo {}
indicates that it's parsed as enum; foo; {}
and generates the parse error Unexpected token `{`, expected the end of an expression statement (`;`)
. It's a deliberate decision for esbuild to not support work-in-progress syntax proposals, so this probably shouldn't be included.
Heads up that I'm currently working on getting a CSS parser working and integrating it into esbuild. I'm about to refactor the JavaScript-related code as I'm adding support for a second fundamental data type, which could potentially introduce a lot of merge conflicts for code that touches JavaScript language support. So now isn't the best time to be adding Flow support.
Makes sense, thanks for the heads up. Right now, I'm mainly tinkering around to better understand the differences between TS and Flow syntax and see how difficult it would be to add Flow support.
At the very least, I'm merely hoping to produce a suite of test cases that will prove useful no matter what kind of refactoring happens.
Regarding enums, they have to be explicitly enabled by adding experimental.enums=true
to .flowconfig
. Agreed it probably doesn't make sense for esbuild to support them yet.
The refactoring I have in mind is mainly renaming files and packages, so it should be straightforward to carry any modifications to the JavaScript parser forward. It鈥檒l just potentially be a lot of conflicts.
Most helpful comment
I'm not currently considering Flow support. I've never used Flow myself and I had the (perhaps incorrect) impression that the web development community was gradually moving away from Flow to TypeScript. My goal for esbuild is to build a bundler that solves for a sweet spot of common use cases, not to build a bundler that works for any codebase.
That said, I could consider it. To get an idea of the scope of work that this would require (since I'm completely unfamiliar with Flow):
enum
andnamespace
) that would need to be converted to JavaScript?