動画生成 Sora2 API 早くも公開!

Cover Image for 動画生成 Sora2 API 早くも公開!
AICU media
AICU media

2025年10月6日(現地時間) OpenAI Soraによる動画生成APIとプロンプトガイドが公開されました。AICU AIDX Labでは早速実際に手を動かして動作するサンプルを開発してみました。

もう一度生成してみます。Soraの雲ロゴマークは入りません。生成時間も1-2分かなり速いと思います。 pic.twitter.com/MYLnyDmtX6

— AICU - つくる人をつくる (@AICUai)

APIにしかない機能としては、無料版アプリにあった「Sora雲マーク」の除去、高品質なSora2-Pro、シーンの構成を表現するスプライトシートの同時生成、過去の生成リストを取得など、プロフェッショナル用途にも向いています。

実際に実装してみた!

AICU AIDX Labでは実際に実装してみました。

APIの利用には通常のGPT系のAPIキーとは別に本人認証が必要です。パスポートや顔を使ったeKYC(電子本人確認)を行いますので企業でのAPI利用の場合は運用部門に確認する必要があります。

このような形でAPIによって任意の動画を生成でき、Slackに通知できます。

生成した過去の動画のリストを取得できます。失敗したこともわかります。

動画 (Video)APIの料金は?

モデル サイズ: 出力解像度 1秒あたりの料金
sora-2 ポートレート (縦長): 720x1280 ランドスケープ (横長): 1280x720 $0.10
sora-2-pro ポートレート (縦長): 720x1280 ランドスケープ (横長): 1280x720 $0.30
sora-2-pro ポートレート (縦長): 1024x1792 ランドスケープ (横長): 1792x1024$0.50

フルHD(1920x1080)にはちょっと足りないのでプロの映像制作、というにはほんの少し足りない感じではありますが、SNS用の高品質なメディアをAPIで生成することはできるようになっています。

可愛い猫動画を常にポストし続けるボットも作れますね!

Coded by Sora2 API! #Sora2 pic.twitter.com/RJp4GWwj3i

— AICU - つくる人をつくる (@AICUai)

AICUの X@AICUai を担当している Saki Noir (AiCuty)に毎時可愛い動画を呟かせるbotを作ってみます。
みなさまのご意見をシェアとともにお聞かせください。

AICU AIDX Labでは画像生成システム、動画生成システム、コンテンツ開発、キャラクターIP開発、インタラクティブシステムや著作権解決技術の研究開発を行っています。現在、事業拡大に伴いリサーチャーおよびパートナー企業を募集しています。またAICU Media事業部においてもパートナー企業を募集しております。資料はこちら。お気軽にお問い合わせください。

[PR]本日20時より開催!AICU Lab+ 勉強会(無料)
ComfyUIで映画制作からNanoBanana、動画生成まで!可愛いキャラクターからエンジニアリングまで使いこなすクリエイターから直接学びませんか?


以下公式資料の翻訳です。

Video generation with Sora

Soraによる動画生成 - SoraAPI

SoraAPIを使用して、動画の作成、イテレーション(反復的な改良)、管理を行うことができるようになりました。Soraは、OpenAIの生成メディアにおける最新のフロンティアであり、自然言語や画像から、音声付きで非常に詳細かつダイナミックなクリップを作成できる最先端の動画モデルです。マルチモーダルな拡散モデルに関する長年の研究に基づき、多様な視覚データでトレーニングされたSoraは、3D空間、動き、シーンの連続性に対する深い理解をテキストからの動画生成にもたらします。
Soraは、これらの機能を開発者に初めて公開し、プログラムによる動画の作成、拡張、リミックスを可能にします。このAPIは5つのエンドポイントを提供し、それぞれが異なる機能を持っています。

  • 動画の作成 (CreateVideo) : プロンプトから新しいレンダリングジョブを開始します。オプションで参照入力やリミックスIDを指定することも可能です。

  • 動画ステータスの取得 (GetVideoStatus) : レンダリングジョブの現在の状態を取得し、その進捗を監視します。

  • 動画のダウンロード (DownloadVideo) : ジョブが完了したら、完成したMP4ファイルをフェッチ(取得)します。

  • 動画の一覧表示 (ListVideos) : 履歴、ダッシュボード、または整理のために、ページネーション付きで動画を列挙します。

  • 動画の削除 (DeleteVideos) : OpenAIのストレージから個別の動画IDを削除します。

