Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Mix.target() is :"" for ElixirLS #694

Closed
mnishiguchi opened this issue Jan 30, 2022 · 7 comments
Closed

Mix.target() is :"" for ElixirLS #694

mnishiguchi opened this issue Jan 30, 2022 · 7 comments

Comments

@mnishiguchi
Copy link
Member

mnishiguchi commented Jan 30, 2022

Maybe ElixirLS specific issue??? elixir-lsp/vscode-elixir-ls#132

  • ElixirLS crashes (?) and gives mix.exs full of red underlines with the error message:
** (File.Error) could not read file "/Users/mnishiguchi/src/nerves_livebook/config/.exs": no such file or directory
  • Presumably the error happens at the last line of config/target.exs (in my case).
  • Other than ElixirLS errors and red underlies in mix.exs, everything is working fine.

Screen Shot 2022-01-30 at 1 10 56 PM

Environment

  • Elixir version (elixir -v):
Erlang/OTP 24 [erts-12.2] [source] [64-bit] [smp:8:8] [ds:8:8:10] [async-threads:1] [jit]

Elixir 1.13.2 (compiled with Erlang/OTP 24)
  • Nerves environment: (mix nerves.env --info)
==> nerves
==> nerves_livebook
|nerves_bootstrap| Environment Package List

  Pkg:         nerves_toolchain_armv6_nerves_linux_gnueabihf
  Vsn:         1.5.0
  Type:        toolchain
  BuildRunner: {Nerves.Artifact.BuildRunners.Local, []}

  Pkg:         nerves_toolchain_ctng
  Vsn:         1.8.5
  Type:        toolchain_platform
  BuildRunner: {nil, []}

  Pkg:         nerves_system_br
  Vsn:         1.18.3
  Type:        system_platform
  BuildRunner: {nil, []}

  Pkg:         nerves_system_rpi0
  Vsn:         1.18.1
  Type:        system
  BuildRunner: {Nerves.Artifact.BuildRunners.Docker, [make_args: ["source", "all", "legal-info"]]}

|nerves_bootstrap| Loadpaths Start


Nerves environment
  MIX_TARGET:   rpi0
  MIX_ENV:      dev

|nerves_bootstrap| Environment Variable List
  target:     rpi0
  toolchain:  /Users/mnishiguchi/.nerves/artifacts/nerves_toolchain_armv6_nerves_linux_gnueabihf-darwin_x86_64-1.5.0
  system:     /Users/mnishiguchi/.nerves/artifacts/nerves_system_rpi0-portable-1.18.1
  app:        .

|nerves_bootstrap| Loadpaths End

  • Additional information about your host, target hardware or environment that
    may help

    • nerves_livebook 0.4.2
    • VS code 1.63.2
    • MacOS 11.6.2
    • ElixirLS v0.9.0

Current behavior

In mix.exs file, all lines are red-underlined, with the error message:

** (File.Error) could not read file "/Users/mnishiguchi/src/nerves_livebook/config/.exs": no such file or directory

Expected behavior

There should not be such an error...

Investigation

Looking at the output from ElixirLS, the error is caused by wrongly named configuration file: config/.exs!!!

MIX_ENV: test
MIX_TARGET:

14:43:29.317 [error] Process #PID<0.24004.0> raised an exception
** (File.Error) could not read file "/Users/mnishiguchi/src/nerves_livebook/config/.exs": no such file or directory
    (elixir 1.13.2) lib/file.ex:355: File.read!/1
    (elixir 1.13.2) lib/config.ex:245: Config.__import__!/1
    (stdlib 3.17) erl_eval.erl:685: :erl_eval.do_apply/6
    (stdlib 3.17) erl_eval.erl:123: :erl_eval.exprs/5
    (elixir 1.13.2) src/elixir.erl:289: :elixir.recur_eval/3
    (elixir 1.13.2) src/elixir.erl:274: :elixir.eval_forms/3
    (elixir 1.13.2) lib/code.ex:404: Code.validated_eval_string/3
    (stdlib 3.17) erl_eval.erl:685: :erl_eval.do_apply/6

In the nerves_livebook project, only location that generate a configuration file name is config/target.exs.

https://github.com/mnishiguchi/nerves_livebook/blob/a7b51e4d840a7304019a637746ba93476f2b7028/config/target.exs#L94

