rescript-compiler icon indicating copy to clipboard operation
rescript-compiler copied to clipboard

Rescript 11 Breaks type declarations

Open Lomand opened this issue 1 year ago • 4 comments

Hi.

I was trying to update the code of Tablecloth to Rescript 11 and faced quite a strange regression. Here is a simple repro:

Demo.res

type t<'a> = option<'a>

let map = (t, ~f) => Belt.Option.map(t, f)

Demo.resi

let map: (option<'a>, ~f: 'a => 'b) => option<'b>

res:build

rescript: [5/5] src/Demo.cmj
FAILED: src/Demo.cmj

  We've found a bug for you!
  /home/lomand/Dev/resi-impl-err/src/Demo.res:3:5-7

  1 │ type t<'a> = option<'a>
  2 │ 
  3 │ let map = (t, ~f) => Belt.Option.map(t, f)
  4 │ 

  The implementation /home/lomand/Dev/resi-impl-err/src/Demo.res
  does not match the interface src/Demo.cmi:
  Values do not match:
    let map: (option<'a>, ~f: 'a => 'b) => option<'b>
  is not included in
    let map: (option<'a>, ~f: 'a => 'b) => option<'b>
  /home/lomand/Dev/resi-impl-err/src/Demo.resi:1:1-49: Expected declaration
  /home/lomand/Dev/resi-impl-err/src/Demo.res:3:5-7: Actual declaration

FAILED: cannot make progress due to previous errors.
error Command failed with exit code 1.

The values are the same, as you can see. It worked in Rescript 10.

Similar problem here:

Demo.res

type t<'a> = option<'a>

let map = (t, ~f) => Belt.Option.map(t, f)



Demo.resi

type t<'a> = option<'a>

let map: (t<'a>, ~f: 'a => 'b) => t<'b>


build output:


  The implementation /home/lomand/Dev/resi-impl-err/src/Demo.res
  does not match the interface src/Demo.cmi:
  Values do not match:
    let map: (option<'a>, ~f: 'a => 'b) => option<'b>
  is not included in
    let map: (t<'a>, ~f: 'a => 'b) => t<'b>
  /home/lomand/Dev/resi-impl-err/src/Demo.resi:3:1-39: Expected declaration
  /home/lomand/Dev/resi-impl-err/src/Demo.res:3:5-7: Actual declaration

Rescript version 11.0.0-rc.4.

Lomand avatar Oct 28 '23 17:10 Lomand

That's because the function in belt is curried. This will go away when belt is moved out of the compiler (and compiled in uncurried mode). Workaround in the next comment

cristianoc avatar Oct 28 '23 17:10 cristianoc

The workaround is to use x => f(x) so an uncurried function is exported, and matches the .resi

cristianoc avatar Oct 28 '23 17:10 cristianoc

Or in this case more likely use mapU

cristianoc avatar Oct 28 '23 17:10 cristianoc

Ok, thanks a lot for the workaround and the quick response Cristiano! :pray:

Lomand avatar Oct 28 '23 19:10 Lomand