What Is VideoObject Schema? The Complete Guide (2026)
What Is VideoObject Schema?
VideoObject schema is a type of structured data — based on the Schema.org VideoObject vocabulary — that tells Google a page contains a video and provides the metadata needed to index and display it in search results. When correctly implemented, Google can show your video with a thumbnail directly in search results, eligible for the video carousel, Key Moments timestamps, and a LIVE badge for livestreams.
Without VideoObject schema, Google must discover and interpret video content by crawling the actual video file — a slow, unreliable process. Structured data gives Google explicit, machine-readable facts about each video: its title, thumbnail, upload date, duration, and where to fetch the video itself. Sites using VideoObject schema see significantly higher video indexing rates and richer search appearances.
- VideoObject schema tells Google what your video is and how to display it — enabling thumbnails in search, Key Moments, and the LIVE badge.
- Three required fields:
name(unique, descriptive),thumbnailUrl(crawlable image, min 60×30px), anduploadDate(ISO 8601 with timezone). - Always provide
contentUrl(direct video file) orembedUrl(player URL) — preferably both. Without one of these, Greadme deducts 12 points and Google cannot crawl the video. - Key Moments use either
hasPart(manual Clip objects) orpotentialAction(SeekToAction — auto-detection). Never both at once.
Required Properties
| Property | Type | Description |
|---|---|---|
name | Text | The title of the video. Must be unique per video on your site — do not reuse the same title across different videos. Greadme warns if the value is a generic placeholder like "video" or "untitled". |
thumbnailUrl | URL or array of URLs | URL of the video's thumbnail image. Must be crawlable by Googlebot — not blocked by robots.txt, login walls, or served as a data URL. Minimum size: 60×30 pixels; larger images preferred. At least 80% of pixels must be opaque (not transparent). Provide three aspect ratios as an array: 1×1, 4×3, and 16×9. |
uploadDate | DateTime | The date the video was first published, in ISO 8601 format. Always include a timezone offset (e.g., 2026-03-15T10:00:00+00:00). Greadme warns if the timezone is missing — Google will default to Googlebot's timezone, which can cause incorrect date display. |
Recommended Properties
| Property | Type | Notes |
|---|---|---|
contentUrl | URL | Direct URL to the raw video file bytes (e.g., an .mp4file). This is Google's preferred method — it allows Google to actually crawl and index the video content. Greadme deducts 12 points if neither contentUrl nor embedUrl is present. |
embedUrl | URL | URL of the video player (not the page where the player is embedded). Use this when contentUrl is not available. Can be provided alongside contentUrl. Must point to the player itself, not a containing page. |
description | Text | A description of the video. Must be unique per video — Greadme warns if it is identical to name. HTML tags are ignored by Google. |
duration | Duration | Video length in ISO 8601 duration format: PT#H#M#S. Example: PT1M54S (1 min 54 sec), PT30M (30 min). Videos under 30 seconds are not eligible for Key Moments — Greadme warns for durations shorter than 30 seconds. |
expires | DateTime | Date after which the video is no longer available. Omit entirely if the video has no expiration. Greadme warns if the date is already in the past. Must include a timezone offset. |
interactionStatistic | InteractionCounter | View count. Use @type: InteractionCounter with interactionType: WatchAction. See the code example below. |
regionsAllowed | Array of ISO 3166-1 codes | Countries where the video is available. Use ISO 3166-1 two-letter codes (e.g., "US", "GB"). Use either regionsAllowed OR ineligibleRegion — never both. Greadme warns if both are present. |
contentUrl vs embedUrl: Which to Use?
Both properties tell Google where to find your video, but they serve different purposes:
| Property | Points to | When to use |
|---|---|---|
contentUrl | The raw video file (e.g., https://example.com/video.mp4) | Always preferred. Allows Google to crawl and index actual video bytes, improving discoverability. |
embedUrl | The video player URL (e.g., https://example.com/embed/123) | Use when a direct file URL is not available — e.g., for streaming videos or third-party hosted content. |
You can provide both simultaneously. Google prefers contentUrl but uses embedUrl as a fallback.
Key Moments: Clip vs SeekToAction
Key Moments are timestamps shown inside your video result in Google Search — letting users jump directly to specific sections. There are two mutually exclusive ways to implement them. Greadme warns if you use both at the same time.
Option A — Clip (Manual Key Moments)
Use hasPart with an array of Clip objects to manually define each moment. Each Clip requires:
| Property | Type | Notes |
|---|---|---|
name | Text | Label for this section (e.g., "Introduction") |
startOffset | Number | Start time in seconds. Must be a number. No two clips on the same video can share the same startOffset — Greadme throws an error for duplicates. |
url | URL | URL with a timestamp parameter pointing to this moment (e.g., ?t=30). Greadme warns if the URL lacks a timestamp parameter. |
endOffset | Number | End time in seconds (recommended). Must be greater than startOffset — Greadme errors if not. |
Videos must be at least 30 seconds long and support deep-linking (timestamp parameters) to be eligible for the Key Moments feature.
Option B — SeekToAction (Automatic Key Moments)
Use potentialAction with a SeekToAction to tell Google how your URL timestamp scheme works. Google then automatically identifies key moments itself.
"potentialAction": {
"@type": "SeekToAction",
"target": "https://example.com/video?t={seek_to_second_number}",
"startOffset-input": "required name=seek_to_second_number"
}The target must contain the literal placeholder {seek_to_second_number} — Greadme throws an error if it is missing. The startOffset-input value must be exactly "required name=seek_to_second_number".
LIVE Badge: BroadcastEvent
To display a LIVE badge on your video in Google Search, nest a BroadcastEvent inside the publication field. All three BroadcastEvent fields are required — Greadme errors on any that are missing:
| Property | Type | Notes |
|---|---|---|
isLiveBroadcast | Boolean | Must be true. |
startDate | DateTime | When the livestream starts/started. ISO 8601 with timezone. |
endDate | DateTime | When the livestream ends/ended. Must be after startDate. ISO 8601 with timezone. The LIVE badge is removed when this date is in the past. |
After updating BroadcastEvent markup (e.g., when going live or ending a stream), use the Google Indexing API to notify Google immediately — otherwise it may take hours for the badge to appear or disappear.
Complete Implementation Examples
1. Standard VideoObject
{
"@context": "https://schema.org",
"@type": "VideoObject",
"name": "How to Make Sourdough Bread at Home",
"description": "Step-by-step guide to baking sourdough from starter to loaf.",
"thumbnailUrl": [
"https://example.com/img/sourdough-1x1.jpg",
"https://example.com/img/sourdough-4x3.jpg",
"https://example.com/img/sourdough-16x9.jpg"
],
"uploadDate": "2026-03-15T10:00:00+00:00",
"duration": "PT18M30S",
"contentUrl": "https://example.com/videos/sourdough.mp4",
"embedUrl": "https://example.com/embed/sourdough",
"interactionStatistic": {
"@type": "InteractionCounter",
"interactionType": { "@type": "WatchAction" },
"userInteractionCount": 24800
}
}2. VideoObject with Key Moments (Clip)
{
"@context": "https://schema.org",
"@type": "VideoObject",
"name": "Complete JavaScript Tutorial 2026",
"thumbnailUrl": "https://example.com/img/js-tutorial.jpg",
"uploadDate": "2026-01-10T08:00:00+00:00",
"duration": "PT2H15M",
"contentUrl": "https://example.com/videos/js-tutorial.mp4",
"hasPart": [
{
"@type": "Clip",
"name": "Variables and Data Types",
"startOffset": 0,
"endOffset": 480,
"url": "https://example.com/js-tutorial?t=0"
},
{
"@type": "Clip",
"name": "Functions and Scope",
"startOffset": 480,
"endOffset": 1200,
"url": "https://example.com/js-tutorial?t=480"
}
]
}3. LIVE Broadcast
{
"@context": "https://schema.org",
"@type": "VideoObject",
"name": "Product Launch Livestream 2026",
"description": "Live announcement and demo of our new product line.",
"thumbnailUrl": "https://example.com/img/launch-thumb.jpg",
"uploadDate": "2026-09-01T14:00:00+00:00",
"contentUrl": "https://example.com/videos/launch-live.mp4",
"embedUrl": "https://example.com/embed/launch",
"publication": {
"@type": "BroadcastEvent",
"isLiveBroadcast": true,
"startDate": "2026-09-01T14:00:00+00:00",
"endDate": "2026-09-01T16:00:00+00:00"
}
}6 Common VideoObject Schema Mistakes
1. Blocking the Thumbnail with robots.txt
The thumbnailUrl must be crawlable by Googlebot Images. If the image is blocked by robots.txt or requires authentication, Google cannot fetch it and will not display the video thumbnail in search results — even if the schema is otherwise valid.
2. Using the Page URL as embedUrl
embedUrl should point to the video player, not the page that contains it. The difference: https://example.com/watch/123 (the page) vs https://example.com/embed/123 (the player). Greadme validates the URL format but cannot detect this semantic error — check it manually.
3. Missing Timezone in uploadDate
"uploadDate": "2026-03-15" is valid ISO 8601 but missing the time component and timezone. Greadme warns when the time is present but the timezone offset is absent. Always use the full format with offset: 2026-03-15T10:00:00+00:00.
4. Using Both hasPart and potentialAction
hasPart (manual Clip objects) and potentialAction (SeekToAction auto-detection) are mutually exclusive strategies for Key Moments. Greadme warns when both are present on the same VideoObject — remove one.
5. Duplicate startOffset Values in Clips
No two Clip objects on the same video can share the same startOffset. Greadme throws an error for duplicate start times. Each clip must begin at a distinct point in the video.
6. Setting expires to a Past Date
If expires is in the past, Google may de-index the video. Greadme warns when the expiry date has already passed. Remove the property entirely for videos that do not expire.
VideoObject Schema and AI Search Visibility
AI search platforms increasingly surface video content in their responses. When a user asks a how-to question, Google AI Overviews and Perplexity both consider video content as a high-authority answer format. VideoObject schema ensures your video's title, description, duration, and thumbnail are machine-readable — making them significantly easier for AI systems to identify as relevant, citable content.
For tutorial and educational content in particular, well-structured VideoObject schema with Key Moments timestamps increases the likelihood of being surfaced as a video answer in AI Overviews, since timestamps give AI systems a signal that the video is structured and navigable rather than a single undifferentiated block.
How to Validate Your VideoObject Schema
Paste your page URL into Greadme to validate your VideoObject schema. Greadme checks all three required fields, validates thumbnail URL format, verifies ISO 8601 duration and date formats, detects conflicting Key Moments strategies (Clip vs SeekToAction), validates every field inside Clip and BroadcastEvent objects, and warns about expired videos and missing timezone offsets.
