Julia LSP in neovim 0.11

Hello everyone,

Neovim 0.11 seems to have introduced some changes in the way lsp is configured, and it seems the julials install from Mason does not work out of the box at the moment (lsp quits returning 1 instead of 0, error log looks like nonsense).

I am currently using the following config, combining the new lsp setting with the instructions from here :

vim.lsp.config['julials'] = {
    cmd = { '' },
    filetypes = { 'julia' },
    root_markers = { 'Project.toml', 'Manifest.toml' },

    settings = {
        require'lspconfig'.julials.setup{
            on_new_config = function(new_config, _)
                local julia = vim.fn.expand("~/.julia/environments/lsp/")
                if require'lspconfig'.util.path.is_file(julia) then
                    new_config.cmd[1] = julia
                end
            end
        }
    }
}

, which seems to work, even though I barely understand how.
The only problem so far with this setup, is that it does not seem to use the local Project.toml, and I don’t get suggestions for packages defined in there.
Would there be a straightforward way to improve it?

Any advice would be very welcome.

4 Likes

Update: The following does the job;

vim.lsp.config('julials', {
    cmd = {
        "julia",
        "--project=".."~/.julia/environments/lsp/",
        "--startup-file=no",
        "--history-file=no",
        "-e", [[
            using Pkg
            Pkg.instantiate()
            using LanguageServer
        depot_path = get(ENV, "JULIA_DEPOT_PATH", "")
        project_path = let
            dirname(something(
                ## 1. Finds an explicitly set project (JULIA_PROJECT)
                Base.load_path_expand((
                    p = get(ENV, "JULIA_PROJECT", nothing);
                        p === nothing ? nothing : isempty(p) ? nothing : p
                    )),
                        ## 2. Look for a Project.toml file in the current working directory,
                        ##    or parent directories, with $HOME as an upper boundary
                        Base.current_project(),
                        ## 3. First entry in the load path
                        get(Base.load_path(), 1, nothing),
                        ## 4. Fallback to default global environment,
                        ##    this is more or less unreachable
                    Base.load_path_expand("@v#.#"),
                ))
            end
                    @info "Running language server" VERSION pwd() project_path depot_path
                    server = LanguageServer.LanguageServerInstance(stdin, stdout, project_path, depot_path)
        server.runlinter = true
            run(server)
        ]]
    },
    filetypes = { 'julia' },
    root_markers = { "Project.toml", "JuliaProject.toml" },
    settings = {}
})

More info here.

3 Likes

should this be updated in Vim and Neovim · julia-vscode/LanguageServer.jl Wiki · GitHub ?

1 Like

Might be a good idea to add some of the links in my posts above about the breaking changes in the newest release. Shall I do a PR?

1 Like

Necroing because this thread comes up via Google.

I have updated the wiki with instructions for the new Neovim API: Vim and Neovim · julia-vscode/LanguageServer.jl Wiki · GitHub

You can definitely handroll your own config as shown above and power users will definitely want to do that, but I think for the average user the easiest way is to still rely on the default configs provided in GitHub - neovim/nvim-lspconfig: Quickstart configs for Nvim LSP, so the instructions I wrote are based on that.

TLDR if you don’t want to click on the link:

  1. Add the GitHub - neovim/nvim-lspconfig: Quickstart configs for Nvim LSP plugin.
  2. julia --project=~/.julia/environments/nvim-lspconfig -e 'using Pkg; Pkg.add("LanguageServer"); Pkg.add("SymbolServer"); Pkg.add("StaticLint")'
  3. add vim.lsp.enable('julials') to init.lua or similar
3 Likes

@penelopeysm, Thanks a lot for taking care of this!

1 Like

Does this approach support using a custom sysimage? Neovim Native LSP with julials using PackageCompiled LanguageServer

Otherwise, I’m afraid the Julia LSP is notorious for its slow startup times.

My final config after using PackageCompiler; create_sysimage([:LanguageServer,:SymbolServer, :StaticLint], sysimage_path="./julials.so", precompile_statements_file="./tracecompilelsp.jl")

-- ~/.config/nvim/after/lsp/julials.lua
local env_path = vim.fn.expand '~/.julia/environments/nvim-lspconfig/'
local sysimage_path = env_path .. 'julials.so'


return {
  cmd = {
    'julia',
    '--project=' .. env_path,
    '--startup-file=no',
    '--history-file=no',
    '--sysimage=' .. sysimage_path,
    '--sysimage-native-code=yes',
    '-e',
    [[
      using Pkg;
      Pkg.instantiate()
      using LanguageServer, SymbolServer, StaticLint
      depot_path = get(ENV, "JULIA_DEPOT_PATH", "")
      project_path = dirname(something(Base.current_project(pwd()), Base.load_path_expand(LOAD_PATH[2])))
      @info "Running mark language server" env=Base.load_path()[1] pwd() project_path depot_path
      server = LanguageServer.LanguageServerInstance(stdin, stdout, project_path, depot_path);
      server.runlinter = true;
      run(server);
    ]],
  },
}
1 Like