logo

Gemini Scraper API

Send a prompt to Google Gemini and get the assistant reply, grounding sources, and model label as structured JSON

The Gemini API takes a single text prompt and returns Gemini's reply from gemini.google.com as structured JSON. One GET request, no Google account, no cookies, and no browser automation on your side.

curl "https://api.scrape.do/plugin/gemini/chat?token=$TOKEN&q=ping"

Credit Usage: Each successful request costs 25 credits. Failed requests are not charged, and there is no render fee.

Key Features

  • One-shot prompt-to-reply: send a prompt, get the full reply back in a single HTTP call.
  • Markdown-clean output: output.text is the reply as Markdown — headings, tables, lists, and code blocks are preserved, while frontend-only placeholders (inline image widgets, card references) are stripped.
  • Grounding sources: when Gemini grounds an answer on the web, the external links it used come back as a flat sources[] array.
  • Prompt language sets reply language: Gemini answers in the language your prompt is written in, so ask in German to get a German reply.
  • Stateless from your side: every call is an independent, fresh conversation. No login, no token refresh, nothing to keep between calls.
  • No render fee: the per-call price covers everything; you do not pay a rendering surcharge.

Endpoint

GET https://api.scrape.do/plugin/gemini/chat

Basic Example

curl --location --request GET 'https://api.scrape.do/plugin/gemini/chat?token=<SDO-token>&q=Explain+quantum+entanglement+in+one+sentence'
import requests
import json

token = "<SDO-token>"

url = f"https://api.scrape.do/plugin/gemini/chat?token={token}&q=Explain+quantum+entanglement+in+one+sentence"

response = requests.request("GET", url)

print(json.dumps(response.json(), indent=2))
const axios = require('axios');

const token = "<SDO-token>";

const url = `https://api.scrape.do/plugin/gemini/chat?token=${token}&q=Explain+quantum+entanglement+in+one+sentence`;

axios.get(url)
  .then(response => {
    console.log(JSON.stringify(response.data, null, 2));
  })
  .catch(error => {
    console.error(error);
  });
package main

import (
	"fmt"
	"io/ioutil"
	"net/http"
)

func main() {
	token := "<SDO-token>"

	url := fmt.Sprintf(
		"https://api.scrape.do/plugin/gemini/chat?token=%s&q=Explain+quantum+entanglement+in+one+sentence",
		token,
	)

	resp, err := http.Get(url)
	if err != nil {
		panic(err)
	}
	defer resp.Body.Close()

	body, _ := ioutil.ReadAll(resp.Body)
	fmt.Println(string(body))
}
require 'net/http'
require 'json'

token = "<SDO-token>"

url = URI("https://api.scrape.do/plugin/gemini/chat?token=#{token}&q=Explain+quantum+entanglement+in+one+sentence")

response = Net::HTTP.get(url)

puts JSON.pretty_generate(JSON.parse(response))
import java.net.HttpURLConnection;
import java.net.URL;
import java.io.BufferedReader;
import java.io.InputStreamReader;

public class GeminiChat {
    public static void main(String[] args) throws Exception {
        String token = "<SDO-token>";

        String url = String.format(
            "https://api.scrape.do/plugin/gemini/chat?token=%s&q=Explain+quantum+entanglement+in+one+sentence",
            token
        );

        HttpURLConnection conn = (HttpURLConnection) new URL(url).openConnection();
        conn.setRequestMethod("GET");

        BufferedReader reader = new BufferedReader(
            new InputStreamReader(conn.getInputStream())
        );
        String line;
        StringBuilder response = new StringBuilder();
        while ((line = reader.readLine()) != null) {
            response.append(line);
        }
        reader.close();

        System.out.println(response.toString());
    }
}
using System;
using System.Net.Http;
using System.Threading.Tasks;

class Program
{
    static async Task Main()
    {
        string token = "<SDO-token>";

        string url = $"https://api.scrape.do/plugin/gemini/chat?token={token}&q=Explain+quantum+entanglement+in+one+sentence";

        using HttpClient client = new HttpClient();
        string response = await client.GetStringAsync(url);

        Console.WriteLine(response);
    }
}
<?php
$token = "<SDO-token>";

$url = "https://api.scrape.do/plugin/gemini/chat?token={$token}&q=Explain+quantum+entanglement+in+one+sentence";

$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);

$response = curl_exec($ch);
curl_close($ch);

echo json_encode(json_decode($response), JSON_PRETTY_PRINT);
?>
curl "https://api.scrape.do/plugin/gemini/chat?token=$TOKEN&q=Explain+quantum+entanglement+in+one+sentence"