2つのモデル

第2世代のSoraモデルには2つの系があり、それぞれ異なるユースケースに合わせて調整されています。

Sora 2

sora-2 は、速度と柔軟性 を重視して設計されています。トーン、構成、ビジュアルスタイルなどを試しながら、完璧な忠実度よりも迅速なフィードバックが必要となる探索フェーズに最適です。

質の良い結果を迅速に生成するため、素早いイテレーション、コンセプト作成、ラフカットに適しています。sora-2 は、ソーシャルメディアコンテンツ、プロトタイプ、超高忠実度よりも納期が重要なシナリオにおいて、多くの場合十分すぎるほどの性能を発揮します。

Sora 2 Pro

sora-2-pro は、より高品質な結果を生成します。プロダクション品質の出力 が必要な場合に適した選択肢です。

sora-2-pro はレンダリングに時間がかかり、実行コストも高くなりますが、より洗練され、安定した結果を生成します。高解像度の映画のような映像、マーケティング用のアセットなど、視覚的な精度が極めて重要なあらゆる状況に最適です。

動画を生成する

動画の生成は非同期 プロセスです。

  1. POST /videosエンドポイントを呼び出すと、APIはジョブidと初期statusを含むジョブオブジェクトを返します。

  2. ステータスがcompletedに遷移するまでGET /videos/{video_id}エンドポイントをポーリング(定期的に問い合わせ)するか、より効率的なアプローチとしてWebhook(下記Webhookのセクション参照)を使用してジョブ完了時に自動的に通知を受け取ることができます。

  3. ジョブがcompleted状態に達したら、GET /videos/{video_id}/contentで最終的なMP4ファイルを取得できます。

レンダリングジョブの開始

まず、テキストプロンプトと必須パラメータを指定してPOST /videosを呼び出します。プロンプトは被写体、カメラ、照明、動きといったクリエイティブなルック&フィールを定義し、sizeやsecondsのようなパラメータは動画の解像度と長さを制御します。

動画を作成する JavaScriptサンプル

import OpenAI from 'openai';

const openai = new OpenAI();

let video = await openai.videos.create({
    model: 'sora-2',
    prompt: "A video of the words 'Thank you' in sparkling letters",
});

console.log('動画生成を開始しました: ', video);

レスポンスは、一意のidとqueued(待機中)やin_progress(処理中)などの初期ステータスを持つJSONオブジェクトです。これはレンダリングジョブが開始されたことを意味します。

JSONによる戻り

{
  "id": "video_68d7512d07848190b3e45da0ecbebcde004da08e1e0678d5",
  "object": "video",
  "created_at": 1758941485,
  "status": "queued",
  "model": "sora-2-pro",
  "progress": 0,
  "seconds": "8",
  "size": "1280x720"
}

ガードレールと制限事項

APIはいくつかのコンテンツ制限を設けています。

  • 18歳未満の視聴者に適したコンテンツのみ(この制限を回避する設定は将来的に利用可能になる予定です)。

  • 著作権で保護されたキャラクターや音楽は拒否されます。

  • 公人を含む実在の人物は生成できません。

  • 人間の顔を含む入力画像は現在拒否されます。

生成の失敗を避けるため、プロンプト、参照画像、トランスクリプトがこれらのルールを遵守していることを確認してください。

効果的なプロンプト作成

最良の結果を得るためには、ショットの種類、被写体、アクション、設定、照明 を記述してください。例:

「芝生の公園で赤い凧を揚げる子供のワイドショット、ゴールデンアワーの日差し、カメラはゆっくりと上にパンする。」

「木製のテーブルの上にある湯気の立つコーヒーカップのクローズアップ、ブラインドから差し込む朝の光、浅い被写界深度。」

このレベルの具体性により、モデルは不要な詳細を創作することなく、一貫した結果を生成しやすくなります。より高度なプロンプト作成技術については、専門のSora2 プロンプトガイド を参照してください。

