summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorpommicket <pommicket@gmail.com>2024-12-07 20:38:11 -0500
committerpommicket <pommicket@gmail.com>2024-12-07 20:38:11 -0500
commitbbe75ba8c590747e7df7664128afdf96aeb539e2 (patch)
tree40342f0fda4dbfcc02030a25dfe78d973170ab9a
parentb74905fcb282603f8afc45cd3f08fa8c28c83d41 (diff)
Better handling of LSP errors
-rw-r--r--ide-autocomplete.c5
-rw-r--r--ide-definitions.c7
-rw-r--r--ide-document-link.c8
-rw-r--r--ide-format.c5
-rw-r--r--ide-highlights.c5
-rw-r--r--ide-hover.c4
-rw-r--r--ide-rename-symbol.c4
-rw-r--r--ide-signature-help.c4
-rw-r--r--ide-usages.c5
-rw-r--r--lsp-parse.c8
-rw-r--r--lsp.c4
-rw-r--r--lsp.h2
-rw-r--r--main.c1
13 files changed, 54 insertions, 8 deletions
diff --git a/ide-autocomplete.c b/ide-autocomplete.c
index 6089818..558b388 100644
--- a/ide-autocomplete.c
+++ b/ide-autocomplete.c
@@ -365,6 +365,11 @@ void autocomplete_process_lsp_response(Ted *ted, const LSPResponse *response) {
assert(0);
return;
}
+ if (!lsp_response_is_error(response)) {
+ autocomplete_close(ted);
+ ted_flash_error_cursor(ted);
+ return;
+ }
TextBuffer *buffer = ted->active_buffer;
if (!buffer)
diff --git a/ide-definitions.c b/ide-definitions.c
index 79677e8..8b895db 100644
--- a/ide-definitions.c
+++ b/ide-definitions.c
@@ -156,6 +156,13 @@ void definitions_process_lsp_response(Ted *ted, LSP *lsp, const LSPResponse *res
}
defs->last_request.id = 0;
+ if (lsp_response_is_error(response)) {
+ if (menu_is_open(ted, MENU_GOTO_DEFINITION)) {
+ menu_close(ted);
+ }
+ ted_flash_error_cursor(ted);
+ return;
+ }
switch (response->request.type) {
case LSP_REQUEST_DEFINITION:
diff --git a/ide-document-link.c b/ide-document-link.c
index 71307b5..754cecd 100644
--- a/ide-document-link.c
+++ b/ide-document-link.c
@@ -112,9 +112,11 @@ void document_link_process_lsp_response(Ted *ted, const LSPResponse *response) {
if (response->request.type != LSP_REQUEST_DOCUMENT_LINK
|| response->request.id != dl->last_request.id)
return;
- if (!dl->last_request.id)
- return; // request was cancelled
-
+ dl->last_request.id = 0;
+ if (lsp_response_is_error(response)) {
+ document_link_clear(ted);
+ return;
+ }
bool key_down = document_link_activation_key_down(ted);
if (!key_down)
return;
diff --git a/ide-format.c b/ide-format.c
index 8cc0059..6cb6e8a 100644
--- a/ide-format.c
+++ b/ide-format.c
@@ -53,6 +53,11 @@ void format_process_lsp_response(Ted *ted, const LSPResponse *response) {
|| request->type == LSP_REQUEST_FORMATTING)) {
return;
}
+ formatting->last_request_id.id = 0;
+ if (lsp_response_is_error(response)) {
+ ted_flash_error_cursor(ted);
+ return;
+ }
TextBuffer *buffer = ted->active_buffer;
if (!buffer) return;
if (buffer_lsp_document_id(buffer) != request->data.formatting.document)
diff --git a/ide-highlights.c b/ide-highlights.c
index b8c3a94..1dc3aff 100644
--- a/ide-highlights.c
+++ b/ide-highlights.c
@@ -54,6 +54,11 @@ void highlights_process_lsp_response(Ted *ted, const LSPResponse *response) {
return; // not a highlight request
if (response->request.id != hls->last_request.id)
return; // old request
+ hls->last_request.id = 0;
+ if (lsp_response_is_error(response)) {
+ highlights_close(ted);
+ return;
+ }
const LSPResponseHighlight *hl_response = &response->data.highlight;
arr_set_len(hls->highlights, arr_len(hl_response->highlights));
// type-safe memcpy
diff --git a/ide-hover.c b/ide-hover.c
index ff5fb19..e77ffa5 100644
--- a/ide-hover.c
+++ b/ide-hover.c
@@ -78,6 +78,10 @@ void hover_process_lsp_response(Ted *ted, const LSPResponse *response) {
}
hover->last_request.id = 0;
+ if (lsp_response_is_error(response)) {
+ hover_close(ted);
+ return;
+ }
const LSPResponseHover *hover_response = &response->data.hover;
TextBuffer *buffer=0;
diff --git a/ide-rename-symbol.c b/ide-rename-symbol.c
index a379d1d..ff96311 100644
--- a/ide-rename-symbol.c
+++ b/ide-rename-symbol.c
@@ -122,6 +122,10 @@ void rename_symbol_process_lsp_response(Ted *ted, const LSPResponse *response) {
if (menu_is_open(ted, MENU_RENAME_SYMBOL))
menu_close(ted);
+ if (lsp_response_is_error(response)) {
+ ted_flash_error_cursor(ted);
+ return;
+ }
const LSPResponseRename *data = &response->data.rename;
if (!lsp) {
// LSP crashed or something
diff --git a/ide-signature-help.c b/ide-signature-help.c
index 90853e6..ea47e1d 100644
--- a/ide-signature-help.c
+++ b/ide-signature-help.c
@@ -96,6 +96,10 @@ void signature_help_process_lsp_response(Ted *ted, const LSPResponse *response)
return;
}
help->last_request.id = 0;
+ if (lsp_response_is_error(response)) {
+ signature_help_clear(help);
+ return;
+ }
const LSPResponseSignatureHelp *lsp_help = &response->data.signature_help;
u32 signature_count = arr_len(lsp_help->signatures);
diff --git a/ide-usages.c b/ide-usages.c
index 9ae31e4..b94eb45 100644
--- a/ide-usages.c
+++ b/ide-usages.c
@@ -44,6 +44,11 @@ void usages_process_lsp_response(Ted *ted, const LSPResponse *response) {
return; // not for us
if (response->request.id != usages->last_request.id)
return;
+ if (lsp_response_is_error(response)) {
+ usages->last_request.id = 0;
+ ted_flash_error_cursor(ted);
+ return;
+ }
LSP *lsp = ted_get_lsp_by_id(ted, usages->last_request.lsp);
const LSPResponseReferences *refs = &response->data.references;
if (lsp && arr_len(refs->locations)) {
diff --git a/lsp-parse.c b/lsp-parse.c
index 16e9804..72c6b88 100644
--- a/lsp-parse.c
+++ b/lsp-parse.c
@@ -382,7 +382,7 @@ static bool parse_completion_response(LSP *lsp, const JSON *json, LSPResponse *r
JSONArray tags = json_object_get_array(json, item_object, "tags");
for (u32 i = 0; i < tags.len; ++i) {
double tag = json_array_get_number(json, tags, i);
- if (tag == LSP_SYMBOL_TAG_DEPRECATED) {
+ if (tag == (double)LSP_SYMBOL_TAG_DEPRECATED) {
item->deprecated = true;
}
}
@@ -395,7 +395,7 @@ static bool parse_completion_response(LSP *lsp, const JSON *json, LSPResponse *r
double edit_type = json_object_get_number(json, item_object, "insertTextFormat");
if (!isnan(edit_type)) {
- if (edit_type != LSP_COMPLETION_EDIT_PLAIN && edit_type != LSP_COMPLETION_EDIT_SNIPPET) {
+ if (edit_type != (double)LSP_COMPLETION_EDIT_PLAIN && edit_type != (double)LSP_COMPLETION_EDIT_SNIPPET) {
// maybe in the future more edit types will be added.
// probably they'll have associated capabilities, but I think it's best to just ignore unrecognized types
debug_println("Bad InsertTextFormat: %g", edit_type);
@@ -675,7 +675,7 @@ static bool parse_symbol_information(LSP *lsp, const JSON *json, JSONValue value
bool deprecated = json_object_get(json, object, "deprecated").type == JSON_TRUE;
JSONArray tags = json_object_get_array(json, object, "tags");
for (size_t i = 0; i < tags.len; ++i) {
- if (json_array_get_number(json, tags, i) == LSP_SYMBOL_TAG_DEPRECATED)
+ if (json_array_get_number(json, tags, i) == (double)LSP_SYMBOL_TAG_DEPRECATED)
deprecated = true;
}
info->deprecated = deprecated;
@@ -1091,7 +1091,7 @@ void process_message(LSP *lsp, JSON *json) {
}
if (!lsp_string_is_empty(response.error)) {
- if (error_code != LSP_ERROR_REQUEST_CANCELLED)
+ if (error_code != (double)LSP_ERROR_REQUEST_CANCELLED)
add_to_messages = true;
} else switch (response.request.type) {
case LSP_REQUEST_COMPLETION:
diff --git a/lsp.c b/lsp.c
index bb1b5e9..7de51c3 100644
--- a/lsp.c
+++ b/lsp.c
@@ -961,3 +961,7 @@ void lsp_quit(void) {
}
lsp_write_quit();
}
+
+bool lsp_response_is_error(const LSPResponse *r) {
+ return !lsp_string_is_empty(r->error);
+}
diff --git a/lsp.h b/lsp.h
index 88a1478..37370bc 100644
--- a/lsp.h
+++ b/lsp.h
@@ -667,6 +667,8 @@ void lsp_cancel_request(LSP *lsp, LSPRequestID id);
// don't free the contents of this response! let me handle it!
void lsp_send_response(LSP *lsp, LSPResponse *response);
const char *lsp_response_string(const LSPResponse *response, LSPString string);
+/// returns `true` if this response is an error
+bool lsp_response_is_error(const LSPResponse *r);
const char *lsp_request_string(const LSPRequest *request, LSPString string);
/// low-level API for allocating message strings.
///
diff --git a/main.c b/main.c
index dc733a9..7136f14 100644
--- a/main.c
+++ b/main.c
@@ -981,7 +981,6 @@ int main(int argc, char **argv) {
// this is a bit spammy
// sometimes clang is just like "this request was cancelled cuz the cursor moved"
//ted_error(ted, "LSP error: %s", lsp_response_string(r, r->error));
- } else {
// it's important that we send error responses here too.
// we don't want to be waiting around for a response that's never coming.
autocomplete_process_lsp_response(ted, r);