@roll-agent/core 0.7.0 → 0.7.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1 +1 @@
1
- import{defineCommand as e}from"citty";import{existsSync as t,mkdirSync as s,writeFileSync as n}from"node:fs";import{stringify as o}from"yaml";import{getAgentEnvFromAgentsConfig as a,inspectAgentEnvRequirements as i}from"../../config/helpers.js";import{inspectConfigFile as r,loadAgentsConfig as l,loadConfig as m,parseConfigDocument as u,validateConfigText as g}from"../../config/loader.js";import{applyKnownConfigMigrations as c}from"../../config/migration.js";import{inspectAgentRuntimeEnvRequirements as f,summarizeAgentRuntimeEnvReport as p}from"../../config/runtime-env.js";import{inspectAgentRuntimeEnv as d}from"../../mcp/agent-diagnostics.js";import{cleanupOrphanAgentRuntimeMetadata as h,inspectManagedAgentRuntime as x}from"../../registry/process-manager.js";import{AgentStore as $}from"../../registry/store.js";const k={ok:"✓",warn:"⚠",fail:"✗"},y={applied:"✓",skipped:"•",failed:"✗"},w={major:22,minor:6,patch:0};function S(e){const t="Browser security (browser-use-agent)";if("unverified"===e.status)return{name:t,status:"warn",message:`未校验: ${e.message}`,fix:"启动 browser-use-agent 后重新运行 `roll doctor`"};const s=e.payload.security;if(void 0===s)return{name:t,status:"warn",message:"browser_status.security 未返回,无法确认浏览器安全策略",fix:"升级并重启 browser-use-agent"};const n=e.payload.policyWarnings??[];return{name:t,status:n.length>0?"warn":"ok",message:j(s,e.payload.toolPolicy,n),...n.length>0?{fix:"检查 BROWSER_SECURITY_JSON 与 BROWSER_USE_POLICY_JSON 的组合;Boss 日常编排建议 browser actionPolicy=log"}:{}}}function j(e,t,s){const n=e.domainAllowlist.length>0?e.domainAllowlist.join(", "):"none",o=P(t),a=s.length>0?`; warnings=${s.map(e=>e.code).join(", ")}`:"";return`actionPolicy=${e.actionPolicy}; domainAllowlist=${n}; maxPageContentBytes=${String(e.maxPageContentBytes)}; maxSnapshotNodes=${String(e.maxSnapshotNodes)}; toolPolicy=${o}`+a}function P(e){if(void 0===e)return"unavailable";const t=Object.entries(e.tools),s=t.length>0?t.map(([e,t])=>`${e}:${t.policy}`).join(","):"none";return`approvalTtlMs=${String(e.approvalTtlMs)},tools=${s}`}export function isNodeVersionSupported(e){const t=/^(\d+)\.(\d+)\.(\d+)/.exec(e);if(!t)return!1;const s=Number(t[1]),n=Number(t[2]),o=Number(t[3]);return s>w.major||!(s<w.major)&&(n>w.minor||!(n<w.minor)&&o>=w.patch)}export default e({meta:{description:"诊断 Roll 配置、Agent 注册表和运行时状态"},args:{json:{type:"boolean",description:"JSON 格式输出",default:!1},"fix-plan":{type:"boolean",description:"输出可执行修复建议(不自动修改)",default:!1},fix:{type:"boolean",description:"执行安全自动修复:配置自动迁移、创建 dataDir、清理孤儿 runtime 元数据",default:!1}},async run({args:e}){const s=[],n=[],o=!0===e.fix;let u;const g=process.versions.node;s.push(isNodeVersionSupported(g)?{name:"Node.js 版本",status:"ok",message:`v${g}`}:{name:"Node.js 版本",status:"fail",message:`v${g} (需要 ≥22.6.0)`,fix:"升级 Node.js 到 22.6.0 或更高版本"});let c,h=r();if("needs-migration"===h.status&&o){const e=v(h);n.push(e),"applied"===e.status&&(h=r())}switch(h.status){case"not-found":s.push({name:"配置文件",status:"warn",message:"未找到,使用默认配置",fix:"运行 `roll config init` 生成显式配置文件"}),u=m().config;break;case"valid":s.push({name:"配置文件",status:"ok",message:h.configPath}),u=h.config;break;case"needs-migration":s.push({name:"配置文件",status:"warn",message:`${h.configPath} (需要迁移,运行 roll config migrate)`,fix:"运行 `roll config migrate`,确认备份文件后提交配置变更"});break;case"invalid":s.push({name:"配置文件",status:"fail",message:h.error.message,fix:"修正配置文件语法或运行 `roll config migrate` 处理 breaking schema change"})}try{c=l().agentsConfig}catch(e){s.push({name:"Agent 配置",status:"fail",message:e instanceof Error?e.message:String(e),fix:"检查 `roll.config.yaml` 的 `agents` 段;如配置版本过旧,运行 `roll config migrate`"})}if(u){const e=Object.keys(u.llm.providers);if(e.length>0){const t=e.filter(e=>{const t=u.llm.providers[e]?.apiKey??"";return t.startsWith("${")||0===t.length});t.length>0?s.push({name:"LLM Providers",status:"warn",message:`${e.join(", ")} (${t.join(", ")} API key 未设置)`,fix:`配置 ${t.map(e=>`llm.providers.${e}.apiKey`).join(", ")} 或对应环境变量`}):s.push({name:"LLM Providers",status:"ok",message:e.join(", ")})}else s.push({name:"LLM Providers",status:"warn",message:"未配置任何 provider",fix:"运行 `roll config init` 或手动配置 `llm.providers`"})}else"needs-migration"===h.status&&s.push({name:"LLM Providers",status:"warn",message:"配置需要迁移,跳过完整 LLM 配置校验",fix:"先运行 `roll config migrate`,再重新执行 `roll doctor`"});if(c){const e=c.dataDir;let r=t(e);if(!r&&o){const s=b(e);n.push(s),r=t(e)}s.push(r?{name:"Agent 数据目录",status:"ok",message:e}:{name:"Agent 数据目录",status:"warn",message:`${e} (不存在,首次 add 时创建)`,fix:"运行 `roll doctor --fix` 创建目录,或手动创建该目录"});const l=new $(c.dataDir).list();s.push({name:"已注册 Agent",status:l.length>0?"ok":"warn",message:l.length>0?`${String(l.length)} 个 (${l.map(e=>e.skill.name).join(", ")})`:"无",...0===l.length?{fix:"运行 `roll agent add <path|git-url>` 注册 Agent"}:{}});for(const e of l){let t;const r=async()=>(t??=await d(e,{agentsConfig:c}),t);if("core-managed"===e.runtime.ownership){let t=x(e,c.dataDir);if(o&&t.issues.some(e=>"orphan-sidecar"===e.code)){const s=A(c.dataDir,e.skill.name);n.push(s),"applied"===s.status&&(t=x(e,c.dataDir))}(void 0!==t.pid||t.issues.length>0)&&s.push({name:`Agent runtime (${e.skill.name})`,status:t.issues.length>0?"warn":"ok",message:t.issues.length>0?t.issues.map(e=>e.message).join(";"):`PID ${String(t.pid)},runtime sidecar 与当前配置一致`,...t.issues.length>0?{fix:N(t.issues.map(e=>e.fix)).join(";")}:{}})}const l=i(e.skill.name,e.skill.env,c.env);if(!l){"browser-use-agent"===e.skill.name&&s.push(S(await r()));continue}t=await r();const m=f(l,a(c,e.skill.name),t),u=p(m);s.push({name:`Agent 环境变量 (${e.skill.name})`,status:u.status,message:u.message,..."ok"===u.status?{}:{fix:`在 \`roll.config.yaml\` 的 \`agents.env.${e.skill.name}\` 或 shell 环境中配置缺失变量`}}),"browser-use-agent"===e.skill.name&&s.push(S(t))}}const k=s.some(e=>"fail"===e.status),y=n.some(e=>"failed"===e.status),w=s.some(e=>"warn"===e.status),j=!0===e["fix-plan"]||o;if(e.json){const e=o?formatDoctorJsonOutput(s,{fixPlan:j,fixes:n}):formatDoctorChecksForJsonOutput(s,{fixPlan:j});return console.log(JSON.stringify(e,null,2)),void((k||y)&&(process.exitCode=1))}console.log("Roll Agent 系统诊断\n");for(const e of s)for(const t of formatDoctorCheckLines(e,{fixPlan:j}))console.log(t);if(o)if(console.log("\nFix 执行结果\n"),0===n.length)console.log(" ✓ 无可自动修复项");else for(const e of n)for(const t of formatDoctorFixLines(e))console.log(t);console.log(k||y?"\n存在问题,请修复后重试。":w?"\n存在警告,可按 fix plan 处理。":"\n系统状态正常。"),(k||y)&&(process.exitCode=1)}});export function formatDoctorCheckLines(e,t){const s=[` ${k[e.status]} ${e.name}: ${e.message}`];return t.fixPlan&&e.fix&&s.push(` fix: ${e.fix}`),s}export function formatDoctorChecksForJsonOutput(e,t){return t.fixPlan?e:e.map(e=>({name:e.name,status:e.status,message:e.message}))}export function formatDoctorJsonOutput(e,t){return{checks:formatDoctorChecksForJsonOutput(e,{fixPlan:t.fixPlan}),fixes:t.fixes}}export function formatDoctorFixLines(e){return[` ${y[e.status]} ${e.name}: ${e.message}`]}function v(e){if(!e.report.canAutoMigrate)return{name:"配置迁移",status:"skipped",message:"检测到需要人工处理的配置迁移项,未自动修改"};try{const t=u(e.raw,e.configPath),s=c(t);if(!s.ok)return{name:"配置迁移",status:"skipped",message:`无法自动迁移:${L(s.issues)}`};if(!s.changed)return{name:"配置迁移",status:"skipped",message:"配置文件已是最新格式"};const a=o(s.document,{lineWidth:0});g(a,e.configPath);const i=D(e.configPath);return n(i,e.raw,"utf-8"),n(e.configPath,a,"utf-8"),{name:"配置迁移",status:"applied",message:`已迁移 ${e.configPath},备份 ${i}`}}catch(e){return{name:"配置迁移",status:"failed",message:e instanceof Error?e.message:String(e)}}}function b(e){try{return s(e,{recursive:!0}),{name:"Agent 数据目录",status:"applied",message:`已创建 ${e}`}}catch(e){return{name:"Agent 数据目录",status:"failed",message:e instanceof Error?e.message:String(e)}}}function A(e,t){try{return h(e,t)?{name:`Agent runtime (${t})`,status:"applied",message:"已清理孤儿 runtime 元数据"}:{name:`Agent runtime (${t})`,status:"skipped",message:"检测到活动 PID,跳过 runtime 元数据清理"}}catch(e){return{name:`Agent runtime (${t})`,status:"failed",message:e instanceof Error?e.message:String(e)}}}function D(e){const t=new Date;return`${e}.bak.${[t.getFullYear().toString().padStart(4,"0"),(t.getMonth()+1).toString().padStart(2,"0"),t.getDate().toString().padStart(2,"0"),"-",t.getHours().toString().padStart(2,"0"),t.getMinutes().toString().padStart(2,"0"),t.getSeconds().toString().padStart(2,"0")].join("")}`}function L(e){return e.map(e=>e.message).join(";")}function N(e){return[...new Set(e)]}
1
+ import{defineCommand as e}from"citty";import{existsSync as t,mkdirSync as s,writeFileSync as n}from"node:fs";import{stringify as o}from"yaml";import{getAgentEnvFromAgentsConfig as a,inspectAgentEnvRequirements as i}from"../../config/helpers.js";import{inspectConfigFile as r,loadAgentsConfig as l,loadConfig as m,parseConfigDocument as u,validateConfigText as g}from"../../config/loader.js";import{applyKnownConfigMigrations as c}from"../../config/migration.js";import{inspectAgentRuntimeEnvRequirements as f,summarizeAgentRuntimeEnvReport as p}from"../../config/runtime-env.js";import{inspectAgentRuntimeEnv as d}from"../../mcp/agent-diagnostics.js";import{cleanupOrphanAgentRuntimeMetadata as h,inspectManagedAgentRuntime as x}from"../../registry/process-manager.js";import{AgentStore as $}from"../../registry/store.js";const k={ok:"✓",warn:"⚠",fail:"✗"},y={applied:"✓",skipped:"•",failed:"✗"},w={major:22,minor:6,patch:0};function S(e){const t="Browser security (browser-use-agent)";if("unverified"===e.status)return{name:t,status:"warn",message:`未校验: ${e.message}`,fix:"启动 browser-use-agent 后重新运行 `roll doctor`"};const s=e.payload.security;if(void 0===s)return{name:t,status:"warn",message:"browser_status.security 未返回,无法确认浏览器安全策略",fix:"升级并重启 browser-use-agent"};const n=e.payload.policyWarnings??[];return{name:t,status:n.length>0?"warn":"ok",message:P(s,e.payload.toolPolicy,n),...n.length>0?{fix:"检查 BROWSER_SECURITY_JSON 与 BROWSER_USE_POLICY_JSON 的组合;Boss 日常编排建议 browser actionPolicy=log"}:{}}}function P(e,t,s){const n=e.domainAllowlist.length>0?e.domainAllowlist.join(", "):"none",o=j(t),a=s.length>0?`; warnings=${s.map(e=>e.code).join(", ")}`:"";return`actionPolicy=${e.actionPolicy}; foregroundPolicy=${e.foregroundPolicy}; domainAllowlist=${n}; maxPageContentBytes=${String(e.maxPageContentBytes)}; maxSnapshotNodes=${String(e.maxSnapshotNodes)}; toolPolicy=${o}`+a}function j(e){if(void 0===e)return"unavailable";const t=Object.entries(e.tools),s=t.length>0?t.map(([e,t])=>`${e}:${t.policy}`).join(","):"none";return`approvalTtlMs=${String(e.approvalTtlMs)},tools=${s}`}export function isNodeVersionSupported(e){const t=/^(\d+)\.(\d+)\.(\d+)/.exec(e);if(!t)return!1;const s=Number(t[1]),n=Number(t[2]),o=Number(t[3]);return s>w.major||!(s<w.major)&&(n>w.minor||!(n<w.minor)&&o>=w.patch)}export default e({meta:{description:"诊断 Roll 配置、Agent 注册表和运行时状态"},args:{json:{type:"boolean",description:"JSON 格式输出",default:!1},"fix-plan":{type:"boolean",description:"输出可执行修复建议(不自动修改)",default:!1},fix:{type:"boolean",description:"执行安全自动修复:配置自动迁移、创建 dataDir、清理孤儿 runtime 元数据",default:!1}},async run({args:e}){const s=[],n=[],o=!0===e.fix;let u;const g=process.versions.node;s.push(isNodeVersionSupported(g)?{name:"Node.js 版本",status:"ok",message:`v${g}`}:{name:"Node.js 版本",status:"fail",message:`v${g} (需要 ≥22.6.0)`,fix:"升级 Node.js 到 22.6.0 或更高版本"});let c,h=r();if("needs-migration"===h.status&&o){const e=v(h);n.push(e),"applied"===e.status&&(h=r())}switch(h.status){case"not-found":s.push({name:"配置文件",status:"warn",message:"未找到,使用默认配置",fix:"运行 `roll config init` 生成显式配置文件"}),u=m().config;break;case"valid":s.push({name:"配置文件",status:"ok",message:h.configPath}),u=h.config;break;case"needs-migration":s.push({name:"配置文件",status:"warn",message:`${h.configPath} (需要迁移,运行 roll config migrate)`,fix:"运行 `roll config migrate`,确认备份文件后提交配置变更"});break;case"invalid":s.push({name:"配置文件",status:"fail",message:h.error.message,fix:"修正配置文件语法或运行 `roll config migrate` 处理 breaking schema change"})}try{c=l().agentsConfig}catch(e){s.push({name:"Agent 配置",status:"fail",message:e instanceof Error?e.message:String(e),fix:"检查 `roll.config.yaml` 的 `agents` 段;如配置版本过旧,运行 `roll config migrate`"})}if(u){const e=Object.keys(u.llm.providers);if(e.length>0){const t=e.filter(e=>{const t=u.llm.providers[e]?.apiKey??"";return t.startsWith("${")||0===t.length});t.length>0?s.push({name:"LLM Providers",status:"warn",message:`${e.join(", ")} (${t.join(", ")} API key 未设置)`,fix:`配置 ${t.map(e=>`llm.providers.${e}.apiKey`).join(", ")} 或对应环境变量`}):s.push({name:"LLM Providers",status:"ok",message:e.join(", ")})}else s.push({name:"LLM Providers",status:"warn",message:"未配置任何 provider",fix:"运行 `roll config init` 或手动配置 `llm.providers`"})}else"needs-migration"===h.status&&s.push({name:"LLM Providers",status:"warn",message:"配置需要迁移,跳过完整 LLM 配置校验",fix:"先运行 `roll config migrate`,再重新执行 `roll doctor`"});if(c){const e=c.dataDir;let r=t(e);if(!r&&o){const s=b(e);n.push(s),r=t(e)}s.push(r?{name:"Agent 数据目录",status:"ok",message:e}:{name:"Agent 数据目录",status:"warn",message:`${e} (不存在,首次 add 时创建)`,fix:"运行 `roll doctor --fix` 创建目录,或手动创建该目录"});const l=new $(c.dataDir).list();s.push({name:"已注册 Agent",status:l.length>0?"ok":"warn",message:l.length>0?`${String(l.length)} 个 (${l.map(e=>e.skill.name).join(", ")})`:"无",...0===l.length?{fix:"运行 `roll agent add <path|git-url>` 注册 Agent"}:{}});for(const e of l){let t;const r=async()=>(t??=await d(e,{agentsConfig:c}),t);if("core-managed"===e.runtime.ownership){let t=x(e,c.dataDir);if(o&&t.issues.some(e=>"orphan-sidecar"===e.code)){const s=A(c.dataDir,e.skill.name);n.push(s),"applied"===s.status&&(t=x(e,c.dataDir))}(void 0!==t.pid||t.issues.length>0)&&s.push({name:`Agent runtime (${e.skill.name})`,status:t.issues.length>0?"warn":"ok",message:t.issues.length>0?t.issues.map(e=>e.message).join(";"):`PID ${String(t.pid)},runtime sidecar 与当前配置一致`,...t.issues.length>0?{fix:N(t.issues.map(e=>e.fix)).join(";")}:{}})}const l=i(e.skill.name,e.skill.env,c.env);if(!l){"browser-use-agent"===e.skill.name&&s.push(S(await r()));continue}t=await r();const m=f(l,a(c,e.skill.name),t),u=p(m);s.push({name:`Agent 环境变量 (${e.skill.name})`,status:u.status,message:u.message,..."ok"===u.status?{}:{fix:`在 \`roll.config.yaml\` 的 \`agents.env.${e.skill.name}\` 或 shell 环境中配置缺失变量`}}),"browser-use-agent"===e.skill.name&&s.push(S(t))}}const k=s.some(e=>"fail"===e.status),y=n.some(e=>"failed"===e.status),w=s.some(e=>"warn"===e.status),P=!0===e["fix-plan"]||o;if(e.json){const e=o?formatDoctorJsonOutput(s,{fixPlan:P,fixes:n}):formatDoctorChecksForJsonOutput(s,{fixPlan:P});return console.log(JSON.stringify(e,null,2)),void((k||y)&&(process.exitCode=1))}console.log("Roll Agent 系统诊断\n");for(const e of s)for(const t of formatDoctorCheckLines(e,{fixPlan:P}))console.log(t);if(o)if(console.log("\nFix 执行结果\n"),0===n.length)console.log(" ✓ 无可自动修复项");else for(const e of n)for(const t of formatDoctorFixLines(e))console.log(t);console.log(k||y?"\n存在问题,请修复后重试。":w?"\n存在警告,可按 fix plan 处理。":"\n系统状态正常。"),(k||y)&&(process.exitCode=1)}});export function formatDoctorCheckLines(e,t){const s=[` ${k[e.status]} ${e.name}: ${e.message}`];return t.fixPlan&&e.fix&&s.push(` fix: ${e.fix}`),s}export function formatDoctorChecksForJsonOutput(e,t){return t.fixPlan?e:e.map(e=>({name:e.name,status:e.status,message:e.message}))}export function formatDoctorJsonOutput(e,t){return{checks:formatDoctorChecksForJsonOutput(e,{fixPlan:t.fixPlan}),fixes:t.fixes}}export function formatDoctorFixLines(e){return[` ${y[e.status]} ${e.name}: ${e.message}`]}function v(e){if(!e.report.canAutoMigrate)return{name:"配置迁移",status:"skipped",message:"检测到需要人工处理的配置迁移项,未自动修改"};try{const t=u(e.raw,e.configPath),s=c(t);if(!s.ok)return{name:"配置迁移",status:"skipped",message:`无法自动迁移:${L(s.issues)}`};if(!s.changed)return{name:"配置迁移",status:"skipped",message:"配置文件已是最新格式"};const a=o(s.document,{lineWidth:0});g(a,e.configPath);const i=D(e.configPath);return n(i,e.raw,"utf-8"),n(e.configPath,a,"utf-8"),{name:"配置迁移",status:"applied",message:`已迁移 ${e.configPath},备份 ${i}`}}catch(e){return{name:"配置迁移",status:"failed",message:e instanceof Error?e.message:String(e)}}}function b(e){try{return s(e,{recursive:!0}),{name:"Agent 数据目录",status:"applied",message:`已创建 ${e}`}}catch(e){return{name:"Agent 数据目录",status:"failed",message:e instanceof Error?e.message:String(e)}}}function A(e,t){try{return h(e,t)?{name:`Agent runtime (${t})`,status:"applied",message:"已清理孤儿 runtime 元数据"}:{name:`Agent runtime (${t})`,status:"skipped",message:"检测到活动 PID,跳过 runtime 元数据清理"}}catch(e){return{name:`Agent runtime (${t})`,status:"failed",message:e instanceof Error?e.message:String(e)}}}function D(e){const t=new Date;return`${e}.bak.${[t.getFullYear().toString().padStart(4,"0"),(t.getMonth()+1).toString().padStart(2,"0"),t.getDate().toString().padStart(2,"0"),"-",t.getHours().toString().padStart(2,"0"),t.getMinutes().toString().padStart(2,"0"),t.getSeconds().toString().padStart(2,"0")].join("")}`}function L(e){return e.map(e=>e.message).join(";")}function N(e){return[...new Set(e)]}
@@ -17,16 +17,19 @@ export declare const BrowserSecurityDiagnosticSchema: z.ZodObject<{
17
17
  maxPageContentBytes: z.ZodNumber;
18
18
  maxSnapshotNodes: z.ZodNumber;
19
19
  actionPolicy: z.ZodEnum<["log", "deny", "confirm"]>;
20
+ foregroundPolicy: z.ZodDefault<z.ZodEnum<["when-minimized", "always", "never"]>>;
20
21
  }, "strip", z.ZodTypeAny, {
21
22
  domainAllowlist: string[];
22
23
  maxPageContentBytes: number;
23
24
  maxSnapshotNodes: number;
24
25
  actionPolicy: "log" | "deny" | "confirm";
26
+ foregroundPolicy: "never" | "when-minimized" | "always";
25
27
  }, {
26
28
  domainAllowlist: string[];
27
29
  maxPageContentBytes: number;
28
30
  maxSnapshotNodes: number;
29
31
  actionPolicy: "log" | "deny" | "confirm";
32
+ foregroundPolicy?: "never" | "when-minimized" | "always" | undefined;
30
33
  }>;