I inspected the outputs of both System.get_env("MIX_TARGET") and Mix.target() in config/target.exs.

IO.puts([
  "---\n",
  [~S[System.get_env("MIX_ENV")    => ], inspect(System.get_env("MIX_ENV")), "\n"],
  [~S[System.get_env("MIX_TARGET") => ], inspect(System.get_env("MIX_TARGET")), "\n"],
  [~S[Mix.env()                    => ], inspect(Mix.env()), "\n"],
  [~S[Mix.target()                 => ], inspect(Mix.target()), "\n"],
  "---\n"
])

Here are results when running mix deps.get. This looks GOOD.

mix deps.get
---
System.get_env("MIX_ENV"))    => nil
System.get_env("MIX_TARGET")) => "rpi0"
Mix.env()                     => :dev
Mix.target()                  => :rpi0
---

Here is the output from ElixirLS. This looks BAD.

  • why Mix.target() is :""???!!!
MIX_ENV: test
MIX_TARGET:
---
System.get_env("MIX_ENV"))    => nil
System.get_env("MIX_TARGET")) => "rpi0"
Mix.env()                     => :test
Mix.target()                  => :""
---


15:00:31.873 [error] Process #PID<0.24074.0> raised an exception
** (File.Error) could not read file "/Users/mnishiguchi/src/nerves_livebook/config/.exs": no such file or directory
    (elixir 1.13.2) lib/file.ex:355: File.read!/1
    (elixir 1.13.2) lib/config.ex:245: Config.__import__!/1
    (stdlib 3.17) erl_eval.erl:685: :erl_eval.do_apply/6
    (stdlib 3.17) erl_eval.erl:123: :erl_eval.exprs/5
    (elixir 1.13.2) src/elixir.erl:289: :elixir.recur_eval/3
    (elixir 1.13.2) src/elixir.erl:274: :elixir.eval_forms/3
    (elixir 1.13.2) lib/code.ex:404: Code.validated_eval_string/3
    (stdlib 3.17) erl_eval.erl:685: :erl_eval.do_apply/6

Potential causes

  • ElixirLS-specific issue?
  • Elixir Mix.target/0's bug?

At least, Mix.target/0 and related code looks GOOD to me.

I do not know what is capable of setting Mix target to :""...

Quick fix

At least, I confirmed the following hack can avoid that error, but this does not address the root cause.

- import_config "#{Mix.target()}.exs"
+ try do
+   import_config "#{Mix.target()}.exs"
+ rescue
+   e in File.Error -> e
+ end
@fhunleth
Copy link
Member

Ugh. I removed the workaround since I thought that the fix had been included for a sufficiently long time. I agree that the code looks good.

Could it be that there's white space in the MIX_TARGET environment variable?

@mnishiguchi
Copy link
Member Author

mnishiguchi commented Jan 31, 2022

Could it be that there's white space in the MIX_TARGET environment variable?

In case MIX_TARGET environment variable is white space for whatever reason, that value should looks the same after converted to Elixir atom. So we can say :"", atom was created from "" string somehow 🤯

iex> ["", " ", "\n", " \t\t "] |> Enum.map(&String.to_atom/1)
[:"", :" ", :"\n", :" \t\t "]

Looking at the elixir-lsp/elixir-ls codebase, Mix target shows in only a few locations.

Ah I think probably this is the root cause:

What can be done

  • In elixir-lsp/elixir-ls, handle blank MIX_TARGET environment variable properly
  • In Mix (Elixir), add def target(value) when is_binary(value) that handles string MIX_TARGET properly

I can make a PR for both.

@fhunleth
Copy link
Member

Yes, I agree that you found an issue (hopefully the issue). I also agree with your proposal. Thank you for figuring this out!

@mnishiguchi
Copy link
Member Author

OK, Elixir does not take responsibility of checking valid Mix target value. It is the user responsibility. That is fair.
Now only thing we can do is fix Elixir LS!

@fhunleth
Copy link
Member

I misunderstood your proposal. Sorry about that. I really thought that it was to only change Elixir LS. I see that I read to quickly now.

@mnishiguchi
Copy link
Member Author

NP! I was not sure what would be best. I am glad we are gradually getting there.

@mnishiguchi
Copy link
Member Author

Close because now we know it is not directly related to Nerves.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants