lustre-labs / lustre

An Elm-inspired framework for building HTML templates, single page applications, and server-rendered components in Gleam!
https://hexdocs.pm/lustre
MIT License
738 stars 52 forks source link

`gleam run -m lustre build app` errors out on the second invocation #56

Closed greenfork closed 3 months ago

greenfork commented 3 months ago

The first time I run gleam run -m lustre build app, I get the expected output:

✅ Project compiled successfully
✅ Esbuild installed!
✅ Bundle produced at `./priv/static/taskmgr.mjs`

right after that the second time I run the same command, I get

✅ Project compiled successfully
❌ Checking if I can bundle your application

I couldn't find a public module called `taskmgr` in your project.
hayleigh-dot-dev commented 3 months ago

Hmm that's very odd 🧐 How much hassle would it be for you to pull main locally and use a path dep to see if you can reproduce this – multiple calls to lustre build app are working fine for me but I may have inadvertently fixed it at some point between the last RC and now.

greenfork commented 3 months ago

Sure, I will try. Previously gleam crashed trying to use the latest main, probably a similar problem to https://github.com/gleam-lang/gleam/issues/2673, I will try to reduce dependencies to figure out how not to crash gleam when adding lustre

greenfork commented 3 months ago

With the latest main esbuild crashes, similar to this one.

Steps to reproduce:

git clone 'https://git.sr.ht/~greenfork/taskmgr'
cd taskmgr
# edit gleam.toml for the correct path to lustre
gleam deps update
make

crashes with

rm -r build/prod
gleam run -m lustre build app
  Compiling argv
  Compiling gleam_stdlib
  Compiling ranger
  Compiling birl
  Compiling filepath
  Compiling gleam_community_colour
  Compiling gleam_community_ansi
  Compiling gleam_erlang
  Compiling thoas
===> Analyzing applications...
===> Compiling thoas
  Compiling gleam_json
  Compiling gleam_otp
  Compiling gleam_package_interface
  Compiling glearray
  Compiling gleeunit
  Compiling snag
  Compiling glint

warning: Deprecated value used
    ┌─ /home/grfork/playground/gleam/testing/taskmgr/build/packages/glint/src/glint.gleam:493:56
    │
493 │   run_and_handle(from: glint, for: args, with: function.constant(Nil))
    │                                                        ^^^^^^^^^ This value has been deprecated

It was deprecated with this message: Use a fn literal instead, it is easier
to understand
  Compiling justin
  Compiling simplifile
  Compiling repeatedly
  Compiling spinner
  Compiling tom
  Compiling lustre
  Compiling lustre_ui
  Compiling taskmgr

warning: Unused imported module
  ┌─ /home/grfork/playground/gleam/testing/taskmgr/src/taskmgr.gleam:3:1
  │
3 │ import gleam/dynamic
  │ ^^^^^^^^^^^^^^^^^^^^ This imported module is never used

Hint: You can safely remove it.
   Compiled in 10.52s
    Running lustre.main
⠋ Building your project
warning: Deprecated value used
    ┌─ /home/grfork/playground/gleam/testing/taskmgr/build/packages/glint/src/glint.gleam:493:56
    │
493 │   run_and_handle(from: glint, for: args, with: function.constant(Nil))
    │                                                        ^^^^^^^^^ This value has been deprecated

It was deprecated with this message: Use a fn literal instead, it is easier
to understand
⠙ Building your project
warning: Unused imported module
  ┌─ /home/grfork/playground/gleam/testing/taskmgr/src/taskmgr.gleam:3:1
  │
3 │ import gleam/dynamic
  │ ^^^^^^^^^^^^^^^^^^^^ This imported module is never used

Hint: You can safely remove it.
✅ Project compiled successfully
⠋ Checking if I can bundle your application
warning: Deprecated value used
    ┌─ /home/grfork/playground/gleam/testing/taskmgr/build/packages/glint/src/glint.gleam:493:56
    │
493 │   run_and_handle(from: glint, for: args, with: function.constant(Nil))
    │                                                        ^^^^^^^^^ This value has been deprecated

It was deprecated with this message: Use a fn literal instead, it is easier
to understand
⠙ Checking if I can bundle your application
warning: Unused imported module
  ┌─ /home/grfork/playground/gleam/testing/taskmgr/src/taskmgr.gleam:3:1
  │
3 │ import gleam/dynamic
  │ ^^^^^^^^^^^^^^^^^^^^ This imported module is never used

