NEWVectors or files. Pick a path.Start →
    Compliance
    8 min read
    Updated 2026-11-10

    How Do I Check Video Against My Own Compliance Rules?

    Write each rule as examples, phrases or a yes-or-no question, index every video into scenes with transcript and on-screen text, and run one retriever per video that returns the scenes breaking a rule, with start and end times. Covers visual rules as a taxonomy, banned phrases, required disclosures, judgment calls, face, logo and slogan checks, cost and limits.

    Ethan Steininger
    By , Founder & CEO, Mixpeek
    Video Compliance
    Ad Review
    Brand Safety
    Taxonomy
    Content Moderation
    Video Understanding
    IP Clearance

    How do I check video against my own compliance rules?



    Turn each rule into something a machine can test: example images of what is not allowed, a list of banned phrases, a line that must appear on screen, or a yes-or-no question. Index every video into scenes, each with its speech transcript, on-screen text and start and end time. Then check each video's scenes against every rule and keep the scenes that break one. What comes back is a list of flagged moments per video: the rule, how close the match was, and where it happens. A person reviews those moments instead of watching every video end to end.

    What kinds of rules can a machine check?



    Most compliance rules fall into five shapes, and each shape uses a different signal:

    Rule shapeExampleSignalHow Mixpeek checks it
    Something must not be shownNo alcohol near a minor, no competitor product on screenThe scene's pictureA taxonomy built from your example images
    Something must not be said or written"Guaranteed results", "risk-free", "cure"Transcript and on-screen textPhrase match on transcription and ocr_text
    Something must be present"Results not typical" on screen, a required disclaimerOn-screen textA phrase query; no matching scene means it is missing
    A judgment callA claim that implies a health benefitTranscript, on-screen text, sometimes the clipA yes-or-no question per scene, answered by a model
    A person, logo or slogan you have no rights toA public figure, another brand's markFaces, logos, copyMixpeek's marketplace IP retrievers


    Write the rules down in these shapes before building anything. A rule like "nothing off-brand" has no shape yet, and no system can check it until someone says what it looks or sounds like.

    Step 1: index each video into scenes



    Upload each video to a bucket with an ID you can filter on, such as asset_id, then create a collection with the multimodal extractor. Split by scene, and turn on transcription and on-screen text, because spoken and written claims are where most ad rules apply:
    {
      "collection_name": "ads",
      "source": { "type": "bucket", "bucket_ids": ["bkt_ads"] },
      "feature_extractor": {
        "feature_extractor_name": "multimodal_extractor",
        "version": "v1",
        "input_mappings": { "video": "video_url" },
        "field_passthrough": [
          { "source_path": "metadata.asset_id" },
          { "source_path": "metadata.market" }
        ],
        "parameters": {
          "split_method": "scene",
          "run_multimodal_embedding": true,
          "run_transcription": true,
          "run_ocr": true,
          "run_video_description": true,
          "enable_thumbnails": true
        }
      }
    }
    Every scene becomes a document with start_time, end_time, transcription, ocr_text, description, a thumbnail and a 1,408-float embedding of the picture. Scenes longer than max_segment_duration (30 seconds by default) are split further.

    Step 2: write the visual rules as a taxonomy



    A taxonomy in Mixpeek labels documents by matching them against a reference collection. For compliance, the reference collection is your rule book: one document per example of a violation, each carrying the rule it belongs to.

    Put a few example frames per rule in a second bucket, each with rule_id, rule and severity as metadata, and index them with the same extractor so their embeddings sit in the same space as your scenes:
    {
      "collection_name": "rule-examples",
      "source": { "type": "bucket", "bucket_ids": ["bkt_rule_examples"] },
      "feature_extractor": {
        "feature_extractor_name": "multimodal_extractor",
        "version": "v1",
        "input_mappings": { "image": "example_image" },
        "field_passthrough": [
          { "source_path": "metadata.rule_id" },
          { "source_path": "metadata.rule" },
          { "source_path": "metadata.severity" }
        ],
        "parameters": { "run_multimodal_embedding": true }
      }
    }
    The taxonomy needs a retriever that finds the nearest examples to a scene's embedding:
    {
      "retriever_name": "nearest-rule",
      "collection_identifiers": ["rule-examples"],
      "input_schema": { "vector": { "type": "array", "required": true } },
      "stages": [
        { "stage_name": "nearest", "stage_type": "filter",
          "config": { "stage_id": "feature_search", "parameters": {
            "final_top_k": 3,
            "searches": [ { "feature_uri": "mixpeek://multimodal_extractor@v1/vertex_multimodal_embedding",
              "query": { "input_mode": "vector", "value": "{{INPUT.vector}}" }, "top_k": 3 } ] } } }
      ]
    }
    Then the taxonomy itself, which feeds each scene's embedding to that retriever and copies the matched example's rule fields onto the scene:
    POST /v1/taxonomies
    {
      "taxonomy_name": "ad_rules",
      "config": {
        "taxonomy_type": "flat",
        "retriever_id": "<nearest-rule retriever ID>",
        "input_mappings": [
          { "input_key": "vector", "source_type": "vector",
            "path": "multimodal_extractor_v1_multimodal_embedding" }
        ],
        "source_collection": {
          "collection_id": "<rule-examples collection ID>",
          "enrichment_fields": [
            { "field_path": "metadata.rule_id", "target_field": "rule_id", "merge_mode": "replace" },
            { "field_path": "metadata.severity", "target_field": "severity", "merge_mode": "replace" }
          ]
        }
      }
    }
    Adding a rule is adding example images to the bucket. Nothing is retrained, and the next check uses them.

    Step 3: check one video against the visual rules



    This retriever loads every scene of one video, labels each with its nearest rule, keeps the scenes that matched one closely enough, and sorts them by time. It uses Attribute Filter, which reads documents straight from the collection when it is the first stage, and Taxonomy Enrich:
    {
      "retriever_name": "check-visual-rules",
      "collection_identifiers": ["ads"],
      "input_schema": { "asset_id": { "type": "text", "required": true } },
      "stages": [
        { "stage_name": "one_video", "stage_type": "filter",
          "config": { "stage_id": "attribute_filter", "parameters": {
            "field": "metadata.asset_id", "operator": "eq", "value": "{{INPUT.asset_id}}" } } },
        { "stage_name": "label", "stage_type": "enrich",
          "config": { "stage_id": "taxonomy_enrich", "parameters": {
            "taxonomy_id": "<ad_rules taxonomy ID>", "top_k": 1, "min_score": 0.75 } } },
        { "stage_name": "flagged_only", "stage_type": "filter",
          "config": { "stage_id": "attribute_filter", "parameters": {
            "field": "rule_id", "operator": "exists", "value": true } } },
        { "stage_name": "in_order", "stage_type": "sort",
          "config": { "stage_id": "sort_attribute", "parameters": {
            "field": "start_time", "direction": "asc" } } }
      ]
    }
    Each result is a flagged moment: start_time, end_time, rule_id, severity, the thumbnail, and the match score in a _taxonomy_..._score field named after the taxonomy ID.

    min_score decides how many moments come back. Set it on your own videos: label a few dozen scenes by hand, run the retriever at a few thresholds, and pick the one that misses nothing your reviewers would have flagged. Scores depend on your examples, so a threshold from someone else's rule book will not carry over.

    Step 4: banned phrases, required lines and judgment calls



    Banned phrases. Match them in the transcript and on-screen text with the phrase operator, which matches the words in order at word boundaries:
    { "stage_name": "banned_phrases", "stage_type": "filter",
      "config": { "stage_id": "attribute_filter", "parameters": { "conditions": { "AND": [
        { "field": "metadata.asset_id", "operator": "eq", "value": "{{INPUT.asset_id}}" },
        { "OR": [
          { "field": "transcription", "operator": "phrase", "value": "guaranteed results" },
          { "field": "ocr_text", "operator": "phrase", "value": "guaranteed results" },
          { "field": "transcription", "operator": "phrase", "value": "risk free" },
          { "field": "ocr_text", "operator": "phrase", "value": "risk free" }
        ] }
      ] } } } }
    Required lines. Run the same query with the line that must appear, such as {"field": "ocr_text", "operator": "phrase", "value": "results not typical"}. An empty result means the video never shows it, which is the flag.

    Judgment calls. Some rules need reading, such as "the ad implies the product treats a medical condition". Load the video's scenes with the first stage above, then add LLM Filter with the rule as its criteria:
    { "stage_name": "judgment", "stage_type": "filter",
      "config": { "stage_id": "llm_filter", "parameters": {
        "criteria": "Keep only scenes where the speech or on-screen text says or implies the product treats, cures or prevents a medical condition",
        "include_reasoning": true } } }
    The model reads each scene's transcript, on-screen text and description. Set include_media to true when the picture matters, and the scene goes to Gemini as video. LLM Filter makes one model call per scene, and its docs advise narrowing first when more than 100 documents reach it. A 30-second ad has a handful of scenes, so per-video checks stay small.

    Step 5: faces, logos and slogans



    Mixpeek's marketplace has public retrievers for the rights side of review:

  1. IP Screen: one frame in, every public figure and
  2. brand mark it contains, scored.
  3. Celebrity Face Match: the public figures
  4. a face matches, with a confidence score.
  5. Brand Logo Match: the reference marks that
  6. look most like a frame, ranked for review.
  7. Trademark Slogan Match: the registered
  8. slogans a line of copy resembles, and who owns them.

    Send each scene's thumbnail to IP Screen and each transcript or on-screen line to Trademark Slogan Match, through POST /v1/marketplace/catalog/{public_name}/execute with {"inputs": {"query": "<frame URL or text>"}}. Without an API key each listing allows 10 requests a minute per IP address, which is enough to try it.

    Where does this run, and on whose storage?



    Mixpeek reads the videos from your bucket (S3, GCS or another object store you connect) and keeps the scenes, transcripts and labels in your namespace. You call it through the API, so the flagged moments go wherever your review happens: a ticket, a spreadsheet, your own review screen. On the Enterprise plan the whole stack can also run in your own AWS, GCP or Azure account.

    What does it cost?



    At the rates in Mixpeek's public features API on 2026-11-10, video indexing with scenes, speech transcript and descriptions is $0.05 a minute, and on-screen text adds $0.10 a minute. Taxonomy enrichment is included.

    LibraryMinutesIndexingOn-screen textTotal
    One 30-second ad0.5$0.025$0.05$0.075
    1,000 thirty-second ads500$25$50$75
    100 hours of long-form video6,000$300$600$900


    You pay to index each video once. Rerunning the checks after a rule changes reads the stored scenes and does not re-index anything. LLM Filter calls are extra, one per scene that reaches the stage.

    What you build on top



    Mixpeek returns the flagged moments and the evidence for each one. It has no reviewer screen or approve-and-reject queue, no signed report format, and no ready-made rule packs for particular regulators or markets. Teams write their own rules from their policy documents and route the results into the tools their reviewers already use. Published accuracy figures for any compliance tool depend on the rules and footage they were measured on, so measure on yours.

    Frequently Asked Questions



    What is video compliance software?



    Software that checks videos against a set of rules, such as ad standards, platform policies or brand guidelines, and points to the moments that break them. The useful output is a list of timestamps per rule, so a reviewer checks those moments instead of watching every video in full.

    Can I use my own rules instead of a fixed list of categories?



    Yes. In Mixpeek the visual rules are a taxonomy built from your own example images, phrase rules are lists you write, and judgment rules are plain sentences a model answers per scene. Changing a rule means changing those inputs, and the next check uses them without re-indexing the videos.

    How do I check that a required disclaimer appears in a video?



    Index the video with on-screen text turned on, then query its scenes for the disclaimer with a phrase match on ocr_text. If no scene matches, the video never shows the line. Spoken disclaimers work the same way against transcription.

    How do I find the exact timestamp where a rule is broken?



    Index the video into scenes so every scene carries its own start and end time, then check scenes one at a time. Each flagged scene comes back with start_time and end_time in seconds, which a player can jump to directly.

    How is this different from a brand safety tool?



    A brand safety tool scores content against a shared list of categories, such as violence or adult content, so advertisers can avoid placements near it. A compliance check uses your own rules on your own videos before they ship. The pipelines overlap, and our guide on brand safety vs brand suitability covers the category side.

    Related reading



  9. Brand safety vs brand suitability for video
  10. Our brand safety tool flags too many false positives on video
  11. How to check if a video is copyrighted
  12. Taxonomies in the Mixpeek docs
  13. Managed Mixpeek

    Put multimodal search to work

    Connect a bucket and Mixpeek runs the whole multimodal search pipeline for you: extraction, indexing, and search over your own objects. No models to wire up, nothing to host.

    Start with Managed
    MVS · bring your own

    Already have vectors?

    Keep your embeddings on your own cloud and run dense, sparse, and BM25 search directly on object storage. From $25/mo.

    Start with MVS

    Check your own videos against your rules

    Mixpeek reads video from S3, GCS or any bucket, cuts it into scenes with transcript and on-screen text, and returns the scenes that break your rules with timestamps.

    Index your videosSee pricing

    Related guides

    Compliance

    How Do You Detect and Redact PII in Images, Video, and Audio?

    Text redaction is a solved problem and media redaction is not. A face is PII, a voice is PII, and so is the licence plate reflected in a shop window behind your subject. This works through what counts as identifying in each modality, why detect-then-blur leaves the original recoverable, how redaction interacts with an embedding you already computed, the irreversibility test that separates real redaction from a visual effect, and how to verify a redaction rather than trust the pipeline that claims it.

    Read guide →
    Search & Discovery

    Brand Safety vs Brand Suitability: How AI Classifies Video for Advertisers

    Safety is a universal floor; suitability is a per-brand tolerance curve over graded risk tiers: and the GARM-style taxonomy remains the reference for both even after the organization wound down. How multimodal classification actually works on video (visual + speech + on-screen text + adjacency), why treatment beats topic, why moderation APIs can't express per-brand tiers, and the query-time reclassification pattern that avoids re-paying analysis.

    Read guide →
    Video Understanding

    How Many Tokens Is an Hour of Video, and What Does It Cost to Send to an LLM?

    One hour of video is about 353,000 tokens in Gemini at low media resolution and 1,044,000 at default resolution, or $0.19 and $0.39 of input on Gemini 2.5 Flash. Sent to Claude as 720p frames once a second it is 4.3 million tokens. Here is the arithmetic from each provider's published rates on 2026-10-24, and why asking many questions about the same video costs more than the first pass.

    Read guide →