Skip to content

Commit c587740

Browse files
committed
Eclipse LS logging OFF, CONSOLE, ERROR LOG
1 parent 530d967 commit c587740

File tree

6 files changed

+98
-92
lines changed

6 files changed

+98
-92
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
/*******************************************************************************
2+
* Copyright (c) 2026 Broadcom, Inc.
3+
* All rights reserved. This program and the accompanying materials
4+
* are made available under the terms of the Eclipse Public License v1.0
5+
* which accompanies this distribution, and is available at
6+
* https://www.eclipse.org/legal/epl-v10.html
7+
*
8+
* Contributors:
9+
* Broadcom, Inc. - initial API and implementation
10+
*******************************************************************************/
11+
package org.springframework.tooling.ls.eclipse.commons;
12+
13+
public enum LoggingTarget {
14+
15+
OFF,
16+
ERROR_LOG,
17+
CONSOLE
18+
19+
}

eclipse-language-servers/org.springframework.tooling.ls.eclipse.commons/src/org/springframework/tooling/ls/eclipse/commons/STS4LanguageServerProcessStreamConnector.java

Lines changed: 42 additions & 44 deletions
Original file line numberDiff line numberDiff line change
@@ -37,45 +37,52 @@
3737
import org.springframework.tooling.ls.eclipse.commons.preferences.LsPreferencesUtil;
3838
import org.springsource.ide.eclipse.commons.core.util.IOUtil;
3939

