fix(agent-browser): restore bounded presentation lifecycle

This commit is contained in:
2026-09-06 12:50:18 +08:00
parent 5c61110f46
commit 9fed0cc7c4
20 changed files with 1714 additions and 49 deletions

View File

@@ -1294,6 +1294,76 @@ describe('AgentBrowserModule', () => {
expect(adapter.views[0].visible).toBe(false);
});
it('waits for the matching browser generation to be presented without polling', async () => {
const adapter = new FakeAdapter();
const module = new AgentBrowserModule(adapter);
const opened = await module.open({
projectId: 'clock',
projectPath,
url: 'http://localhost:3000',
visible: false,
});
let settled = false;
const presented = module.waitForPresentation({
projectPath,
generation: opened.generation,
timeoutMs: 1_000,
}).finally(() => {
settled = true;
});
await Promise.resolve();
expect(settled).toBe(false);
await module.present({
projectPath,
visible: true,
bounds: { x: 1, y: 2, width: 640, height: 480 },
});
await expect(presented).resolves.toMatchObject({
state: 'attached',
generation: opened.generation,
visible: true,
bounds: { x: 1, y: 2, width: 640, height: 480 },
});
});
it('keeps diagnostics enabled until every explicit owner releases them', async () => {
const adapter = new FakeAdapter();
const module = new AgentBrowserModule(adapter);
await module.open({
projectId: 'clock',
projectPath,
url: 'http://localhost:3000',
diagnosticsOwner: 'agent:conversation-a:run-a',
visible: true,
bounds: { x: 0, y: 0, width: 800, height: 600 },
});
const commands = adapter.views[0].webContents.debugger.commands;
expect(commands.map(({ method }) => method)).toEqual(expect.arrayContaining([
'Runtime.enable',
'Log.enable',
'Network.enable',
'Page.enable',
]));
await module.setDiagnostics({ projectPath, enabled: true, owner: 'renderer' });
await module.setDiagnostics({
projectPath,
enabled: false,
owner: 'agent:conversation-a:run-a',
});
expect(commands.some(({ method }) => method === 'Runtime.disable')).toBe(false);
await module.setDiagnostics({ projectPath, enabled: false, owner: 'renderer' });
expect(commands.map(({ method }) => method)).toEqual(expect.arrayContaining([
'Page.disable',
'Network.disable',
'Log.disable',
'Runtime.disable',
]));
});
it('tears down the native view when initial navigation fails', async () => {
const adapter = new FakeAdapter();
adapter.onCreate = (view) => {