BuckleScript 8.1: new syntax option


I think FCM is still a thing in the new syntax, since there is a function in napkin called parseFirstClassModuleExpr: https://github.com/BuckleScript/bucklescript/blob/9551c6975809961a37a3341309790889b4e949c5/jscomp/napkin/napkin_core.ml#L1820

Edit: According to the comment in the code, it seems the syntax is like: module(module-expr) or module(module-expr : package-type)

Btw: This was the first time, I’ve been looking into this source and I found it right away. I think this is some evidence for the quality of the work which has been put into napkin.


That’s really cool. Love this change. It’s been discussed for Reason syntax too, I hope it gets in :crossed_fingers:


Haven’t looked at all the features, but wanted to say that you have no idea how thrilled I am to have expressions and Unicode in string interpolation. And without all the {j|..|j}. Thank you!


@woeps well this can just make me cry. Yes that’s a very important goal we’ve been aiming for.
And yeah the first class module syntax is that. I’ve forgotten to document it. It’s really amazing that you found out by reading the parser code.

@jdeisenberg thanks. It’s about to get better I think. We’ll finally bridge this gap.

Edit: first class module documented now.


Alright, this compiles, phew!

module type X = {let x: int}

let fn = (~x: module (X)) => {
  let module (X) = x


can you file an issue? I think the parens are still too many, ideally it should be

let fn = (~x : module X) => {
   let module X = x


You can also use the new unpack that replaces (val binding)

module type X = {let x: int}

let fn = (~x: module(X)) => {
  module X = unpack(x)


Sure! But in the light of the changes, I’m a bit confused in which repo it should go :sweat_smile: Guessing it belongs to BuckleScript now?



Already found, thanks!


Wow that is … way better than before


Well, Elm 0.19 completely disallows custom infix operators, and for the same reasons, I believe: turning a language into a DSL makes a codebase hard to understand.

But then again, maybe custom operators should be disallowed in packages but allowed in apps.


Well, I need to amend my earlier statement a bit. I took a look at the parser and it looks like it hard-codes the allowed infix ops as variant constructors. I get why they did it, I imagine implementing general-purpose infix ops properly can be difficult especially with precedence and associativity concerns.

I hope this will be reconsidered though. It’s paying a high price in expressiveness.


This says that .ml/.mli syntax is still supported for now in BuckleScript 8.x. Is it fair to assume that there’s a significant risk of BuckleScript dropping plain OCaml support in the next decade?

Also just curious, why was this announced on the ReasonML blog instead of https://bucklescript.github.io/blog/ ? I had dismissed it as a ReasonML update when it was first announced because of that. :wink:


I was going to save this for when there is more clarity over infix / letop moving forward, but I might as well just get it out there.

If reason (and bucklescript syntax) is heading the way of Elm then I’m sorry but I’m out. I’ll escape-hatch to OCaml. Some parts of my team will be less happy in OCaml but I’ll wear that education cost. If OCaml support in BuckleScript gets bad enough (i.e. we stop upgrading OCaml versions), I’d even invest the effort to convert to JSOO. My projects will be worse off but I feel that strongly about this. FP-minded people are leaving Elm for a reason and I will lose all desire to participate if this community is going the same way.

I don’t expect it’ll happen immediately, unless Reason 4 drops infix as well, but that’s where my head is at.


@spyder btw we’ve released a new post regarding such concerns: [BuckleScript 8.1 New Syntax]: New Blog Post about BuckleScript’s New Syntax and Its Future Support Commitments


I’m catching up with this long thread, I’d like to put in my 2 cents.

The Reason language is good if it’s practical/useful for building real-world apps. Reason obviously wasn’t very useful before as shown by its 0.01% (making this number up) usage share compared the TS and JS.

I understand that everyone wants to chime in with their opinion regarding, for example, list vs array. But if that’s the way the JS ecosystem works, what can you do about it? I think it’s difficult to force people to use a feature that is “better” or “more correct” if it’s going to make their life more complicated or difficult ultimately. (If every time you write the smallest program you have to think about the different semantics and how you’re going to export/import data structures from JS-land)

So personally, I care most about the best possible integration with JS, and practical uses. First, because I want to use Reason to create useful stuff, and second because that’s the way Reason is going to get traction in the real world.


I couldn’t agree more with @vonwao. I want Reason to be in the best position possible to compete with TypeScript and to pull from that community. To do that we need less friction and up-to-par tooling to make that happen (thinking reason-language-server is the next big item here). This approach is a giant step in that direction. I’m excited to be apart of this community and to see what’s next. Thanks, Maxim!


Yes, thank you for posting that, but I did read it before my post. While it certainly helps with my concerns it still leaves the door open to remove OCaml and Reason in the future. If BuckleScript syntax turns out to be not what my team wants to use, why would we invest in BuckleScript OCaml when that might be pulled out from under us in 5 years? I work on projects that have very long maintenance cycles. My team doesn’t mind syntax tweaks, but the prospect of our chosen language being dropped completely is concerning.

I actually like a lot of things about BuckleScript syntax, removing some of the brackets pulls us back towards v2 reason which I always preferred over v3, but our codebase has 5-10 custom infix operators (and not weird ones, they’re copied from or inspired by other languages). A quick search reveals these operators are collectively used over 600 times in a codebase of 325 modules. We avoid them when performance matters but in all other cases (mostly in ways letop would help) they make our development easier. Any syntax without custom infix (or perhaps letop) simply isn’t viable for us.


Btw, for these issues, let’s post in the new thread.

If BuckleScript syntax turns out to be not what my team wants to use, why would we invest in BuckleScript OCaml when […]

The extra wiggle room we’ve gotten from being able to be a bit more opinionated on the new syntax has only been made possible thanks to the reassurance that the the OCaml and Reason option still exist in BS; because otherwise we’d have truly wrecked userland codebases now.

why would we invest in BuckleScript OCaml when that might be pulled out from under us in 5 years?

Consider that BuckleScript has been here for the past five years. This is what we can say, beyond what we already outlined in the post.

Regarding infix: there are many ways of ensuring we have proper solutions to most of the use-cases. For example, the set of first-class infixes very likely solves your situation (and I know there are debates around this approach; this is just an example!).