Skip to main content

Documentation Index

Fetch the complete documentation index at: https://docs.mavera.io/llms.txt

Use this file to discover all available pages before exploring further.

Scenario

Use Mavera to generate a video script, feed it to OpenAI’s Sora to generate video, then loop results through Mavera’s Mave Agent for quality assessment — brand alignment, narrative coherence, visual impact — and iterate until quality thresholds are met. Flow: Mavera POST /generations (script) → OpenAI Sora POST /images/generations → Mavera POST /mave/chat (analyze) → Iterate
Sora’s API is actively evolving. The example below uses the images.generate endpoint with model="sora", which reflects the current API surface. Check OpenAI’s Sora documentation for the latest endpoint details.

Code

import os, requests, time, base64, re
from openai import OpenAI

client = OpenAI(api_key=os.environ["OPENAI_API_KEY"])
MV = os.environ["MAVERA_API_KEY"]
MV_BASE = "https://app.mavera.io/api/v1"
MV_H = {"Authorization": f"Bearer {MV}", "Content-Type": "application/json"}

os.makedirs("sora_output", exist_ok=True)
MAX_ITERATIONS = 3
QUALITY_THRESHOLD = 8

# 1. Generate video script with Mavera
script_gen = requests.post(f"{MV_BASE}/generations", headers=MV_H, json={
    "prompt": "Write a detailed 15-second video prompt for Sora. "
        "Product: SaaS marketing analytics dashboard. "
        "Style: Clean, modern, cinematic. Show the dashboard in use — "
        "charts animating upward, a milestone notification popping. "
        "End on a wide shot with the tagline visible. "
        "Include camera angles, lighting, transitions.",
}).json()
script = script_gen.get("output") or script_gen.get("content") or ""
print(f"Script generated: {len(script)} chars")
time.sleep(2)

for iteration in range(1, MAX_ITERATIONS + 1):
    print(f"\n{'='*60}\nITERATION {iteration}\n{'='*60}")

    # 2. Generate video with Sora
    try:
        sora_resp = client.images.generate(model="sora", prompt=script, n=1, size="1792x1024")
        video_url = sora_resp.data[0].url
        video_b64 = sora_resp.data[0].b64_json
        output_path = f"sora_output/video_v{iteration}.mp4"

        if video_b64:
            with open(output_path, "wb") as f:
                f.write(base64.b64decode(video_b64))
            print(f"Video saved: {output_path} ({os.path.getsize(output_path) // 1024} KB)")
        elif video_url:
            vid_data = requests.get(video_url).content
            with open(output_path, "wb") as f:
                f.write(vid_data)
            print(f"Video downloaded: {output_path} ({len(vid_data) // 1024} KB)")
    except Exception as e:
        print(f"Sora error: {e} — retrying...")
        time.sleep(5)
        continue

    time.sleep(2)

    # 3. Analyze with Mavera
    analysis = requests.post(f"{MV_BASE}/mave/chat", headers=MV_H, json={
        "message": f"Video quality assessor. Iteration {iteration}.\n\n"
            f"SCRIPT:\n{script[:3000]}\n\n"
            "Score 1-10 on: BRAND ALIGNMENT, NARRATIVE COHERENCE, "
            "VISUAL QUALITY, EMOTIONAL IMPACT, CTA CLARITY.\n"
            "Give OVERALL SCORE (1-10) and SPECIFIC IMPROVEMENTS as a refined Sora prompt.",
    }).json()

    analysis_text = analysis.get("content", "")
    print(analysis_text[:2000])

    score_line = [l for l in analysis_text.split("\n") if "OVERALL" in l.upper()]
    nums = re.findall(r'\b(\d+)\b', score_line[0]) if score_line else []
    score = int(nums[0]) if nums else 0
    print(f"\nScore: {score}/10 (threshold: {QUALITY_THRESHOLD})")

    if score >= QUALITY_THRESHOLD:
        print(f"Quality met at iteration {iteration}. Final: {output_path}")
        break

    # 4. Refine prompt
    refined = [l for l in analysis_text.split("\n") if "prompt" in l.lower() or "refine" in l.lower()]
    if refined:
        script += "\n\nRefinements: " + " ".join(refined)[:500]
    time.sleep(3)
else:
    print(f"Max iterations ({MAX_ITERATIONS}) reached.")

Example Output

Script: 487 chars

ITERATION 1 → video_v1.mp4 (2,814 KB)
BRAND ALIGNMENT: 7/10 — Colors muted, should be #2563EB
NARRATIVE: 6/10 — Chart animation starts too early
QUALITY: 8/10 — Clean, no artifacts
IMPACT: 6/10 — Needs faster transitions
CTA: 5/10 — Tagline too small
OVERALL: 6/10 — Prompt refined for iteration 2

ITERATION 2 → video_v2.mp4 (3,102 KB)
OVERALL: 8/10 — Colors corrected, CTA prominent, timing fixed.
Quality met at iteration 2.

Error Handling

Sora access may require a specific tier. If you get a 404 or model-not-found error, verify access at platform.openai.com/settings. Fall back to DALL-E 3 for static frames if unavailable.
Video generation can take 30-120 seconds. Set HTTP client timeout to at least 180 seconds. The OpenAI SDK handles this automatically, but raw requests calls need timeout=180.
The loop caps at 3 iterations to prevent runaway costs. Each iteration consumes Sora credits plus Mavera credits. If scores plateau, review the base script rather than continuing to refine.