Banner X video captions

개요

The Epsilon Retail Media platform supports closed caption and transcript files for Banner X video campaigns. Advertisers upload caption files (.vtt, .srt) and transcript files (.txt) alongside their video assets. Your integration consumes these file URLs from the ad response and renders captions in your video player.

This integration helps you meet accessibility requirements such as the European Accessibility Act (EAA), which mandates user-controlled closed captions on public-facing video content.

  • Caption files are time-synced subtitle tracks for your video player.
  • Transcript files are plain-text representations of the video's audio content for SEO and screen reader use.

This guide covers:

  • How caption and transcript files appear in VAST and JSON ad responses
  • VAST 4.3 <ClosedCaptionFile> element structure
  • JSON videoTranscriptFiles[] array structure
  • How to render captions using the provided CDN URLs
  • Testing and validation

Delivery model

Caption file URLs (.vtt / .srt) are delivered only via VAST, not JSON.
Transcript file URLs (.txt) are delivered only via JSON, not VAST.
Captions are consumed by your video player; transcripts are consumed at the page level.

Integration flow

Caption and transcript files follow the same delivery path as video assets. No additional API calls are required beyond your existing Banner X ad request.

  1. An advertiser uploads video, caption, and transcript files via the campaign wizard.
  2. Files are validated, stored, and served via CDN.
  3. Your existing Banner X ad request returns caption URLs in VAST and transcript URLs in JSON.
  4. Your video player reads the caption file URL and renders subtitles.
  5. Your page optionally displays transcript text for accessibility or SEO.

Supported file types

AssetFormatsMax size
Closed captions.vtt (WebVTT), .srt (SubRip)Configurable per retailer content standard (typically 1–4 MB)
Transcript.txt (plain text)Configurable per retailer content standard (typically 1–4 MB)

Files are served as-is; the platform does not convert formats. Your video player is responsible for rendering captions.

사전 필수 조건

Before integrating captions and transcripts, confirm the following:

  • Existing Banner X video integration — you already consume <MediaFiles> from the VAST tag in the adm field. See Video ads for a complete ad response example that includes caption and transcript file delivery.
  • Video player with caption support — WebVTT or SRT caption tracks (e.g. HTML5 <track> element, or equivalent native player API).
  • Feature enabled for your namespace — contact your account team to enable caption and transcript uploads for your namespace.
  • CORS configured — allow cross-origin fetch of .vtt files from the Epsilon CDN domain when using HTML5 <track> elements.

Authentication and security

No additional authentication is required. Caption and transcript files are served via the same CDN as video assets. File URLs returned in the ad response are publicly accessible, using the same security model as video file URLs.

If your video player uses HTML5 <track> elements to load .vtt files, ensure your page's Content Security Policy allows fetching from the Epsilon CDN domain. The CDN sets appropriate CORS headers for cross-origin <track> loading.

Step 1: Parse caption files from the VAST response

Purpose: Retrieve time-synced caption file URLs from the VAST XML in the adm field for rendering in your video player.

What you need to do

  • In your VAST parser, look for the <ClosedCaptionFiles> element within each <Linear> creative (inside <MediaFiles>).
  • Each <ClosedCaptionFile> child element contains the CDN URL as its text content.
  • The type attribute indicates the MIME type (text/vtt or application/x-subrip for SRT).
  • The language attribute indicates the caption language (e.g. en).

Example VAST response