Hint: You can safely remove it.
✅ Esbuild installed!
▲ [WARNING] Import "create_from_string" will always be undefined because there is no matching export in "build/dev/javascript/gleam_erlang/gleam/erlang/atom.mjs" [import-is-undefined]

    build/dev/javascript/gleam_erlang/gleam/erlang/process.mjs:78:18:
      78 │   let tag = $atom.create_from_string("EXIT");
         ╵                   ~~~~~~~~~~~~~~~~~~

▲ [WARNING] Import "create_from_string" will always be undefined because there is no matching export in "build/dev/javascript/gleam_erlang/gleam/erlang/atom.mjs" [import-is-undefined]

    build/dev/javascript/gleam_otp/gleam/otp/actor.mjs:135:10:
      135 │     $atom.create_from_string("gleam@otp@actor"),
          ╵           ~~~~~~~~~~~~~~~~~~

▲ [WARNING] Import "from_string" will always be undefined because there is no matching export in "build/dev/javascript/gleam_erlang/gleam/erlang/charlist.mjs" [import-is-undefined]

    build/dev/javascript/gleam_otp/gleam/otp/actor.mjs:169:18:
      169 │         $charlist.from_string("Actor discarding unexpected message: ~s"),
          ╵                   ~~~~~~~~~~~

✘ [ERROR] No matching export in "build/dev/javascript/lustre/lustre/cli/utils.mjs" for import "exec"

    build/dev/javascript/lustre/lustre/cli/project.mjs:18:9:
      18 │ import { exec, map, try$ } from "../../lustre/cli/utils.mjs";
         ╵          ~~~~

✘ [ERROR] No matching export in "build/dev/javascript/lustre/lustre/cli/utils.mjs" for import "exec"

    build/dev/javascript/lustre/lustre/cli/esbuild.mjs:22:9:
      22 │ import { exec, keep, replace } from "../../lustre/cli/utils.mjs";
         ╵          ~~~~

▲ [WARNING] Import "new_subject" will always be undefined because there is no matching export in "build/dev/javascript/gleam_erlang/gleam/erlang/process.mjs" [import-is-undefined]

    build/dev/javascript/gleam_otp/gleam/otp/actor.mjs:197:25:
      197 │   let subject = $process.new_subject();
          ╵                          ~~~~~~~~~~~

4 of 19 warnings and all 2 errors shown (disable the message limit with --log-limit=0)
❌ Bundling with esbuild

I ran into an error while trying to create a bundle with esbuild:

cp priv/static/taskmgr.mjs public/
cp: cannot stat 'priv/static/taskmgr.mjs': No such file or directory
make: *** [Makefile:4: build] Error 1
greenfork commented 3 months ago

The log is similar to https://github.com/lustre-labs/lustre/issues/57

hayleigh-dot-dev commented 3 months ago

Thanks for the reproduction, this is super odd let me take a look.

greenfork commented 3 months ago

Let me know if I need to test something, I'm glad to help

hayleigh-dot-dev commented 3 months ago

OK this is tricky, i can't reproduce 😬

$ gleam run -m lustre build app
  Resolving versions
Downloading packages
 Downloaded 22 packages in 0.38s
  Compiling argv
  Compiling gleam_stdlib
  Compiling ranger
  Compiling birl
  Compiling filepath
  Compiling gleam_community_colour
  Compiling gleam_community_ansi
  Compiling gleam_erlang
  Compiling thoas
===> Analyzing applications...
===> Compiling thoas
  Compiling gleam_json
  Compiling gleam_otp
  Compiling gleam_package_interface
  Compiling glearray
  Compiling gleeunit
  Compiling snag
  Compiling glint

warning: Deprecated value used
    ┌─ /Users/hayleigh/work/lustre-labs/lustre/bugs/taskmgr/build/packages/glint/src/glint.gleam:493:56
    │
493 │   run_and_handle(from: glint, for: args, with: function.constant(Nil))
    │                                                        ^^^^^^^^^ This value has been deprecated

It was deprecated with this message: Use a fn literal instead, it is easier
to understand
  Compiling justin
  Compiling simplifile
  Compiling repeatedly
  Compiling spinner
  Compiling tom
  Compiling lustre
  Compiling lustre_ui
  Compiling taskmgr

warning: Unused imported module
  ┌─ /Users/hayleigh/work/lustre-labs/lustre/bugs/taskmgr/src/taskmgr.gleam:3:1
  │
3 │ import gleam/dynamic
  │ ^^^^^^^^^^^^^^^^^^^^ This imported module is never used

