YouTube Videos
Give it YouTube channels, playlists, search terms, hashtags or video links and it returns one JSON row per video or Short: title, channel, exact publish date, duration, views, likes, category, Shorts and live flags, tags, hashtags, description, thumbnail and caption languages. Shorts also get comment count and sound.
Sample output
One row as the API returns it. Long text is shortened here; names inside text read [name].
| Field | Value |
|---|---|
| rowType | video |
| platform | youtube |
| videoId | dQw4w9WgXcQ |
| url | https://www.youtube.com/watch?v=dQw4w9WgXcQ |
| title | Rick Astley - Never Gonna Give You Up (Official Video) (4K Remaster) |
| channelName | Rick Astley |
| channelId | UCuAXFkgsw1L7xaCfnd5JJOw |
| channelHandle | @RickAstleyYT |
| channelUrl | https://www.youtube.com/channel/UCuAXFkgsw1L7xaCfnd5JJOw |
| publishDate | 2009-10-24T23:57:33-07:00 |
| publishDateIsApprox | false |
| durationSeconds | 213 |
Call it from code or from your agent
This is the request. Small runs answer in the same call; large ones return a run ID.
curl -X POST https://scrapers-api.arcadiumdata.io/v1/scrapers/youtube-videos/runs \
-H "Authorization: Bearer $ARCADIUM_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"input": {
"urls": [
"https://www.youtube.com/@kurzgesagt"
],
"contentType": "videos",
"maxResults": 10
}
}'What each row holds
Every row says what it is in rowType: video rows are charged, coverage and error rows are free.
The video 36 fields
| Field | Type | What it holds |
|---|---|---|
| platform | string | Always 'youtube'. |
| videoId | string | YouTube video id, 11 characters, e.g. dQw4w9WgXcQ. |
| url | string | Watch page link of the video (Shorts included). |
| title | string | Video title. |
| channelName | string | Name of the channel that published the video (the publisher, not a viewer). |
| channelId | string | Channel id, starts with UC, e.g. UCuAXFkgsw1L7xaCfnd5JJOw. |
| channelHandle | string | Channel handle with the @, e.g. @RickAstleyYT. Null if YouTube did not return it. |
| channelUrl | string | Link to the channel page built from channelId. |
| publishDate | string | Publish date. Full rows: ISO 8601 with YouTube's offset, e.g. 2009-10-24T23:57:33-07:00. Fast-mode rows: YYYY-MM-DD estimated from the relative date (publishDateIsApprox true). |
| publishDateIsApprox | boolean | True when publishDate was estimated from a relative date such as '3 months ago' (fast mode); false for exact dates. |
| publishedText | Relative date as the listing shows it, e.g. '3 days ago', 'Streamed 2 weeks ago'. Null for direct video URLs. | |
| durationSeconds | number | Video length in seconds. Null for running live streams and some Shorts in fast mode. |
| viewCount | number | Views at the time of the run. Exact on full rows, rounded (3.5M) on fast-mode rows. |
| likeCount | number | Likes at the time of the run; null when hidden or in fast mode. |
| commentCount | Comments at the time of the run, exact. Shorts in full mode always; regular videos when includeCommentCount is on; null otherwise. 0 when comments are off. | |
| category | string | YouTube category, e.g. Music, Education, News & Politics. Null in fast mode. |
| isShort | boolean | True for YouTube Shorts. Null when unknown (fast mode outside the Shorts tab and search). |
| isLive | boolean | True while the video is a live stream running now. |
| isLiveContent | boolean | True for live streams and recorded live streams. Null in fast mode. |
| isUpcoming | boolean | True for a scheduled premiere or live stream that has not started. |
| isUnlisted | boolean | True for unlisted videos (reachable by link only). Null in fast mode. |
| isFamilySafe | boolean | YouTube's family-safe flag. Null in fast mode. |
| keywords | array | Tags the creator set on the video (may be empty). Null in fast mode. |
| hashtags | array | #hashtags in the title and description, lower-cased, without the #. Null in fast mode. |
| soundTitle | Shorts: the sound or song the Short uses, as YouTube's sound link shows it (e.g. a song title or 'Original sound'). Null for regular videos, Shorts without a sound link and fast mode. | |
| soundArtist | Shorts: the artist or channel credited for the sound (the part after the dot on the sound link). Null when not shown. | |
| description | string | Video description, full or short per input; emails and phone numbers are removed. Null in fast mode. |
| thumbnailUrl | string | Thumbnail image, 480x360 (hqdefault), exists for every video. |
| thumbnailMaxUrl | string | Largest thumbnail (maxresdefault, 1280x720 or more) when the upload has one; null otherwise or in fast mode. |
| captionLanguages | array | Every caption track of the video: code (e.g. en, de-DE), name, isAutoGenerated. Empty list: no captions. Null when not requested, in fast mode, or YouTube did not answer. |
| hasCaptions | boolean | True when the video has at least one caption track; null when captionLanguages is null. |
| detailLevel | string | 'full': read from the video's player data (exact date, likes, category). 'listing': only what the channel, playlist or search listing shows (fast mode). |
| source | The channel tab, playlist URL or search term this video came from; null for videos given directly. | |
| sourceType | string | Values: 'video' (given directly), 'channel', 'playlist', 'search', 'hashtag'. |
| position | 1-based position in the source list (search rank, playlist index, channel order); null for direct videos. | |
| scrapedAt | string | When the row was read, ISO 8601. |
Error rows, free 3 fields
| Field | Type | What it holds |
|---|---|---|
| input | Error rows: the URL, id or search term as given. | |
| code | Error rows: not_found (private, removed, unknown channel or playlist), no_match (nothing found for the input), unavailable (age-restricted, members-only, temporary error), blocked (rate limited, retry later), invalid_input. | |
| message | Error rows: what happened, in plain English. |
What it can't do
- It returns captions YouTube already has. It does not transcribe audio.
- It does not return comments or the names of commenters.
- Private and members-only videos are not read.
Channel names and URLs are the publisher labels YouTube shows publicly on every video.
What you send
Every field is optional. The example request above fills the ones shown here.
| Field | Type | What it does |
|---|---|---|
| urls | array | Example: https://www.youtube.com/@kurzgesagt (add /shorts or /streams for those tabs), @handle, a channel id (UC...), a playlist URL (https://www.youtube.com/playlist?list=...), a video or Shorts URL, a hashtag page (https://www.youtube.com/hashtag/cooking, add /shorts for Shorts only), a bare video id (dQw4w9WgXcQ) or a search page URL (https://www.youtube.com/results?search_query=lofi). Channels give up to maxResults videos each, newest first by default. |
| searchQueries | array | YouTube search terms, e.g. ["web scraping tutorial", "iphone 17 review"]. Each term gives up to maxResults videos in YouTube's search order (position is the rank). Can be combined with urls. |
| hashtags | array | YouTube hashtags, e.g. ["#cooking", "dancechallenge"] (letters, digits and _ only). Each gives up to maxResults videos from the hashtag page; with contentType shorts only its Shorts. Can be combined with urls and searchQueries. |
| contentType | string (one of 2) | Values: videos (default), shorts. With shorts, search terms return Shorts only and hashtags read their Shorts tab. Channels: use maxResultsShorts or a /shorts channel URL. Full Shorts rows add commentCount, soundTitle and soundArtist and are charged as the short event. |
| maxResults | integer | Videos per channel videos tab, playlist or search term, up to 10,000 (default 50). Videos outside the date range, private or members-only videos do not count. Direct video URLs are not limited by this. |
More options (20)
| Field | Type | What it does |
|---|---|---|
| maxResultsShorts | integer | Also read the channel's Shorts tab, up to this many Shorts per channel (0 = skip the tab, default). A /shorts channel URL reads only that tab.Default 0 |
| maxResultStreams | integer | Also read the channel's Live tab (past, running and scheduled streams), up to this many per channel (0 = skip the tab, default).Default 0 |
| maxItems | integer | Stops the run after this many videos across all inputs, 1 to 1,000,000. A cost cap; leave empty for no limit. |
| publishedAfter | string | Date as YYYY-MM-DD (e.g. 2026-01-01) or a relative age such as "30 days", "2 weeks", "1 year". Older videos are skipped for free; a channel listed newest first stops at the first older videos. |
| publishedBefore | string | Date as YYYY-MM-DD (e.g. 2026-06-30) or a relative age such as "7 days". Newer videos are skipped for free. |
| sortVideosBy | string (one of 3) | Values: NEWEST (default), POPULAR (most viewed first), OLDEST. Applies to channel tabs. The date-range early stop works with NEWEST and OLDEST. |
| listingOnly | boolean | Skips the per-video details request and returns what the channel, playlist or search listing shows: title, rounded views, duration, approximate date (publishDateIsApprox true), channel. No likes, category, description or caption languages. Charged at the lower video-listing price. Off by default. |
| includeCaptionLanguages | boolean | Adds captionLanguages (every caption track: code, name, auto-generated flag) and hasCaptions. One more small request per video. On by default; ignored in fast mode.Default true |
| includeCommentCount | boolean | Adds commentCount to regular videos (one more small request each). Shorts always get it. Ignored in fast mode. Off by default.Default false |
| description | string (one of 3) | Values: full (default), short (about 300 characters), none. Emails and phone numbers are removed.Default "full" |
| sortingOrder | string (one of 4) | Values: relevance (default), rating, date (upload date), views. Applies to searchQueries and search URLs. |
| searchCountry | string | Two-letter country code YouTube ranks search results for, e.g. DE or IN (default US). Applies to searchQueries and search URLs; titles and dates stay as published. |
| dateFilter | string (one of 5) | Values: hour, today, week, month, year. YouTube's own upload-date filter for searches; it is loose, so combine it with publishedAfter for an exact range. |
| lengthFilter | string (one of 3) | Values: under4 (under 4 minutes), between420 (4 to 20 minutes), plus20 (over 20 minutes). |
| isHD | boolean | Search results in HD only (YouTube's HD feature filter). |
| hasSubtitles | boolean | Search results that have subtitles or closed captions only. |
| hasCC | boolean | Search results under a Creative Commons licence only. |
| isLive | boolean | Search results that are live streams only. |
| is4K | boolean | Search results in 4K only (YouTube's 4K feature filter). |
| includeErrorRows | boolean | Adds a free row (rowType error, with a code and message) for every URL, private, age-restricted, members-only or missing video that gave no data. On by default.Default true |
Questions people ask before they top up
What does a run cost?
Each video costs $0.00125, which is $1.25 per 1,000. A run that delivers rows also pays a $0.001 start fee.
Shorts: $1.25 per 1,000. Videos in fast listing mode: $0.50 per 1,000.
A run that returns rows costs at least $0.005, start fee included. Failed runs, empty runs and duplicate rows cost $0. You set the most a run may cost, and it stops there.
Do you ever return personal data?
Not about reviewers or users. Reviewer names, profile links, photos, emails and phone numbers are not collected. When a name appears inside a review or a reply, it is replaced with [name].
Job titles and company sizes stay where a site shows them, because they describe a role rather than a person. On YouTube, channel names and URLs are the publisher labels YouTube shows publicly.
How fresh is the data?
Each run reads the live site when you start it, so rows are as current as the site itself.
More from YouTube
Full text, timed segments, language, SRT and VTT, video details
$1.50per 1,000 transcripts