From d5a3370d7c6c0f2f85d5b99cb331d4a5ce3d616a Mon Sep 17 00:00:00 2001 From: Kirill Bulatov Date: Thu, 8 Feb 2024 16:17:47 +0200 Subject: [PATCH] Fix gopls langserver downloads (#7571) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Fixes https://github.com/zed-industries/zed/issues/7534 by not requiring assets for gopls and vscode-eslint langservers — those two are the only ones in Zed that do not use assets directly when determining langserver version and retrieving those. All other servers deal with assets, hence require those to be present. The problem with https://github.com/tamasfe/taplo/releases is that they host multiple binary releases in the same release list, so for now the code works because only the langserver has assets — but as soon as another release there gets assets, it will break again. We could filter out those by names also, but they also tend to change (and can be edited manually), so keeping it as is for now. Release Notes: - Fixed gopls language server downloads ([7534](https://github.com/zed-industries/zed/issues/7534)) --- crates/copilot/src/copilot.rs | 5 +++-- crates/util/src/github.rs | 4 +++- crates/zed/src/languages/c.rs | 3 ++- crates/zed/src/languages/csharp.rs | 11 +++++++---- crates/zed/src/languages/deno.rs | 3 ++- crates/zed/src/languages/elixir.rs | 17 +++++++++-------- crates/zed/src/languages/gleam.rs | 2 +- crates/zed/src/languages/go.rs | 3 ++- crates/zed/src/languages/lua.rs | 14 +++++++++----- crates/zed/src/languages/rust.rs | 9 +++++++-- crates/zed/src/languages/toml.rs | 3 ++- crates/zed/src/languages/typescript.rs | 9 +++++++-- crates/zed/src/languages/zig.rs | 5 +++-- 13 files changed, 57 insertions(+), 31 deletions(-) diff --git a/crates/copilot/src/copilot.rs b/crates/copilot/src/copilot.rs index 16f941d16f7f9ea19bea8a10609f9b394e14da5e..dc134eba4a9db277079fc0f41d54ccfad99b54f8 100644 --- a/crates/copilot/src/copilot.rs +++ b/crates/copilot/src/copilot.rs @@ -976,7 +976,8 @@ async fn get_copilot_lsp(http: Arc) -> anyhow::Result { ///Check for the latest copilot language server and download it if we haven't already async fn fetch_latest(http: Arc) -> anyhow::Result { - let release = latest_github_release("zed-industries/copilot", false, http.clone()).await?; + let release = + latest_github_release("zed-industries/copilot", true, false, http.clone()).await?; let version_dir = &*paths::COPILOT_DIR.join(format!("copilot-{}", release.name)); @@ -997,7 +998,7 @@ async fn get_copilot_lsp(http: Arc) -> anyhow::Result { let mut response = http .get(url, Default::default(), true) .await - .map_err(|err| anyhow!("error downloading copilot release: {}", err))?; + .context("error downloading copilot release")?; let decompressed_bytes = GzipDecoder::new(BufReader::new(response.body_mut())); let archive = Archive::new(decompressed_bytes); archive.unpack(dist_dir).await?; diff --git a/crates/util/src/github.rs b/crates/util/src/github.rs index fc250be32f13e4011bfc8776c110af56cc33d726..8503c692672b0c7e78e3521b17a6f973b6d9e78a 100644 --- a/crates/util/src/github.rs +++ b/crates/util/src/github.rs @@ -27,6 +27,7 @@ pub struct GithubReleaseAsset { pub async fn latest_github_release( repo_name_with_owner: &str, + require_assets: bool, pre_release: bool, http: Arc, ) -> Result { @@ -68,6 +69,7 @@ pub async fn latest_github_release( releases .into_iter() - .find(|release| !release.assets.is_empty() && release.pre_release == pre_release) + .filter(|release| !require_assets || !release.assets.is_empty()) + .find(|release| release.pre_release == pre_release) .ok_or(anyhow!("Failed to find a release")) } diff --git a/crates/zed/src/languages/c.rs b/crates/zed/src/languages/c.rs index 655ac044c15dbc164d62f9344a87ee2d9189479c..8b5902ff75c0b80e1e2e715457d62acef8ac22c3 100644 --- a/crates/zed/src/languages/c.rs +++ b/crates/zed/src/languages/c.rs @@ -28,7 +28,8 @@ impl super::LspAdapter for CLspAdapter { &self, delegate: &dyn LspAdapterDelegate, ) -> Result> { - let release = latest_github_release("clangd/clangd", false, delegate.http_client()).await?; + let release = + latest_github_release("clangd/clangd", true, false, delegate.http_client()).await?; let asset_name = format!("clangd-mac-{}.zip", release.name); let asset = release .assets diff --git a/crates/zed/src/languages/csharp.rs b/crates/zed/src/languages/csharp.rs index e70bc78279f8a7304265663756a48181700a8351..9d3c63ed51db5142b0a169683be0301d65f20634 100644 --- a/crates/zed/src/languages/csharp.rs +++ b/crates/zed/src/languages/csharp.rs @@ -29,10 +29,6 @@ impl super::LspAdapter for OmniSharpAdapter { &self, delegate: &dyn LspAdapterDelegate, ) -> Result> { - let release = - latest_github_release("OmniSharp/omnisharp-roslyn", false, delegate.http_client()) - .await?; - let mapped_arch = match ARCH { "aarch64" => Some("arm64"), "x86_64" => Some("x64"), @@ -42,6 +38,13 @@ impl super::LspAdapter for OmniSharpAdapter { match mapped_arch { None => Ok(Box::new(())), Some(arch) => { + let release = latest_github_release( + "OmniSharp/omnisharp-roslyn", + true, + false, + delegate.http_client(), + ) + .await?; let asset_name = format!("omnisharp-osx-{}-net6.0.tar.gz", arch); let asset = release .assets diff --git a/crates/zed/src/languages/deno.rs b/crates/zed/src/languages/deno.rs index 475181ec3f0df062141805656cd38800afea42a9..0020f94a46777bec9e77f137cf846f3394c88f71 100644 --- a/crates/zed/src/languages/deno.rs +++ b/crates/zed/src/languages/deno.rs @@ -70,7 +70,8 @@ impl LspAdapter for DenoLspAdapter { &self, delegate: &dyn LspAdapterDelegate, ) -> Result> { - let release = latest_github_release("denoland/deno", false, delegate.http_client()).await?; + let release = + latest_github_release("denoland/deno", true, false, delegate.http_client()).await?; let asset_name = format!("deno-{}-apple-darwin.zip", consts::ARCH); let asset = release .assets diff --git a/crates/zed/src/languages/elixir.rs b/crates/zed/src/languages/elixir.rs index 6172be16838b9a37420e9f849ac26302c3f3ed8d..f6b19ad06611a001696635ae9d65ad699e5c282d 100644 --- a/crates/zed/src/languages/elixir.rs +++ b/crates/zed/src/languages/elixir.rs @@ -111,19 +111,19 @@ impl LspAdapter for ElixirLspAdapter { delegate: &dyn LspAdapterDelegate, ) -> Result> { let http = delegate.http_client(); - let release = latest_github_release("elixir-lsp/elixir-ls", false, http).await?; + let release = latest_github_release("elixir-lsp/elixir-ls", true, false, http).await?; let version_name = release .name .strip_prefix("Release ") .context("Elixir-ls release name does not start with prefix")? .to_owned(); - let asset_name = format!("elixir-ls-{}.zip", &version_name); + let asset_name = format!("elixir-ls-{version_name}.zip"); let asset = release .assets .iter() .find(|asset| asset.name == asset_name) - .ok_or_else(|| anyhow!("no asset found matching {:?}", asset_name))?; + .ok_or_else(|| anyhow!("no asset found matching {asset_name:?}"))?; let version = GitHubLspBinaryVersion { name: version_name, @@ -313,20 +313,21 @@ impl LspAdapter for NextLspAdapter { &self, delegate: &dyn LspAdapterDelegate, ) -> Result> { - let release = - latest_github_release("elixir-tools/next-ls", false, delegate.http_client()).await?; - let version = release.name.clone(); let platform = match consts::ARCH { "x86_64" => "darwin_amd64", "aarch64" => "darwin_arm64", other => bail!("Running on unsupported platform: {other}"), }; - let asset_name = format!("next_ls_{}", platform); + let release = + latest_github_release("elixir-tools/next-ls", true, false, delegate.http_client()) + .await?; + let version = release.name; + let asset_name = format!("next_ls_{platform}"); let asset = release .assets .iter() .find(|asset| asset.name == asset_name) - .ok_or_else(|| anyhow!("no asset found matching {:?}", asset_name))?; + .with_context(|| format!("no asset found matching {asset_name:?}"))?; let version = GitHubLspBinaryVersion { name: version, url: asset.browser_download_url.clone(), diff --git a/crates/zed/src/languages/gleam.rs b/crates/zed/src/languages/gleam.rs index 90b10a3657c291d7b4f0ee56eb47420b161d685b..d8020a0a8542267bffad8348686e2ba1e4002e15 100644 --- a/crates/zed/src/languages/gleam.rs +++ b/crates/zed/src/languages/gleam.rs @@ -35,7 +35,7 @@ impl LspAdapter for GleamLspAdapter { delegate: &dyn LspAdapterDelegate, ) -> Result> { let release = - latest_github_release("gleam-lang/gleam", false, delegate.http_client()).await?; + latest_github_release("gleam-lang/gleam", true, false, delegate.http_client()).await?; let asset_name = format!( "gleam-{version}-{arch}-apple-darwin.tar.gz", diff --git a/crates/zed/src/languages/go.rs b/crates/zed/src/languages/go.rs index 12a63c3efee18f784c3c8bdc40713a51547b8952..5039cbe1e32725ca311e66ec1bf3d0a33f51333c 100644 --- a/crates/zed/src/languages/go.rs +++ b/crates/zed/src/languages/go.rs @@ -45,7 +45,8 @@ impl super::LspAdapter for GoLspAdapter { &self, delegate: &dyn LspAdapterDelegate, ) -> Result> { - let release = latest_github_release("golang/tools", false, delegate.http_client()).await?; + let release = + latest_github_release("golang/tools", false, false, delegate.http_client()).await?; let version: Option = release.name.strip_prefix("gopls/v").map(str::to_string); if version.is_none() { log::warn!( diff --git a/crates/zed/src/languages/lua.rs b/crates/zed/src/languages/lua.rs index c9753e0f6c1624642cf6aa506002acc6152b52d2..c25bb3d12576aac3f6f86b650b6f7e26d6e07b3a 100644 --- a/crates/zed/src/languages/lua.rs +++ b/crates/zed/src/languages/lua.rs @@ -30,15 +30,19 @@ impl super::LspAdapter for LuaLspAdapter { &self, delegate: &dyn LspAdapterDelegate, ) -> Result> { - let release = - latest_github_release("LuaLS/lua-language-server", false, delegate.http_client()) - .await?; - let version = release.name.clone(); let platform = match consts::ARCH { "x86_64" => "x64", "aarch64" => "arm64", other => bail!("Running on unsupported platform: {other}"), }; + let release = latest_github_release( + "LuaLS/lua-language-server", + true, + false, + delegate.http_client(), + ) + .await?; + let version = &release.name; let asset_name = format!("lua-language-server-{version}-darwin-{platform}.tar.gz"); let asset = release .assets @@ -46,7 +50,7 @@ impl super::LspAdapter for LuaLspAdapter { .find(|asset| asset.name == asset_name) .ok_or_else(|| anyhow!("no asset found matching {:?}", asset_name))?; let version = GitHubLspBinaryVersion { - name: release.name.clone(), + name: release.name, url: asset.browser_download_url.clone(), }; Ok(Box::new(version) as Box<_>) diff --git a/crates/zed/src/languages/rust.rs b/crates/zed/src/languages/rust.rs index ffbe706fe84c0fa18b714b33a2195f5625a5b382..bd00e9350cf8b416515bd5154d09b2da3885b8e1 100644 --- a/crates/zed/src/languages/rust.rs +++ b/crates/zed/src/languages/rust.rs @@ -31,8 +31,13 @@ impl LspAdapter for RustLspAdapter { &self, delegate: &dyn LspAdapterDelegate, ) -> Result> { - let release = - latest_github_release("rust-lang/rust-analyzer", false, delegate.http_client()).await?; + let release = latest_github_release( + "rust-lang/rust-analyzer", + true, + false, + delegate.http_client(), + ) + .await?; let asset_name = format!("rust-analyzer-{}-apple-darwin.gz", consts::ARCH); let asset = release .assets diff --git a/crates/zed/src/languages/toml.rs b/crates/zed/src/languages/toml.rs index 129b5fcb6603cdb1eaf0c31b0e061792dd3f764d..e16109be9a3e5c3f0145a711b0099c0a52f789a0 100644 --- a/crates/zed/src/languages/toml.rs +++ b/crates/zed/src/languages/toml.rs @@ -26,7 +26,8 @@ impl LspAdapter for TaploLspAdapter { &self, delegate: &dyn LspAdapterDelegate, ) -> Result> { - let release = latest_github_release("tamasfe/taplo", false, delegate.http_client()).await?; + let release = + latest_github_release("tamasfe/taplo", true, false, delegate.http_client()).await?; let asset_name = format!("taplo-full-darwin-{arch}.gz", arch = std::env::consts::ARCH); let asset = release diff --git a/crates/zed/src/languages/typescript.rs b/crates/zed/src/languages/typescript.rs index 08dc21965b64f0e452ad426e90ddf443da37ef85..ff83220922b75589f630972182c1c29f8c89bedd 100644 --- a/crates/zed/src/languages/typescript.rs +++ b/crates/zed/src/languages/typescript.rs @@ -246,8 +246,13 @@ impl LspAdapter for EsLintLspAdapter { // At the time of writing the latest vscode-eslint release was released in 2020 and requires // special custom LSP protocol extensions be handled to fully initialize. Download the latest // prerelease instead to sidestep this issue - let release = - latest_github_release("microsoft/vscode-eslint", true, delegate.http_client()).await?; + let release = latest_github_release( + "microsoft/vscode-eslint", + false, + false, + delegate.http_client(), + ) + .await?; Ok(Box::new(GitHubLspBinaryVersion { name: release.name, url: release.tarball_url, diff --git a/crates/zed/src/languages/zig.rs b/crates/zed/src/languages/zig.rs index 734d21e2eabf9f68a23267f8eca770edfc3ad795..8fac5c195fc1e83c411e85e9e440d01a88491015 100644 --- a/crates/zed/src/languages/zig.rs +++ b/crates/zed/src/languages/zig.rs @@ -28,8 +28,9 @@ impl LspAdapter for ZlsAdapter { &self, delegate: &dyn LspAdapterDelegate, ) -> Result> { - let release = latest_github_release("zigtools/zls", false, delegate.http_client()).await?; - let asset_name = format!("zls-{}-macos.tar.gz", ARCH); + let release = + latest_github_release("zigtools/zls", true, false, delegate.http_client()).await?; + let asset_name = format!("zls-{ARCH}-macos.tar.gz"); let asset = release .assets .iter()