Hint: You can safely remove it.
   Compiled in 5.26s
    Running lustre.main

warning: Deprecated value used
    ┌─ /Users/hayleigh/work/lustre-labs/lustre/bugs/taskmgr/build/packages/glint/src/glint.gleam:493:56
    │
493 │   run_and_handle(from: glint, for: args, with: function.constant(Nil))
    │                                                        ^^^^^^^^^ This value has been deprecated

It was deprecated with this message: Use a fn literal instead, it is easier
to understand
⠋ Building your project
warning: Unused imported module
  ┌─ /Users/hayleigh/work/lustre-labs/lustre/bugs/taskmgr/src/taskmgr.gleam:3:1
  │
3 │ import gleam/dynamic
  │ ^^^^^^^^^^^^^^^^^^^^ This imported module is never used

Hint: You can safely remove it.
✅ Project compiled successfully
⠋ Checking if I can bundle your application
warning: Deprecated value used
    ┌─ /Users/hayleigh/work/lustre-labs/lustre/bugs/taskmgr/build/packages/glint/src/glint.gleam:493:56
    │
493 │   run_and_handle(from: glint, for: args, with: function.constant(Nil))
    │                                                        ^^^^^^^^^ This value has been deprecated

It was deprecated with this message: Use a fn literal instead, it is easier
to understand

warning: Unused imported module
  ┌─ /Users/hayleigh/work/lustre-labs/lustre/bugs/taskmgr/src/taskmgr.gleam:3:1
  │
3 │ import gleam/dynamic
  │ ^^^^^^^^^^^^^^^^^^^^ This imported module is never used

Hint: You can safely remove it.
✅ Esbuild installed!
⠙ Bundling with esbuild
  priv/static/taskmgr.mjs  65.8kb

⚡ Done in 21ms
✅ Bundle produced at `./priv/static/taskmgr.mjs`

What OS etc are you running on?

greenfork commented 3 months ago

I run on the latest Arch Linux x86_64

greenfork commented 3 months ago

esbuild problems maybe, or maybe I have some global JS libs somewhere. esbuild also doesn't seem to behave consistently. Sometimes it says that it found the one already on my system, other times it downloads. When I do this now, it downloads esbuild. I have another project I work on where I use esbuild, maybe it found it and tries to use it and crashes because of version incompatibility or something. I'm not sure how to test this hypothesis

greenfork commented 3 months ago

Also maybe gleam misbehaves, since I get a crash when combining several libraries with lustre. Not sure how to test this either

hayleigh-dot-dev commented 3 months ago

Lustre checks if there is a binary at build/.lustre/bin/esbuild. That build/ dir is managed by gleam mostly so if you do gleam clean it gets deleted and lustre will re-download the binary.

Other than that it should definitely not be using any global esbuild binary or similar.

Maybe as a quick test you can run, from the project root, ./build/.lustre/bin/esbuild --version and see what it says?

hayleigh-dot-dev commented 3 months ago

@giacomocavalieri is also investigating, super sorry you're running into these issues :c

greenfork commented 3 months ago

Esbuild outputs version 0.19.10.

Thanks for caring, I appreciate it. So far a hack to delete build/prod solves my initial problem in the very first post of this issue. I have a script in the make file that does the thing:

build:
    -rm -r build/prod
    gleam run -m lustre build app
    cp priv/static/taskmgr.mjs public/
hayleigh-dot-dev commented 3 months ago

Super weird because lustre doesn't even touch the files in build/prod only build/dev.

lpil commented 3 months ago

Looks like it's bundling Erlang only code as JavaScript, how strange

hayleigh-dot-dev commented 3 months ago

Mmhm, but I don't see why/how and it's very odd that I can't reproduce it running the build on my own machine. Super hard to tell where the problem lies here.

greenfork commented 3 months ago

A similar bug, maybe this is reproducible:

git clone 'https://git.sr.ht/~greenfork/taskmgr'
cd taskmgr
git checkout erlang-bug
gleam run -m lustre build app

fails for me with

/tmp/taskmgr/build/dev/erlang/taskmgr/_gleam_artefacts/taskmgr.erl:110:25: function row_show_hide_ani_effect/0 undefined
%  110|                         row_show_hide_ani_effect()};
%     |                         ^

error: Shell command failure
hayleigh-dot-dev commented 3 months ago

As with #57, this should be fixed in the new lustre_dev_tools package! Please give it a try and open an issue on the repo there if you run into anything.