Sora 2 Prompting Guide | OpenAI Cookbook Think of prompting like briefing a cinematographer who has ne cookbook.openai.com

進捗の監視

動画の生成には時間がかかります。モデル、APIの負荷、解像度によっては、1回のレンダリングに数分かかる場合があります

これを効率的に管理するために、APIをポーリングしてステータスの更新をリクエストするか、Webhookを介して通知を受け取ることができます。

ステータスエンドポイントのポーリング

作成時の呼び出しで返されたidを使ってGET /videos/{video_id}を呼び出します。レスポンスには、ジョブの現在のステータス、進捗率(利用可能な場合)、およびエラーが表示されます。

典型的な状態はqueued(待機中)、in_progress(処理中)、completed(完了)、failed(失敗)です。適切な間隔(例:10~20秒ごと)でポーリングし、必要に応じて指数バックオフを使用し、ジョブがまだ進行中であることをユーザーにフィードバックしてください。

ステータスエンドポイントのポーリング

import OpenAI from 'openai';

const openai = new OpenAI();

async function main() {
  const video = await openai.videos.createAndPoll({
    model: 'sora-2',
    prompt: "A video of the words 'Thank you' in sparkling letters",
  });

  if (video.status === 'completed') {
    console.log('動画が正常に完了しました: ', video);
  } else {
    console.log('動画の作成に失敗しました。ステータス: ', video.status);
  }
}

main();

レスポンス例:

{
  "id": "video_68d7512d07848190b3e45da0ecbebcde004da08e1e0678d5",
  "object": "video",
  "created_at": 1758941485,
  "status": "in_progress",
  "model": "sora-2-pro",
  "progress": 33,
  "seconds": "8",
  "size": "1280x720"
}

Webhookによる通知の利用

GETでジョブのステータスを繰り返しポーリングする代わりに、Webhook を登録して、動画生成が完了または失敗したときに自動的に通知を受け取ることができます。

WebhookはWebhook設定ページ で設定できます。ジョブが終了すると、APIはvideo.completedとvideo.failedの2つのイベントタイプのいずれかを発行します。各イベントには、それをトリガーしたジョブのIDが含まれます。

Webhookペイロードの例: JSON

{
  "id": "evt_abc123",
  "object": "event",
  "created_at": 1758941485,
  "type": "video.completed", // または "video.failed"
  "data": {
    "id": "video_abc123"
  }
}

結果の取得とMP4のダウンロード

ジョブのステータスがcompletedになったら、GET /videos/{video_id}/contentでMP4を取得します。このエンドポイントはバイナリの動画データをストリーミングし、標準のコンテントヘッダーを返すため、ファイルを直接ディスクに保存するか、クラウドストレージにパイプすることができます。

MP4のダウンロード

 import OpenAI from 'openai';
import fs from 'fs';

const openai = new OpenAI();

let video = await openai.videos.create({
    model: 'sora-2',
    prompt: "A video of the words 'Thank you' in sparkling letters",
});

console.log('動画生成を開始しました: ', video);

let progress = video.progress ?? 0;

while (video.status === 'in_progress' || video.status === 'queued') {
    video = await openai.videos.retrieve(video.id);
    progress = video.progress ?? 0;

    // プログレスバーの表示
    const barLength = 30;
    const filledLength = Math.floor((progress / 100) * barLength);
    // ターミナル出力用のシンプルなASCIIプログレス表示
    const bar = '='.repeat(filledLength) + '-'.repeat(barLength - filledLength);
    const statusText = video.status === 'queued' ? 'Queued' : 'Processing';

    process.stdout.write(`\r${statusText}: [${bar}] ${progress.toFixed(1)}%`);
    await new Promise((resolve) => setTimeout(resolve, 2000));
}

// プログレス行をクリアして完了を表示
process.stdout.write('\n');

if (video.status === 'failed') {
    console.error('動画生成に失敗しました');
    return;
}

console.log('動画生成が完了しました: ', video);
console.log('動画コンテンツをダウンロードしています...');

const content = await openai.videos.downloadContent(video.id);
const body = content.arrayBuffer();
const buffer = Buffer.from(await body);

fs.writeFileSync('video.mp4', buffer);
console.log('video.mp4を書き込みました');

