@@ -2636,11 +2636,10 @@ impl LspCommand for GetCodeActions {
relevant_diagnostics.push(entry.to_lsp_diagnostic_stub()?);
}
- let supported =
- Self::supported_code_action_kinds(language_server.adapter_server_capabilities());
-
let only = if let Some(requested) = &self.kinds {
- if let Some(supported_kinds) = supported {
+ if let Some(supported_kinds) =
+ Self::supported_code_action_kinds(language_server.adapter_server_capabilities())
+ {
let filtered = requested
.iter()
.filter(|requested_kind| {
@@ -2655,7 +2654,7 @@ impl LspCommand for GetCodeActions {
Some(requested.clone())
}
} else {
- supported
+ None
};
Ok(lsp::CodeActionParams {
@@ -7755,6 +7755,92 @@ async fn test_code_actions_only_kinds(cx: &mut gpui::TestAppContext) {
);
}
+#[gpui::test]
+async fn test_code_actions_without_requested_kinds_do_not_send_only_filter(
+ cx: &mut gpui::TestAppContext,
+) {
+ init_test(cx);
+
+ let fs = FakeFs::new(cx.executor());
+ fs.insert_tree(
+ path!("/dir"),
+ json!({
+ "a.ts": "a",
+ }),
+ )
+ .await;
+
+ let project = Project::test(fs, [path!("/dir").as_ref()], cx).await;
+
+ let language_registry = project.read_with(cx, |project, _| project.languages().clone());
+ language_registry.add(typescript_lang());
+ let mut fake_language_servers = language_registry.register_fake_lsp(
+ "TypeScript",
+ FakeLspAdapter {
+ capabilities: lsp::ServerCapabilities {
+ code_action_provider: Some(lsp::CodeActionProviderCapability::Options(
+ lsp::CodeActionOptions {
+ code_action_kinds: Some(vec![
+ CodeActionKind::SOURCE_ORGANIZE_IMPORTS,
+ "source.doc".into(),
+ ]),
+ ..lsp::CodeActionOptions::default()
+ },
+ )),
+ ..lsp::ServerCapabilities::default()
+ },
+ ..FakeLspAdapter::default()
+ },
+ );
+
+ let (buffer, _handle) = project
+ .update(cx, |p, cx| {
+ p.open_local_buffer_with_lsp(path!("/dir/a.ts"), cx)
+ })
+ .await
+ .unwrap();
+ cx.executor().run_until_parked();
+
+ let fake_server = fake_language_servers
+ .next()
+ .await
+ .expect("failed to get the language server");
+
+ let mut request_handled = fake_server.set_request_handler::<
+ lsp::request::CodeActionRequest,
+ _,
+ _,
+ >(move |params, _| async move {
+ assert_eq!(
+ params.context.only, None,
+ "Code action requests without explicit kind filters should not send `context.only`"
+ );
+ Ok(Some(vec![lsp::CodeActionOrCommand::CodeAction(
+ lsp::CodeAction {
+ title: "Add test".to_string(),
+ kind: Some("source.addTest".into()),
+ ..lsp::CodeAction::default()
+ },
+ )]))
+ });
+
+ let code_actions_task = project.update(cx, |project, cx| {
+ project.code_actions(&buffer, 0..buffer.read(cx).len(), None, cx)
+ });
+
+ let () = request_handled
+ .next()
+ .await
+ .expect("The code action request should have been triggered");
+
+ let code_actions = code_actions_task.await.unwrap().unwrap();
+ assert_eq!(code_actions.len(), 1);
+ assert_eq!(
+ code_actions[0].lsp_action.action_kind(),
+ Some("source.addTest".into())
+ );
+}
+
#[gpui::test]
async fn test_multiple_language_server_actions(cx: &mut gpui::TestAppContext) {
init_test(cx);