惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

U
Unit 42
罗磊的独立博客
博客园 - 聂微东
T
The Blog of Author Tim Ferriss
博客园 - 司徒正美
Stack Overflow Blog
Stack Overflow Blog
F
Fortinet All Blogs
A
About on SuperTechFans
腾讯CDC
Apple Machine Learning Research
Apple Machine Learning Research
B
Blog RSS Feed
IT之家
IT之家
V
Visual Studio Blog
freeCodeCamp Programming Tutorials: Python, JavaScript, Git & More
宝玉的分享
宝玉的分享
C
Check Point Blog
Cyber Security Advisories - MS-ISAC
Cyber Security Advisories - MS-ISAC
Vercel News
Vercel News
爱范儿
爱范儿
Microsoft Security Blog
Microsoft Security Blog
月光博客
月光博客
T
Tailwind CSS Blog
The Cloudflare Blog
Hugging Face - Blog
Hugging Face - Blog

Recent Commits to openclaw:main

test: merge chat side-result checks · openclaw/openclaw@ddd2c2a test: merge cron history checks · openclaw/openclaw@f7eb746 test: merge responsive navigation shell checks · openclaw/openclaw@c2e4b47 docs(changelog): add codex oauth fixes · openclaw/openclaw@628e6cd test: merge navigation routing cases · openclaw/openclaw@5d8cecb Tests: mock channel registry bundled fallback · openclaw/openclaw@2b08233 Secrets: avoid broad web search discovery for single plugin config · openclaw/openclaw@a464f59 test: merge config view browser checks · openclaw/openclaw@20cf511 fix(status): align oauth health with runtime · openclaw/openclaw@eed7116 feat: add macOS screen snapshots for monitor preview (#67954) thanks … · openclaw/openclaw@f377db1 fix: report shared auth scopes in hello-ok (#67810) thanks @BunsDev · openclaw/openclaw@0b6c39b Auto-reply: avoid eager bundled route fallback · openclaw/openclaw@3ea1bf4 Tests: narrow session binding contract setup · openclaw/openclaw@54e4e16 fix(macOS): enable undo/redo in webchat composer text input (#34962) · openclaw/openclaw@00951dc Tests: speed up channel setup promotion · openclaw/openclaw@82b529a Docs: refresh agent instructions · openclaw/openclaw@5775fe2 fix(auth): serialize OAuth refresh across agents to fix #26322 (#67876) · openclaw/openclaw@8e79080 test: allow ollama public surface boundary test · openclaw/openclaw@7d4f1a6 Docs: add test performance guardrails · openclaw/openclaw@89706d3 Tests: restore context-engine usage proof · openclaw/openclaw@e4c4f95 Tests: slim context engine runtime coverage · openclaw/openclaw@74c198f ci: retry failed custom checkouts · openclaw/openclaw@0ee5baf test: trim duplicate provider auth onboarding cases · openclaw/openclaw@1ffc02e matrix: fix sessions_spawn --thread subagent session spawning (#67643) · openclaw/openclaw@1ce2596 test: reduce auth choice fixture churn · openclaw/openclaw@857b9cd test: mock health status config boundaries · openclaw/openclaw@9d5ab4a test: mock onboard config io boundary · openclaw/openclaw@299694d test: mock legacy state plugin boundaries · openclaw/openclaw@2713089 test: mock channel install boundaries · openclaw/openclaw@b945248 test: mock doctor preview channel boundaries · openclaw/openclaw@b1a3ad4
fix(exec): harden backend sandbox exec cleanup (#96926) ·...
jesse-merhi · 2026-06-26 · via Recent Commits to openclaw:main

@@ -143,6 +143,13 @@ type ResolvedExecEnvPreparedState = {

143143

pluginEnv?: Record<string, string>;

144144

};

145145

const resolvedExecEnvPreparedStates = new WeakMap<ExecToolArgs, ResolvedExecEnvPreparedState>();

146+

type DeferredResolveExecEnvPreparedState = {

147+

hookContext?: HookContext;

148+

};

149+

const deferredResolveExecEnvPreparedStates = new WeakMap<

150+

ExecToolArgs,

151+

DeferredResolveExecEnvPreparedState

152+

>();

146153

type ResolvedExecWorkdirPreparedState = {

147154

host: ExecHost;

148155

inputWorkdir?: string;

@@ -162,6 +169,10 @@ const XML_ARG_VALUE_EXEC_PARAM_KEYS = [

162169

"node",

163170

] as const;

164171172+

function isExecToolArgsObject(value: unknown): value is ExecToolArgs {

173+

return typeof value === "object" && value !== null && !Array.isArray(value);

174+

}

175+165176

function filterPluginExecEnv(rawEnv: Record<string, string>): Record<string, string> | undefined {

166177

const env: Record<string, string> = {};

167178

for (const [rawKey, value] of Object.entries(rawEnv)) {

@@ -201,6 +212,20 @@ function isResolveExecEnvPrepared(params: ExecToolArgs): boolean {

201212

return Boolean(getResolvedExecEnvPreparedState(params));

202213

}

203214215+

function markDeferredResolveExecEnvPrepared<T extends ExecToolArgs>(

216+

params: T,

217+

state: DeferredResolveExecEnvPreparedState,

218+

): T {

219+

deferredResolveExecEnvPreparedStates.set(params, state);

220+

return params;

221+

}

222+223+

function getDeferredResolveExecEnvPreparedState(

224+

params: ExecToolArgs,

225+

): DeferredResolveExecEnvPreparedState | undefined {

226+

return deferredResolveExecEnvPreparedStates.get(params);

227+

}

228+204229

function markResolvedExecWorkdirPrepared<T extends ExecToolArgs>(

205230

params: T,

206231

state: ResolvedExecWorkdirPreparedState,

@@ -1475,20 +1500,31 @@ export function createExecTool(

14751500

if (workdirState?.resolution.kind === "unavailable") {

14761501

return params;

14771502

}

1478-

if (shouldDeferResolveExecEnvUntilWorkdirValidated(params)) {

1503+

if (!isExecToolArgsObject(params)) {

14791504

return params;

14801505

}

1506+

if (shouldDeferResolveExecEnvUntilWorkdirValidated(params)) {

1507+

return markDeferredResolveExecEnvPrepared(params, {

1508+

hookContext: context.hookContext as HookContext | undefined,

1509+

});

1510+

}

14811511

return prepareParamsWithResolvedExecEnv(params, {

14821512

hookContext: context.hookContext as HookContext | undefined,

14831513

});

14841514

},

14851515

finalizeBeforeToolCallParams: (params, preparedParams) => {

1486-

const execParams = params as ExecToolArgs;

14871516

const envState = getResolvedExecEnvPreparedState(preparedParams as ExecToolArgs);

1517+

const deferredEnvState = getDeferredResolveExecEnvPreparedState(

1518+

preparedParams as ExecToolArgs,

1519+

);

14881520

const workdirState = getResolvedExecWorkdirPreparedState(preparedParams as ExecToolArgs);

1489-

if (!envState && !workdirState) {

1521+

if (!envState && !deferredEnvState && !workdirState) {

1522+

return params;

1523+

}

1524+

if (!isExecToolArgsObject(params)) {

14901525

return params;

14911526

}

1527+

const execParams = params;

14921528

let host: ExecHost | undefined;

14931529

const resolveFinalHost = () => {

14941530

host ??= resolveHostForParams(execParams);

@@ -1511,6 +1547,9 @@ export function createExecTool(

15111547

if (envState) {

15121548

markResolveExecEnvPrepared(execParams, envState);

15131549

}

1550+

if (deferredEnvState) {

1551+

markDeferredResolveExecEnvPrepared(execParams, deferredEnvState);

1552+

}

15141553

if (workdirState) {

15151554

markResolvedExecWorkdirPrepared(execParams, workdirState);

15161555

}

@@ -1522,6 +1561,7 @@ export function createExecTool(

15221561

XML_ARG_VALUE_EXEC_PARAM_KEYS,

15231562

);

15241563

const resolveExecEnvPrepared = isResolveExecEnvPrepared(args as ExecToolArgs);

1564+

const deferredResolveExecEnvState = getDeferredResolveExecEnvPreparedState(params);

15251565

const preparedWorkdirState = getResolvedExecWorkdirPreparedState(params);

1526156615271567

const maxOutput = DEFAULT_MAX_OUTPUT;

@@ -1724,7 +1764,9 @@ export function createExecTool(

17241764

logInfo(`exec: elevated command ${truncateMiddle(params.command, 120)}`);

17251765

}

17261766

if (!resolveExecEnvPrepared) {

1727-

params = await prepareParamsWithResolvedExecEnv(params);

1767+

params = await prepareParamsWithResolvedExecEnv(params, {

1768+

hookContext: deferredResolveExecEnvState?.hookContext,

1769+

});

17281770

}

1729177117301772

const inheritedBaseEnv = coerceEnv(process.env);