Quickstart
Get one real result out of Bowmark before you install anything, then wire it into your agent.
Most integrations ask you to install first and trust that something happened. Bowmark is a public HTTP endpoint with no auth, so you can do it the other way round: get a real answer out of it first, decide it is worth installing second.
1 — See it work. Nothing installed.
Paste this into any terminal. No account, no key, no signup.
curl -s https://api.bowmark.ai/v1/run \
-H 'Content-Type: application/json' \
-d '{"script":"const { offers } = await bowmark.pcparts.search(\"RTX 5080\"); return offers.slice(0, 3);"}'It sits there for about ten seconds, because in that time Bowmark is searching Newegg, Micro Center and B&H at once and price-sorting what comes back. This is what it printed, recorded 2026-08-24:
{
"ok": true,
"status": "ok",
"ms": 9953,
"result": [
{
"store": "newegg",
"price": 1449.99,
"title": "MSI INSPIRE GeForce RTX 5080 16GB GDDR7 PCI Express 5.0 Graphics Card"
},
{
"store": "bhphoto",
"price": 1499.99,
"title": "Gigabyte GeForce RTX 5080 MASTER Graphics Card"
},
{
"store": "newegg",
"price": 1549.99,
"title": "PNY GeForce RTX 5080 OC 16GB 256-Bit GDDR7 DLSS 4.0 Graphics Card"
}
]
}Your prices will differ, and that is the point: those numbers came off the retailers' live pages while the request was open, not out of an index.
What the ten seconds were spent on
Every response also carries a trace. It is the receipt — one row per site Bowmark
actually reached, with what each one gave back. Summarised, from the same run:
newegg ok 3 offers 4100ms
bhphoto ok 3 offers 5426ms
microcenter empty 0 offers 9943ms
-> pcparts ok 9946msThree retailers were searched in parallel and Micro Center had nothing matching, so the answer is the cheapest of two. Bowmark reports that rather than hiding it — which is the difference between a result you can quote and one you can only hope about.
That was the whole product
You just wrote a script against the capability library and had it executed against live retail sites. No browser was opened, no page was rendered, and nothing was installed. Everything below is about getting your agent to do that on its own.
2 — Install it into your agent
One line, one time. Pick your host. Where a plugin exists, take it — it wires the MCP and installs the skill that teaches your agent when to reach for Bowmark, and it lands in the host's own plugin list. Installation has the shortest path for every host in one table, including the double-click bundle for Claude Desktop.
claude mcp add bowmark --transport http https://api.bowmark.ai/mcpRun it from any terminal. Every project picks Bowmark up — there is no per-project step, and nothing to name in a prompt. Claude reaches for it on its own when a task needs the live web.
Want the skill bundled in too? One install does both:
claude plugin marketplace add bowmark-ai/plugin
claude plugin install bowmark@bowmark-aiFour clicks, about a minute. Full screenshots are on Installation.
Go to chatgpt.com/plugins and click + (top right).
Name it Bowmark, choose Server URL, paste https://api.bowmark.ai/mcp, set
No Auth, tick the box, hit Create.
Hit Connect on the next screen.
In a chat, type @ and pick Bowmark. You must do this every turn — see the warning below.
Settings → MCP → Add new MCP server, then paste:
{
"mcpServers": {
"bowmark": { "url": "https://api.bowmark.ai/mcp" }
}
}codex plugin marketplace add bowmark-ai/pluginThen codex /plugins and install Bowmark from the list. Or edit
~/.codex/config.toml directly:
[mcp_servers.bowmark]
url = "https://api.bowmark.ai/mcp"Same URL, same no-auth server. Windsurf, Claude Desktop, LM Studio, browser-use, your own agent — every path is on Installation.
If your host speaks stdio rather than HTTP, bridge it:
{
"mcpServers": {
"bowmark": { "command": "npx", "args": ["@bowmark/mcp"] }
}
}3 — Give your agent its first task
Paste this into a fresh chat, verbatim:
Price an RTX 5080 across every retailer you can reach, and tell me
which store is cheapest and what it costs right now.In ChatGPT, type @ and pick Bowmark first. Everywhere else, just send it.
A working agent does three things, in this order, and you can watch each one:
- Calls
get_librarywith something like"pc parts". No site is touched. - Calls
runwith a few lines of JavaScript it wrote against what came back. - Answers with a store name, a price, and a link you can click.
If it answers without calling a tool, it did not use Bowmark — it answered from
memory or browsed. In ChatGPT that is almost always the missing @.
4 — When it doesn't work
Three failures account for nearly all of them.
The agent never called Bowmark
In ChatGPT, a custom connector is inert until you attach it for that turn. This is
documented OpenAI behaviour and no amount of prompt wording changes it. Type @,
pick Bowmark, then ask. Everywhere else, the tools are in scope on every turn.
TypeError: Cannot read properties of undefined
The script called a function with the wrong argument shape and then read a field off
undefined. Signatures are not uniform on purpose — bowmark.pcparts.search takes a
plain string, bowmark.flights.search takes an object.
// wrong — search takes a string here
const { offers } = await bowmark.pcparts.search({ query: "RTX 5080" });
// right
const { offers } = await bowmark.pcparts.search("RTX 5080");The fix is always the same: call get_library for that capability and read the
signature. It costs nothing and touches no site.
It answered, but the answer looks thin
Read warnings and the trace together — they say different things, and reading
only one of them is how a thin answer gets quoted as a complete one.
warningsnames every site dropped from the fan-out: it failed, or it timed out. A populatedwarningsmeans a site was never heard from at all.tracehas one row per site regardless, with what each one returned. A row readingemptyis a site that answered and had nothing matching.
So an empty warnings does not mean every site had a result — it means none were
dropped. The run above is exactly that case: warnings was [], and Micro Center
still contributed nothing. Read both before you call an answer complete.
Check status before ok — partial means the script ran and the result is real
but narrower than you asked for. Full rules in Scripting.
Where to go next
- How it works — the two calls, drawn, and why the surface is a language rather than a menu of tools.
- Scripting — the globals, the sandbox rules, and how to read the response envelope.
- Installation — every host, with screenshots, plus API keys and what they unlock.