新增: 初始化 DevFlow 项目仓库

Tauri 2 + Vue 3 + Vite 6 桌面应用,Rust workspace 含 13 个 crate
(df-ai / df-storage / df-workflow / df-core / df-execute 等)。
核心能力:AI 聊天 agentic 循环(工具调用+人工审批)、工作流引擎、
任务/想法/项目/阶段管理、可追溯性,及配套前端组件。
This commit is contained in:
2026-06-12 01:31:05 +08:00
commit 98393b4908
178 changed files with 27859 additions and 0 deletions

View File

@@ -0,0 +1,73 @@
//! Shell 执行器 — 通过 tokio::process 执行 shell 命令
use serde::{Deserialize, Serialize};
/// Shell 命令执行结果
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct ShellResult {
/// 标准输出
pub stdout: String,
/// 标准错误
pub stderr: String,
/// 退出码
pub exit_code: Option<i32>,
/// 执行耗时(毫秒)
pub duration_ms: u64,
}
/// Shell 命令执行请求
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct ShellRequest {
/// 要执行的命令
pub command: String,
/// 工作目录
pub working_dir: Option<String>,
/// 环境变量
pub env: std::collections::HashMap<String, String>,
/// 超时时间None 表示不超时
pub timeout_secs: Option<u64>,
}
/// 执行 Shell 命令
///
/// TODO: 完整实现,支持超时、环境变量、工作目录等
pub async fn execute(request: ShellRequest) -> anyhow::Result<ShellResult> {
let start = std::time::Instant::now();
let mut cmd = if cfg!(windows) {
let mut c = tokio::process::Command::new("cmd");
c.arg("/C").arg(&request.command);
c
} else {
let mut c = tokio::process::Command::new("sh");
c.arg("-c").arg(&request.command);
c
};
if let Some(dir) = &request.working_dir {
cmd.current_dir(dir);
}
for (key, value) in &request.env {
cmd.env(key, value);
}
let output = match request.timeout_secs {
Some(secs) => tokio::time::timeout(
std::time::Duration::from_secs(secs),
cmd.output(),
)
.await
.map_err(|_| anyhow::anyhow!("命令执行超时: {}秒", secs))??,
None => cmd.output().await?,
};
let duration = start.elapsed().as_millis() as u64;
Ok(ShellResult {
stdout: String::from_utf8_lossy(&output.stdout).to_string(),
stderr: String::from_utf8_lossy(&output.stderr).to_string(),
exit_code: output.status.code(),
duration_ms: duration,
})
}