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

mill-bsp: language features lacking/incorrect #2304

Closed
kubukoz opened this issue Feb 5, 2023 · 9 comments
Closed

mill-bsp: language features lacking/incorrect #2304

kubukoz opened this issue Feb 5, 2023 · 9 comments

Comments

@kubukoz
Copy link
Contributor

kubukoz commented Feb 5, 2023

Hi! I talked about these issues briefly with @lefou before, managed to minimize a reproduction of some of these.

Here's my build:

  1. project/model.sc:
object exports {
  type Thing = String

  def doThing(): Unit = ()
}
  1. build.sc:
import $file.project.model

import model.exports._

doThing()

@
object demo extends Module {

  def thing: T[Thing] = T {
    "aa": Thing
  }

}

What happens:

  • in the main build (demo module), I'm seeing no completions for Thing or doThing
  • when I try "go to definition" on one of them, it navigates to the closing brace of the file.

For the completions, LSP returns an empty list. For the definitions, this is what the server returns:

[Trace - 05:43:29 PM] Sending response 'textDocument/definition - (184)'. Processing request took 24ms
Result: [
  {
    "uri": "file:///Users/kubukoz/projects/demos/build.sc",
    "range": {
      "start": {
        "line": 13,
        "character": 1
      },
      "end": {
        "line": 13,
        "character": 1
      }
    }
  }
]

Additionally, if I add a reference to something that doesn't exist, that has the same behavior - completions not working and go-to-definition sends me to the end of the file. Example:

object demo extends Module {

  def thing: T[Thing] = T {
    "aa": Thing
  }

  foo

}

Mill version: 0.11.0-M3-22-ac0ea4 / 0.10.11, I'm using mill-bsp. Full repro here.

@lefou
Copy link
Member

lefou commented Feb 5, 2023

I think, you experience an issue with multi-stage scripts. I think they are not well supported by editors in general, and in Mill I remember that they were often the initial cause for trouble. You should try to avoid them, and in your particular example, you can completely remove the line with the @. For me, completion then works as expected.

@kubukoz
Copy link
Contributor Author

kubukoz commented Feb 5, 2023

yeah, this is a very simplified multi-stage script though - my real usecase requires us to set up an extra Resolver for dependencies used by the build, I'm not sure how we could get rid of that...

more context: we put our artifacts in AWS CodeArtifact. The build requires some private dependencies from there, and we configure the resolver by fetching a temporary token using AWS's SDK (also caching it in a file). I think we could remove this and have Coursier credentials for CodeArtifact set up in a global config file, but that'd require changing this file daily (the tokens are short-lived) + it'd be a change in the workflows of about a hundred people running scripts in that repository.

edit: I guess we could have a custom Mill launcher that would deal with the creds... perhaps it's worth exploring.

@lefou
Copy link
Member

lefou commented Feb 5, 2023

Maybe, you can move all the early initialization stuff into a separate file (e.g. project/init.sc). If necessary, make that script a multi-stage script, but hopefully this avoids your build.sc file to be a multi-stage script. You can also try to use import $exec (https://ammonite.io/#import$exec). Hopefully one of these ideas work around the bad editing experience. I haven't tried it myself, though.

@kubukoz
Copy link
Contributor Author

kubukoz commented Feb 5, 2023

That early init stuff would still have to be imported somehow in an earlier stage I think... my second stage has some import $ivy. that requires the resolver to be there. Either way, it seems like I need at least one line in my early stage:

import $exec.project.init
@

otherwise it's too late

@lefou
Copy link
Member

lefou commented Feb 5, 2023

I case you haven't tried it, I think you should. A line import $file.project.init in the beginning of your build.sc results in the file project/init.sc being evaluated before the rest of your build.sc.

Given the following file:

// project/init.sc
println("early stuff")

import coursierapi.{Credentials, MavenRepository}

@

interp.repositories() ++= Seq(
  MavenRepository
    .of("https://localhost:8080/content/repositories/releases")
    .withCredentials(Credentials.of("user", "pass"))
)

println(interp.repositories.live()().mkString(","))

and

// build.sc
import $file.project.init

println("define our project")

object demo extends Module {

  def thing: T[Thing] = T {
    "aa": Thing
  }
}

When we run:

$ mill resolve demo
Compiling /home/lefou/work/tmp/repro-mill-issue-2304/project/init.sc
early stuff
Compiling /home/lefou/work/tmp/repro-mill-issue-2304/project/init.sc #2
ApiRepo(IvyRepository(Pattern(List(Const(file:/home/lefou/.ivy2/local/), Var(organisation), Const(/), Var(module), Const(/), Opt(List(Const(scala_), Var(scalaVersion), Const(/))), Opt(List(Const(sbt_), Var(sbtVersion), Const(/))), Var(revision), Const(/), Var(type), Const(s/), Var(artifact), Opt(List(Const(-), Var(classifier))), Const(.), Var(ext))), None, None, true, true, true, true, None, true)),ApiRepo(MavenRepository(https://repo1.maven.org/maven2, None, None, true, true)),MavenRepository(https://localhost:8080/content/repositories/releases, Credentials(user, ****))
Compiling /home/lefou/work/tmp/repro-mill-issue-2304/project/model.sc
Compiling /home/lefou/work/tmp/repro-mill-issue-2304/build.sc
define our project
[1/1] resolve 
demo

@lefou
Copy link
Member

lefou commented Feb 5, 2023

I think you can even get rid of the multi-stage scripting by just splitting up into multiple files.

@kubukoz
Copy link
Contributor Author

kubukoz commented Feb 5, 2023

I did try before, but this definitely helped! I had to play around with my magic import order too, scalafmt was sorting them and that clearly can affect things.

I got rid of all my @s, but the IDE problems haven't stopped...

the only hint I see in the logs:

2023.02.06 00:23:39 ERROR /Users/kubukoz/Library/Caches/Coursier/v1/https/repo1.maven.org/maven2/com/lihaoyi/mill-moduledefs_2.13/0.10.9/mill-moduledefs_2.13-0.10.9.jarjava.nio.file.NoSuchFileException: /scalac-plugin.xml

I can only assume 0.10.9 is Metals's version of a Mill interface or something, as I tried 0.10.11 and the snapshot mentioned above.

However, Metals did work fine in the updated example thanks to your suggestions.

I'll get back to this in the workweek and try to minimize my project's problems with that new setup (without multi-module scripts).

@lefou
Copy link
Member

lefou commented Feb 6, 2023

@lefou
Copy link
Member

lefou commented Apr 27, 2023

Closing this, as it is releated to multi-stage script which we no longer support since Mill 0.11.0-M8. In fact, we no longer use Ammonite at all.

@lefou lefou closed this as completed Apr 27, 2023
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