Skip to main content
These patterns cover the most common ways to integrate TinyFish Web Agent into your application.

Simple Extraction

Use the synchronous endpoint for quick, one-off extractions where you need the result immediately.
async function extractData(url: string, dataDescription: string) {
  const response = await fetch("https://agent.tinyfish.ai/v1/automation/run", {
    method: "POST",
    headers: {
      "X-API-Key": process.env.TINYFISH_API_KEY,
      "Content-Type": "application/json",
    },
    body: JSON.stringify({
      url,
      goal: `Extract ${dataDescription}. Return as JSON.`,
    }),
  });

  const run = await response.json();
  return run.status === "COMPLETED" ? run.result : null;
}

// Usage
const products = await extractData(
  "https://example.com/products",
  "all product names and prices"
);

Batch Processing

For multiple URLs, use the async endpoint to submit all tasks at once, then poll for results. This avoids blocking while waiting for each task to complete.
async function processBatch(tasks: { url: string; goal: string }[]) {
  // Submit all tasks
  const runIds = await Promise.all(
    tasks.map(async (task) => {
      const response = await fetch("https://agent.tinyfish.ai/v1/automation/run-async", {
        method: "POST",
        headers: {
          "X-API-Key": process.env.TINYFISH_API_KEY,
          "Content-Type": "application/json",
        },
        body: JSON.stringify(task),
      });
      const { run_id } = await response.json();
      return run_id;
    })
  );

  // Poll for completion
  const results = await Promise.all(runIds.map((id) => pollUntilComplete(id)));

  return results;
}

Retry with Stealth Mode

Some sites block automated requests. Start with lite mode for speed, then automatically retry with stealth mode if you get blocked.
async function extractWithFallback(url: string, goal: string) {
  // Try standard mode first
  let result = await runAutomation(url, goal, { browser_profile: "lite" });

  if (result.status === "FAILED" && result.error?.message.includes("blocked")) {
    // Retry with stealth mode
    result = await runAutomation(url, goal, {
      browser_profile: "stealth",
      proxy_config: { enabled: true, country_code: "US" },
    });
  }

  return result;
}

Rate Limit Handling

TinyFish has concurrency limits based on your plan. When you hit the limit, implement exponential backoff to retry failed requests.
async function withRetry(fn: () => Promise<any>, maxRetries = 3) {
  for (let i = 0; i < maxRetries; i++) {
    try {
      return await fn();
    } catch (e) {
      if (e.status === 429 && i < maxRetries - 1) {
        await sleep(Math.pow(2, i) * 1000);
        continue;
      }
      throw e;
    }
  }
}