Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions crates/cockpit-core/src/models/qoder.rs
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,8 @@ pub struct QoderAccountSummary {
#[serde(skip_serializing_if = "Option::is_none")]
pub user_id: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub display_name: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub plan_type: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub tags: Option<Vec<String>>,
Expand Down Expand Up @@ -89,6 +91,7 @@ impl QoderAccount {
id: self.id.clone(),
email: self.email.clone(),
user_id: self.user_id.clone(),
display_name: self.display_name.clone(),
plan_type: self.plan_type.clone(),
tags: self.tags.clone(),
created_at: self.created_at,
Expand Down
38 changes: 37 additions & 1 deletion crates/cockpit-core/src/modules/config.rs
Original file line number Diff line number Diff line change
Expand Up @@ -221,9 +221,18 @@ pub struct UserConfig {
/// CodeBuddy CN 启动路径(为空则使用默认路径)
#[serde(default = "default_codebuddy_cn_app_path")]
pub codebuddy_cn_app_path: String,
/// Qoder 启动路径(为空则使用默认路径)
/// Qoder 启动路径(国际版 IDE,为空则使用默认路径)
#[serde(default = "default_qoder_app_path")]
pub qoder_app_path: String,
/// Qoder 国际版 App / Launcher 启动路径
#[serde(default = "default_qoder_app_path")]
pub qoder_app_app_path: String,
/// Qoder 国内版 IDE 启动路径
#[serde(default = "default_qoder_app_path")]
pub qoder_cn_ide_app_path: String,
/// Qoder 国内版 App 启动路径
#[serde(default = "default_qoder_app_path")]
pub qoder_cn_app_path: String,
/// Trae 启动路径(为空则使用默认路径)
#[serde(default = "default_trae_app_path")]
pub trae_app_path: String,
Expand Down Expand Up @@ -846,6 +855,9 @@ impl Default for UserConfig {
codebuddy_share_sessions_on_switch: default_codebuddy_share_sessions_on_switch(),
codebuddy_cn_app_path: default_codebuddy_cn_app_path(),
qoder_app_path: default_qoder_app_path(),
qoder_app_app_path: default_qoder_app_path(),
qoder_cn_ide_app_path: default_qoder_app_path(),
qoder_cn_app_path: default_qoder_app_path(),
trae_app_path: default_trae_app_path(),
trae_solo_app_path: default_trae_app_path(),
trae_cn_app_path: default_trae_app_path(),
Expand Down Expand Up @@ -1659,6 +1671,30 @@ pub fn load_user_config() -> Result<UserConfig, String> {
}
});

// 自动感知探测 Qoder 4 个渠道的安装路径
let mut qoder_paths_detected = false;
let qoder_probes = [
(crate::modules::qoder_channel::QoderChannel::QoderIde, &mut config.qoder_app_path),
(crate::modules::qoder_channel::QoderChannel::QoderApp, &mut config.qoder_app_app_path),
(crate::modules::qoder_channel::QoderChannel::QoderCnIde, &mut config.qoder_cn_ide_app_path),
(crate::modules::qoder_channel::QoderChannel::QoderCnApp, &mut config.qoder_cn_app_path),
];
for (channel, path_ref) in qoder_probes {
let is_missing = path_ref.trim().is_empty() || !std::path::Path::new(path_ref.trim()).exists();
if is_missing {
if let Some(detected) = channel.detect_installed_exe() {
let detected_str = detected.to_string_lossy().to_string();
if *path_ref != detected_str {
*path_ref = detected_str;
qoder_paths_detected = true;
}
}
}
}
if qoder_paths_detected {
let _ = persist_user_config(&config);
}

Ok(config)
}

Expand Down
2 changes: 2 additions & 0 deletions crates/cockpit-core/src/modules/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,8 @@ pub mod oauth_pending_state;
// pub mod opencode_auth;
pub mod process;
pub mod qoder_account;
pub mod qoder_app_auth;
pub mod qoder_channel;
pub mod qoder_instance;
pub mod qoder_oauth;
pub mod quota;
Expand Down
5 changes: 4 additions & 1 deletion crates/cockpit-core/src/modules/process_core_discovery.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1168,7 +1168,10 @@ fn update_app_path_in_config(app: &str, path: &Path, expected_current: &str) {
"opencode" => &mut current.opencode_app_path,
"codebuddy" => &mut current.codebuddy_app_path,
"codebuddy_cn" => &mut current.codebuddy_cn_app_path,
"qoder" => &mut current.qoder_app_path,
"qoder" | "qoder_ide" => &mut current.qoder_app_path,
"qoder_app" => &mut current.qoder_app_app_path,
"qoder_cn_ide" => &mut current.qoder_cn_ide_app_path,
"qoder_cn_app" => &mut current.qoder_cn_app_path,
"trae" => &mut current.trae_app_path,
"workbuddy" => &mut current.workbuddy_app_path,
_ => return Ok(()),
Expand Down
33 changes: 26 additions & 7 deletions crates/cockpit-core/src/modules/process_core_matching.rs
Original file line number Diff line number Diff line change
Expand Up @@ -459,13 +459,32 @@ pub fn detect_and_save_app_path(app: &str, force: bool) -> Option<String> {
return Some(config::get_user_config().codebuddy_cn_app_path);
}
}
"qoder" => {
if !force && !current.qoder_app_path.trim().is_empty() {
return Some(current.qoder_app_path);
}
if let Some(detected) = detect_qoder_exec_path() {
update_app_path_in_config("qoder", &detected, &current.qoder_app_path);
return Some(config::get_user_config().qoder_app_path);
"qoder" | "qoder_ide" | "qoder_app" | "qoder_cn_ide" | "qoder_cn_app" => {
let channel = match app {
"qoder_app" => crate::modules::qoder_channel::QoderChannel::QoderApp,
"qoder_cn_ide" => crate::modules::qoder_channel::QoderChannel::QoderCnIde,
"qoder_cn_app" => crate::modules::qoder_channel::QoderChannel::QoderCnApp,
_ => crate::modules::qoder_channel::QoderChannel::QoderIde,
};
let configured = match channel {
crate::modules::qoder_channel::QoderChannel::QoderIde => current.qoder_app_path.clone(),
crate::modules::qoder_channel::QoderChannel::QoderApp => current.qoder_app_app_path.clone(),
crate::modules::qoder_channel::QoderChannel::QoderCnIde => current.qoder_cn_ide_app_path.clone(),
crate::modules::qoder_channel::QoderChannel::QoderCnApp => current.qoder_cn_app_path.clone(),
};
if !force && !configured.trim().is_empty() {
return Some(configured);
}
if let Some(detected) = channel.detect_installed_exe() {
update_app_path_in_config(app, &detected, &configured);
let refreshed = config::get_user_config();
let refreshed_val = match channel {
crate::modules::qoder_channel::QoderChannel::QoderIde => refreshed.qoder_app_path,
crate::modules::qoder_channel::QoderChannel::QoderApp => refreshed.qoder_app_app_path,
crate::modules::qoder_channel::QoderChannel::QoderCnIde => refreshed.qoder_cn_ide_app_path,
crate::modules::qoder_channel::QoderChannel::QoderCnApp => refreshed.qoder_cn_app_path,
};
return Some(refreshed_val);
}
}
"trae" => {
Expand Down
Loading
Loading