From 94ee80b2229975a0dd2d578e6673bef33163d10f Mon Sep 17 00:00:00 2001 From: David Schulz Date: Fri, 12 Feb 2021 14:05:10 +0100 Subject: [PATCH] JLS: add special java client that can execute jls commands the java language server uses special "java.apply.workspaceEdit" commands that already contain the workspace edit that should be applied when triggering the command. Change-Id: If7c53b9b097aaeca289e3958a39be37a9725d395 Reviewed-by: Christian Stenger --- src/plugins/android/CMakeLists.txt | 2 +- src/plugins/android/android.qbs | 1 + src/plugins/android/android_dependencies.pri | 1 + src/plugins/android/javalanguageserver.cpp | 31 +++++++++++++++++++ src/plugins/android/javalanguageserver.h | 1 + src/plugins/languageclient/client.h | 2 +- .../languageclient/languageclientsettings.cpp | 7 ++++- .../languageclient/languageclientsettings.h | 1 + .../languageclient/languageclientutils.h | 24 ++++++++------ 9 files changed, 57 insertions(+), 13 deletions(-) diff --git a/src/plugins/android/CMakeLists.txt b/src/plugins/android/CMakeLists.txt index 2759888b03d..d2f57f253ef 100644 --- a/src/plugins/android/CMakeLists.txt +++ b/src/plugins/android/CMakeLists.txt @@ -1,5 +1,5 @@ add_qtc_plugin(Android - DEPENDS QtcSsh QmlDebug Qt5::Xml + DEPENDS QtcSsh QmlDebug Qt5::Xml LanguageServerProtocol PLUGIN_DEPENDS Core Debugger ProjectExplorer QtSupport LanguageClient SOURCES adbcommandswidget.cpp adbcommandswidget.h adbcommandswidget.ui diff --git a/src/plugins/android/android.qbs b/src/plugins/android/android.qbs index 2cd4722b24b..777be666f49 100644 --- a/src/plugins/android/android.qbs +++ b/src/plugins/android/android.qbs @@ -8,6 +8,7 @@ Project { Depends { name: "Core" } Depends { name: "Debugger" } Depends { name: "LanguageClient" } + Depends { name: "LanguageServerProtocol" } Depends { name: "ProParser" } Depends { name: "ProjectExplorer" } Depends { name: "QmlDebug" } diff --git a/src/plugins/android/android_dependencies.pri b/src/plugins/android/android_dependencies.pri index c0bd7fe84e7..3de057ea7fb 100644 --- a/src/plugins/android/android_dependencies.pri +++ b/src/plugins/android/android_dependencies.pri @@ -9,6 +9,7 @@ QTC_PLUGIN_DEPENDS += \ QTC_LIB_DEPENDS += \ extensionsystem \ + languageserverprotocol \ qmldebug \ ssh \ utils diff --git a/src/plugins/android/javalanguageserver.cpp b/src/plugins/android/javalanguageserver.cpp index 60ead987446..d0b900a6066 100644 --- a/src/plugins/android/javalanguageserver.cpp +++ b/src/plugins/android/javalanguageserver.cpp @@ -27,6 +27,8 @@ #include "androidconstants.h" +#include +#include #include #include #include @@ -180,5 +182,34 @@ LanguageClient::BaseSettings *JLSSettings::copy() const return new JLSSettings(*this); } +class JLSClient : public LanguageClient::Client +{ +public: + using Client::Client; + + void executeCommand(const LanguageServerProtocol::Command &command) override; +}; + +void JLSClient::executeCommand(const LanguageServerProtocol::Command &command) +{ + if (command.command() == "java.apply.workspaceEdit") { + const QJsonArray arguments = command.arguments().value_or(QJsonArray()); + for (const QJsonValue &argument : arguments) { + if (!argument.isObject()) + continue; + LanguageServerProtocol::WorkspaceEdit edit(argument.toObject()); + if (edit.isValid(nullptr)) + LanguageClient::applyWorkspaceEdit(edit); + } + } else { + Client::executeCommand(command); + } +} + +LanguageClient::Client *JLSSettings::createClient(LanguageClient::BaseClientInterface *interface) const +{ + return new JLSClient(interface); +} + } // namespace Internal } // namespace Android diff --git a/src/plugins/android/javalanguageserver.h b/src/plugins/android/javalanguageserver.h index ac2179db84a..58310070771 100644 --- a/src/plugins/android/javalanguageserver.h +++ b/src/plugins/android/javalanguageserver.h @@ -41,6 +41,7 @@ public: QVariantMap toMap() const final; void fromMap(const QVariantMap &map) final; LanguageClient::BaseSettings *copy() const final; + LanguageClient::Client *createClient(LanguageClient::BaseClientInterface *interface) const final; QString m_languageServer; QString m_workspace; diff --git a/src/plugins/languageclient/client.h b/src/plugins/languageclient/client.h index 24050dc9872..6575ea5e33f 100644 --- a/src/plugins/languageclient/client.h +++ b/src/plugins/languageclient/client.h @@ -145,7 +145,7 @@ public: void requestCodeActions(const LanguageServerProtocol::CodeActionRequest &request); void handleCodeActionResponse(const LanguageServerProtocol::CodeActionRequest::Response &response, const LanguageServerProtocol::DocumentUri &uri); - void executeCommand(const LanguageServerProtocol::Command &command); + virtual void executeCommand(const LanguageServerProtocol::Command &command); // language support void addAssistProcessor(TextEditor::IAssistProcessor *processor); diff --git a/src/plugins/languageclient/languageclientsettings.cpp b/src/plugins/languageclient/languageclientsettings.cpp index c5b6fd557ae..030fefef3d8 100644 --- a/src/plugins/languageclient/languageclientsettings.cpp +++ b/src/plugins/languageclient/languageclientsettings.cpp @@ -561,13 +561,18 @@ Client *BaseSettings::createClient() return nullptr; BaseClientInterface *interface = createInterface(); QTC_ASSERT(interface, return nullptr); - auto *client = new Client(interface); + auto *client = createClient(interface); client->setName(Utils::globalMacroExpander()->expand(m_name)); client->setSupportedLanguage(m_languageFilter); client->setInitializationOptions(initializationOptions()); return client; } +Client *BaseSettings::createClient(BaseClientInterface *interface) const +{ + return new Client(interface); +} + QVariantMap BaseSettings::toMap() const { QVariantMap map; diff --git a/src/plugins/languageclient/languageclientsettings.h b/src/plugins/languageclient/languageclientsettings.h index 25a55e27d5e..be190987ef6 100644 --- a/src/plugins/languageclient/languageclientsettings.h +++ b/src/plugins/languageclient/languageclientsettings.h @@ -101,6 +101,7 @@ public: protected: virtual BaseClientInterface *createInterface() const { return nullptr; } + virtual Client *createClient(BaseClientInterface *interface) const; BaseSettings(const BaseSettings &other) = default; BaseSettings(BaseSettings &&other) = default; diff --git a/src/plugins/languageclient/languageclientutils.h b/src/plugins/languageclient/languageclientutils.h index d9a5bb7a9ec..99a52a2d88e 100644 --- a/src/plugins/languageclient/languageclientutils.h +++ b/src/plugins/languageclient/languageclientutils.h @@ -25,8 +25,10 @@ #pragma once -#include +#include "languageclient_global.h" + #include +#include #include #include @@ -44,15 +46,17 @@ class Client; Utils::ChangeSet editsToChangeSet(const QList &edits, const QTextDocument *doc); -bool applyWorkspaceEdit(const LanguageServerProtocol::WorkspaceEdit &edit); -bool applyTextDocumentEdit(const LanguageServerProtocol::TextDocumentEdit &edit); -bool applyTextEdits(const LanguageServerProtocol::DocumentUri &uri, - const QList &edits); -void applyTextEdit(TextEditor::TextDocumentManipulatorInterface &manipulator, - const LanguageServerProtocol::TextEdit &edit); -void updateCodeActionRefactoringMarker(Client *client, - const LanguageServerProtocol::CodeAction &action, - const LanguageServerProtocol::DocumentUri &uri); +bool LANGUAGECLIENT_EXPORT applyWorkspaceEdit(const LanguageServerProtocol::WorkspaceEdit &edit); +bool LANGUAGECLIENT_EXPORT +applyTextDocumentEdit(const LanguageServerProtocol::TextDocumentEdit &edit); +bool LANGUAGECLIENT_EXPORT applyTextEdits(const LanguageServerProtocol::DocumentUri &uri, + const QList &edits); +void LANGUAGECLIENT_EXPORT applyTextEdit(TextEditor::TextDocumentManipulatorInterface &manipulator, + const LanguageServerProtocol::TextEdit &edit); +void LANGUAGECLIENT_EXPORT +updateCodeActionRefactoringMarker(Client *client, + const LanguageServerProtocol::CodeAction &action, + const LanguageServerProtocol::DocumentUri &uri); void updateEditorToolBar(Core::IEditor *editor); const QIcon symbolIcon(int type);