これで、再生、編集、または配信の準備ができた最終的な動画ファイルが手に入ります。ダウンロードURLは生成後最大24時間有効です。長期的な保管が必要な場合は、速やかにご自身のストレージシステムにファイルをコピーしてください。

サポートアセットのダウンロード

完了した各動画について、サムネイルスプライトシート もダウンロードできます。これらはプレビュー、スクラバー、またはカタログ表示に役立つ軽量なアセットです。variantクエリパラメータを使用して、ダウンロードしたいものを指定します。デフォルトはMP4用のvariant=videoです。

# サムネイルをダウンロード
curl -L "https://api.openai.com/v1/videos/video_abc123/content?variant=thumbnail" \
  -H "Authorization: Bearer $OPENAI_API_KEY" \
  --output thumbnail.webp

# スプライトシートをダウンロード
curl -L "https://api.openai.com/v1/videos/video_abc123/content?variant=spritesheet" \
  -H "Authorization: Bearer $OPENAI_API_KEY" \
  --output spritesheet.jpg

画像リファレンスの使用

入力画像で生成をガイドすることができ、その画像は動画の最初のフレーム として機能します。これは、出力動画がブランドのアセット、キャラクター、または特定の環境の見た目を維持する必要がある場合に便利です。POST /videosリクエストのinput_referenceパラメータとして画像ファイルを含めます。画像はターゲット動画の解像度(size)と一致する必要があります。

サポートされているファイル形式はimage/jpeg、image/png、image/webpです。

curl -X POST "https://api.openai.com/v1/videos" \
  -H "Authorization: Bearer $OPENAI_API_KEY" \
  -H "Content-Type: multipart/form-data" \
  -F prompt="She turns around and smiles, then slowly walks out of the frame." \
  -F model="sora-2-pro" \
  -F size="1280x720" \
  -F seconds="8" \
  -F input_reference="@sample_720p.jpeg;type=image/jpeg"

リミックス機能を使用すると、既存の動画を取得し、すべてをゼロから再生成することなく的を絞った調整を行う ことができます。完了したジョブのremix_video_idと、変更内容を記述した新しいプロンプトを提供すると、システムは元の動画の構造、連続性、構図を再利用しながら、変更を適用します。これは、単一の明確に定義された変更 を行う場合に最も効果的です。なぜなら、より小さく焦点の合った編集は、元の忠実度をより多く保持し、アーティファクトが発生するリスクを低減するからです。

curl -X POST "https://api.openai.com/v1/videos/<previous_video_id>/remix" \
  -H "Authorization: Bearer $OPENAI_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "prompt": "カラーパレットをティール、サンド、ラスト(錆色)に変更し、暖かいバックライトを追加する。"
  }'

リミックスは、すでに機能している部分を破棄することなく改良できるため、イテレーションに特に価値があります。各リミックスを1つの明確な調整に限定することで、ビジュアルスタイル、被写体の一貫性、カメラのフレーミングを安定させながら、雰囲気、パレット、または演出のバリエーションを探求できます。これにより、小さく信頼性の高いステップを通じて、洗練されたシーケンスを構築することがはるかに容易になります。

(画像例) リミックスで生成された動画

  • プロンプト : 「モンスターの色をオレンジ色に変更する。」

  • プロンプト : 「直後にもう一体のモンスターが出てくる。」

ライブラリの維持

GET /videosを使用して動画を列挙します。このエンドポイントは、ページネーションとソートのためのオプションのクエリパラメータをサポートしています。

# デフォルト
curl "https://api.openai.com/v1/videos" \
  -H "Authorization: Bearer $OPENAI_API_KEY" | jq .

# パラメータ付き
curl "https://api.openai.com/v1/videos?limit=20&after=video_123&order=asc" \
  -H "Authorization: Bearer $OPENAI_API_KEY" | jq .

DELETE /videos/{video_id}を使用して、不要になった動画をOpenAIのストレージから削除します。

curl -X DELETE "https://api.openai.com/v1/videos/[YOUR_VIDEO_IDに置き換えてください]" \
  -H "Authorization: Bearer $OPENAI_API_KEY" | jq .