Docs
Dashboard
Examples / Get startedBeta

Get a page, or a browser?

The same site two ways. fetch is one call that returns the page as Markdown (rendered in a real browser in a sandbox): use it to read. A session is a browser that stays open between calls, so it can click through pages, fill forms and sign in: here it clicks on to page 3.

When to use it: You are deciding between one fetch call and a browser session that stays open.

Usesfetch (Markdown and links), a session driven by the actions API (goto, click, wait, evaluate)
Needsany plan; no shell, no model
Sitequotes.toscrape.com, a demo site made for scraping practice
Outputoutput/result.json: what fetch returned (title, size, links, time) and what the session read on pages 2 and 3
LanguagesNode and Python

The code

The example as it is in its folder. Both versions do the same job and write the same output/, so one result check covers both.

/** * Get a page, or a browser? The same site two ways: fetch (one call, the page as Markdown: for reading) and a session * (a browser that stays open between calls: for clicking through pages, forms and sign-ins). * *   npx tsx node/index.ts            (BOXLINE_API_KEY in the environment; PAGE_URL for another site) */import { mkdirSync, writeFileSync } from "node:fs";import { join } from "node:path";import { Boxline } from "@boxline/sdk";const out = process.env.OUTPUT_DIR ?? "output";const url = process.env.PAGE_URL ?? "https://quotes.toscrape.com/";const bx = new Boxline();// 1. fetch: the page is rendered in a real browser inside a sandbox and comes back as Markdown, with its links.let t0 = Date.now();const page = await bx.fetch(url, { format: "markdown", links: true });const fetched = { title: page.title, status: page.status, chars: page.content.length, links: page.links?.length ?? 0, ms: Date.now() - t0 };console.log(`fetch: "${page.title}" (HTTP ${page.status}), ${fetched.chars} characters of Markdown and ${fetched.links} links in ${fetched.ms} ms`);// 2. A session: the browser keeps its page, cookies and history between calls, so it can click on to page 3.const session = await bx.sessions.create({ timeout: 300, userMetadata: { example: "fetch-or-browser" } });console.log(`Session: ${session.id}`);try {  t0 = Date.now();  await session.goto(url);  const pages: { url: string; authors: string[] }[] = [];  for (let i = 0; i < 2; i++) {    const results = await session.actions([      { action: "click", selector: "li.next a" },      { action: "wait", selector: ".quote" },      { action: "evaluate", expression: "({ url: location.href, authors: [...document.querySelectorAll('.quote .author')].map((a) => a.textContent) })" },    ]);    const read = results.at(-1)!.value as { url: string; authors: string[] };    console.log(`session: ${read.url}: ${read.authors.length} quotes, the first by ${read.authors[0]}`);    pages.push(read);  }  const browsed = { ms: Date.now() - t0, pages };  mkdirSync(out, { recursive: true });  writeFileSync(join(out, "result.json"), JSON.stringify({ url, fetch: { ...fetched, hasEinstein: page.content.includes("Albert Einstein") }, session: browsed }, null, 2));  console.log("Use fetch to read a page; use a session when you need to act on it (click, type, sign in, download).");} finally {  await session.stop();}

Inputs

Environment variables the example reads:

  • PAGE_URL: the page to read (the session part clicks li.next a) (default https://quotes.toscrape.com/).

Run it

Get the examples with git clone https://github.com/Boxline-dev/examples.git and open this one: cd examples/fetch-or-browser. Put your API key in BOXLINE_API_KEY (and BOXLINE_API_URL for another API), then run either version from the example’s folder. Both write to output/ and stop their sessions when they finish.

# Node 18 or newer, in the example's folderexport BOXLINE_API_KEY=…   # your API keynpm install @boxline/sdk tsxnpx tsx node/index.ts

Then check the result, from the same folder: npx tsx check.ts output. It exits with 0 only when the result is right.

What its check proves

check.ts reads what the example wrote and passes only when the result is right, not merely when the example ran.

Fetch returned the page (HTTP 200, Einstein's quote, over 10 links), and the session ended on /page/3/ with 10 quotes on each page.

Source

github.com/Boxline-dev/examples/fetch-or-browser on GitHub, with its README.md, check.ts and .env.example. The examples are open source. See all examples.

These docs describe a beta API. Endpoints, fields and SDK methods may change before general availability; breaking changes will be listed in the changelog.