forked from qt-creator/qt-creator
ClangCodeModel: Request clangd quickfix for -Wswitch warning
This way, a warning about missing switch cases will be accompanied by a matching code action, which allows the user to fix it right away by clicking on the lightbulb. Requires clangd >= 15; see https://reviews.llvm.org/D118976. Change-Id: I11e82264c41e4154f979d28a5e44e72c8158595b Reviewed-by: David Schulz <david.schulz@qt.io>
This commit is contained in:
@@ -1544,8 +1544,18 @@ void ClangdClient::handleDiagnostics(const PublishDiagnosticsParams ¶ms)
|
|||||||
return;
|
return;
|
||||||
for (const Diagnostic &diagnostic : params.diagnostics()) {
|
for (const Diagnostic &diagnostic : params.diagnostics()) {
|
||||||
const ClangdDiagnostic clangdDiagnostic(diagnostic);
|
const ClangdDiagnostic clangdDiagnostic(diagnostic);
|
||||||
for (const CodeAction &action : clangdDiagnostic.codeActions().value_or(QList<CodeAction>{}))
|
const auto codeActions = clangdDiagnostic.codeActions();
|
||||||
|
if (codeActions && !codeActions->isEmpty()) {
|
||||||
|
for (const CodeAction &action : *codeActions)
|
||||||
LanguageClient::updateCodeActionRefactoringMarker(this, action, uri);
|
LanguageClient::updateCodeActionRefactoringMarker(this, action, uri);
|
||||||
|
} else {
|
||||||
|
// We know that there's only one kind of diagnostic for which clangd has
|
||||||
|
// a quickfix tweak, so let's not be wasteful.
|
||||||
|
const Diagnostic::Code code = diagnostic.code().value_or(Diagnostic::Code());
|
||||||
|
const QString * const codeString = Utils::get_if<QString>(&code);
|
||||||
|
if (codeString && *codeString == "-Wswitch")
|
||||||
|
requestCodeActions(uri, diagnostic);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -866,7 +866,19 @@ SymbolSupport &Client::symbolSupport()
|
|||||||
return m_symbolSupport;
|
return m_symbolSupport;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Client::requestCodeActions(const LanguageServerProtocol::DocumentUri &uri,
|
||||||
|
const LanguageServerProtocol::Diagnostic &diagnostic)
|
||||||
|
{
|
||||||
|
requestCodeActions(uri, diagnostic.range(), {diagnostic});
|
||||||
|
}
|
||||||
|
|
||||||
void Client::requestCodeActions(const DocumentUri &uri, const QList<Diagnostic> &diagnostics)
|
void Client::requestCodeActions(const DocumentUri &uri, const QList<Diagnostic> &diagnostics)
|
||||||
|
{
|
||||||
|
requestCodeActions(uri, {}, diagnostics);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Client::requestCodeActions(const DocumentUri &uri, const Range &range,
|
||||||
|
const QList<Diagnostic> &diagnostics)
|
||||||
{
|
{
|
||||||
const Utils::FilePath fileName = uri.toFilePath();
|
const Utils::FilePath fileName = uri.toFilePath();
|
||||||
TextEditor::TextDocument *doc = TextEditor::TextDocument::textDocumentForFilePath(fileName);
|
TextEditor::TextDocument *doc = TextEditor::TextDocument::textDocumentForFilePath(fileName);
|
||||||
@@ -878,10 +890,14 @@ void Client::requestCodeActions(const DocumentUri &uri, const QList<Diagnostic>
|
|||||||
context.setDiagnostics(diagnostics);
|
context.setDiagnostics(diagnostics);
|
||||||
codeActionParams.setContext(context);
|
codeActionParams.setContext(context);
|
||||||
codeActionParams.setTextDocument(TextDocumentIdentifier(uri));
|
codeActionParams.setTextDocument(TextDocumentIdentifier(uri));
|
||||||
|
if (range.isEmpty()) {
|
||||||
Position start(0, 0);
|
Position start(0, 0);
|
||||||
const QTextBlock &lastBlock = doc->document()->lastBlock();
|
const QTextBlock &lastBlock = doc->document()->lastBlock();
|
||||||
Position end(lastBlock.blockNumber(), lastBlock.length() - 1);
|
Position end(lastBlock.blockNumber(), lastBlock.length() - 1);
|
||||||
codeActionParams.setRange(Range(start, end));
|
codeActionParams.setRange(Range(start, end));
|
||||||
|
} else {
|
||||||
|
codeActionParams.setRange(range);
|
||||||
|
}
|
||||||
CodeActionRequest request(codeActionParams);
|
CodeActionRequest request(codeActionParams);
|
||||||
request.setResponseCallback(
|
request.setResponseCallback(
|
||||||
[uri, self = QPointer<Client>(this)](const CodeActionRequest::Response &response) {
|
[uri, self = QPointer<Client>(this)](const CodeActionRequest::Response &response) {
|
||||||
|
@@ -168,6 +168,8 @@ public:
|
|||||||
void updateConfiguration(const QJsonValue &configuration);
|
void updateConfiguration(const QJsonValue &configuration);
|
||||||
|
|
||||||
// commands
|
// commands
|
||||||
|
void requestCodeActions(const LanguageServerProtocol::DocumentUri &uri,
|
||||||
|
const LanguageServerProtocol::Diagnostic &diagnostic);
|
||||||
void requestCodeActions(const LanguageServerProtocol::DocumentUri &uri,
|
void requestCodeActions(const LanguageServerProtocol::DocumentUri &uri,
|
||||||
const QList<LanguageServerProtocol::Diagnostic> &diagnostics);
|
const QList<LanguageServerProtocol::Diagnostic> &diagnostics);
|
||||||
void requestCodeActions(const LanguageServerProtocol::CodeActionRequest &request);
|
void requestCodeActions(const LanguageServerProtocol::CodeActionRequest &request);
|
||||||
@@ -253,6 +255,9 @@ private:
|
|||||||
void requestDocumentHighlightsNow(TextEditor::TextEditorWidget *widget);
|
void requestDocumentHighlightsNow(TextEditor::TextEditorWidget *widget);
|
||||||
LanguageServerProtocol::SemanticRequestTypes supportedSemanticRequests(TextEditor::TextDocument *document) const;
|
LanguageServerProtocol::SemanticRequestTypes supportedSemanticRequests(TextEditor::TextDocument *document) const;
|
||||||
void handleSemanticTokens(const LanguageServerProtocol::SemanticTokens &tokens);
|
void handleSemanticTokens(const LanguageServerProtocol::SemanticTokens &tokens);
|
||||||
|
void requestCodeActions(const LanguageServerProtocol::DocumentUri &uri,
|
||||||
|
const LanguageServerProtocol::Range &range,
|
||||||
|
const QList<LanguageServerProtocol::Diagnostic> &diagnostics);
|
||||||
void documentClosed(Core::IDocument *document);
|
void documentClosed(Core::IDocument *document);
|
||||||
|
|
||||||
virtual void handleDocumentClosed(TextEditor::TextDocument *) {}
|
virtual void handleDocumentClosed(TextEditor::TextDocument *) {}
|
||||||
|
Reference in New Issue
Block a user