feat: run agent tools with host permissions

This commit is contained in:
mesalogo
2026-08-15 18:06:03 +08:00
parent 79e2511f6f
commit 34bbfab2af
38 changed files with 224 additions and 1395 deletions
+12 -134
View File
@@ -4,14 +4,11 @@ import { isAbsolute, join } from 'node:path'
import { parse as parseYaml } from 'yaml'
import AgentRegistry from '@deepseek-ai/dsh-agent'
import AgentLoop from '@deepseek-ai/dsh-agent-loop'
import SandboxedBash from '@deepseek-ai/dsh-bash-sandbox'
import SandboxedPwsh from '@deepseek-ai/dsh-pwsh-sandbox'
import SandboxedFileSystem from '@deepseek-ai/dsh-fs-sandbox'
import LocalBash from '@deepseek-ai/dsh-bash-local'
import LocalPwsh from '@deepseek-ai/dsh-pwsh-local'
import LocalFileSystem from '@deepseek-ai/dsh-fs-local'
import LlmRuntime from '@deepseek-ai/dsh-llm'
import * as PiAiLlm from '@deepseek-ai/dsh-llm-pi-ai'
import ApprovalService from '@deepseek-ai/dsh-user-approval'
import LocalSandbox from '@deepseek-ai/dsh-sandbox-local'
import SandboxPolicy from '@deepseek-ai/dsh-sandbox-policy'
import SessionStore from '@deepseek-ai/dsh-session'
import SkillRegistry from '@deepseek-ai/dsh-skill'
import LocalSubprocess from '@deepseek-ai/dsh-subprocess-local'
@@ -29,7 +26,6 @@ import {
type GoodBuddyHarnessControlConfig
} from './agent/goodbuddy-harness-control-plane'
import type { Stream } from '@agentclientprotocol/sdk'
import type { SandboxEnforcement } from '@deepseek-ai/dsh-sandbox'
import { isDeepSeekHarnessCompatibleBaseUrl } from '../shared/deepseek-harness-compatibility'
const DEFAULT_MAX_FRAME_BYTES = 1024 * 1024
@@ -37,7 +33,7 @@ const MAX_DIAGNOSTIC_BYTES = 64 * 1024
export type ControlledHarnessHostConfig = Omit<
GoodBuddyHarnessControlConfig,
'stream' | 'skills'
'stream' | 'skills' | 'execution'
> & {
workspace: string
baseUrl: string
@@ -59,12 +55,6 @@ export type ControlledHarnessHost = {
export type ControlledHarnessHostStartupCode =
| 'HOST_PLUGIN_GRAPH_FAILED'
| 'HOST_SANDBOX_CONFIGURATION_FAILED'
| 'HOST_SANDBOX_EXECUTION_FAILED'
| 'HOST_SANDBOX_PROBE_ABORTED'
| 'HOST_SANDBOX_PROBE_EXIT_FAILED'
| 'HOST_SANDBOX_PROBE_RUNNER_FAILED'
| 'HOST_SANDBOX_PROBE_TIMED_OUT'
| 'HOST_CONTROL_PLANE_FAILED'
export class ControlledHarnessHostStartupError extends Error {
@@ -77,55 +67,6 @@ export class ControlledHarnessHostStartupError extends Error {
}
}
async function verifySandboxExecution(
ctx: Context,
expected: GoodBuddyHarnessControlConfig['sandbox'],
workspace: string
): Promise<void> {
const result = await ctx.shell.run(
ctx.shell.resolve({
command:
process.platform === 'win32'
? 'Write-Output goodbuddy-sandbox-probe'
: 'printf goodbuddy-sandbox-probe',
workdir: workspace,
timeoutMs: 10_000,
stdoutMaxBytes: 1_024,
sandboxPolicy: {
mode: 'read-only',
workspaceRoot: workspace
}
})
)
if (
result.sandbox?.enforcement !== expected.enforcement
) {
throw new Error(
'Controlled Harness sandbox execution probe failed'
)
}
if (result.timedOut) {
throw new ControlledHarnessHostStartupError(
'HOST_SANDBOX_PROBE_TIMED_OUT'
)
}
if (result.aborted) {
throw new ControlledHarnessHostStartupError(
'HOST_SANDBOX_PROBE_ABORTED'
)
}
if (result.sandbox?.runnerFailed) {
throw new ControlledHarnessHostStartupError(
'HOST_SANDBOX_PROBE_RUNNER_FAILED'
)
}
if (result.exitCode !== 0) {
throw new ControlledHarnessHostStartupError(
'HOST_SANDBOX_PROBE_EXIT_FAILED'
)
}
}
type PluginSpec = {
plugin: Parameters<Context['plugin']>[0]
config?: unknown
@@ -231,55 +172,6 @@ async function loadControlledSkills(
)
}
function sandboxProviderName(): string {
return process.platform === 'win32'
? 'windows-acl'
: process.platform === 'darwin'
? 'seatbelt'
: 'local-linux'
}
function verifySandbox(
sandbox: {
confine(
argv: readonly string[],
policy: {
mode: 'read-only'
workspaceRoot: string
}
): {
enforcement: SandboxEnforcement
}
},
config: ControlledHarnessHostConfig
): GoodBuddyHarnessControlConfig['sandbox'] {
const expectedEnforcement: SandboxEnforcement =
process.platform === 'win32' ? 'partial' : 'full'
const probe = sandbox.confine(
process.platform === 'win32'
? ['cmd.exe', '/d', '/s', '/c', 'exit 0']
: ['/usr/bin/env', 'true'],
{
mode: 'read-only',
workspaceRoot: config.workspace
}
)
if (probe.enforcement !== expectedEnforcement) {
throw new Error(
'Controlled Harness sandbox enforcement probe returned an unexpected result'
)
}
if (config.sandbox.enforcement !== probe.enforcement) {
throw new Error(
'Controlled Harness sandbox capability does not match the verified provider'
)
}
return {
provider: sandboxProviderName(),
enforcement: probe.enforcement
}
}
/**
* Boots a fixed, programmatic Cordis graph. It never imports app-boot, a
* profile loader, settings-file, local credentials, persistence, telemetry,
@@ -326,24 +218,18 @@ export async function startControlledDeepSeekHarnessHost(
}
}
},
{
plugin: SandboxPolicy,
config: {
mode: 'read-only',
workspaceRoot: config.workspace
}
},
{ plugin: ApprovalService, config: { policy: 'never' } },
{ plugin: LocalSubprocess },
{ plugin: LocalSandbox },
{ plugin: SandboxedFileSystem, config: { cwd: config.workspace } },
{ plugin: LocalFileSystem, config: { cwd: config.workspace } },
{ plugin: ShellEnv, config: { dshHome: config.dshHome } },
{
plugin:
process.platform === 'win32'
? SandboxedPwsh
: SandboxedBash,
config: { timeoutMs: 60_000 }
? LocalPwsh
: LocalBash,
config: {
cwd: config.workspace,
timeoutMs: 60_000
}
},
{ plugin: ToolFs },
{
@@ -376,14 +262,6 @@ export async function startControlledDeepSeekHarnessHost(
'Controlled Harness credential provider failed to start'
)
}
startupCode = 'HOST_SANDBOX_CONFIGURATION_FAILED'
const verifiedSandbox = verifySandbox(ctx.sandbox, config)
startupCode = 'HOST_SANDBOX_EXECUTION_FAILED'
await verifySandboxExecution(
ctx,
verifiedSandbox,
config.workspace
)
startupCode = 'HOST_CONTROL_PLANE_FAILED'
const rawStream =
config.stream ??
@@ -395,7 +273,7 @@ export async function startControlledDeepSeekHarnessHost(
const controlPlane = new GoodBuddyHarnessControlPlane(ctx, {
...config,
skills,
sandbox: verifiedSandbox,
execution: { mode: 'host' },
stream: createBoundedAcpStream(
rawStream,
config.maxFrameBytes ?? DEFAULT_MAX_FRAME_BYTES