762 lines · 27.9 KB · Rust
RawDownload
use collections::{HashMap, IndexMap};use schemars::{JsonSchema, json_schema};use serde::{Deserialize, Serialize};use settings_macros::{MergeFrom, with_fallible_options};use std::sync::Arc;use std::{borrow::Cow, path::PathBuf}; use crate::ExtendingVec; use crate::DockPosition; /// Where new threads should start by default.#[derive(    Clone,    Copy,    Debug,    Default,    PartialEq,    Eq,    Serialize,    Deserialize,    JsonSchema,    MergeFrom,    strum::VariantArray,    strum::VariantNames,)]#[serde(rename_all = "snake_case")]pub enum NewThreadLocation {    /// Start threads in the current project.    #[default]    LocalProject,    /// Start threads in a new worktree.    NewWorktree,} #[with_fallible_options]#[derive(Clone, PartialEq, Serialize, Deserialize, JsonSchema, MergeFrom, Debug, Default)]pub struct AgentSettingsContent {    /// Whether the Agent is enabled.    ///    /// Default: true    pub enabled: Option<bool>,    /// Whether to show the agent panel button in the status bar.    ///    /// Default: true    pub button: Option<bool>,    /// Where to dock the agent panel.    ///    /// Default: right    pub dock: Option<DockPosition>,    /// Default width in pixels when the agent panel is docked to the left or right.    ///    /// Default: 640    #[serde(serialize_with = "crate::serialize_optional_f32_with_two_decimal_places")]    pub default_width: Option<f32>,    /// Default height in pixels when the agent panel is docked to the bottom.    ///    /// Default: 320    #[serde(serialize_with = "crate::serialize_optional_f32_with_two_decimal_places")]    pub default_height: Option<f32>,    /// The default model to use when creating new chats and for other features when a specific model is not specified.    pub default_model: Option<LanguageModelSelection>,    /// Favorite models to show at the top of the model selector.    #[serde(default)]    pub favorite_models: Vec<LanguageModelSelection>,    /// Model to use for the inline assistant. Defaults to default_model when not specified.    pub inline_assistant_model: Option<LanguageModelSelection>,    /// Model to use for the inline assistant when streaming tools are enabled.    ///    /// Default: true    pub inline_assistant_use_streaming_tools: Option<bool>,    /// Model to use for generating git commit messages. Defaults to default_model when not specified.    pub commit_message_model: Option<LanguageModelSelection>,    /// Model to use for generating thread summaries. Defaults to default_model when not specified.    pub thread_summary_model: Option<LanguageModelSelection>,    /// Additional models with which to generate alternatives when performing inline assists.    pub inline_alternatives: Option<Vec<LanguageModelSelection>>,    /// The default profile to use in the Agent.    ///    /// Default: write    pub default_profile: Option<Arc<str>>,    /// Which view type to show by default in the agent panel.    ///    /// Default: "thread"    pub default_view: Option<DefaultAgentView>,    /// Where new threads should start by default.    ///    /// Default: "local_project"    pub new_thread_location: Option<NewThreadLocation>,    /// The available agent profiles.    pub profiles: Option<IndexMap<Arc<str>, AgentProfileContent>>,    /// Where to show a popup notification when the agent is waiting for user input.    ///    /// Default: "primary_screen"    pub notify_when_agent_waiting: Option<NotifyWhenAgentWaiting>,    /// Whether to play a sound when the agent has either completed its response, or needs user input.    ///    /// Default: false    pub play_sound_when_agent_done: Option<bool>,    /// Whether to display agent edits in single-file editors in addition to the review multibuffer pane.    ///    /// Default: true    pub single_file_review: Option<bool>,    /// Additional parameters for language model requests. When making a request    /// to a model, parameters will be taken from the last entry in this list    /// that matches the model's provider and name. In each entry, both provider    /// and model are optional, so that you can specify parameters for either    /// one.    ///    /// Default: []    #[serde(default)]    pub model_parameters: Vec<LanguageModelParameters>,    /// Whether to show thumb buttons for feedback in the agent panel.    ///    /// Default: true    pub enable_feedback: Option<bool>,    /// Whether to have edit cards in the agent panel expanded, showing a preview of the full diff.    ///    /// Default: true    pub expand_edit_card: Option<bool>,    /// Whether to have terminal cards in the agent panel expanded, showing the whole command output.    ///    /// Default: true    pub expand_terminal_card: Option<bool>,    /// Whether clicking the stop button on a running terminal tool should also cancel the agent's generation.    /// Note that this only applies to the stop button, not to ctrl+c inside the terminal.    ///    /// Default: true    pub cancel_generation_on_terminal_stop: Option<bool>,    /// Whether to always use cmd-enter (or ctrl-enter on Linux or Windows) to send messages in the agent panel.    ///    /// Default: false    pub use_modifier_to_send: Option<bool>,    /// Minimum number of lines of height the agent message editor should have.    ///    /// Default: 4    pub message_editor_min_lines: Option<usize>,    /// Whether to show turn statistics (elapsed time during generation, final turn duration).    ///    /// Default: false    pub show_turn_stats: Option<bool>,    /// Per-tool permission rules for granular control over which tool actions    /// require confirmation.    ///    /// The global `default` applies when no tool-specific rules match.    /// For external agent servers (e.g. Claude Agent) that define their own    /// permission modes, "deny" and "confirm" still take precedence — the    /// external agent's permission system is only used when Zed would allow    /// the action. Per-tool regex patterns (`always_allow`, `always_deny`,    /// `always_confirm`) match against the tool's text input (command, path,    /// URL, etc.).    pub tool_permissions: Option<ToolPermissionsContent>,} impl AgentSettingsContent {    pub fn set_dock(&mut self, dock: DockPosition) {        self.dock = Some(dock);    }     pub fn set_model(&mut self, language_model: LanguageModelSelection) {        self.default_model = Some(language_model)    }     pub fn set_inline_assistant_model(&mut self, provider: String, model: String) {        self.inline_assistant_model = Some(LanguageModelSelection {            provider: provider.into(),            model,            enable_thinking: false,            effort: None,        });    }     pub fn set_profile(&mut self, profile_id: Arc<str>) {        self.default_profile = Some(profile_id);    }     pub fn set_new_thread_location(&mut self, value: NewThreadLocation) {        self.new_thread_location = Some(value);    }     pub fn add_favorite_model(&mut self, model: LanguageModelSelection) {        if !self.favorite_models.contains(&model) {            self.favorite_models.push(model);        }    }     pub fn remove_favorite_model(&mut self, model: &LanguageModelSelection) {        self.favorite_models.retain(|m| m != model);    }     pub fn set_tool_default_permission(&mut self, tool_id: &str, mode: ToolPermissionMode) {        let tool_permissions = self.tool_permissions.get_or_insert_default();        let tool_rules = tool_permissions            .tools            .entry(Arc::from(tool_id))            .or_default();        tool_rules.default = Some(mode);    }     pub fn add_tool_allow_pattern(&mut self, tool_name: &str, pattern: String) {        let tool_permissions = self.tool_permissions.get_or_insert_default();        let tool_rules = tool_permissions            .tools            .entry(Arc::from(tool_name))            .or_default();        let always_allow = tool_rules.always_allow.get_or_insert_default();        if !always_allow.0.iter().any(|r| r.pattern == pattern) {            always_allow.0.push(ToolRegexRule {                pattern,                case_sensitive: None,            });        }    }     pub fn add_tool_deny_pattern(&mut self, tool_name: &str, pattern: String) {        let tool_permissions = self.tool_permissions.get_or_insert_default();        let tool_rules = tool_permissions            .tools            .entry(Arc::from(tool_name))            .or_default();        let always_deny = tool_rules.always_deny.get_or_insert_default();        if !always_deny.0.iter().any(|r| r.pattern == pattern) {            always_deny.0.push(ToolRegexRule {                pattern,                case_sensitive: None,            });        }    }} #[with_fallible_options]#[derive(Debug, PartialEq, Clone, Serialize, Deserialize, JsonSchema, MergeFrom)]pub struct AgentProfileContent {    pub name: Arc<str>,    #[serde(default)]    pub tools: IndexMap<Arc<str>, bool>,    /// Whether all context servers are enabled by default.    pub enable_all_context_servers: Option<bool>,    #[serde(default)]    pub context_servers: IndexMap<Arc<str>, ContextServerPresetContent>,    /// The default language model selected when using this profile.    pub default_model: Option<LanguageModelSelection>,} #[with_fallible_options]#[derive(Debug, PartialEq, Clone, Default, Serialize, Deserialize, JsonSchema, MergeFrom)]pub struct ContextServerPresetContent {    pub tools: IndexMap<Arc<str>, bool>,} #[derive(Copy, Clone, Default, Debug, PartialEq, Serialize, Deserialize, JsonSchema, MergeFrom)]#[serde(rename_all = "snake_case")]pub enum DefaultAgentView {    #[default]    Thread,    TextThread,} #[derive(    Copy,    Clone,    Default,    Debug,    Serialize,    Deserialize,    JsonSchema,    MergeFrom,    PartialEq,    strum::VariantArray,    strum::VariantNames,)]#[serde(rename_all = "snake_case")]pub enum NotifyWhenAgentWaiting {    #[default]    PrimaryScreen,    AllScreens,    Never,} #[with_fallible_options]#[derive(Clone, Debug, Serialize, Deserialize, JsonSchema, MergeFrom, PartialEq)]pub struct LanguageModelSelection {    pub provider: LanguageModelProviderSetting,    pub model: String,    #[serde(default)]    pub enable_thinking: bool,    pub effort: Option<String>,} #[with_fallible_options]#[derive(Clone, Debug, Serialize, Deserialize, JsonSchema, MergeFrom, PartialEq)]pub struct LanguageModelParameters {    pub provider: Option<LanguageModelProviderSetting>,    pub model: Option<String>,    #[serde(serialize_with = "crate::serialize_optional_f32_with_two_decimal_places")]    pub temperature: Option<f32>,} #[derive(Clone, Debug, Serialize, Deserialize, PartialEq, MergeFrom)]pub struct LanguageModelProviderSetting(pub String); impl JsonSchema for LanguageModelProviderSetting {    fn schema_name() -> Cow<'static, str> {        "LanguageModelProviderSetting".into()    }     fn json_schema(_: &mut schemars::SchemaGenerator) -> schemars::Schema {        // list the builtin providers as a subset so that we still auto complete them in the settings        json_schema!({            "anyOf": [                {                    "type": "string",                    "enum": [                        "amazon-bedrock",                        "anthropic",                        "copilot_chat",                        "deepseek",                        "google",                        "lmstudio",                        "mistral",                        "ollama",                        "openai",                        "openrouter",                        "vercel",                        "vercel_ai_gateway",                        "x_ai",                        "zed.dev"                    ]                },                {                    "type": "string",                }            ]        })    }} impl From<String> for LanguageModelProviderSetting {    fn from(provider: String) -> Self {        Self(provider)    }} impl From<&str> for LanguageModelProviderSetting {    fn from(provider: &str) -> Self {        Self(provider.to_string())    }} #[with_fallible_options]#[derive(Default, PartialEq, Deserialize, Serialize, Clone, JsonSchema, MergeFrom, Debug)]#[serde(transparent)]pub struct AllAgentServersSettings(pub HashMap<String, CustomAgentServerSettings>); impl std::ops::Deref for AllAgentServersSettings {    type Target = HashMap<String, CustomAgentServerSettings>;     fn deref(&self) -> &Self::Target {        &self.0    }} impl std::ops::DerefMut for AllAgentServersSettings {    fn deref_mut(&mut self) -> &mut Self::Target {        &mut self.0    }} #[with_fallible_options]#[derive(Deserialize, Serialize, Clone, JsonSchema, MergeFrom, Debug, PartialEq)]#[serde(tag = "type", rename_all = "snake_case")]pub enum CustomAgentServerSettings {    Custom {        #[serde(rename = "command")]        path: PathBuf,        #[serde(default, skip_serializing_if = "Vec::is_empty")]        args: Vec<String>,        /// Default: {}        #[serde(default, skip_serializing_if = "HashMap::is_empty")]        env: HashMap<String, String>,        /// The default mode to use for this agent.        ///        /// Note: Not only all agents support modes.        ///        /// Default: None        default_mode: Option<String>,        /// The default model to use for this agent.        ///        /// This should be the model ID as reported by the agent.        ///        /// Default: None        default_model: Option<String>,        /// The favorite models for this agent.        ///        /// These are the model IDs as reported by the agent.        ///        /// Default: []        #[serde(default, skip_serializing_if = "Vec::is_empty")]        favorite_models: Vec<String>,        /// Default values for session config options.        ///        /// This is a map from config option ID to value ID.        ///        /// Default: {}        #[serde(default, skip_serializing_if = "HashMap::is_empty")]        default_config_options: HashMap<String, String>,        /// Favorited values for session config options.        ///        /// This is a map from config option ID to a list of favorited value IDs.        ///        /// Default: {}        #[serde(default, skip_serializing_if = "HashMap::is_empty")]        favorite_config_option_values: HashMap<String, Vec<String>>,    },    Extension {        /// Additional environment variables to pass to the agent.        ///        /// Default: {}        #[serde(default, skip_serializing_if = "HashMap::is_empty")]        env: HashMap<String, String>,        /// The default mode to use for this agent.        ///        /// Note: Not only all agents support modes.        ///        /// Default: None        default_mode: Option<String>,        /// The default model to use for this agent.        ///        /// This should be the model ID as reported by the agent.        ///        /// Default: None        default_model: Option<String>,        /// The favorite models for this agent.        ///        /// These are the model IDs as reported by the agent.        ///        /// Default: []        #[serde(default, skip_serializing_if = "Vec::is_empty")]        favorite_models: Vec<String>,        /// Default values for session config options.        ///        /// This is a map from config option ID to value ID.        ///        /// Default: {}        #[serde(default, skip_serializing_if = "HashMap::is_empty")]        default_config_options: HashMap<String, String>,        /// Favorited values for session config options.        ///        /// This is a map from config option ID to a list of favorited value IDs.        ///        /// Default: {}        #[serde(default, skip_serializing_if = "HashMap::is_empty")]        favorite_config_option_values: HashMap<String, Vec<String>>,    },    Registry {        /// Additional environment variables to pass to the agent.        ///        /// Default: {}        #[serde(default, skip_serializing_if = "HashMap::is_empty")]        env: HashMap<String, String>,        /// The default mode to use for this agent.        ///        /// Note: Not only all agents support modes.        ///        /// Default: None        default_mode: Option<String>,        /// The default model to use for this agent.        ///        /// This should be the model ID as reported by the agent.        ///        /// Default: None        default_model: Option<String>,        /// The favorite models for this agent.        ///        /// These are the model IDs as reported by the agent.        ///        /// Default: []        #[serde(default, skip_serializing_if = "Vec::is_empty")]        favorite_models: Vec<String>,        /// Default values for session config options.        ///        /// This is a map from config option ID to value ID.        ///        /// Default: {}        #[serde(default, skip_serializing_if = "HashMap::is_empty")]        default_config_options: HashMap<String, String>,        /// Favorited values for session config options.        ///        /// This is a map from config option ID to a list of favorited value IDs.        ///        /// Default: {}        #[serde(default, skip_serializing_if = "HashMap::is_empty")]        favorite_config_option_values: HashMap<String, Vec<String>>,    },} #[with_fallible_options]#[derive(Clone, Debug, Default, PartialEq, Serialize, Deserialize, JsonSchema, MergeFrom)]pub struct ToolPermissionsContent {    /// Global default permission when no tool-specific rules match.

Lines 1–500 of 762.