Request Parameters

Required

ParameterTypeDescription
tokenstringYour Scrape.do API authentication token
qstringPrompt text to send to Gemini. Maximum 4000 characters. URL-encode multi-word prompts

Parameter names are case-insensitive, so Q works the same as q.

Example Requests

# Basic prompt
curl "https://api.scrape.do/plugin/gemini/chat?q=hello&token=$TOKEN"

# Multi-word prompt (URL-encode)
curl --get "https://api.scrape.do/plugin/gemini/chat" \
  --data-urlencode "q=Write a haiku about the ocean" \
  --data-urlencode "token=$TOKEN"

# German prompt gets a German reply
curl --get "https://api.scrape.do/plugin/gemini/chat" \
  --data-urlencode "q=Was sind die wichtigsten Nachrichten heute" \
  --data-urlencode "token=$TOKEN"

# Prompt that tends to produce grounded answers with sources
curl --get "https://api.scrape.do/plugin/gemini/chat" \
  --data-urlencode "q=Latest developments in AI with sources" \
  --data-urlencode "token=$TOKEN"

Response

Top-Level Structure

{
  "prompt": "Latest developments in AI with sources",
  "output": {
    "text": "AI development has shifted toward autonomous agents...\n\n## 1. Agentic AI\n..."
  },
  "sources": [
    "https://openai.com/index/...",
    "https://www.whitehouse.gov/presidential-actions/2026/06/..."
  ],
  "model": "3.5 Flash"
}

Fields

FieldTypeDescription
promptstringEcho of the prompt you submitted
output.textstringThe reply as Markdown — headings, tables, lists, and code blocks are preserved for rich answers (comparisons, recipes, product round-ups). Frontend-only placeholders such as inline image widgets and card references are removed
sourcesstring[]External links Gemini grounded the answer on, deduplicated and in the order they appear. Best-effort; omitted entirely when the answer was not grounded on external pages
modelstringLabel of the model that produced the reply, such as "3.5 Flash". Omitted when Gemini does not report it

prompt and output.text are always present on a 200. sources and model are omitted rather than returned empty, so treat both as optional in your parser.

Example

{
  "prompt": "Explain quantum entanglement in one sentence",
  "output": {
    "text": "Quantum entanglement is a phenomenon where two or more particles share a single quantum state, so measuring one instantly determines the corresponding property of the other, no matter how far apart they are."
  },
  "model": "3.5 Flash"
}

A grounded answer additionally carries sources:

{
  "prompt": "Who won the last Formula 1 race and where",
  "output": {
    "text": "## Latest Race Result\n\n| Position | Driver | Team |\n|---|---|---|\n| 1 | ... | ... |\n\nThe race was held at ..."
  },
  "sources": [
    "https://www.formula1.com/en/results/...",
    "https://www.autosport.com/f1/news/..."
  ],
  "model": "3.5 Flash"
}

Notes

  • Prompt limit is 4000 characters. Longer prompts are rejected before the call runs, so no credits are spent on them.
  • No multi-turn state. One call returns one reply; to follow up, include the prior context inside the new q.
  • Reply language follows the prompt. The reply is written in the language of your prompt. Grounding sources may still be a globally mixed set, because Gemini decides which pages to cite.
  • Markdown, not HTML. output.text is Markdown. Render it with any Markdown renderer; there is no separate HTML field.
  • sources is best-effort. It collects the external links present in the reply payload and filters out platform infrastructure links, capped at 30 entries. An answer with no sources field is a normal answer that was not web-grounded, not a failure.
  • Response variance. Gemini A/B-tests its answers, so the same prompt can return different wording, formatting, or a different model label across calls. Do not treat exact text as stable.
  • Typical latency is a few seconds and depends on prompt complexity and reply length. The endpoint waits for the complete reply and does not stream partial output.
  • Per-call timeout is 45 seconds. If you hit it, shorten unusually long prompts or retry.
  • Retry on 502. Both 502 bodies are transient conditions; a retry a few seconds later normally succeeds and you are not charged for the failed call.

Error Responses

StatusBodyCause
400{ "error": "token is required" }Missing token parameter
400{ "error": "q (prompt) is required" }Missing or empty q parameter
400{ "error": "q is too long (max 4000 characters)", "message": "..." }Prompt exceeds the 4000-character limit
502{ "error": "no warm session available", "message": "..." }Capacity is being prepared; retry shortly
502{ "error": "failed to get a response from Gemini", "message": "..." }Upstream did not return a usable reply; retry, and contact support if it persists
500{ "error": "internal server error" }Unexpected internal failure

On this page