Points Controlled Browser

The Points Controlled Browser lets AI operators control a real browser session from within a code point. Built on ArcSurf — MelodyArc's browser automation service — it runs a full Playwright-backed Chromium, Firefox, or WebKit instance that your code can navigate, interact with, and extract content from.

This fills a gap that API integrations cannot: websites that have no API, pages that require a login flow before exposing data, and content rendered dynamically by JavaScript that isn't present in a raw HTTP response.


When to use it

Use the Points Controlled Browser when a task requires information or actions that aren't reachable through a standard API integration:

ScenarioExample
No public APIA supplier portal publishes inventory updates only on a web dashboard
JavaScript-rendered pagesPricing or availability data is loaded dynamically and absent from the raw HTML
Multi-step web workflowsSubmitting a form, waiting for a confirmation page, then extracting a reference number
Visual captureTaking a screenshot of a report or dashboard to attach to a task

For straightforward data retrieval over a documented API, use a standard fetch call in a code point instead — the browser adds overhead that isn't necessary when an API is available.


How it works

ArcSurf runs as a separate service alongside the MelodyArc platform. When a code point calls the browser helper, the following happens:

  1. A temporary browser session is created (Chromium by default).
  2. The Point Engine executes your command sequence — navigating pages, interacting with elements, extracting content.
  3. Results, screenshots, and any captured HTML are returned to the code point and written to the data token.
  4. The session is torn down automatically. Sessions also expire after 15 minutes if not explicitly closed.

The browser runs headless by default. No persistent state is carried between sessions unless you explicitly manage it.


Configuration

Before using the Points Controlled Browser in a code point, set the following value points in your configuration:

Value pointDescription
__arcsurf_api_tokenAPI token for the ArcSurf service
arcsurf_api_endpointFull URL of the ArcSurf service, including protocol (e.g. https://arcsurf.example.com)
arcsurf_api_org_idYour MelodyArc organization ID

These are read automatically by the browser helper — you do not pass them as arguments in your code point.


Using in a code point

Load the browser helper at the start of your code point, then call _arcsurf.runSingleSession() with a list of commands.

async function execute_process() {
  await get_arcsurf_helper();

  const result = await _arcsurf.runSingleSession({
    session: {
      browser: "chromium",
      headless: true,
      viewport: { width: 1280, height: 720 },
    },
    commands: [
      { name: "goto", args: { url: "https://example.com/inventory" } },
      { name: "waitForSelector", args: { selector: ".inventory-table" } },
      { name: "getHTML", args: { selector: ".inventory-table" } },
    ],
  });

  // result.outputs[0].results contains the command responses
  // result.screenshot contains a PNG of the final page state
  return result;
}

runSingleSession() handles the full lifecycle: it creates the session, runs all commands in sequence, optionally captures a screenshot and page state, then tears the session down and returns all outputs.

The extracted HTML or other command results can then be written to the data token and processed by downstream points.


Common patterns

Extract content from a page

Use getHTML to retrieve the rendered HTML of a specific element. Pass the result to a code point that parses or summarises it.

commands: [
  { name: "goto", args: { url: "https://example.com/status" } },
  { name: "waitForSelector", args: { selector: "#status-panel" } },
  { name: "getHTML", args: { selector: "#status-panel" } },
]

Submit a form and capture the result

commands: [
  { name: "goto", args: { url: "https://example.com/lookup" } },
  { name: "fill", args: { selector: "#order-id", value: _token.order_id } },
  { name: "click", args: { selector: "button[type=submit]" } },
  { name: "waitForSelector", args: { selector: ".confirmation" } },
  { name: "getHTML", args: { selector: ".confirmation" } },
]

Take a screenshot

runSingleSession() captures a screenshot of the final page state automatically. To capture at a specific point mid-sequence, add an explicit command:

{ name: "screenshot", args: { name: "report-snapshot" } }

Screenshots are returned in result.screenshot (on-demand PNG) and result.assets (named captures from screenshot commands).


Available commands

CommandDescriptionKey arguments
gotoNavigate to a URLurl
clickClick an elementselector
fillFill an input fieldselector, value
pressPress a key on an elementselector, key
waitForSelectorWait for an element to appearselector
scrollScroll the page or an elementselector (optional), x, y
executeScriptRun JavaScript in the page contextscript, arg (optional)
focusFocus an elementselector
validateAssert element values or statesassertions[]
pauseDelay executionduration (ms)
screenshotCapture and store a screenshotname (optional)
getHTMLRetrieve HTML from an element or the full pageselector (optional), outer (boolean)