31
34
  export declare const BrowserUseToolPolicyDiagnosticSchema: z.ZodObject<{
32
35
  approvalTtlMs: z.ZodNumber;
@@ -74,16 +77,19 @@ export declare const AgentRuntimeEnvDiagnosticPayloadSchema: z.ZodObject<{
74
77
  maxPageContentBytes: z.ZodNumber;
75
78
  maxSnapshotNodes: z.ZodNumber;
76
79
  actionPolicy: z.ZodEnum<["log", "deny", "confirm"]>;
80
+ foregroundPolicy: z.ZodDefault<z.ZodEnum<["when-minimized", "always", "never"]>>;
77
81
  }, "strip", z.ZodTypeAny, {
78
82
  domainAllowlist: string[];
79
83
  maxPageContentBytes: number;
80
84
  maxSnapshotNodes: number;
81
85
  actionPolicy: "log" | "deny" | "confirm";
86
+ foregroundPolicy: "never" | "when-minimized" | "always";
82
87
  }, {
83
88
  domainAllowlist: string[];
84
89
  maxPageContentBytes: number;
85
90
  maxSnapshotNodes: number;
86
91
  actionPolicy: "log" | "deny" | "confirm";
92
+ foregroundPolicy?: "never" | "when-minimized" | "always" | undefined;
87
93
  }>>;
88
94
  toolPolicy: z.ZodOptional<z.ZodObject<{
89
95
  approvalTtlMs: z.ZodNumber;
@@ -125,6 +131,7 @@ export declare const AgentRuntimeEnvDiagnosticPayloadSchema: z.ZodObject<{
125
131
  maxPageContentBytes: number;
126
132
  maxSnapshotNodes: number;
127
133
  actionPolicy: "log" | "deny" | "confirm";
134
+ foregroundPolicy: "never" | "when-minimized" | "always";
128
135
  } | undefined;
129
136
  toolPolicy?: {
130
137
  tools: Record<string, {
@@ -146,6 +153,7 @@ export declare const AgentRuntimeEnvDiagnosticPayloadSchema: z.ZodObject<{
146
153
  maxPageContentBytes: number;
147
154
  maxSnapshotNodes: number;
148
155
  actionPolicy: "log" | "deny" | "confirm";
156
+ foregroundPolicy?: "never" | "when-minimized" | "always" | undefined;
149
157
  } | undefined;
150
158
  toolPolicy?: {
151
159
  tools: Record<string, {
@@ -1 +1 @@
1
- import{createHash as e}from"node:crypto";import{z as n}from"zod";export const DIAGNOSTIC_TOOL_CANDIDATES=["diagnostic_status","browser_status"];const t=new Set(DIAGNOSTIC_TOOL_CANDIDATES),i=/^[0-9a-f]{8}$/;export const EffectiveEnvSourceSchema=n.object({present:n.boolean(),fingerprint:n.string().regex(i).optional()});export const BrowserSecurityDiagnosticSchema=n.object({domainAllowlist:n.array(n.string()),maxPageContentBytes:n.number(),maxSnapshotNodes:n.number(),actionPolicy:n.enum(["log","deny","confirm"])});export const BrowserUseToolPolicyDiagnosticSchema=n.object({approvalTtlMs:n.number(),tools:n.record(n.object({policy:n.enum(["log","deny","confirm"])}))});export const BrowserUsePolicyWarningDiagnosticSchema=n.object({code:n.string(),message:n.string()});export const AgentRuntimeEnvDiagnosticPayloadSchema=n.object({effectiveEnvSources:n.record(EffectiveEnvSourceSchema),security:BrowserSecurityDiagnosticSchema.optional(),toolPolicy:BrowserUseToolPolicyDiagnosticSchema.optional(),policyWarnings:n.array(BrowserUsePolicyWarningDiagnosticSchema).optional()});export function shouldSkipRuntimeReadinessForTool(e){return t.has(e)}export function inspectAgentRuntimeEnvRequirements(e,n,t){const i=e.items.map(e=>{const i=n?.[e.name],r=void 0!==i;if("unverified"===t.status)return{...e,configuredInAgentsEnv:r,runtime:{verified:!1,reason:t.reason,message:t.message}};const o=t.payload.effectiveEnvSources[e.name];return o?.present?{...e,configuredInAgentsEnv:r,runtime:{verified:!0,present:!0,...void 0!==o.fingerprint?{fingerprint:o.fingerprint}:{},matchesAgentsEnv:void 0!==i&&void 0!==o.fingerprint&&s(i)===o.fingerprint}}:{...e,configuredInAgentsEnv:r,runtime:{verified:!0,present:!1}}});return{items:i,inspection:t,missingRequired:i.filter(e=>e.required&&r(e)),ephemeralItems:i.filter(o)}}export function summarizeAgentRuntimeEnvReport(e){if(e.missingRequired.length>0){const n=c(e.missingRequired);return"verified"===e.inspection.status?{status:"fail",message:`运行态缺失: ${n}`}:{status:"fail",message:`${a(e)};${e.inspection.message}`}}if(e.ephemeralItems.length>0)return{status:"warn",message:`运行态漂移: ${c(e.ephemeralItems)}`};if("verified"===e.inspection.status)return{status:"ok",message:`声明的必填项已在运行态生效(${e.inspection.toolName})`};const n=e.items.filter(e=>e.required&&"process.env"===e.source);return n.length>0?{status:"warn",message:`依赖当前 shell 环境: ${c(n)};${e.inspection.message}`}:"diagnostic-tool-unavailable"===e.inspection.reason?{status:"ok",message:`声明的必填项已满足(${e.inspection.message})`}:{status:"warn",message:`声明的必填项已满足;${e.inspection.message}`}}export function formatAgentEnvDeclarationSource(e){switch(e.source){case"agents.env":return"已配置于 agents.env";case"process.env":return"仅当前 shell 环境";case"default":return`默认值 (${e.default})`;case"missing":return"缺失"}}export function formatAgentRuntimeVerification(e){return"verified"===e.inspection.status?`已验证(${e.inspection.toolName})`:`未校验(${e.inspection.message})`}export function formatAgentEnvRuntimeStatus(e){if(e.runtime.verified)return e.runtime.present?e.runtime.matchesAgentsEnv?"✓ from yaml (stable)":e.configuredInAgentsEnv?"⚠ differs from yaml (ephemeral)":"⚠ from shell (ephemeral)":"default"===e.source?"未设置(使用默认值)":"process.env"===e.source?"✗ 当前运行 agent 未看到该变量":"✗ missing"}function s(n){return e("sha256").update(n).digest("hex").slice(0,8)}function r(e){return e.runtime.verified?!e.runtime.present&&"default"!==e.source:"missing"===e.source}function o(e){return e.runtime.verified&&e.runtime.present&&!e.runtime.matchesAgentsEnv}function a(e){return`缺少必填项: ${c(e.missingRequired)}`}function c(e){return e.map(e=>e.name).join(", ")}
1
+ import{createHash as e}from"node:crypto";import{z as n}from"zod";export const DIAGNOSTIC_TOOL_CANDIDATES=["diagnostic_status","browser_status"];const t=new Set(DIAGNOSTIC_TOOL_CANDIDATES),i=/^[0-9a-f]{8}$/;export const EffectiveEnvSourceSchema=n.object({present:n.boolean(),fingerprint:n.string().regex(i).optional()});export const BrowserSecurityDiagnosticSchema=n.object({domainAllowlist:n.array(n.string()),maxPageContentBytes:n.number(),maxSnapshotNodes:n.number(),actionPolicy:n.enum(["log","deny","confirm"]),foregroundPolicy:n.enum(["when-minimized","always","never"]).default("when-minimized")});export const BrowserUseToolPolicyDiagnosticSchema=n.object({approvalTtlMs:n.number(),tools:n.record(n.object({policy:n.enum(["log","deny","confirm"])}))});export const BrowserUsePolicyWarningDiagnosticSchema=n.object({code:n.string(),message:n.string()});export const AgentRuntimeEnvDiagnosticPayloadSchema=n.object({effectiveEnvSources:n.record(EffectiveEnvSourceSchema),security:BrowserSecurityDiagnosticSchema.optional(),toolPolicy:BrowserUseToolPolicyDiagnosticSchema.optional(),policyWarnings:n.array(BrowserUsePolicyWarningDiagnosticSchema).optional()});export function shouldSkipRuntimeReadinessForTool(e){return t.has(e)}export function inspectAgentRuntimeEnvRequirements(e,n,t){const i=e.items.map(e=>{const i=n?.[e.name],s=void 0!==i;if("unverified"===t.status)return{...e,configuredInAgentsEnv:s,runtime:{verified:!1,reason:t.reason,message:t.message}};const o=t.payload.effectiveEnvSources[e.name];return o?.present?{...e,configuredInAgentsEnv:s,runtime:{verified:!0,present:!0,...void 0!==o.fingerprint?{fingerprint:o.fingerprint}:{},matchesAgentsEnv:void 0!==i&&void 0!==o.fingerprint&&r(i)===o.fingerprint}}:{...e,configuredInAgentsEnv:s,runtime:{verified:!0,present:!1}}});return{items:i,inspection:t,missingRequired:i.filter(e=>e.required&&s(e)),ephemeralItems:i.filter(o)}}export function summarizeAgentRuntimeEnvReport(e){if(e.missingRequired.length>0){const n=c(e.missingRequired);return"verified"===e.inspection.status?{status:"fail",message:`运行态缺失: ${n}`}:{status:"fail",message:`${a(e)};${e.inspection.message}`}}if(e.ephemeralItems.length>0)return{status:"warn",message:`运行态漂移: ${c(e.ephemeralItems)}`};if("verified"===e.inspection.status)return{status:"ok",message:`声明的必填项已在运行态生效(${e.inspection.toolName})`};const n=e.items.filter(e=>e.required&&"process.env"===e.source);return n.length>0?{status:"warn",message:`依赖当前 shell 环境: ${c(n)};${e.inspection.message}`}:"diagnostic-tool-unavailable"===e.inspection.reason?{status:"ok",message:`声明的必填项已满足(${e.inspection.message})`}:{status:"warn",message:`声明的必填项已满足;${e.inspection.message}`}}export function formatAgentEnvDeclarationSource(e){switch(e.source){case"agents.env":return"已配置于 agents.env";case"process.env":return"仅当前 shell 环境";case"default":return`默认值 (${e.default})`;case"missing":return"缺失"}}export function formatAgentRuntimeVerification(e){return"verified"===e.inspection.status?`已验证(${e.inspection.toolName})`:`未校验(${e.inspection.message})`}export function formatAgentEnvRuntimeStatus(e){if(e.runtime.verified)return e.runtime.present?e.runtime.matchesAgentsEnv?"✓ from yaml (stable)":e.configuredInAgentsEnv?"⚠ differs from yaml (ephemeral)":"⚠ from shell (ephemeral)":"default"===e.source?"未设置(使用默认值)":"process.env"===e.source?"✗ 当前运行 agent 未看到该变量":"✗ missing"}function r(n){return e("sha256").update(n).digest("hex").slice(0,8)}function s(e){return e.runtime.verified?!e.runtime.present&&"default"!==e.source:"missing"===e.source}function o(e){return e.runtime.verified&&e.runtime.present&&!e.runtime.matchesAgentsEnv}function a(e){return`缺少必填项: ${c(e.missingRequired)}`}function c(e){return e.map(e=>e.name).join(", ")}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@roll-agent/core",
3
- "version": "0.7.0",
3
+ "version": "0.7.1",
4
4
  "type": "module",
5
5
  "repository": {
6
6
  "type": "git",