feat: 配置回退到 ~/.ias/ 目录
配置加载顺序(当前目录 → 全局目录 → 默认): 1. .env → ~/.ias/.env → 无 2. config.json → ~/.ias/config.json → 默认内置 3. resources/skills/ (始终从项目目录加载) 现在可以在任意目录运行 ias,如: cd /tmp && ias whoami # 读取 ~/.ias/ 的配置
This commit is contained in:
+32
-13
@@ -142,27 +142,46 @@ impl Default for AppConfig {
|
||||
|
||||
impl AppConfig {
|
||||
/// 从文件加载配置,缺失字段回退到环境变量
|
||||
/// 尝试顺序:path → ~/.ias/config.json → 默认
|
||||
pub fn from_file(path: impl AsRef<Path>) -> Self {
|
||||
let path = path.as_ref();
|
||||
|
||||
// 尝试指定路径
|
||||
if path.exists() {
|
||||
match std::fs::read_to_string(path) {
|
||||
Ok(content) => {
|
||||
// 先做环境变量替换
|
||||
let resolved = resolve_env_vars(&content);
|
||||
match serde_json::from_str(&resolved) {
|
||||
Ok(cfg) => return cfg,
|
||||
Err(e) => {
|
||||
tracing::warn!("解析配置文件失败 ({}): {},使用默认配置", path.display(), e);
|
||||
}
|
||||
}
|
||||
}
|
||||
Err(e) => {
|
||||
tracing::warn!("读取配置文件失败 ({}): {},使用默认配置", path.display(), e);
|
||||
match Self::try_load(path) {
|
||||
Some(cfg) => return cfg,
|
||||
None => tracing::warn!("解析配置文件失败: {},尝试回退", path.display()),
|
||||
}
|
||||
}
|
||||
|
||||
// 回退到 ~/.ias/config.json
|
||||
let home = dirs::home_dir();
|
||||
if let Some(home) = home {
|
||||
let fallback = home.join(".ias").join("config.json");
|
||||
if fallback.exists() {
|
||||
tracing::info!("使用全局配置: {}", fallback.display());
|
||||
match Self::try_load(&fallback) {
|
||||
Some(cfg) => return cfg,
|
||||
None => tracing::warn!("解析全局配置失败: {}", fallback.display()),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
tracing::info!("使用默认配置");
|
||||
Self::default()
|
||||
}
|
||||
|
||||
fn try_load(path: &Path) -> Option<Self> {
|
||||
let content = std::fs::read_to_string(path).ok()?;
|
||||
let resolved = resolve_env_vars(&content);
|
||||
match serde_json::from_str(&resolved) {
|
||||
Ok(cfg) => Some(cfg),
|
||||
Err(e) => {
|
||||
tracing::warn!("解析配置文件失败 ({}): {}", path.display(), e);
|
||||
None
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// 替换字符串中的 `${VAR_NAME}` 为环境变量值
|
||||
|
||||
+10
-1
@@ -28,7 +28,16 @@ async fn main() {
|
||||
let is_service = matches!(cli.command, Commands::Service);
|
||||
logger::init_logger(Some(".data/logs"), is_service);
|
||||
|
||||
dotenvy::dotenv().ok();
|
||||
// .env 加载:先当前目录,再 ~/.ias/.env
|
||||
if std::path::Path::new(".env").exists() {
|
||||
dotenvy::dotenv().ok();
|
||||
} else if let Ok(home) = std::env::var("HOME") {
|
||||
let fallback = std::path::PathBuf::from(&home).join(".ias").join(".env");
|
||||
if fallback.exists() {
|
||||
dotenvy::from_path(&fallback).ok();
|
||||
tracing::info!("使用全局环境配置: {}", fallback.display());
|
||||
}
|
||||
}
|
||||
|
||||
let config = AppConfig::from_file("config.json");
|
||||
|
||||
|
||||
Reference in New Issue
Block a user