It looks fine. However, there is one issue with importing the module.
The example (example/App.res) is compiling to:
import * as UltimateExpress from "ultimate-express";
import UltimateExpress$1 from "ultimate-express";
var app = UltimateExpress$1();
var router = UltimateExpress.Router();
Importing with * does not work here, so I get an error message: UltimateExpress.Router is not a function.
It looks like ultimate-express uses a default export, rather than exporting everything by name. One way to fix the bindings would be to use @send decorators on the default value.
If you put something like this in UltimateExpress.res:
type ultimateExpressObject
@module("ultimate-express")
external ultimateExpressObject: ultimateExpressObject = "default"
...
module Router = {
type t
@send external rawMake: ultimateExpressObject => t = "Router"
let make = () => rawMake(ultimateExpressObject)
...
and then only export make in UltimateExpress.resi:
...
module Router = {
type t
let make: unit => t
...
you’ll get the same rescript semantics while fixing the js output. (After doing likewise for the other properties, of course)
It seems that it needs to be called as a method on the default return of UltimateExpress. By wrapping it, you don’t have to pass around that value, but you could omit it if you wanted to.