gleam
gleam copied to clipboard
Bug: Record update + pipe == Erlang binding errors
This Gleam code
pub type Rad {
Rad(some: String)
}
fn update(rad: Rad, with str: String) -> Rad {
Rad(str)
}
pub fn main() {
let rad = Rad("a")
Rad(
..rad
|> update("b")
)
}
produces this invalid Erlang code
-module(main).
-compile(no_auto_import).
-export([main/0]).
-export_type([rad/0]).
-type rad() :: {rad, binary()}.
-spec update(rad(), binary()) -> rad().
update(Rad, Str) ->
{rad, Str}.
-spec main() -> rad().
main() ->
Rad = {rad, <<"a"/utf8>>},
_pipe = Rad, % error: variable _pipe is bound multiple times in this pattern.
update(_pipe, <<"b"/utf8>>). % error: variable _pipe is unbound
https://johndoneth.github.io/gleam-playground/?s=A4VwRgBALgnsCmEBKBDAJhA3gKAs9AFAM4D2AtvAFwQDKUATgJYB2A5gJTYC%2B22AZswghgaFFHgF66aqjQAaCAHdGUABYQiDanSZt2EALQA%2BfBhx5ZxBpx7ZQkARDIoWBfeYgAbeFAhSMALymBABEKCGcFoS4eBAAdHH%2BMXgAPibCouKhYBExNthAA%3D%3D
Sorry, I'm a bit confused. I can only see the point variable being bound once there. Is this the right code snippet?
Sorry, I didn't test this simplified snippet; looks like it's not quite enough.
The following Gleam compiles and runs fine for the JavaScript target.
fn iterable_builder() {
Task(
..[]
|> task.new(run: task.basic(["echo"]))
|> task.flags(add: iterable_flags()),
config: "gleam.toml"
|> toml.parse_file
|> result.lazy_unwrap(or: toml.new)
|> Parsed,
)
}
But produces this invalid Erlang.
-spec iterable_builder() -> rad@task:task({ok, binary()} | {error, snag:snag()}).
iterable_builder() ->
erlang:setelement(
9,
_pipe = [],
_pipe@1 = rad@task:new(_pipe, rad@task:basic([<<"echo"/utf8>>])),
rad@task:flags(_pipe@1, iterable_flags()),
begin
_pipe@2 = <<"gleam.toml"/utf8>>,
_pipe@3 = rad@toml:parse_file(_pipe@2),
_pipe@4 = gleam@result:lazy_unwrap(_pipe@3, fun rad@toml:new/0),
{parsed, _pipe@4}
end
).
It looks like the problem manifests because the first pipe inside of setelement
should be wrapped in a block.
There it is! Thank you very much