Skip to content

Add browser pool parity fields to MCP#112

Open
IlyaasK wants to merge 21 commits into
mainfrom
browser-pools-parity-mcp-tool
Open

Add browser pool parity fields to MCP#112
IlyaasK wants to merge 21 commits into
mainfrom
browser-pools-parity-mcp-tool

Conversation

@IlyaasK
Copy link
Copy Markdown
Contributor

@IlyaasK IlyaasK commented Jun 1, 2026

Summary

  • add update support to the existing manage_browser_pools MCP tool
  • add browser pool create/update parity fields from the SDK: start_url, chrome_policy, kiosk_mode, extension selection, profile ID/save settings, and viewport settings
  • add update-only discard_all_idle support without requiring agents to resend unchanged pool size/config
  • reuse shared browser config helpers for profile, extension, and viewport request shaping across manage_browsers and manage_browser_pools
  • derive browser config response payload types from SDK method params instead of locally re-declaring SDK-shaped objects
  • improve MCP agent ergonomics with compact browser-pool/browser list responses, structured next_actions, stable pool-ID follow-ups, and structured SSH forwarding guidance
  • centralize MCP response helpers, pagination response formatting, and pagination schemas so tools do not hand-roll repeated { items, has_more, next_offset } payloads
  • tighten MCP schema validation for integer-valued fields such as pagination, timeouts, viewport dimensions, click counts, and durations
  • address review-bot findings by preserving full default profile inventory listing, keeping explicit empty paginated pages as structured JSON, ignoring empty chrome_policy objects, and guarding nullish pool list responses
  • restore the cleaner computer_action schema/execution structure from main while keeping clipboard support and integer validation from this stack

Why

  • browser pools can now be configured with the same core browser-session options used when warming pool browsers
  • MCP clients should be able to create and update pools without dropping to the SDK/CLI for start URLs, Chrome policy, extensions, profiles, or viewport settings
  • update-only operations such as discard_all_idle should not force agents to resend unchanged pool size/configuration
  • agents need compact list responses for selection, full get responses for inspection, and explicit next-step guidance after create/update/acquire operations
  • default profile listing should remain a complete inventory for agents, while explicit limit/offset still provides paginated control when requested
  • explicit empty pages should not read like global inventory absence, because that can make agents run setup or recovery flows unnecessarily
  • keeping browser config mapping, response formatting, and pagination behavior in shared helpers avoids drift across stacked project/API-key/browser/app/profile changes

Agent Experience / Flow

This PR gives agents a fast-session workflow for repeated browser work. Instead of creating a fresh browser for every task, an agent can configure a pool once, acquire pre-warmed sessions, use normal browser tools, and release sessions back into the pool.

Typical flow:

  1. Agent decides a pool is useful when a workflow needs repeated browser sessions with the same profile, viewport, policy, start URL, extension, proxy, or timeout configuration.
  2. Agent calls manage_browser_pools create size=<n> name=<name> with the same browser-shaping options it would otherwise pass to manage_browsers create, such as profile_id, start_url, chrome_policy, viewport_width, and extension_id.
  3. Agent uses manage_browser_pools list for a compact pool inventory and manage_browser_pools get id_or_name=<pool_id> for full details.
  4. Agent calls manage_browser_pools acquire id_or_name=<pool_id> to get a browser session.
  5. Agent uses the returned session_id with computer_action, execute_playwright_code, browser_curl, or exec_command.
  6. Agent calls manage_browser_pools release id_or_name=<pool_id> session_id=<id> reuse=true when the session can return to the pool, or reuse=false when it should be discarded and replaced.
  7. Agent calls manage_browser_pools update id_or_name=<pool_id> with only the fields it wants to change. size is required for create, but update accepts partial bodies such as discard_all_idle=true.
  8. Agent uses flush to remove idle browsers without deleting the pool, and delete only when the pool is no longer needed.

Agent-facing response behavior:

  • manage_browser_pools create/update returns a compact browser_pool summary plus next_actions.
  • manage_browser_pools acquire returns a compact browser summary plus next_actions for control/release/get-detail follow-up.
  • manage_browser_pools list returns compact summaries and points agents to get for full details.
  • Pool next-actions use the stable pool id, not the display name.
  • manage_browsers create/update returns structured JSON with browser and next_actions.
  • SSH forwarding guidance is now structured under ssh_port_forwarding instead of appended as mixed JSON + markdown.
  • Paginated tools share the same response shape through paginatedJsonResponse(page, { mapItem, note }); paginated empty pages always stay structured JSON with items, has_more, and next_offset.
  • manage_profiles list keeps the old agent-friendly default of returning the full matching inventory unless the caller explicitly asks for limit or offset.
  • Empty full-inventory guidance remains available through itemsJsonResponse, not through paginated responses.

