Qt
Internal/Contributor docs for the Qt SDK. Note: These are NOT official API docs; those are found at https://doc.qt.io/
Loading...
Searching...
No Matches
qworkspace.cpp
Go to the documentation of this file.
1// Copyright (C) 2021 The Qt Company Ltd.
2// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
3// Qt-Security score:significant reason:default
4
6#include "qworkspace_p.h"
9
10#include <QtLanguageServer/private/qlanguageserverspectypes_p.h>
11#include <QtLanguageServer/private/qlspnotifysignals_p.h>
12
13#include <QtCore/qfile.h>
14#include <variant>
15
17using namespace Qt::StringLiterals;
18using namespace QLspSpecification;
19
20void WorkspaceHandlers::registerHandlers(QLanguageServer *server, QLanguageServerProtocol *protocol)
21{
22 QObject::connect(server->notifySignals(),
23 &QLspNotifySignals::receivedDidChangeWorkspaceFoldersNotification, this,
24 [this](const DidChangeWorkspaceFoldersParams &params) {
25 const WorkspaceFoldersChangeEvent &event = params.event;
26
27 const QList<WorkspaceFolder> &removed = event.removed;
28 QList<QByteArray> toRemove;
29 for (const WorkspaceFolder &folder : removed) {
30 toRemove.append(QQmlLSUtils::lspUriToQmlUrl(folder.uri));
31 m_codeModelManager->removeDirectory(
32 QQmlLSUtils::lspUriToQmlUrl(folder.uri));
33 }
34 m_codeModelManager->removeRootUrls(toRemove);
35 const QList<WorkspaceFolder> &added = event.added;
36 QList<QByteArray> toAdd;
37 for (const WorkspaceFolder &folder : added) {
38 toAdd.append(QQmlLSUtils::lspUriToQmlUrl(folder.uri));
39 }
40 m_codeModelManager->addRootUrls(toAdd);
41 });
42
43 QObject::connect(server, &QLanguageServer::clientInitialized, this,
44 &WorkspaceHandlers::clientInitialized, Qt::SingleShotConnection);
45
46 protocol->typedRpc()->registerNotificationHandler<Notifications::AddBuildDirsParams>(
48 [this](const QByteArray &, const Notifications::AddBuildDirsParams &params) {
49 for (const auto &buildDirs : params.buildDirsToSet) {
50 QStringList dirPaths;
51 dirPaths.resize(buildDirs.buildDirs.size());
52 std::transform(buildDirs.buildDirs.begin(), buildDirs.buildDirs.end(),
53 dirPaths.begin(), [](const QByteArray &utf8Str) {
54 return QString::fromUtf8(utf8Str);
55 });
56 m_codeModelManager->setBuildPathsForRootUrl(buildDirs.baseUri, dirPaths);
57 }
58 });
59}
60
61void WorkspaceHandlers::setupCapabilities(QLspSpecification::ServerCapabilities &caps)
62{
63 WorkspaceFoldersServerCapabilities folders;
64 folders.supported = true;
65 folders.changeNotifications = true;
66 if (!caps.workspace)
67 caps.workspace = QJsonObject();
68 caps.workspace->insert(u"workspaceFolders"_s, QTypedJson::toJsonValue(folders));
69
70 QJsonObject expCap;
71 if (caps.experimental.has_value() && caps.experimental->isObject())
72 expCap = caps.experimental->toObject();
73 expCap.insert(u"addBuildDirs"_s, QJsonObject({ { u"supported"_s, true } }));
74 caps.experimental = expCap;
75}
76
77void WorkspaceHandlers::openInitialWorkspace(const InitializeParams &clientInfo)
78{
79 if (clientInfo.workspaceFolders) {
80 const auto *folders = std::get_if<QList<WorkspaceFolder>>(&*clientInfo.workspaceFolders);
81
82 // note: if *clientInfo.workspaceFolders contains a nullptr_t than it means that no WS was
83 // opened yet.
84 if (!folders)
85 return;
86
87 QList<QByteArray> rootPaths;
88 for (const auto &folder : std::as_const(*folders)) {
89 rootPaths.append(QQmlLSUtils::lspUriToQmlUrl(folder.uri));
90 }
91 m_codeModelManager->addRootUrls(rootPaths);
92 return;
93 }
94
95 // note: rootUri is deprecated in the LSP protocol
96 if (const auto *rootUri = std::get_if<QByteArray>(&clientInfo.rootUri)) {
97 m_codeModelManager->addRootUrls({ QQmlLSUtils::lspUriToQmlUrl(*rootUri) });
98 return;
99 }
100 // note: rootPath is also deprecated in the LSP protocol. It was deprecated even before rootUri
101 // was deprecated.
102 if (clientInfo.rootPath) {
103 if (const auto *rootPath = std::get_if<QByteArray>(&*clientInfo.rootPath)) {
104 m_codeModelManager->addRootUrls({
105 QUrl::fromLocalFile(QString::fromUtf8(*rootPath)).toEncoded(),
106 });
107 return;
108 }
109 }
110}
111
112void WorkspaceHandlers::clientInitialized(QLanguageServer *server)
113{
114 const auto &clientInfo = server->clientInfo();
115
116 if (clientInfo.capabilities.workspace
117 && clientInfo.capabilities.workspace->value(u"workspaceFolders"_s).toBool(false)) {
118 openInitialWorkspace(clientInfo);
119 }
120}
121
122QT_END_NAMESPACE
void setupCapabilities(QLspSpecification::ServerCapabilities &caps) override
Combined button and popup list for selecting options.