40-
import com.google.common.base.Supplier;
41-
4240
public abstract class STS4LanguageServerProcessStreamConnector extends ProcessStreamConnectionProvider {
4341

4442
private static LanguageServerProcessReaper processReaper = new LanguageServerProcessReaper();
4543

4644
private static final String LOG_RESOLVE_VM_ARG_PREFIX = "-Xlog:jni+resolve=";
4745

48-
private Supplier<Console> consoles = null;
49-
private String connectorId;
46+
private final ServerInfo serverInfo;
5047

51-
public STS4LanguageServerProcessStreamConnector(ServerInfo server) {
52-
this.connectorId = server.bundleId();
53-
this.consoles = LanguageServerConsoles.getConsoleFactory(server);
48+
public STS4LanguageServerProcessStreamConnector(ServerInfo serverInfo) {
49+
this.serverInfo = serverInfo;
5450
}
5551

5652
@Override
5753
public void start() throws IOException {
5854
super.start();
5955

6056
Process process = LanguageServerProcessReaper.getProcess(this);
61-
processReaper.addProcess(connectorId, process);
57+
processReaper.addProcess(serverInfo.bundleId(), process);
58+
59+
streamLogging();
60+
}
6261

63-
if (consoles!=null) {
64-
Console console = consoles.get();
65-
if (console!=null) {
62+
private void streamLogging() {
63+
switch (getLoggingTarget()) {
64+
case CONSOLE:
65+
Console console = LanguageServerConsoles.getConsoleFactory(serverInfo.label()).get();
66+
if (console != null) {
6667
forwardTo(getLanguageServerLog(), console.out);
67-
} else {
68-
new Thread("Consume LS error stream") {
69-
@Override
70-
public void run() {
71-
try {
72-
IOUtil.consume(getLanguageServerLog());
73-
} catch (IOException e) {
74-
// ignore
75-
}
76-
}
77-
}.start();
68+
return;
7869
}
70+
// fall through to NONE case if there is no console created to simply consume the error log.
71+
case OFF:
72+
new Thread("Consume LS error stream") {
73+
@Override
74+
public void run() {
75+
try {
76+
IOUtil.consume(getLanguageServerLog());
77+
} catch (IOException e) {
78+
// ignore
79+
}
80+
}
81+
}.start();
82+
break;
83+
case ERROR_LOG:
84+
// Otherwise logging to ERROR LOG nothing to do see `getErrorStream()`
85+
break;
7986
}
8087
}
8188

@@ -135,10 +142,8 @@ private void fillCommand(List<String> command, List<String> extraVmArgs) {
135142

136143
LsPreferencesUtil.getServerInfo(getPluginId()).ifPresent(info -> {
137144
IPreferenceStore preferenceStore = LanguageServerCommonsActivator.getInstance().getPreferenceStore();
138-
if (!preferenceStore.getBoolean(info.preferenceKeyConsoleLog())) {
139-
}
140145
String pathStr = preferenceStore.getString(info.preferenceKeyFileLog());
141-
if (pathStr != null && !pathStr.isBlank()) {
146+
if (pathStr != null && !pathStr.isBlank()) {
142147
command.add("-Dlogging.file.name=" + pathStr);
143148
}
144149
command.add("-Dlogging.level.root=" + preferenceStore.getString(info.preferenceKeyLogLevel()));
@@ -208,9 +213,6 @@ protected static boolean hasVmArgStartingWith(List<String> vmargs, String prefix
208213

209214
@Override
210215
protected ProcessBuilder createProcessBuilder() {
211-
if (consoles==null) {
212-
return super.createProcessBuilder();
213-
}
214216
ProcessBuilder builder = new ProcessBuilder(getCommands());
215217
builder.directory(new File(getWorkingDirectory()));
216218
//Super does this, but we do not:
@@ -223,7 +225,7 @@ private void forwardTo(InputStream is, OutputStream os) {
223225
@Override
224226
protected IStatus run(IProgressMonitor arg0) {
225227
try {
226-
pipe(is, os);
228+
is.transferTo(os);
227229
} catch (IOException e) {
228230
}
229231
finally {
@@ -236,34 +238,30 @@ protected IStatus run(IProgressMonitor arg0) {
236238
return Status.OK_STATUS;
237239
}
238240

239-
void pipe(InputStream input, OutputStream output) throws IOException {
240-
try {
241-
byte[] buf = new byte[1024*4];
242-
int n = input.read(buf);
243-
while (n >= 0) {
244-
output.write(buf, 0, n);
245-
n = input.read(buf);
246-
}
247-
output.flush();
248-
} finally {
249-
input.close();
250-
}
251-
}
252-
253241
};
254242
consoleJob.setSystem(true);
255243
consoleJob.schedule();
256244
}
257245

258246
@Override
259247
public InputStream getErrorStream() {
260-
return null;
248+
return getLoggingTarget() == LoggingTarget.ERROR_LOG ? getLanguageServerLog() : null;
261249
}
262250

263251
private InputStream getLanguageServerLog() {
264252
return super.getErrorStream();
265253
}
266254

255+
private LoggingTarget getLoggingTarget() {
256+
LanguageServerCommonsActivator plugin = LanguageServerCommonsActivator.getInstance();
257+
try {
258+
return LoggingTarget.valueOf(plugin.getPreferenceStore().getString(serverInfo.prefernceKeyLogTarget()));
259+
} catch (Exception e) {
260+
plugin.getLog().error("Cannot determine language srever logging target", e);
261+
return LoggingTarget.OFF;
262+
}
263+
}
264+
267265
@Override
268266
public void stop() {
269267
super.stop();
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*******************************************************************************
2-
* Copyright (c) 2018, 2023 Pivotal, Inc.
2+
* Copyright (c) 2018, 2026 Pivotal, Inc.
33
* All rights reserved. This program and the accompanying materials
44
* are made available under the terms of the Eclipse Public License v1.0
55
* which accompanies this distribution, and is available at
@@ -13,31 +13,26 @@
1313
import java.util.HashMap;
1414
import java.util.Map;
1515

16-
import org.springframework.tooling.ls.eclipse.commons.LanguageServerCommonsActivator;
1716
import org.springframework.tooling.ls.eclipse.commons.console.ConsoleUtil.Console;
18-
import org.springframework.tooling.ls.eclipse.commons.preferences.LanguageServerConsolePreferenceConstants.ServerInfo;
1917

2018
import com.google.common.base.Supplier;
2119

2220
public class LanguageServerConsoles {
2321

2422
private static Map<String, Supplier<Console>> managers;
2523

26-
public static synchronized Supplier<Console> getConsoleFactory(ServerInfo server) {
24+
public static synchronized Supplier<Console> getConsoleFactory(String serverLabel) {
2725
if (managers==null) {
2826
managers = new HashMap<>();
2927
}
30-
return managers.computeIfAbsent(server.label(), label -> new Supplier<Console>() {
28+
return managers.computeIfAbsent(serverLabel, label -> new Supplier<Console>() {
3129
ConsoleUtil consoleMgr = new ConsoleUtil(); //one console manager per language server type. This way each has their
3230
// own history (which limits number of open consoles per type)
3331
int consoleCounter = 0;
3432

3533
@Override
3634
public Console get() {
37-
if (isConsoleEnabled(server)) {
38-
return consoleMgr.getConsole(server.label()+" Language Server "+consoleCounter());
39-
}
40-
return null;
35+
return consoleMgr.getConsole(serverLabel+" Language Server "+consoleCounter());
4136
}
4237

4338
private synchronized int consoleCounter() {
@@ -46,8 +41,4 @@ private synchronized int consoleCounter() {
4641
});
4742
}
4843

49-
private static boolean isConsoleEnabled(ServerInfo server) {
50-
return LanguageServerCommonsActivator.getInstance().getPreferenceStore().getBoolean(server.preferenceKeyConsoleLog());
51-
}
52-
5344
}

eclipse-language-servers/org.springframework.tooling.ls.eclipse.commons/src/org/springframework/tooling/ls/eclipse/commons/preferences/LanguageServerConsolePreferenceConstants.java

Lines changed: 6 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*******************************************************************************
2-
* Copyright (c) 2018, 2025 Pivotal, Inc.
2+
* Copyright (c) 2018, 2026 Pivotal, Inc.
33
* All rights reserved. This program and the accompanying materials
44
* are made available under the terms of the Eclipse Public License v1.0
55
* which accompanies this distribution, and is available at
@@ -12,15 +12,13 @@
1212

1313
public class LanguageServerConsolePreferenceConstants {
1414

15-
public static final boolean ENABLE_BY_DEFAULT = false;
16-
1715
public static final String PREFIX_BOSH = "bosh";
1816
public static final String PREFIX_CF = "cloudfoundry";
1917
public static final String PREFIX_CONCOURSE = "concourse";
2018
public static final String PREFIX_SPRING_BOOT = "boot-java";
2119

20+
public static final String SUFFIX_LOG_TARGET = ".log.target";
2221
public static final String SUFFIX_LOG_FILE = ".log.file";
23-
public static final String SUFFIX_LOG_CONSOLE = ".console.enabled";
2422
public static final String SUFFIX_LOG_LEVEL = ".log.level";
2523

2624

@@ -38,16 +36,16 @@ public class LanguageServerConsolePreferenceConstants {
3836

3937
public record ServerInfo(String lsPrefix, String label, String bundleId) {
4038

41-
public String preferenceKeyConsoleLog() {
42-
return lsPrefix + SUFFIX_LOG_CONSOLE;
43-
}
44-
4539
public String preferenceKeyFileLog() {
4640
return lsPrefix + SUFFIX_LOG_FILE;
4741
}
4842

4943
public String preferenceKeyLogLevel() {
5044
return lsPrefix + SUFFIX_LOG_LEVEL;
5145
}
46+
47+
public String prefernceKeyLogTarget() {
48+
return lsPrefix + SUFFIX_LOG_TARGET;
49+
}
5250
}
5351
}

eclipse-language-servers/org.springframework.tooling.ls.eclipse.commons/src/org/springframework/tooling/ls/eclipse/commons/preferences/LanguageServerPreferencesPage.java

Lines changed: 24 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*******************************************************************************
2-
* Copyright (c) 2018, 2025 Pivotal, Inc.
2+
* Copyright (c) 2018, 2026 Pivotal, Inc.
33
* All rights reserved. This program and the accompanying materials
44
* are made available under the terms of the Eclipse Public License v1.0
55
* which accompanies this distribution, and is available at
@@ -14,7 +14,6 @@
1414
import java.nio.file.Files;
1515
import java.nio.file.Path;
1616

17-
import org.eclipse.jface.preference.BooleanFieldEditor;
1817
import org.eclipse.jface.preference.ComboFieldEditor;
1918
import org.eclipse.jface.preference.FieldEditorPreferencePage;
2019
import org.eclipse.jface.preference.FileFieldEditor;
@@ -28,6 +27,7 @@
2827
import org.eclipse.ui.IWorkbench;
2928
import org.eclipse.ui.IWorkbenchPreferencePage;
3029
import org.springframework.tooling.ls.eclipse.commons.LanguageServerCommonsActivator;
30+
import org.springframework.tooling.ls.eclipse.commons.LoggingTarget;
3131
import org.springframework.tooling.ls.eclipse.commons.preferences.LanguageServerConsolePreferenceConstants.ServerInfo;
3232

3333
public class LanguageServerPreferencesPage extends FieldEditorPreferencePage implements IWorkbenchPreferencePage {
@@ -38,10 +38,7 @@ static IPreferenceStore getPrefsStoreFromPlugin() {
3838

3939
@Override
4040
public void init(IWorkbench workbench) {
41-
setDescription("Log settings for STS Language Servers. "
42-
+ "Changes only take effect the next time a Language Server is started.\n"
43-
+ "\n"
44-
+ "Note: Enabling logging to console disables logging to file!\n");
41+
setDescription("Log settings for STS Language Servers. Changes only take effect the next time a Language Server is started.");
4542
setPreferenceStore(getPrefsStoreFromPlugin());
4643
}
4744

@@ -67,6 +64,27 @@ protected void createFieldEditors() {
6764
Composite c = new Composite(group, SWT.NONE);
6865
c.setLayout(new GridLayout());
6966
c.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
67+
addField(new ComboFieldEditor(s.preferenceKeyLogLevel(), "Logging Level", new String[][] {
68+
{"Error", "error"},
69+
{"Warn", "warn"},
70+
{"Info", "info"},
71+
{"Debug", "debug"},
72+
{"Trace", "trace"},
73+
{"Off", "off"},
74+
}, c));
75+
76+
c = new Composite(group, SWT.NONE);
77+
c.setLayout(new GridLayout());
78+
c.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
79+
addField(new ComboFieldEditor(s.prefernceKeyLogTarget(), "Logging to IDE", new String[][] {
80+
{"Off", LoggingTarget.OFF.toString()},
81+
{"Console", LoggingTarget.CONSOLE.toString()},
82+
{"Error Log", LoggingTarget.ERROR_LOG.toString()},
83+
}, c));
84+
85+
c = new Composite(group, SWT.NONE);
86+
c.setLayout(new GridLayout());
87+
c.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
7088
addField(new FileFieldEditor(s.preferenceKeyFileLog(), "Logging to File", true, c) {
7189

7290
@Override
@@ -114,23 +132,6 @@ protected boolean checkState() {
114132

115133
});
116134

117-
c = new Composite(group, SWT.NONE);
118-
c.setLayout(new GridLayout());
119-
c.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
120-
addField(new BooleanFieldEditor(s.preferenceKeyConsoleLog(), "Logging to Console", c));
121-
122-
c = new Composite(group, SWT.NONE);
123-
c.setLayout(new GridLayout());
124-
c.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
125-
addField(new ComboFieldEditor(s.preferenceKeyLogLevel(), "Logging Level", new String[][] {
126-
{"Error", "error"},
127-
{"Warn", "warn"},
128-
{"Info", "info"},
129-
{"Debug", "debug"},
130-
{"Trace", "trace"},
131-
{"Off", "off"},
132-
}, c));
133-
134135
}
135136
}
136137
}

eclipse-language-servers/org.springframework.tooling.ls.eclipse.commons/src/org/springframework/tooling/ls/eclipse/commons/preferences/PrefsInitializer.java

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*******************************************************************************
2-
* Copyright (c) 2018, 2025 Pivotal, Inc.
2+
* Copyright (c) 2018, 2026 Pivotal, Inc.
33
* All rights reserved. This program and the accompanying materials
44
* are made available under the terms of the Eclipse Public License v1.0
55
* which accompanies this distribution, and is available at
@@ -10,10 +10,9 @@
1010
*******************************************************************************/
1111
package org.springframework.tooling.ls.eclipse.commons.preferences;
1212

13-
import static org.springframework.tooling.ls.eclipse.commons.preferences.LanguageServerConsolePreferenceConstants.ENABLE_BY_DEFAULT;
14-
1513
import org.eclipse.core.runtime.preferences.AbstractPreferenceInitializer;
1614
import org.eclipse.jface.preference.IPreferenceStore;
15+
import org.springframework.tooling.ls.eclipse.commons.LoggingTarget;
1716
import org.springframework.tooling.ls.eclipse.commons.preferences.LanguageServerConsolePreferenceConstants.ServerInfo;
1817

1918
public class PrefsInitializer extends AbstractPreferenceInitializer {
@@ -22,8 +21,8 @@ public void initializeDefaultPreferences() {
2221
IPreferenceStore store = LanguageServerPreferencesPage.getPrefsStoreFromPlugin();
2322
ServerInfo[] installedServers = LsPreferencesUtil.getInstalledLs();
2423
for (ServerInfo s : installedServers) {
25-
store.setDefault(s.preferenceKeyConsoleLog(), ENABLE_BY_DEFAULT);
2624
store.setDefault(s.preferenceKeyLogLevel(), "error");
25+
store.setDefault(s.prefernceKeyLogTarget(), LoggingTarget.OFF.toString());
2726
// Bundle bundle = Platform.getBundle(s.bundleId);
2827
// if (bundle != null) {
2928
// IPath stateLocation = Platform.getStateLocation(bundle);

0 commit comments

Comments
 (0)