feat: 增加共享 Agent Browser 调试能力

需求:在 AI 编程会话中让用户与 Agent 共享同一浏览器页面,并查看控制台与网络信息。

实现:新增沙箱浏览器内核、Host API/渲染器面板、OpenCode 工具接入及安全边界测试。
This commit is contained in:
2026-07-31 14:53:36 +08:00
parent 80e8386fa6
commit e97a7ce9df
39 changed files with 6734 additions and 9 deletions

View File

@@ -8,6 +8,7 @@ import {
type SpawnOptionsWithoutStdio,
} from 'node:child_process';
import {
ensureBundledAgentBrowserPlugin,
ensureBundledCourseSkills,
ensureBundledSuperpowersPlugin,
getManagedOpencodeConfigDir,
@@ -163,6 +164,7 @@ export interface OpencodeManagerOptions {
userDataDir?: string;
bundledSuperpowersDir?: string;
bundledCourseSkillsDir?: string;
bundledAgentBrowserPluginPath?: string;
pythonRuntime?: PythonRuntime;
spawn?: SpawnFn;
configProvider?: ConfigProvider;
@@ -580,6 +582,10 @@ export class OpencodeManager extends EventEmitter {
managedConfigDir,
sourceDir: this.options.bundledCourseSkillsDir,
});
ensureBundledAgentBrowserPlugin({
managedConfigDir,
sourcePath: this.options.bundledAgentBrowserPluginPath,
});
const environment = {
...runtimeEnv,
OPENCODE_CONFIG_DIR: managedConfigDir,

View File

@@ -34,6 +34,7 @@ const SUPERPOWERS_REPO_DIR = 'superpowers';
const SUPERPOWERS_BUNDLES_DIR = 'superpowers-bundles';
const SUPERPOWERS_ACTIVE_MANIFEST = 'superpowers-active.json';
export const BUNDLED_COURSE_SKILL_IDS = [
'agent-browser',
'deploy-publish-check',
'designer-design-spec',
'dev-build-test',
@@ -63,6 +64,16 @@ export function resolveBundledCourseSkillsDir(input: BundledSuperpowersPathInput
: join(input.appPath, '.opencode', 'skills');
}
export function resolveBundledAgentBrowserPluginPath(input: BundledSuperpowersPathInput): string {
return join(
resolveBundledCourseSkillsDir(input),
'agent-browser',
'.opencode',
'plugins',
'niancode-agent-browser.js',
);
}
export function getManagedOpencodeConfigDir(userDataDir: string): string {
return join(userDataDir, 'opencode', 'niancode-config');
}
@@ -266,3 +277,15 @@ export function ensureBundledCourseSkills(options: EnsureBundledCourseSkillsOpti
return true;
}
export function ensureBundledAgentBrowserPlugin(options: {
managedConfigDir: string;
sourcePath?: string;
}): boolean {
const sourcePath = options.sourcePath?.trim();
if (!sourcePath || !existsSync(sourcePath)) return false;
const targetPluginsDir = join(options.managedConfigDir, 'plugins');
mkdirSync(targetPluginsDir, { recursive: true });
cpSync(sourcePath, join(targetPluginsDir, 'niancode-agent-browser.js'), { force: true });
return true;
}