Skip to content

Commit 6c17798

Browse files
authored
Adding option to debug the cli launcher (elastic#102464)
* Adding debug args to cli tools * Adding instructions
1 parent 66ee208 commit 6c17798

File tree

4 files changed

+58
-3
lines changed

4 files changed

+58
-3
lines changed

TESTING.asciidoc

+20-3
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,7 @@ run it using Gradle:
4545

4646
==== Launching and debugging from an IDE
4747

48-
If you want to run Elasticsearch from your IDE, the `./gradlew run` task
48+
If you want to run and debug Elasticsearch from your IDE, the `./gradlew run` task
4949
supports a remote debugging option. Run the following from your terminal:
5050

5151
---------------------------------------------------------------------------
@@ -55,7 +55,7 @@ supports a remote debugging option. Run the following from your terminal:
5555
Next start the "Debug Elasticsearch" run configuration in IntelliJ. This will enable the IDE to connect to the process and allow debug functionality.
5656

5757

58-
As such the IDE needs to be instructed to listen for connections on this port.
58+
As such the IDE needs to be instructed to listen for connections on the debug port.
5959
Since we might run multiple JVMs as part of configuring and starting the cluster it's
6060
recommended to configure the IDE to initiate multiple listening attempts. In case of IntelliJ, this option
6161
is called "Auto restart" and needs to be checked.
@@ -64,6 +64,22 @@ NOTE: If you have imported the project into IntelliJ according to the instructio
6464
link:/CONTRIBUTING.md#importing-the-project-into-intellij-idea[CONTRIBUTING.md] then a debug run configuration
6565
named "Debug Elasticsearch" will be created for you and configured appropriately.
6666

67+
===== Debugging the CLI launcher
68+
69+
The gradle task does not start the Elasticsearch server process directly; like in the Elasticsearch distribution,
70+
the job of starting the server process is delegated to a launcher CLI tool. If you need to debug the launcher itself,
71+
add the following option to the `run` task:
72+
---------------------------------------------------------------------------
73+
./gradlew run --debug-cli-jvm
74+
---------------------------------------------------------------------------
75+
This option can be specified in isolation or combined with `--debug-jvm`. Since the CLI launcher lifespan may overlap
76+
with the server process lifespan, the CLI launcher process will be started on a different port (5107 for the first node,
77+
5108 and following for additional cluster nodes).
78+
79+
As with the `--debug-jvm` command, the IDE needs to be instructed to listen for connections on the debug port.
80+
You need to configure and start an appropriate Remote JVM Debug configuration, e.g. by cloning and editing
81+
the "Debug Elasticsearch" run configuration to point to the correct debug port.
82+
6783
==== Disabling assertions
6884

6985
When running Elasticsearch with `./gradlew run`, assertions are enabled by
@@ -103,7 +119,8 @@ password: `elastic-password`.
103119
- In order to start a node with a different max heap space add: `-Dtests.heap.size=4G`
104120
- In order to use a custom data directory: `--data-dir=/tmp/foo`
105121
- In order to preserve data in between executions: `--preserve-data`
106-
- In order to remotely attach a debugger to the process: `--debug-jvm`
122+
- In order to remotely attach a debugger to the server process: `--debug-jvm`
123+
- In order to remotely attach a debugger to the CLI launcher process: `--debug-cli-jvm`
107124
- In order to set a different keystore password: `--keystore-password`
108125
- In order to set an Elasticsearch setting, provide a setting with the following prefix: `-Dtests.es.`
109126
- In order to pass a JVM setting, e.g. to disable assertions: `-Dtests.jvm.argline="-da"`

build-tools/src/main/java/org/elasticsearch/gradle/testclusters/ElasticsearchNode.java

+9
Original file line numberDiff line numberDiff line change
@@ -151,6 +151,7 @@ public class ElasticsearchNode implements TestClusterConfiguration {
151151
private final LazyPropertyMap<String, CharSequence> systemProperties = new LazyPropertyMap<>("System properties", this);
152152
private final LazyPropertyMap<String, CharSequence> environment = new LazyPropertyMap<>("Environment", this);
153153
private final LazyPropertyList<CharSequence> jvmArgs = new LazyPropertyList<>("JVM arguments", this);
154+
private final LazyPropertyList<CharSequence> cliJvmArgs = new LazyPropertyList<>("CLI JVM arguments", this);
154155
private final LazyPropertyMap<String, File> extraConfigFiles = new LazyPropertyMap<>("Extra config files", this, FileEntry::new);
155156
private final LazyPropertyList<FileCollection> extraJarConfigurations = new LazyPropertyList<>("Extra jar files", this);
156157
private final List<Map<String, String>> credentials = new ArrayList<>();
@@ -471,6 +472,10 @@ public void jvmArgs(String... values) {
471472
jvmArgs.addAll(Arrays.asList(values));
472473
}
473474

475+
public void cliJvmArgs(String... values) {
476+
cliJvmArgs.addAll(Arrays.asList(values));
477+
}
478+
474479
@Internal
475480
public Path getConfigDir() {
476481
return configFile.getParent();
@@ -932,6 +937,10 @@ private void startElasticsearchProcess() {
932937
// Don't inherit anything from the environment for as that would lack reproducibility
933938
environment.clear();
934939
environment.putAll(getESEnvironment());
940+
if (cliJvmArgs.isEmpty() == false) {
941+
String cliJvmArgsString = String.join(" ", cliJvmArgs);
942+
environment.put("CLI_JAVA_OPTS", cliJvmArgsString);
943+
}
935944

936945
// Direct the stderr to the ES log file. This should capture any jvm problems to start.
937946
// Stdout is discarded because ES duplicates the log file to stdout when run in the foreground.

build-tools/src/main/java/org/elasticsearch/gradle/testclusters/RunTask.java

+14
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@ public abstract class RunTask extends DefaultTestClustersTask {
4040
private static final String transportCertificate = "private-cert2.p12";
4141

4242
private Boolean debug = false;
43+
private Boolean cliDebug = false;
4344
private Boolean apmServerEnabled = false;
4445

4546
private Boolean preserveData = false;
@@ -62,11 +63,21 @@ public void setDebug(boolean enabled) {
6263
this.debug = enabled;
6364
}
6465

66+
@Option(option = "debug-cli-jvm", description = "Enable debugging configuration, to allow attaching a debugger to the cli launcher.")
67+
public void setCliDebug(boolean enabled) {
68+
this.cliDebug = enabled;
69+
}
70+
6571
@Input
6672
public Boolean getDebug() {
6773
return debug;
6874
}
6975

76+
@Input
77+
public Boolean getCliDebug() {
78+
return cliDebug;
79+
}
80+
7081
@Input
7182
public Boolean getApmServerEnabled() {
7283
return apmServerEnabled;
@@ -204,6 +215,9 @@ public void beforeStart() {
204215
if (debug) {
205216
enableDebug();
206217
}
218+
if (cliDebug) {
219+
enableCliDebug();
220+
}
207221
}
208222

209223
@TaskAction

build-tools/src/main/java/org/elasticsearch/gradle/testclusters/TestClustersAware.java

+15
Original file line numberDiff line numberDiff line change
@@ -54,4 +54,19 @@ default void enableDebug() {
5454
}
5555
}
5656
}
57+
58+
default void enableCliDebug() {
59+
int cliDebugPort = 5107;
60+
for (ElasticsearchCluster cluster : getClusters()) {
61+
for (ElasticsearchNode node : cluster.getNodes()) {
62+
getLogger().lifecycle(
63+
"Running cli launcher in debug mode, {} expecting running debug server on port {}",
64+
node,
65+
cliDebugPort
66+
);
67+
node.cliJvmArgs("-agentlib:jdwp=transport=dt_socket,server=n,suspend=y,address=" + cliDebugPort);
68+
cliDebugPort += 1;
69+
}
70+
}
71+
}
5772
}

0 commit comments

Comments
 (0)