How

  • typed pool create/update request bodies from KernelClient["browserPools"]
  • SDK-derived browser config output types from KernelClient["browsers"] and KernelClient["browserPools"]
  • shared profile, extension, viewport, and start URL request shaping in src/lib/mcp/browser-config.ts
  • shared response helpers in src/lib/mcp/responses.ts, including separate item and paginated response helpers
  • shared pagination input schema in src/lib/mcp/schemas.ts
  • create requires size; update allows partial configuration/update-only bodies and rejects only completely empty update requests
  • empty chrome_policy: {} is ignored, so it does not count as a real update field or get sent to the API
  • compact pool/browser summaries intentionally omit routine connection details while keeping full details available through get
  • computer_action keeps a single action schema and prefix executor so clipboard support does not split or duplicate the computer-use surface

Validation

Static and build checks:

  • bunx prettier --check src/lib/mcp/responses.ts src/lib/mcp/tools/apps.ts src/lib/mcp/tools/browsers.ts src/lib/mcp/tools/profiles.ts
  • git diff --check
  • git diff --cached --check
  • bunx tsc --noEmit --incremental false
  • production bun run build with dummy deployment env and network access for Google Fonts

Focused checks from the latest commit:

  • Direct response-helper smoke verified unpaginated empty inventories can still show setup guidance through itemsJsonResponse.
  • Direct response-helper smoke verified paginated empty pages preserve structured JSON with items: [], has_more, and next_offset.
  • Direct response-helper smoke verified paginated responses stay structured even if emptyText is forced through at runtime.
  • TypeScript verified emptyText is no longer part of paginatedJsonResponse options.

Earlier PR validation retained:

  • In-process toolset normalization test verified manage_computer_action, manage_search_docs, and legacy browser_utilities aliases disable the expected toolsets, and unknown disabled toolsets throw a clear error.
  • Focused MCP handler smoke verified default profile listing auto-iterates all matching profiles, explicit profile pagination preserves page metadata, empty pool chrome_policy returns a clean MCP error instead of sending an empty update, non-empty chrome_policy is still sent and summarized, and nullish pool list responses return No browser pools found.
  • Local MCP HTTP smoke against http://localhost:3002/mcp verified initialize, OPTIONS /mcp, tools/list, resources/list, prompts/list, schema assertions, and search_docs dummy-env behavior.
  • Live MCP validation checks verified fractional/invalid inputs return isError: true for pagination, pool size, browser_curl, computer_action, exec_command, and manage_browsers update validation paths.

Platform/API smoke context:

  • Full localhost browser-pool CRUD against the supplied org/key remains blocked by the platform plan gate: 403 Browser pools require a Start-Up or Enterprise plan.
  • The latest pass used a dummy opaque Bearer token for MCP transport/schema/validation tests, so it did not perform real Kernel API CRUD.

Notes

  • bun run format:check still fails on pre-existing AGENTS.md markdown table formatting. This PR uses touched-file Prettier checks to avoid unrelated project-instruction churn.

@vercel
Copy link
Copy Markdown

vercel Bot commented Jun 1, 2026

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
mcp Ready Ready Preview, Comment Jun 3, 2026 10:05pm

