SkillLite 自进化 Agent:五层门控 + OS 级沙箱,让「越用越强」可审计、可回滚
摘要
自进化 AI 在 Agent 层体现为规则、记忆与可执行技能的持续沉淀,但若缺少硬边界,「优化任务完成率」可能演化为危险捷径。开源项目 SkillLite 采用「不可变 Rust 内核 + 可进化本地数据层」:进化产物仅允许写入受控目录,并依次经过路径白名单、变更幅度、敏感信息扫描、静态代码模式检测与 OS 级沙箱试运行。本文结合架构图与演进流程图,说明五层 Gatekeeper 的设计意图,并给出进化互斥与生命周期相关的源码锚点,便于读者对照仓库自行验证。
目录
- 一、问题背景:自进化不是单一功能
- 二、架构总览:不可变层与可进化层
- 三、进化三维度与数据落点
- 四、五层 Gatekeeper 与 L5 沙箱
- 五、从反馈到落盘:流程说明
- 六、并发控制与频率约束(代码)
- 七、验证与生态:EvoTown
- 八、小结
- 参考与链接
一、问题背景:自进化不是单一功能
当 Agent 能在多步工具链上稳定运行时,「根据历史任务自动改进策略」自然成为产品方向。但自进化引入了三类典型风险:
- 目标漂移:优化指标若只有「完成任务」,系统可能学会未预期的捷径(例如破坏性清理)。
- 产物不可解释:自动生成的技能目录中的脚本,在真正被调用前难以被人工完整审计。
- 难以回滚:规则、记忆、技能相互引用,若无版本与事件日志,出问题后无法定位是哪一次进化引入回归。
因此,自进化的工程化前提是:明确「哪里可以变」、「怎么变才允许落地」、「如何追溯与撤销」。SkillLite 的选择是把「会变」的边界严格限制在本地 chat/ 数据层,并用多层门控把「允许写入」变成可测试、可审计的流程。
二、架构总览:不可变层与可进化层
核心思想可以用一张分层图概括:Brain / Core / Sandbox 编译进二进制,不在运行时被 Agent 自修改;进化只发生在数据目录。
读图要点:
- 安全基线随二进制发布,不依赖「模型承诺不改内核」这类软约束。
- 进化写入路径与沙箱执行能力解耦又协同:静态规则过滤不完备时,仍可用 OS 级隔离观察实际行为。
三、进化三维度与数据落点
SkillLite 将 Agent 自进化拆为三个可观测维度,便于分别限幅、记录与回滚:
| 进化维度 | 含义(简述) | 典型落点 |
|---|---|---|
| Prompts / Rules | 规划与执行策略、few-shot 等 | chat/prompts/ 等 |
| Memory | 跨会话结构化经验、检索增强 | chat/memory/ |
| Skills | 可复用工具代码,含自动生成与精炼 | chat/skills/(进化产物常在 _evolved/) |
触发往往与结构化 decisions 数据相关:任务结束后的工具成败、重规划次数、耗时等进入反馈通道,达到阈值后异步启动进化。这样「变强」来自真实运行数据,而不是单次对话的偶然输出。
四、五层 Gatekeeper 与 L5 沙箱
五层门控可以理解为从「文件系统」到「运行时」逐步收紧的信任链:
| 层级 | 作用 | 约束类型 |
|---|---|---|
| L1 | 路径白名单:仅允许写入约定目录(如 prompts、memory、skills/_evolved) | 文件系统级 |
| L2 | 单次进化的变更幅度上限(规则条数、示例条数、新增 Skill 个数等) | 幅度与爆炸半径 |
| L3 | 敏感内容扫描:密钥、密码、PII 等 | 内容安全 |
| L4 | 静态代码模式检测(如 ScriptScanner 风险等级) | 静态分析 |
| L5 | 在沙箱中试运行进化产物 | OS 内核级隔离 |
L5 的关键意义:前四层能拦截大量已知风险,但「代码跑起来究竟会做什么」最终仍需要受控执行环境来兜底。SkillLite 在 macOS 上使用 Seatbelt 等机制,在 Linux 上结合命名空间与 seccomp 等(具体策略以仓库实现为准)。资源上限(如 rlimit)还可限制单次试运行的消耗。
五、从反馈到落盘:流程说明
下图描述从任务执行到「是否采纳本次进化」的主干路径(实现细节以源码为准,此处强调工程语义)。
并发语义:全局互斥避免多次进化并发覆盖同一批规则或技能文件,降低状态撕裂概率。配合「每日次数上限、最短间隔」等配置,还可抑制进化过快导致的方向漂移(具体默认值以项目配置文档为准)。
六、并发控制与频率约束(代码)
进化过程使用原子布尔实现「尝试开始 / 结束释放」,源码位于 crates/skilllite-evolution/src/run_state.rs:
//! Global evolution run mutex and result type.
use std::sync::atomic::{AtomicBool, Ordering};
static EVOLUTION_IN_PROGRESS: AtomicBool = AtomicBool::new(false);
pub fn try_start_evolution() -> bool {
EVOLUTION_IN_PROGRESS
.compare_exchange(false, true, Ordering::SeqCst, Ordering::SeqCst)
.is_ok()
}
pub fn finish_evolution() {
EVOLUTION_IN_PROGRESS.store(false, Ordering::SeqCst);
}
EvolutionRunResult 区分「忙碌跳过」「无进化范围」「已执行」等状态,便于上层日志与监控:
#[derive(Debug, Clone)]
pub enum EvolutionRunResult {
SkippedBusy,
NoScope,
Completed(Option<String>),
}
进程退出路径上,lifecycle 会在取得同一把锁后刷新指标(节选):
pub fn on_shutdown(chat_root: &Path) {
if !try_start_evolution() {
return;
}
if let Ok(conn) = feedback::open_evolution_db(chat_root) {
let _ = feedback::update_daily_metrics(&conn);
}
finish_evolution();
}
阅读建议:结合 crates/skilllite-evolution/ 下 run.rs、lifecycle.rs 与命令 skilllite evolution 相关实现,可串起完整调用链。
七、验证与生态:EvoTown
仅有门控仍不够:还需要在接近真实负载的场景下观察「进化是否真的带来 completion / quality / efficiency 的净收益」。社区可参考 EvoTown 一类竞技场式环境,在独立进程与独立技能目录中并行跑多 Agent,配合 LLM-Judge 等评分与经济压力机制,把「进化好坏」从主观感受推进到可对比实验。
- SkillLite:https://github.com/EXboys/skilllite
- EvoTown:https://github.com/EXboys/Evotown
八、小结
- 自进化的安全工程化,核心是 边界(哪里能写)、门控(写什么算合法)、追溯(每次进化可查)。
- SkillLite 用 不可变二进制 + 可进化数据层 划界,用 L1–L5 把风险从路径收敛到运行时验证。
- 全局互斥与频率上限 是容易被忽视但至关重要的「稳定性旋钮」,与沙箱并列构成可运维的自进化系统。
AtomGit 是由开放原子开源基金会联合 CSDN 等生态伙伴共同推出的新一代开源与人工智能协作平台。平台坚持“开放、中立、公益”的理念,把代码托管、模型共享、数据集托管、智能体开发体验和算力服务整合在一起,为开发者提供从开发、训练到部署的一站式体验。
更多推荐

所有评论(0)