dansomething / coc-java-debug

An extension for coc.nvim to enable Java debugging via jdt.ls
https://www.npmjs.com/package/coc-java-debug
Eclipse Public License 2.0
100 stars 8 forks source link
coc-java debugging java jdt lsp nvim vim vimspector

coc-java-debug

An extension for coc.nvim to enable the Java Debug Server for the Java language server (jdt.ls) in Vim/Neovim.

It also provides an easy way to launch Vimspector and connect it to the Java debug server.

Features

Requirements

Quick Start

Install the coc-java-debug extension.

:CocInstall coc-java-debug

Open a Java file with a main method in Vim.

Set a breakpoint in your main method.

Execute this Vim command.

:CocCommand java.debug.vimspector.start

Goals

Non-Goals

Available commands

The following :CocCommand options are provided:

Command Arguments

java.debug.vimspector.start

:CocCommand java.debug.vimspector.start {"configuration":"Run Test","Test":"Name of the test"}

Supported settings

The following settings are supported in CocConfig:

java.debug.vimspector

java.debug.settings

Usage and Setup

Debug a Main Method

This example will demonstrate how to load a Java program with a main method and debug it using Vimspector.

If you don't have a .vimspector.json file in the root directory of your Java project then coc-java-debug will create one for you unless java.debug.vimspector.config.createIfNotExists is disabled.

If you already have a .vimspector.json file then add the config below.

{
  "adapters": {
    "coc-java-debug": {
      "port": "${AdapterPort}"
    }
  },
  "configurations": {
    "javaLaunch": {
      "default": true,
      "adapter": "coc-java-debug",
      "configuration": {
        "args": "${args}",
        "request": "launch",
        "projectName": "${ProjectName}",
        "mainClass": "${MainClass}",
        "classPaths": ["*${ClassPaths}"]
      },
      "breakpoints": {
        "exception": {
          "caught": "N",
          "uncaught": "N"
        }
      }
    }
  }
}

Next, open a Java file with a main method in Vim and set a breakpoint in your main method.

Execute the command to start debugging.

:CocCommand java.debug.vimspector.start

You will be prompted with

Enter value for args:

If you don't have any program arguments just press your enter key. Otherwise, type in your args just as you would from a terminal and then press your enter key.

At this point Vimspector should open and pause your Java program on the breakpoint you set.

That's it! You may now step debug your way through your Java program from within Vim.

Remote Debugging

This example will demonstrate attaching to a Java program that is running with remote debugging enabled. This is useful for debugging tests or running services.

Vimspector Attach Config

Add the following contents to the .vimspector.json file in the root directory of your Java project. Note, don't change "${AdapterPort}". See issue #3 for an explanation of how this port value works.

{
  "adapters": {
    "coc-java-debug": {
      "port": "${AdapterPort}"
    }
  },
  "configurations": {
    "javaAttach": {
      "default": true,
      "adapter": "coc-java-debug",
      "configuration": {
        "request": "attach",
        "host": "127.0.0.1",
        "port": "5005"
      },
      "breakpoints": {
        "exception": {
          "caught": "N",
          "uncaught": "N"
        }
      }
    }
  }
}

Review the Vimspector config docs for what's possible within this file.

Configure Vim

This extension provides :CocCommand java.debug.vimspector.start to simplify launching Vimspector.

Note, it does not start your Java process in remote debug mode. An example of how to do that is covered below.

To further simplify, launching Vimspector, add the following config to your ~/.vimrc file or wherever appropriate for your Vim setup.

" Press F1 key to launch Vimspector
nmap <F1> :CocCommand java.debug.vimspector.start<CR>
Start the Remote Debug Session

First, run a Java program with remote debugging enabled. Be sure it is configured to pause and wait for a remote connection on port 5005 for this example work.

For a simple Java program. Create a Hello.java file with these contents.

public class Hello {
  public static void main(String[] args) {
    System.out.println("Hello World!");
  }
}

Next, run these commands from a shell to compile the program and then start it with remote debugging enabled.

javac -g Hello.java
java -Xdebug -Xrunjdwp:server=y,transport=dt_socket,address=5005,suspend=y Hello

If everything works correctly you will see this message.

Listening for transport dt_socket at address: 5005

Now, open the file you want to debug in Vim and set a breakpoint with Vimspector.

Finally, start the debug session in Vim by pressing your F1 key or use your custom key mapping if you have altered the config from this example. This should result in Vimspector opening in a new tab in Vim with your Java program paused at the breakpoint you set.

That's it! You may now step debug your way through a Java program from within Vim.

Note, if you use a Java debug port different than 5005 you will need to change that value in your .vimspector.json file. It is also possible to configure this port dynamically in Vimspector in the same manner as the debug adapter port.

Also note, if you use Maven for builds you may start remote debugging for tests and then run Vimspector.

mvn test -Dmaven.surefire.debug
Alternative Configuration (Optional)

If you'd prefer to launch the Vimspector plugin directly with your own configuration then add something similar the following config to your ~/.vimrc file or wherever appropriate for your Vim setup.

Note, this will bypass using the :CocCommand documented above to start the debug session.

function! JavaStartDebugCallback(err, port)
  execute "cexpr! 'Java debug started on port: " . a:port . "'"
  call vimspector#LaunchWithSettings({ "configuration": "Java Attach", "AdapterPort": a:port })
endfunction

function JavaStartDebug()
  call CocActionAsync('runCommand', 'vscode.java.startDebugSession', function('JavaStartDebugCallback'))
endfunction

nmap <F1> :call JavaStartDebug()<CR>

This example provides a way to start the Java debug server through coc.vim and then tell Vimspector which port to use to connect to the debug server. It maps the F1 key to kick things off, but you can change this key mapping to whatever you want.

License

EPL 2.0, See LICENSE for more information.