Cargo.lock 🔗
@@ -6819,7 +6819,6 @@ dependencies = [
"regex",
"rope",
"rust-embed",
- "schemars",
"serde",
"serde_json",
"settings",
Michael Sloan created
Release Notes:
- N/A
Cargo.lock | 1
crates/languages/Cargo.toml | 1
crates/languages/src/json.rs | 14 -----
crates/settings/src/keymap_file.rs | 14 +++++
crates/zed/src/zed.rs | 67 ++++++++++++++++++++++++++++++++
5 files changed, 81 insertions(+), 16 deletions(-)
@@ -6819,7 +6819,6 @@ dependencies = [
"regex",
"rope",
"rust-embed",
- "schemars",
"serde",
"serde_json",
"settings",
@@ -56,7 +56,6 @@ project.workspace = true
regex.workspace = true
rope.workspace = true
rust-embed.workspace = true
-schemars.workspace = true
serde.workspace = true
serde_json.workspace = true
settings.workspace = true
@@ -10,7 +10,6 @@ use language::{LanguageRegistry, LanguageToolchainStore, LspAdapter, LspAdapterD
use lsp::{LanguageServerBinary, LanguageServerName};
use node_runtime::NodeRuntime;
use project::{lsp_store::language_server_settings, ContextProviderWithTasks};
-use schemars::gen::SchemaSettings;
use serde_json::{json, Value};
use settings::{KeymapFile, SettingsJsonSchemaParams, SettingsStore};
use smol::{
@@ -76,6 +75,7 @@ impl JsonLspAdapter {
}
fn get_workspace_config(language_names: Vec<String>, cx: &mut AppContext) -> Value {
+ let keymap_schema = KeymapFile::generate_json_schema_for_registered_actions(cx);
let font_names = &cx.text_system().all_font_names();
let settings_schema = cx.global::<SettingsStore>().json_schema(
&SettingsJsonSchemaParams {
@@ -115,7 +115,7 @@ impl JsonLspAdapter {
},
{
"fileMatch": [schema_file_match(paths::keymap_file())],
- "schema": Self::generate_keymap_schema(cx),
+ "schema": keymap_schema,
},
{
"fileMatch": [
@@ -129,16 +129,6 @@ impl JsonLspAdapter {
}
})
}
-
- fn generate_keymap_schema(cx: &mut AppContext) -> Value {
- let mut generator = SchemaSettings::draft07()
- .with(|settings| settings.option_add_null_type = false)
- .into_generator();
-
- let action_schemas = cx.action_schemas(&mut generator);
- let deprecations = cx.action_deprecations();
- KeymapFile::generate_json_schema(generator, action_schemas, deprecations)
- }
}
#[async_trait(?Send)]
@@ -3,7 +3,7 @@ use anyhow::{anyhow, Context, Result};
use collections::{BTreeMap, HashMap};
use gpui::{Action, AppContext, KeyBinding, SharedString};
use schemars::{
- gen::SchemaGenerator,
+ gen::{SchemaGenerator, SchemaSettings},
schema::{ArrayValidation, InstanceType, Metadata, Schema, SchemaObject, SubschemaValidation},
JsonSchema,
};
@@ -139,7 +139,17 @@ impl KeymapFile {
Ok(())
}
- pub fn generate_json_schema(
+ pub fn generate_json_schema_for_registered_actions(cx: &mut AppContext) -> Value {
+ let mut generator = SchemaSettings::draft07()
+ .with(|settings| settings.option_add_null_type = false)
+ .into_generator();
+
+ let action_schemas = cx.action_schemas(&mut generator);
+ let deprecations = cx.action_deprecations();
+ KeymapFile::generate_json_schema(generator, action_schemas, deprecations)
+ }
+
+ fn generate_json_schema(
generator: SchemaGenerator,
action_schemas: Vec<(SharedString, Option<Schema>)>,
deprecations: &HashMap<SharedString, SharedString>,
@@ -3502,6 +3502,73 @@ mod tests {
assert_key_bindings_for(workspace.into(), cx, vec![("6", &Deploy)], line!());
}
+ #[gpui::test]
+ async fn test_generate_keymap_json_schema_for_registered_actions(
+ cx: &mut gpui::TestAppContext,
+ ) {
+ init_keymap_test(cx);
+ cx.update(|cx| {
+ // Make sure it doesn't panic.
+ KeymapFile::generate_json_schema_for_registered_actions(cx);
+ });
+ }
+
+ /// Actions that don't build from empty input won't work from command palette invocation.
+ #[gpui::test]
+ async fn test_actions_build_with_empty_input(cx: &mut gpui::TestAppContext) {
+ init_keymap_test(cx);
+ cx.update(|cx| {
+ let all_actions = cx.all_action_names();
+ let mut failing_names = Vec::new();
+ let mut errors = Vec::new();
+ for action in all_actions {
+ match action.to_string().as_str() {
+ "vim::FindCommand"
+ | "vim::Literal"
+ | "vim::ResizePane"
+ | "vim::SwitchMode"
+ | "vim::PushOperator"
+ | "vim::Number"
+ | "vim::SelectRegister"
+ | "terminal::SendText"
+ | "terminal::SendKeystroke"
+ | "app_menu::OpenApplicationMenu"
+ | "app_menu::NavigateApplicationMenuInDirection"
+ | "picker::ConfirmInput"
+ | "editor::HandleInput"
+ | "editor::FoldAtLevel"
+ | "pane::ActivateItem"
+ | "workspace::ActivatePane"
+ | "workspace::ActivatePaneInDirection"
+ | "workspace::MoveItemToPane"
+ | "workspace::MoveItemToPaneInDirection"
+ | "workspace::OpenTerminal"
+ | "workspace::SwapPaneInDirection"
+ | "workspace::SendKeystrokes"
+ | "zed::OpenBrowser"
+ | "zed::OpenZedUrl" => {}
+ _ => {
+ let result = cx.build_action(action, None);
+ match &result {
+ Ok(_) => {}
+ Err(err) => {
+ failing_names.push(action);
+ errors.push(format!("{action} failed to build: {err:?}"));
+ }
+ }
+ }
+ }
+ }
+ if errors.len() > 0 {
+ panic!(
+ "Failed to build actions using {{}} as input: {:?}. Errors:\n{}",
+ failing_names,
+ errors.join("\n")
+ );
+ }
+ });
+ }
+
#[gpui::test]
fn test_bundled_settings_and_themes(cx: &mut AppContext) {
cx.text_system()