From 71921db245410f7f08251729eac579284238c741 Mon Sep 17 00:00:00 2001 From: danielrainer <34983953+danielrainer@users.noreply.github.com> Date: Tue, 6 Aug 2024 02:59:42 +0000 Subject: [PATCH] feat: enable localDocs (#1261) Opening docs (rust-analyzer.openDocs) was broken by commit 1410329b4625f3b6b02bb96675ec5313ba0fab25. This commit contains changes preparing for the rust-analyzer "localDocs" feature https://github.com/rust-lang/rust-analyzer/blob/master/docs/dev/lsp-extensions.md#local-documentation However, this feature is only activated by specifying the "localDocs" capability. This commits does so in src/client.ts. To actually make use of the local documentation, the src/commands.ts:openDocs function also needs adjustment. I wrote it such that if a local URI is provided and a corresponding file exists, it is opened. Otherwise, if a web link is provided, this link is opened. Note that "vscode.open" would open the local URI in the editor instead of the browser. Whether local documentation exists depends on whether 'cargo doc' has been executed. If it has been executed but not recently, the documentation might be outdated, so it might be reasonable to generate local documentation before trying to open it. This is not done so far, but could be added. It might make sense to run 'cargo doc --no-deps'. Co-authored-by: Daniel Rainer <daniel.rainer@localhost> --- src/client.ts | 1 + src/commands.ts | 19 ++++++++++++++++--- 2 files changed, 17 insertions(+), 3 deletions(-) diff --git a/src/client.ts b/src/client.ts index 23086304..1c5e630c 100644 --- a/src/client.ts +++ b/src/client.ts @@ -24,6 +24,7 @@ class ExperimentalFeatures implements StaticFeature { const caps: any = capabilities.experimental ?? {}; caps.snippetTextEdit = true; caps.serverStatusNotification = true; + caps.localDocs = true; caps.commands = { commands: [ 'rust-analyzer.runSingle', diff --git a/src/commands.ts b/src/commands.ts index c4ad78f6..f5e6fe2b 100644 --- a/src/commands.ts +++ b/src/commands.ts @@ -14,9 +14,10 @@ import { window, workspace, type WorkspaceEdit, + nvim, } from 'coc.nvim'; import { randomBytes } from 'node:crypto'; -import { writeFileSync } from 'node:fs'; +import { existsSync, writeFileSync } from 'node:fs'; import { tmpdir } from 'node:os'; import { join } from 'node:path'; import readline from 'node:readline'; @@ -695,9 +696,21 @@ export function openDocs(ctx: Ctx): Cmd { textDocument: { uri: document.uri }, position, }; + // TODO: Should 'cargo doc' run at this point? Or 'cargo doc --no-deps'? const doclink = await ctx.client.sendRequest(ra.openDocs, param); - if (doclink?.web) { - await commands.executeCommand('vscode.open', Uri.parse(doclink.web)); + if (doclink) { + if (doclink.local) { + // remove leading 'file://' + const absolutePath = doclink.local.substring(7); + const isReadable = existsSync(absolutePath); + if (isReadable) { + await nvim.call('coc#ui#open_url', doclink.local); + return; + } + } + if (doclink.web) { + await commands.executeCommand('vscode.open', Uri.parse(doclink.web)); + } } }; }