<Linear>
  <Duration></Duration>
  <MediaFiles>
    <ClosedCaptionFiles>
      <ClosedCaptionFile type="text/vtt" language="en"><![CDATA[https://dev12.flavedo.io./citrus/0f04cbc2-c933-4384-8d37-772e939d8d02]]></ClosedCaptionFile>
    </ClosedCaptionFiles>
    <Mezzanine><![CDATA[https://dev12.flavedo.io./citrus/37bb15a2-fd4d-4eb1-9dd7-7630b5df29d1]]></Mezzanine>
    <MediaFile delivery="progressive" type="video/mp4" width="1280" height="720" bitrate="8700" codec="h264"><![CDATA[https://dev12.flavedo.io./citrus/37bb15a2-fd4d-4eb1-9dd7-7630b5df29d1]]></MediaFile>
  </MediaFiles>
  <VideoClicks>
    <ClickTracking><![CDATA[https://integration.dev12.citrusad.com/v1/resource/second-c/...]]></ClickTracking>
    <ClickThrough></ClickThrough>
  </VideoClicks>
</Linear>

Validation

  • Confirm your VAST parser extracts the <ClosedCaptionFile> URL when present.
  • Confirm your parser gracefully handles the absence of <ClosedCaptionFiles> (not all campaigns include captions).

Common errors

오류Cause
<ClosedCaptionFiles> not foundThe campaign may not have an approved caption file, or caption delivery is not yet enabled for your environment. This is expected for campaigns without captions.

Step 2: Parse transcript files from the JSON response

Purpose: Retrieve plain-text transcript file URLs from the JSON ad response for SEO or screen reader accessibility.

What you need to do

  • In the Banner X generate response, look for the videoTranscriptFiles array on each ad object.
  • Each entry includes a videoFileId so you can match transcripts to their corresponding video.
  • Transcripts are plain text (.txt) — use them for SEO metadata, screen readers, or alternative text display.

Example JSON response

"videoTranscriptFiles": [
  {
    "videoFileId": "a6f4c4a6-6982-4a8c-9a81-ecdfd4b3fa36",
    "format": "txt",
    "url": "https://dev12.flavedo.io./citrus/03d98ae2-67d5-49d3-9e9b-c8f278520657",
    "language": "en"
  }
]

Validation

  • Confirm your JSON parser reads the videoTranscriptFiles array when present.
  • Confirm graceful handling when the array is empty or absent.
📘

Caption file URLs (for .vtt/.srt) are only delivered via VAST, not JSON. Transcript files (.txt) are only delivered via JSON, not VAST. This separation reflects the different consumption patterns: captions are for video players (VAST), transcripts are for page-level accessibility (JSON).

Step 3: Render captions in your video player

Purpose: Display closed captions to shoppers during video playback.

What you need to do

  • After parsing the caption URL from VAST, add a <track> element to your HTML5 video player (or equivalent in your native player SDK).
  • Set kind="captions". Use the default attribute if you want captions enabled by default.
  • For .srt files, some players require conversion to WebVTT at runtime (prepend WEBVTT\n\n and replace comma with period in timestamps).

Example HTML5 implementation

<video controls crossorigin="anonymous">
  <source src="https://cdn.citrusad.com/video/abc123.mp4" type="video/mp4">
  <track
    kind="captions"
    src="https://cdn.citrusad.com/captions/def456.vtt"
    srclang="en"
    label="English"
    default
  >
</video>

Validation

  • Play the video and confirm captions appear as an overlay.
  • Confirm the shopper can toggle captions on/off via player controls.
  • Confirm captions are time-synced with the video audio.

Common errors

오류Solution
Captions don't load (CORS error in console)Ensure your Content Security Policy and CORS configuration allow fetching .vtt files from the Epsilon CDN domain.
Captions appear garbled or emptyVerify the file URL returns valid WebVTT content. Fetch the URL directly to inspect the file.

Step 4: (Optional) Display transcript text

Purpose: Provide accessible text content alongside or below the video for screen readers and SEO.

What you need to do

  • Fetch the transcript URL from the videoTranscriptFiles entry in the JSON response.
  • Use the transcript text for accessibility, SEO, screen readers, or other retailer-specific use cases.

예시

<details>
  <summary>Video transcript</summary>
  <p id="transcript-content"></p>
</details>
<script>
  fetch('https://cdn.citrusad.com/transcripts/ghi789.txt')
    .then(r => r.text())
    .then(text => {
      document.getElementById('transcript-content').textContent = text;
    });
</script>

Data models and field definitions

VAST: ClosedCaptionFile element

Attribute / field유형필수 입력 항목입니다설명Accepted values
type문자열MIME type of the caption filetext/vtt, application/x-subrip
language문자열아니요Language of the caption tracke.g. en
Element textstring (URL)CDN URL of the caption fileHTTPS URL

JSON: videoTranscriptFiles

필드유형필수 입력 항목입니다설명Accepted values
videoFileId문자열ID of the video file this transcript belongs toUUID
format문자열File format of the transcripttxt
urlstring (URL)CDN URL of the transcript fileHTTPS URL
language문자열Language of the transcripte.g. en

Backward compatibility

These additions are fully backward-compatible:

  • If no caption files are attached to a campaign, the <ClosedCaptionFiles> element is omitted from VAST entirely.
  • If no transcript files are attached, videoTranscriptFiles is absent or an empty array in JSON.
  • Existing integrations that do not parse these new elements continue to work without changes.

Testing, sandbox, and go-live

Sandbox / test environment

  • Request access to a test namespace with caption and transcript uploads enabled (contact your account team).
  • Upload a test campaign with a sample .vtt caption file via the campaign wizard.
  • Approve the campaign through the review cycle.
  • Call the Banner X generate endpoint and inspect the VAST and JSON response.

Sample test cases

TestStepsExpected result
VAST caption presentRequest ad for campaign with approved .vtt captionVAST contains <ClosedCaptionFiles> with valid CDN URL
VAST caption absentRequest ad for campaign without captionsNo <ClosedCaptionFiles> element in VAST
JSON transcript presentRequest ad for campaign with approved .txt transcriptJSON contains videoTranscriptFiles array with entry
Caption file accessibleFetch the CDN URL from the VAST response directlyReturns valid WebVTT content with WEBVTT header
Player renders captionsLoad video + caption track in your playerCaptions display time-synced with video audio
CORS for track elementLoad .vtt via <track> cross-originNo CORS errors in browser console; captions render

Go-live checklist

  • VAST parser extracts <ClosedCaptionFile> URLs when present
  • JSON parser reads videoTranscriptFiles[] when present
  • Graceful fallback when captions or transcripts are absent
  • Video player renders captions from CDN URL
  • Shopper can toggle captions on/off
  • CORS validated for cross-origin .vtt fetch
  • Transcript text accessible (if implementing Step 4)
  • Tested with both .vtt and .srt caption formats

Troubleshooting and FAQ

<ClosedCaptionFiles> element missing from VAST response

Likely cause: The campaign does not have an approved caption file, or caption delivery is not enabled in your environment.

Solution:

  • Confirm the campaign has an approved caption file (uploaded and passed review).
  • Contact your account team to verify the feature is enabled for your namespace.

CORS error when loading .vtt via <track> element

Likely cause: Content Security Policy or browser CORS enforcement blocking cross-origin fetch of the .vtt file.

Solution:

  • Add the Epsilon CDN domain to your Content Security Policy's connect-src and media-src directives.
  • Set crossorigin="anonymous" on the parent <video> element if required.

Captions render but are not synced with video

Likely cause: The caption file was authored with incorrect timestamps, or the file is an SRT being loaded as VTT without conversion.

Solution:

  • Fetch the caption file URL and inspect timestamps against video playback.
  • If the file is .srt and your player only supports .vtt, convert at runtime (prepend WEBVTT\n\n, replace , with . in timestamps).

Transcript URL returns 404

Likely cause: The campaign was updated and the transcript file was removed, or CDN propagation delay.

Solution:

  • Re-fetch the ad response to get the current file URL.
  • If the issue persists, contact support.

When contacting support, include:

  • Request ID or correlation ID from the generate call
  • Timestamp (UTC) of the ad request
  • The <ClosedCaptionFile> or videoTranscriptFiles URL that is failing
  • Browser console error (for CORS issues)
  • Namespace and campaign ID

Related articles