YouTube Search Scraper API
Our YouTube search API takes a search query and returns the ranked organic results as clean JSON: video IDs, titles, channel names, view counts, and thumbnails, with paid placements split out into a separate <code>ads</code> array so you never mistake an ad for a real ranking. No Google Cloud project and no daily quota to ration. A second endpoint goes one step earlier: pass a seed query to <code>/youtube/suggest</code> and it returns YouTube's own related and autocomplete searches, so you can scrape YouTube related searches for keyword research before you ever pull a results page.
Why YouTube Search data is hard to get
The official YouTube Data API v3 charges 100 quota units per search.list call against a default 10,000 units a day, which caps you at roughly 100 searches before it returns quota errors. Scraping the results page yourself means fighting client fingerprinting and a consent wall, so a hosted YouTube search API that returns a flat result list is the simpler path.
The YouTube Search Scraper API in one request
curl "https://api.youtubescraperapi.com/api/v1/youtube/search?search_query=lofi+beats&api_key=$API_KEY" import requests
resp = requests.get(
"https://api.youtubescraperapi.com/api/v1/youtube/search",
params={
"search_query": "lofi beats",
"api_key": "YOUR_API_KEY",
},
timeout=60,
)
data = resp.json()
print(data["results_count"], "organic results,", data["ads_count"], "ads, for", data["query"])
for video in data["organic_results"]:
print(video["position"], video["title"], "-", video["channel"]["name"], "-", video["views"]) Parameters
| Parameter | Required | Default | Notes |
|---|---|---|---|
search_query | required | - | The search terms to look up on YouTube, exactly as you would type them into the search bar. |
api_key | required | - | Your API key, passed as a query parameter. Create one on the free plan. |
What the YouTube Search Scraper API returns
{
"query": "lofi beats",
"results_count": 20,
"organic_results": [
{
"position": 1,
"title": "lofi hip hop radio - beats to relax/study to",
"link": "https://www.youtube.com/watch?v=jfKfPfyJRdk",
"video_id": "jfKfPfyJRdk",
"channel": {
"name": "Lofi Girl",
"link": "https://www.youtube.com/channel/UCSJ4gkVC6NrvII8umztf0Ow",
"thumbnail": "https://yt3.ggpht.com/lofi-girl-avatar=s68-c-k-c0x00ffffff-no-rj",
"verified": true
},
"views": "92,431,008 views",
"published": "Streamed 2 years ago",
"length": "LIVE",
"description": null,
"thumbnail": {
"static": "https://i.ytimg.com/vi/jfKfPfyJRdk/hq720.jpg",
"rich": "https://i.ytimg.com/an_webp/jfKfPfyJRdk/mqdefault_6s.webp"
}
}
],
"ads": [],
"ads_count": 0
} | Field | Type | Description |
|---|---|---|
query | string | The search query that was run, echoed back from your request. |
results_count | integer | Number of organic video results returned in this response. |
organic_results | array | List of ranked organic video result objects, in the order YouTube returned them, with paid placements excluded and surfaced separately under ads. |
organic_results[].position | integer | 1-based rank of the video within the organic results. |
organic_results[].title | string | Video title as shown on the results page. |
organic_results[].link | string | Full watch URL for the video. |
organic_results[].video_id | string | The 11-character YouTube video ID. |
organic_results[].channel | object | The uploading channel: name, link, thumbnail, and a verified boolean. |
organic_results[].channel.name | string | Display name of the channel that uploaded the video. |
organic_results[].channel.link | string | Canonical URL of the uploading channel. |
organic_results[].channel.verified | boolean | Whether YouTube marks the channel as verified. |
organic_results[].views | string | View count text as displayed by YouTube, for example "1.2M views". |
organic_results[].published | string | Relative upload time, for example "3 weeks ago". |
organic_results[].length | string | Runtime string such as "10:42", or "LIVE" for active streams. |
organic_results[].description | string | Description snippet when YouTube shows one for the result, otherwise null. |
organic_results[].thumbnail | object | Thumbnail URLs for the video: a static image and a rich animated preview. |
ads | array | Paid/ad placements returned for the query, kept separate from the organic results so you never mistake an ad for a real ranking. |
ads_count | integer | Number of ad placements in the ads array, often 0. |
What you can build using the API
Scrape YouTube related searches for keyword research
Keyword and topic monitoring
Competitor and niche research
Content discovery feeds
Dataset building for analysis
Influencer and channel sourcing
Trend and demand tracking
Why teams choose our YouTube Search Scraper API
Each call returns the ranked organic_results parsed into flat JSON, with paid placements split into a separate ads array and an ads_count, so you read the real ranking without an ad slipping into it. No nested resource tree to walk and no units to count. We rotate proxies, clear the consent wall, and retry across pools at a 2.6s median, and the free plan covers 1,000 requests so you can confirm the fields before you pay.
Related and autocomplete searches
Quota-free searching
Anti-bot and proxy rotation
Organic results split from ads
Parsed JSON output
Live parity
YouTube Search Scraper API vs the official YouTube API
| Our YouTube Search API | DIY (requests + headless) | YouTube Data API v3 | |
|---|---|---|---|
| Search volume | Pay per successful request, no daily cap | Limited by your IP pool before blocks hit | search.list costs 100 units against a 10,000-unit default daily quota, about 100 searches per day |
| Setup | One REST call with an API key | Build and maintain a headless scraper | Cloud project, enable API, generate key, then raise quota |
| Output | Flat parsed JSON, organic_results split from ads | Raw HTML you parse yourself | Nested resource JSON you deserialize |
| Anti-bot handling | Proxies, retries, consent wall handled | You build and maintain it | Not applicable, but quota limits apply |
| Blocks and maintenance | Handled on our side | Breaks when YouTube changes layout | Stable, but capped and key-gated |
Start free, scale when ready
| Plan | Price | Best for |
|---|---|---|
| Free | 1,000 requests | Testing and small jobs |
| Pro | $0.60 / 1k | Production workloads |
| Pay-as-you-go | $0.90 / 1k | Spiky or one-off volume |
Median response 2.6s. You only pay for successful requests.
FAQ
Yes. The official option is the YouTube Data API v3 search.list method, which returns video, channel, and playlist results that match a query. Its catch is cost: each search.list call uses 100 quota units and a project gets 10,000 units per day by default, so you get about 100 searches per day. Our YouTube search API skips that model and returns parsed search results per request with no quota counter.
The official YouTube Data API is free to use but limited by the daily quota, which works out to roughly 100 search.list calls per day before you must request more from Google. Our API includes 1,000 free requests on the starter plan so you can test real searches, then continues on usage-based pricing with no daily search cap.
A request returns the query you sent, a results_count, an organic_results array, and an ads array with its ads_count. Each organic video object includes the position, title, link, video_id, a channel object (name, link, thumbnail, verified), views, published time, length, an optional description, and a thumbnail object. Keeping the organic results separate from ads means you read the real ranking without filtering ad rows out first.
Send a GET request to https://api.youtubescraperapi.com/api/v1/youtube/search with two query parameters: search_query for your terms and api_key for your key. The response is JSON, so you read data["organic_results"] directly in any language that can make an HTTP request, with paid placements available separately under data["ads"].
Yes. Send a GET request to https://api.youtubescraperapi.com/api/v1/youtube/suggest?query=YOUR_SEED&api_key=YOUR_API_KEY and the response returns the seed query you sent, a related_searches array of the related and autocomplete phrases YouTube surfaces for it, and a related_count. It is the keyword-research companion to the search endpoint: expand one seed into the phrases viewers actually type, then run the promising ones through the search endpoint for ranking and view-count data. Both endpoints share the same key and the same 1,000-request free tier.
Most YouTube search results are public data, and courts have generally treated scraping public pages as permissible, though you still must respect copyright and personal-data rules such as GDPR. We handle the request layer; you stay responsible for how you store and use the data. For a deeper look, see our guide on whether scraping YouTube is legal.
One call returns a page of ranked video results, typically a few dozen, in the same order YouTube ranks them. The exact count is reported in results_count, so your code can read that value directly on each response.