Releases: Agent-Pattern-Labs/geometra
v1.62.1
Release notes — 1.62.1 (Playwright browser cache recovery)
Summary
1.62.1 hardens the MCP browser proxy against Playwright browser-cache skew:
@geometra/proxynow retries stock Chromium launch once after installing the browser revision required by the resolved local Playwright package. This covers shared-cache states where another Playwright version pruned the expectedchromium_headless_shellrevision.@geometra/mcpnow treats managed child-process proxy startup as ready only after the structured ready signal, which is emitted after browser launch and initial page readiness.- Added
npm run browsers:installas a local-version-safe repair command for the Playwright Chromium cache.
Migration notes
No API or protocol changes. GEOM v1 stays compatible.
Operators can disable automatic browser repair with:
GEOMETRA_PROXY_AUTO_INSTALL_BROWSERS=0If browser downloads are disabled via PLAYWRIGHT_SKIP_BROWSER_DOWNLOAD=1, Geometra will not auto-install Chromium and will surface the explicit local install command instead.
Performance notes
- Normal proxy startup is unchanged when the expected browser revision already exists.
- The retry path only runs after Playwright reports a missing Chromium executable.
- No hit-test, text metrics, layout, or geometry-diff behavior changed.
Verification
-
npm run check -w @geometra/proxy -
npm run mcp:check -
npx vitest run mcp/src/__tests__/connect-utils.test.ts mcp/src/__tests__/proxy-session-recovery.test.ts -
npm run build -w @geometra/proxy -
npm run mcp:build - Stock proxy smoke through
launchProxyRuntime({ stealth: false })
v1.61.3
Release v1.61.3 adds opt-in CloakBrowser stealth Chromium support for Geometra proxy and MCP pageUrl flows.\n\nHighlights:\n- Add --stealth / GEOMETRA_STEALTH=1 / GEOMETRA_BROWSER=stealth to geometra-proxy.\n- Add stealth: true to proxy-backed MCP connect, prepare, schema, fill, submit, and run-actions flows.\n- Partition the warm proxy pool by browser flavor so stock and stealth Chromium sessions cannot reuse each other.\n- Document CloakBrowser setup and add focused MCP coverage.\n\nVerification run locally:\n- bun run build\n- bun run release:gate\n- bun run lint\n- npm run check -w @geometra/proxy\n- npm run check in mcp\n- npx vitest run mcp/src/tests/proxy-session-recovery.test.ts mcp/src/tests/server-batch-results.test.ts
v1.61.2
Fix Geometra MCP host-timeout behavior by adding host-safe soft deadlines, resumable run_actions progress, submit_form timeout capping, and bounded semantic reveal loops.
v1.61.1 — Publish gateway package
Summary
- Adds @geometra/gateway to the publish manifest so deploy apps can install it from npm.
- Adds public hosted sandbox deployment guidance.
- Bumps publishable packages to 1.61.1.
Verification
- Quality checks passed on main for 95caeee.
- Release source check includes @geometra/gateway at 1.61.1.
v1.61.0 — Agent-native claims hardening
Summary
- Adds a public audit replay viewer for the agent-native claims workflow.
- Adds core gateway approval/result hooks for webhook-style integrations.
- Deepens the claims/compliance starter with queue filters, evidence panels, risk policy, and audit packet export.
- Expands the live browser comparison into a fuller approval flow with DOM/screenshot trace comparison.
Verification
- Quality checks passed on main for d93292d.
- Local focused gateway tests, demo build, examples check, lint, and live benchmark passed.
v1.60.0 — Agent-native UI protocol runtime
Summary
- Add agent-native semantic geometry snapshots and stable UI ids in
@geometra/core. - Add
createAgentRuntime()for inspect/click/focus/type/key/replay workflows. - Add gateway
/inspect, MCP-style inspect tooling, replay artifacts, external-agent demo script, and benchmark methodology.
Validation
- GitHub
qualitycheck passed onb9915acd. - Local focused tests, core/gateway builds, demo build, and
benchmark:agent-native:assertpassed before release.
v1.59.1 — menu-trigger dropdowns with container labels
Fix
pickListboxOption / setFieldChoice / fillFields kind:choice now match GitHub Primer–style dropdown triggers where the button's accessible name is the current selected value (e.g. Branch) rather than the field label (Ref type).
- Adds
[aria-haspopup="menu"]/[aria-haspopup="true"]to labeled-control discovery - Adds
[role="menuitemradio"]/[role="menuitemcheckbox"]to the option picker - New
findMenuTriggerByContainerLabelfallback walks up to 4 parent levels to match on the container's visible text minus the button's own text, with trailing-colon tolerance (Ref type:) - 2 new fixture tests in
packages/proxy/src/__tests__/dom-actions.test.ts
Motivating case
GitHub's Add deployment branch or tag rule dialog (and other Primer admin UIs) render dropdowns as <span>Ref type</span><button aria-haspopup="menu">Branch</button> — this pattern was previously invisible to fill_fields/pick_listbox_option. Tested live against GitHub settings while fixing it.
Verified
- 2473 / 2473 fast tests across 88 files
packages/proxy+mcpbuilds clean
🤖 Generated with Claude Code
v1.59.0 — BYO proxy passthrough in geometra_connect / prepare_browser
Summary
Adds optional BYO proxy passthrough so consumers can route the spawned Chromium through a residential / mobile / SOCKS proxy.
- New
proxyparameter ongeometra_connectandgeometra_prepare_browserMCP tools:{ server, username?, password?, bypass? } - Forwarded to Playwright's
chromium.launch({ proxy })— supportshttp://,https://,socks5://servers with optional basic auth and comma-separated bypass patterns - Reusable proxy pool partitioned by proxy identity (server + username + bypass) so direct and proxied sessions never share a Chromium, and sessions with different proxy configs don't pool either
- CLI flags on
geometra-proxy:--proxy-server,--proxy-username,--proxy-password,--proxy-bypass - Env fallbacks:
GEOMETRA_PROXY_SERVER,GEOMETRA_PROXY_USERNAME,GEOMETRA_PROXY_PASSWORD,GEOMETRA_PROXY_BYPASS - Back-compat: no proxy argument → identical existing behavior
Why
Apply portals on Ashby, Lever, and Cloudflare-fronted ATSes fingerprint datacenter IPs and silently reject headless submits as bots ("flagged as possible spam"). Giving consumers a BYO proxy hook lets them pay for residential IP coverage without Geometra needing to bundle or resell bandwidth.
Usage
await geometra_connect({
pageUrl: "https://jobs.ashbyhq.com/acme",
isolated: true,
proxy: {
server: "http://residential-proxy.example.com:8080",
username: "me",
password: "secret",
bypass: "*.internal,localhost",
},
})v1.58.0 — durable MCP sessions via @razroo/parallel-mcp
@geometra/mcp — durable sessions
Wired @razroo/parallel-mcp into Geometra MCP so session state survives WebSocket crashes.
- Sessions get UUID-backed ids backed by a
SqliteParallelMcpStore. - Snapshots on proxy attach, transport close, reconnect, and navigate.
- A WebSocket crash no longer erases the logical session — it stays addressable, records a
session.transport_closedsnapshot, and Geometra reconnects on the next tool call. - Explicit disconnect now finalizes durable state instead of just dropping in-memory state.
- SQLite file is process-scoped by default (override with
GEOMETRA_MCP_STATE_FILE) to avoid lock contention across parallel workers.
CI
Includes a CI fix hoisting @razroo/parallel-mcp into the root lockfile so root vitest can resolve imports from mcp/src (mcp/ isn't a bun workspace).
Scope
Improves the failure mode for parallel MCP state: durable, reconnectable, less likely to smear across workers. Does not magically fix every upstream proxy/browser crash — live DOM/layout and some workflow state remain in-memory for now.
v1.57.0 — draggableSort + vitest cleanup + cookbook fix
Release notes — 1.57.0 (draggableSort + vitest cleanup + cookbook fix)
Summary
1.57.0 adds the second big gesture-driven UI primitive, fixes a long-standing cookbook error, and cleans up the default vitest run invocation on a fresh checkout:
@geometra/ui— newdraggableSortprimitive. Vertical list that reorders via pan gesture (canvas) or keyboard (ArrowUp/Down, Home/End). ComplementsswipeableListto round out the gesture-driven list family.INTEGRATION_COOKBOOK.md— the modal focus policy recipe no longer uses the non-existentSignal.subscribe(callback)API; it now useseffect(() => signal.value)which is the real Signal observation surface shipped from@geometra/core.vitest.config.ts— excludestests/e2e/**so Playwright specs (which import@playwright/test) no longer crash a barevitest runon a fresh checkout. Spec runs still happen through the Playwright runner.
@geometra/ui — draggableSort
Vertical reorderable list. Rows carry their own click + key handlers, so drag and keyboard flows share the same hit pipeline:
import { draggableSort } from '@geometra/ui'
import { attachGestureRecognizers } from '@geometra/renderer-canvas'
const list = draggableSort({
items: tasks,
itemHeight: 48,
renderItem: (task, { index, isDragging }) =>
taskRow(task, index, isDragging),
onReorder: (from, to, next) => saveOrder(next),
})
attachGestureRecognizers(canvas, list.recognizers)
// Imperative rail:
list.moveUp(0) // bump first task up (no-op at edge)
list.move(3, 0) // move index 3 to index 0
list.order.value // current snapshot
list.draggingIndex.value // index held by the user, or nullKeyboard rail (bound to each row automatically):
- ArrowDown / ArrowUp — move the focused row down / up one slot
- Home / End — jump the focused row to the top / bottom
Reorder semantics:
itemHeightis fixed across all rows (variable row height is out of scope).- Drag uses the pan recognizer's
deltaYdivided byitemHeightto compute the target slot; live reorder updates while the pointer is held, committed on release. - Pointer-cancel keeps the interim reorder (undo is a caller concern).
Scope note: attach list.recognizers when there's no other canvas-wide pan consumer. Scoping recognizers to a region is an app-level concern — the local-canvas demo intentionally runs draggableSort with keyboard-only input because swipeableList.recognizers are already attached canvas-wide.
Cookbook fix — modal focus policy
The 1.55.0 recipe for composing focusFirstInside + trapFocusStep + animatedDialog used a dlg.isOpen.subscribe((open) => …) call. Signal<T> in @geometra/core exposes value / set / peek — there is no .subscribe() method. The correct pattern uses effect:
import { effect } from '@geometra/core'
effect(() => {
const open = dlg.isOpen.value
if (!open) return
queueMicrotask(() => {
focusFirstInside(app.tree, app.layout, DIALOG_PATH)
})
})Anyone who followed the 1.55.0 recipe literally would have hit a runtime TypeError on the .subscribe call. The updated recipe in INTEGRATION_COOKBOOK.md uses effect and matches the real API.
vitest cleanup
Before this release, npx vitest run (no config parameter) picked up tests/e2e/full-stack-dashboard.spec.ts via vitest's default **/*.spec.ts glob and crashed on the @playwright/test import. vitest.config.ts now explicitly excludes tests/e2e/** while keeping vitest's default excludes (node_modules, dist, various build configs).
Consequence: a fresh checkout can run vitest run from the repo root and get a clean unit-test pass (2,701 / 2,701 across 92 files). Playwright specs continue to run through npx playwright test.
Migration notes
All additions are additive. No protocol changes. GEOM v1 stays fully compatible.
New exports from @geometra/ui:
draggableSort<T>- Types:
DraggableSort<T>,DraggableSortOptions<T>,DraggableSortItemState
No existing export signatures changed.
Performance notes
draggableSort's pan path fires only when a row has latchedpendingIndexat pointerdown — dragging empty space in the list bounds does nothing, matching swipeableList's cost profile.draggableSort.view()re-renders onorder/draggingIndexchanges via signals — no extra reconciler work when idle.- vitest
excludeis a bare glob check; no measurable test-suite time change.
Verification
- Full fast suite: 2,471 / 2,471 passing across 88 test files.
- Default
vitest run(no config parameter): 2,701 / 2,701 passing across 92 files. - New tests: 7 for
draggableSort.