Google Trends Scraper - A tool to scrape Google Trends data with a simple API. Get interest over time, regional interest, related topics, and related queries for any search term.
Get results as structured JSON for applications or Markdown for LLMs and AI agents, without managing HTML parsing or proxies.
This guide covers Google Trends Explore data using google_trends. For the separate list of currently trending searches, see the Google Trending Now Scraper.
Using a simple GET request, you can retrieve Google Trends data:
https://serpapi.com/search?engine=google_trends&q=coffee&data_type=TIMESERIES&date=today+12-m&geo=US&api_key=YOUR_SERPAPI_API_KEY
- Register at SerpApi to get your API Key. Keep your key private.
q: a search term or topic ID. Up to five comma-separated queries are supported forTIMESERIESandGEO_MAP; other data types accept only one.data_type: the chart to retrieve, defaulting toTIMESERIES(interest over time).dateandgeo: the time range and geographic scope. These examples use the past 12 months in the United States.
JSON is the default output and is useful when you need individual result fields. Add output=md to receive Markdown for text-based workflows, LLMs, and AI agents.
curl --get https://serpapi.com/search \
--data-urlencode engine="google_trends" \
--data-urlencode q="coffee" \
--data-urlencode data_type="TIMESERIES" \
--data-urlencode date="today 12-m" \
--data-urlencode geo="US" \
--data-urlencode output="md" \
--data-urlencode api_key="YOUR_SERPAPI_API_KEY"Markdown is returned as text, not a JSON object. Read it with a text response reader instead of a JSON parser. The JSON field names below do not define a guaranteed Markdown structure.
Here are some code examples based on your favorite programming languages.
curl --get https://serpapi.com/search \
--data-urlencode engine="google_trends" \
--data-urlencode q="coffee" \
--data-urlencode data_type="TIMESERIES" \
--data-urlencode date="today 12-m" \
--data-urlencode geo="US" \
--data-urlencode output="json" \
--data-urlencode api_key="YOUR_SERPAPI_API_KEY"Step 1:
Create a new main.py file.
Step 2: Install requests package with:
pip install requests
Step 3: Add this code to your file:
import requests
SERPAPI_API_KEY = "YOUR_SERPAPI_API_KEY"
params = {
"api_key": SERPAPI_API_KEY,
"engine": "google_trends",
"q": "coffee",
"data_type": "TIMESERIES",
"date": "today 12-m",
"geo": "US",
"output": "json"
}
search = requests.get("https://serpapi.com/search", params=params, timeout=60)
search.raise_for_status()
response = search.json()
if "error" in response:
raise RuntimeError(response["error"])
print(response)If you're only interested in the interest_over_time, you can print it from the response directly:
print(response["interest_over_time"])To request Markdown instead, keep the parameter definitions above and replace the request and response-handling lines with:
params["output"] = "md"
search = requests.get("https://serpapi.com/search", params=params, timeout=60)
search.raise_for_status()
print(search.text)Step 1: Install the SerpApi JavaScript package:
npm install serpapi
Step 2:
Create a new index.js file.
Step 3: Add this to your file:
const { getJson } = require("serpapi");
const API_KEY = "YOUR_SERPAPI_API_KEY";
getJson({
api_key: API_KEY,
engine: "google_trends",
q: "coffee",
data_type: "TIMESERIES",
date: "today 12-m",
geo: "US"
}, (json) => {
if (json.error) {
throw new Error(json.error);
}
console.log(json);
});For Markdown, use a text-capable HTTP client rather than getJson. This standalone alternative uses built-in fetch in Node.js 18 or later:
async function main() {
const params = new URLSearchParams({
api_key: "YOUR_SERPAPI_API_KEY",
engine: "google_trends",
q: "coffee",
data_type: "TIMESERIES",
date: "today 12-m",
geo: "US",
output: "md"
});
const response = await fetch(`https://serpapi.com/search?${params}`, {
signal: AbortSignal.timeout(60000)
});
const text = await response.text();
if (!response.ok) {
throw new Error(`SerpApi HTTP ${response.status}: ${text}`);
}
console.log(text);
}
main().catch((error) => {
console.error(error);
process.exitCode = 1;
});While you can use our APIs using a simple GET request with any programming language, you can also see our ready-to-use libraries here: SerpApi Integrations.
Please find the main parameters for the Google Trends API below:
| Name | Description | Requirement |
|---|---|---|
| engine | Must be set to google_trends. |
Required |
| api_key | Your SerpApi private API key. | Required |
| q | Search term(s) or topic ID(s), separated by commas. Each query is limited to 100 characters. Query-count limits depend on data_type, as shown below. |
Required |
| data_type | TIMESERIES (default), GEO_MAP, GEO_MAP_0, RELATED_TOPICS, or RELATED_QUERIES. |
Optional |
| Localization | ||
| hl | Language code, such as en, es, or fr; regional variants such as en-gb are supported. |
Optional |
| geo | Geographic scope, such as US. Omit or leave empty for worldwide. Multiple locations are supported only for TIMESERIES, with one nonempty location per query. |
Optional |
| region | Regional granularity: COUNTRY, REGION, DMA, or CITY. Only accepted for GEO_MAP and GEO_MAP_0; availability and default depend on geo. |
Optional |
| Time Range and Filters | ||
| date | Relative range such as today 12-m, today 5-y, or all (2004-present), or a supported custom date range. See the rules below. |
Optional |
| cat | Category ID; defaults to 0 (all categories). Use the Trends categories, not Trending Now categories. |
Optional |
| gprop | Omit or leave empty for Web Search. Other values: images, news, froogle (Google Shopping), or youtube. Do not use web or shopping. |
Optional |
| tz | Time-zone offset in minutes, from -1439 to 1439. Defaults to 420. Uses the UTC-minus-local convention; for example, UTC+8 is -480. |
Optional |
| include_low_search_volume | Set to true to include low-search-volume regions. Ignored unless data_type is GEO_MAP or GEO_MAP_0. |
Optional |
| csv | Set to true to retrieve CSV results as an array. This is separate from the output format selector. |
Optional |
| SerpApi Parameters | ||
| no_cache | Set to true to request fresh results instead of using the one-hour cache. Cannot be combined with async. |
Optional |
| async | Set to true for later retrieval through the Searches Archive API. Cannot be combined with no_cache or used with Ludicrous Speed enabled. |
Optional |
| output | json (default) for structured results, md for Markdown, or html for raw HTML. |
Optional |
Visit the official documentation for all available parameters.
Each request retrieves the selected chart, rather than every chart at once:
| data_type | Queries per request | JSON result key |
|---|---|---|
TIMESERIES |
1-5 | interest_over_time |
GEO_MAP |
2-5 | compared_breakdown_by_region |
GEO_MAP_0 |
1 | interest_by_region |
RELATED_TOPICS |
1 | related_topics |
RELATED_QUERIES |
1 | related_queries |
For example, use q=coffee,tea with data_type=GEO_MAP to compare regional interest, or q=coffee with data_type=RELATED_QUERIES for related searches. Make separate requests for other charts; this API does not document offset or next-page-token pagination.
For topics rather than literal search terms, obtain the encoded topic ID from the Google Trends Autocomplete API.
Supported relative ranges are now 1-H, now 4-H, now 1-d, now 7-d, today 1-m, today 3-m, today 12-m, today 5-y, and all.
Custom dates use YYYY-MM-DD YYYY-MM-DD from 2004 to the present. Hour-specific ranges use YYYY-MM-DDThh YYYY-MM-DDThh within a week; hours are interpreted using tz.
Only TIMESERIES supports a different location or date range for each query. For q=coffee,tea, geo=US,GB compares coffee in the US with tea in the UK. The number of locations must match the queries, and no location in the list may be empty. Per-query date ranges must also match the query count, use the same custom format (all dates or all dates with hours), and cover reasonably similar durations.
The result shape depends on data_type and available source data. These are field guides, not literal API responses.
{
"interest_over_time": {
"timeline_data": [
{
"date": "String - Date or date range",
"timestamp": "String - Unix timestamp",
"values": [
{
"query": "String - Search term",
"query_index": "Integer - Index of the query in the request",
"value": "String - Displayed relative interest",
"extracted_value": "Integer - Numeric interest value"
}
]
}
]
}
}{
"related_topics": {
"rising": [
{
"topic": {
"value": "String - Topic ID",
"title": "String - Topic title",
"type": "String - Topic category"
},
"value": "String - Growth percentage or Breakout",
"link": "String - URL to explore"
}
],
"top": [
{
"topic": { "title": "String", "type": "String" },
"value": "String - Displayed relative interest",
"extracted_value": "Integer - Numeric interest value"
}
]
}
}{
"related_queries": {
"rising": [
{
"query": "String - Related search query",
"value": "String - Growth percentage or Breakout",
"link": "String - URL to explore"
}
],
"top": [
{
"query": "String - Related search query",
"value": "String - Displayed relative interest",
"extracted_value": "Integer - Numeric interest value",
"link": "String - URL to explore"
}
]
}
}Regional results use an interest_by_region array for one query or a compared_breakdown_by_region array for comparisons. Entries may include geo, coordinates, and location; single-query results have value and extracted_value, while comparisons contain a values array with per-query scores. See the single-query regional schema and comparison schema.
Fields and chart sections may be absent when there is insufficient data. Interest scores are normalized, not absolute search volumes; a zero does not necessarily mean nobody searched. Related-query and related-topic growth values describe a different measure from the 0-100 interest scores.
For Markdown output, use output=md and read the response as text as shown above.
Here are some use cases for the Google Trends API:
- Track keyword popularity over time for SEO and content strategy.
- Compare search interest between competing brands or products.
- Identify seasonal trends for marketing campaigns.
- Research emerging topics and rising search queries.
- Analyze regional interest for geo-targeted marketing.
- Build trend monitoring dashboards for market research.
- How to scrape Google Trends
- Google Trends API with Python (PyTrends simple alternative)
- Keyword vs Intent: Why Topics Matter
- Google Trends Numbers: From 0 to 100, What is it?
Interesting use cases:
Feel free to reach out via contact@serpapi.com.
Check other Google Scrapers from SerpApi.
