Add live web search to a Mastra agent

Superhighway guides

Mastra's createTool() helper and MCP support make it easy to give any TypeScript agent live web search — either via an autonomous x402 wallet or a free API key.

Two paths

PathBest forWhat you need
MCPConfigurationAll five tools, fully autonomous — agent pays per callA funded Base wallet + npx
createTool() + API keyTyped tools with Zod schemas, controlled spendA free API key from /pricing

Path 1: MCP via MCPConfiguration (recommended for autonomous agents)

npm install @mastra/core @mastra/mcp @ai-sdk/openai zod
import { Agent } from '@mastra/core/agent'
import { MCPConfiguration } from '@mastra/mcp'
import { openai } from '@ai-sdk/openai'

const mcp = new MCPConfiguration({
  servers: {
    superhighway: {
      command: 'npx',
      args: ['-y', 'superhighway-mcp'],
      env: {
        AGENT_PRIVATE_KEY: process.env.AGENT_PRIVATE_KEY!,
        X402_NETWORK: 'base',
      },
    },
  },
})

const agent = new Agent({
  name: 'Search Agent',
  instructions: 'You are a research assistant with access to live web search.',
  model: openai('gpt-4o'),
  tools: await mcp.getTools(),
})

const result = await agent.generate(
  'What are the latest developments in AI agent frameworks?',
)
console.log(result.text)

The MCP server exposes all five tools — web_search, news_search, image_search, scrape, research — and each call settles a $0.001–$0.005 USDC payment automatically via x402. See wallet setup or the x402 flow.

Path 2: createTool() with an API key

Get a free API key (1,000 calls/month) and define typed tools with Zod input schemas:

npm install @mastra/core @ai-sdk/openai zod
import { Agent } from '@mastra/core/agent'
import { createTool } from '@mastra/core/tools'
import { openai } from '@ai-sdk/openai'
import { z } from 'zod'

const BASE = 'https://superhighway.walls.sh'
const KEY = process.env.SUPERHIGHWAY_API_KEY!

const webSearch = createTool({
  id: 'web-search',
  description: 'Search the live web for current information, facts, and events.',
  inputSchema: z.object({
    query: z.string(),
    limit: z.number().optional(),
  }),
  execute: async ({ context }) => {
    const { query, limit = 5 } = context
    const res = await fetch(
      `${BASE}/search?q=${encodeURIComponent(query)}&limit=${limit}`,
      { headers: { Authorization: `Bearer ${KEY}` } },
    )
    const data = await res.json()
    return data.results
      .map((r: any) => `${r.title}\n${r.url}\n${r.description}`)
      .join('\n\n')
  },
})

const newsSearch = createTool({
  id: 'news-search',
  description: 'Search recent news articles with published dates.',
  inputSchema: z.object({ query: z.string() }),
  execute: async ({ context }) => {
    const res = await fetch(
      `${BASE}/news?q=${encodeURIComponent(context.query)}`,
      { headers: { Authorization: `Bearer ${KEY}` } },
    )
    const data = await res.json()
    return data.results
      .map((r: any) => `${r.title} (${r.publishedDate ?? ''})\n${r.url}\n${r.description}`)
      .join('\n\n')
  },
})

const research = createTool({
  id: 'research',
  description: 'Search + read the top matching pages in one call. Use for deep synthesis.',
  inputSchema: z.object({
    query: z.string(),
    pages: z.number().optional(),
  }),
  execute: async ({ context }) => {
    const { query, pages = 2 } = context
    const res = await fetch(
      `${BASE}/research?q=${encodeURIComponent(query)}&pages=${pages}`,
      { headers: { Authorization: `Bearer ${KEY}` } },
    )
    const data = await res.json()
    return data.pages
      .filter((p: any) => !p.error)
      .map((p: any) => `## ${p.title}\n${p.url}\n\n${p.markdown.slice(0, 3000)}`)
      .join('\n\n---\n\n')
  },
})

const agent = new Agent({
  name: 'Search Agent',
  instructions: 'You are a research assistant with access to live web search.',
  model: openai('gpt-4o'),
  tools: { webSearch, newsSearch, research },
})

const result = await agent.generate('Summarize the top AI news from the last 48 hours.')
console.log(result.text)

Each createTool() definition is typed end-to-end with Zod: the inputSchema validates the agent's call and populates context in execute. Add only the tools your agent needs — webSearch + newsSearch for real-time Q&A, research for multi-page synthesis.

Which tools are available

Tool / endpointWhat it returnsPrice
web_search / /searchRanked web results — title, URL, description$0.001
news_search / /newsRecent news with published dates$0.001
image_search / /imagesImage URLs, thumbnails, source pages$0.001
scrape / /scrapeAny URL → clean markdown text$0.002
research / /researchSearch + read top pages in one call$0.005

Full API reference: /openapi.json. Get a free API key or learn the x402 wallet flow.