Comment thread src/lib/mcp/tools/browser-pools.ts Outdated
width,
height,
...(params.viewport_refresh_rate !== undefined && {
refresh_rate: params.viewport_refresh_rate,
Copy link
Copy Markdown

@vercel vercel Bot Jun 1, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Browser pool update action fails with "size is required" error even when user only wants to update other fields

Fix on Vercel

Comment thread src/lib/mcp/tools/browser-pools.ts Outdated
Comment thread src/lib/mcp/tools/browser-pools.ts
@firetiger-agent
Copy link
Copy Markdown

Monitoring Plan: Add update action to manage_browser_pools MCP tool

What this PR does: Lets AI agents update existing browser pool configurations (size, profile, extensions, viewport, chrome policy, kiosk mode, etc.) via the MCP tool — previously only create was supported.

Intended effect:

  • PATCH /browser_pools/{id_or_name} volume: baseline 119–169 req/hr; confirmed if requests flow successfully with ≤1% 4xx rate post-deploy
  • PATCH 5xx rate: baseline 0/hr; confirmed if stays at 0

Risks:

  • Field-scope validation regressionactionFieldError() may block valid fields; alert if PATCH 4xx rate exceeds 5/hr for 2 consecutive hours (baseline: 0–1/hr)
  • size required on updatebuildPoolConfigParams() throws if size is omitted; callers intending to patch only chrome_policy or kiosk_mode will get a silent MCP error; alert if any "size is required" log appears in API logs post-deploy
  • discard_all_idle pool drain — updating a live pool with this flag destroys idle browsers; alert if kernel_browser_pool_building_count sustains above 30 for >15 min
  • Acquire 5xx regression — misconfigured chrome_policy on a pool could cause new provisions to fail; alert if acquire 5xx exceed 20/hr for 2 consecutive hours (baseline: 0–20/hr isolated)

Status updates will be posted automatically on this PR as monitoring progresses.

View monitor

@firetiger-agent
Copy link
Copy Markdown

Monitoring plan created for browser pool update action and field-scope enforcement in MCP server.

Affected services: kernel-mcp-server (Vercel Preview), api

Key signals to watch (baseline: 24h pre-deploy):

  • PATCH /browser_pools/{id_or_name} error rate (4xx/5xx) — expect stable or slight increase from new update calls
  • kernel_browser_pool_building_count — watch for sustained spike if discard_all_idle is used
  • POST /browser_pools/{id_or_name}/acquire 5xx rate — baseline has sparse spikes (0–20/hr); sustained elevation would indicate pool configuration regression

Alert thresholds:

  • PATCH 4xx rate exceeds 5 errors/hr (baseline: 0–1/hr)
  • PATCH 5xx any spike (baseline: 0/hr)
  • Acquire 5xx sustained above 20/hr for 2+ hours (post-deploy)

[View monitor]

View monitor

Comment thread src/lib/mcp/tools/browser-pools.ts
Copy link
Copy Markdown
Collaborator

@masnwilliams masnwilliams left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

reviewed — large but well-structured: extracts shared helpers (responses.ts, browser-config.ts, resource-templates.ts) and brings browser pools to create/update parity. typechecks clean across the branch. this is the cleanup the earlier PRs were pointing at — resolves the duplicate textResponse, and the ResourceTemplate migration likely fixes "get one by URI" resources that the old static-URI + startsWith approach couldn't actually serve. also removes the dead extension-check from #110.

worth confirming before merge

  • pool update size cast (browser-pools.ts, ~updateParams as BrowserPoolUpdateParams): verified BrowserPoolUpdateParams.size is required in @onkernel/sdk@0.58.0, so the cast silences a real type error. it rests entirely on the comment's claim that the backend PATCH accepts partial bodies. if true → the SDK type is wrong, please file an SDK/OpenAPI fix and reference it here. if not → an update that omits size (e.g. just toggling headless) will 4xx at runtime despite typechecking. this is the one real risk in the PR.

notes

  • resource URI changed browser_pools://browser-pools:// (hyphen). documented in the README diff so it's intentional — just confirm nothing external referenced the old underscore form. note the other three schemes stayed single-word (apps:///browsers:///profiles://), so this is the only one that changed.

agent-fit

no new concern — pool lifecycle (incl. flush/delete) is core. cross-cutting: still no MCP annotations on any tool; adding readOnlyHint/destructiveHint here would let clients auto-confirm reads and prompt on flush/delete.

Comment thread src/lib/mcp/register.ts
Comment thread src/lib/mcp/tools/browser-pools.ts Outdated
@IlyaasK IlyaasK force-pushed the browser-utilities-mcp-tool branch 2 times, most recently from 0895123 to 384ec31 Compare June 3, 2026 00:04
Base automatically changed from browser-utilities-mcp-tool to main June 3, 2026 15:36
Comment thread src/lib/mcp/tools/browser-pools.ts Outdated
Comment thread src/lib/mcp/tools/browser-pools.ts Outdated
Comment thread src/lib/mcp/browser-config.ts Outdated
Comment thread src/lib/mcp/tools/browser-utilities.ts Outdated
@IlyaasK IlyaasK requested a review from masnwilliams June 3, 2026 20:04
@IlyaasK IlyaasK removed the request for review from masnwilliams June 3, 2026 20:22
Comment thread src/lib/mcp/tools/profiles.ts Outdated
Comment thread src/lib/mcp/tools/browser-pools.ts Outdated
Comment thread src/lib/mcp/tools/browser-pools.ts
Comment thread src/lib/mcp/tools/browsers.ts
@socket-security
Copy link
Copy Markdown

socket-security Bot commented Jun 3, 2026

Review the following changes in direct dependencies. Learn more about Socket for GitHub.

Diff Package Supply Chain
Security
Vulnerability Quality Maintenance License
Updated@​onkernel/​sdk@​0.58.0 ⏵ 0.60.082 +1010010098 +1100

View full report

Copy link
Copy Markdown

@cursor cursor Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cursor Bugbot has reviewed your changes and found 1 potential issue.

Fix All in Cursor

❌ Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, enable autofix in the Cursor dashboard.

Reviewed by Cursor Bugbot for commit dd77f9f. Configure here.

Comment thread src/lib/mcp/tools/profiles.ts Outdated
Resolve the active Cursor profile pagination bug by preserving structured JSON for explicit empty pages, restore the cleaner computer_action structure from main with clipboard support, derive browser config payload types from the SDK, and remove stale dead types.
Remove emptyText from paginated response options so explicit empty pages always return items, has_more, and next_offset. Keep empty guidance only on non-paginated item responses and update app/browser list callers accordingly.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants