前回の AIでパワポを作るOSS「Presenton」をAWSに構築する で、EC2 上に Presenton を立てるところまでを扱いました。ただ、画面から1本ずつ作っているうちは省力化になりません。月次レポートや部署ごとの定例資料のように「同じ形のものを繰り返し作る」用途でこそ効いてきます。
この記事では、Presenton の REST API を使って外部からスライドを生成する方法をまとめます。API キーの発行から、定例運用で必要になる非同期処理、そして README には載っていないエンドポイント群までを扱います。

1. 先に管理画面でアカウントを作る
いきなり API を叩くと、次のエラーで弾かれます。
428 Precondition Required
Login setup is required
Presenton は初回に管理画面でアカウントを作るまで、API を受け付けません。前回の記事でも触れましたが、API から入ろうとすると最初にここで詰まります。ブラウザで http://<ホスト>/ を開き、最初のユーザーを作成してください。
アカウントができたら、管理画面の Admin → API keys でキーを発行します。sk-presenton- から始まる文字列です。
キーは発行時にしか表示されないので、その場で控えます。失効させると即時に効きます。外部システムに渡したキーを止めたいときは、ここから無効化すれば通信をその時点で遮断できます。
2. 1本作ってみる
生成のエンドポイントはこれだけです。
POST /api/v1/ppt/presentation/generate
Authorization: Bearer sk-presenton-XXXX
Content-Type: application/json
リクエストの本体は次のような JSON です。
{
"content": "社内AI活用の現状",
"n_slides": 8,
"template": "general",
"language": "Japanese",
"export_as": "pptx"
}
PowerShell から投げる場合はこう書きます。
# APIキーは環境変数などから読み込む。スクリプトに直書きしない
$key = $env:PRESENTON_API_KEY
$body = @{
content = '社内AI活用の現状'
n_slides = 8
template = 'general'
language = 'Japanese'
export_as = 'pptx'
} | ConvertTo-Json
$res = Invoke-RestMethod -Method Post `
-Uri 'http://203.0.113.10/api/v1/ppt/presentation/generate' `
-Headers @{ Authorization = "Bearer $key" } `
-ContentType 'application/json; charset=utf-8' `
-Body $body
$res
返ってくるのは生成物の場所と編集用のURLです。
{
"presentation_id": "d3000f96-...",
"path": "/app_data/d3000f96-.../file.pptx",
"edit_path": "/presentation?id=d3000f96-..."
}
ここで注意が必要です。path はファイルの中身ではなく、コンテナ内のパスです。レスポンスに PPTX そのものは含まれません。前回の構成ではホストの /opt/presenton/app_data をマウントしているので、サーバー側では次の場所にファイルが置かれます。
# ホスト側から生成物を確認する
ls -l /opt/presenton/app_data/d3000f96-*/
edit_path をブラウザで開けば、生成された内容をそのまま編集できます。
3. 押さえておくパラメータ
content だけでも動きますが、実務では出力の振れ幅を抑えたいので、指定できる項目を把握しておきます。
| パラメータ | 内容 |
|---|---|
content | 生成のもとになる内容 |
slides_markdown | スライドごとの中身を直接指定する |
instructions | 追加の作成指示 |
tone | professional / casual / educational など |
verbosity | concise / standard / text-heavy |
n_slides | 枚数(既定は8) |
template | 使うテンプレート |
language | 出力言語 |
export_as | pptx または pdf |
web_search | 生成時に Web 検索で裏取りするか |
定例資料の自動生成で効くのは slides_markdown です。content にテーマを渡すだけだと構成は毎回変わりますが、章立てを Markdown で渡せば、中身だけが差し替わった同じ形の資料が出てきます。
日本語は language に Japanese を指定します。ただし仕上がりは使う LLM に左右されます。テンプレートとモデルの組み合わせは、本番に載せる前に何本か試して決めるのが確実です。
4. 定例で回すなら非同期にする
生成には時間がかかります。1本ずつ手で作る分には同期で構いませんが、バッチで何十本も回すと、HTTP 接続を掴んだまま待ち続けることになります。タイムアウトの調整にも限界があります。
そのために非同期のエンドポイントが用意されています。
POST /api/v1/ppt/presentation/generate/async # 投げるとすぐタスクIDが返る
GET /api/v1/async-tasks/status/{task_id} # 進捗を問い合わせる
実機で3枚を流したところ、投入は0.1秒で返り、生成完了までは56.7秒でした。同期で同じ3枚を作ったときは33.3秒かかっており、その間ずっと接続を掴んだままになります。
ここで2か所つまずきました。
ひとつは進捗の問い合わせ先です。presentation/status/{id} というパスは存在しますが、レスポンスに返る presentation_id を渡しても 404 No presentation generation task found になります。追うべきは async-tasks のほうで、パスはアンダースコアではなくハイフン区切りです。
もうひとつは Webhook です。
POST /api/v1/webhook/subscribe # /ppt は付かない
DELETE /api/v1/webhook/unsubscribe
/api/v1/ppt/webhook/subscribe は404になります。 ほかのエンドポイントが /api/v1/ppt/ 配下なので釣られやすいところです。正しいパスに登録すると 201 と Webhook の ID が返り、解除は 204 でした。
月次バッチのように「投げっぱなしにして、終わったら通知が欲しい」構成なら、generate/async と webhook/subscribe の組み合わせが素直です。
5. エンドポイントは約100本ある
ここが調べていて一番意外だったところです。README に書かれているのは生成とファイルアップロードだけですが、v1系だけで約100本のエンドポイントがあります。

大きく3つに分かれます。
| 区分 | 本数 | 代表的なもの |
|---|---|---|
| プレゼンテーション | 16本 | generate / generate/async / {id}/export / edit / slide_update / {id}/duplicate |
| 素材・見た目 | 40本ほど | files/upload / template/fonts-upload-and-slides-preview / template/init / theme/create / fonts/upload |
| 運用・連携 | 30本ほど | admin/users / auth/token/create / webhook/subscribe / chat/message/stream |
上の一覧はパスの接頭辞(/api/v1/ppt/ など)を省いています。正確な定義は /docs と /openapi.json で確認できます。どちらもログインが必要です。
ここで注意があります。エンドポイントが存在することと、API キーで呼べることは別です。
利用者アカウントを払い出す admin/users は用意されていますが、API キーで叩くと弾かれました。
{"detail": "Admin browser session required"}
HTTP ステータスは403です。API キーは発行したユーザーとして動くため、管理者のブラウザセッションが要るエンドポイントは呼べません。 PPTX の使用フォントを調べる fonts/check も同じでした。アカウントの払い出しまで自動化することは、現状ではできません。
生成まわり(generate / generate/async / webhook/subscribe)は API キーで通ったので、自動化の本線には支障ありません。どれが通ってどれが通らないかは、組み込む前に一度叩いて確かめてください。
なお、MCP サーバーは /mcp で動いています。AI エージェントから直接スライドを作らせる構成も取れますが、そちらは別途扱います。
6. 運用前に見積もっておくもの
自動化すると生成本数が一気に増えるので、先に2つ見積もっておきます。
6.1 ディスク
検証環境で生成した1本のサイズは 約1.04MB でした。単純計算で次のようになります。
| 月あたりの生成本数 | 1年で増える容量 |
|---|---|
| 100本 | 約1.2GB |
| 1,000本 | 約12GB |
前回の構成は gp3 30GB なので、月1,000本ペースだと2年ほどで手狭になります。生成物はホストの app_data に溜まり続けるため、古いものを消す仕組みか、定期的に外へ退避する運用を先に決めておく必要があります。
Presenton には S3 用の設定項目もコードもなく、保存先はローカル固定です。この点は Dify と違うところで、DifyのファイルストレージをS3にする のようにオブジェクトストレージへ逃がすことはできません。
6.2 LLMの費用
スライド1本あたりの費用は、使うモデルの単価で決まります。入力20,000トークン・出力10,000トークンと仮定して概算すると、入出力が $2 / $10(100万トークンあたり)のモデルで1本あたり20円前後という水準になります。月100本なら2,000円ほどです。
(20,000 / 1,000,000) × $2 = $0.04
(10,000 / 1,000,000) × $10 = $0.10
合計 $0.14 ≒ 約21円(1USD=150円換算)
モデルの単価は改定が入るため、実際の見積りは必ず公式の価格表で確認してください。上の数字は計算方法を示すための例です。トークン数も資料の内容で変わるので、まず数本流して実測するのが確実です。
7. まとめ
Presenton の REST API でスライド生成を自動化する方法をまとめました。
- 先に管理画面でアカウントを作らないと API は 428 で弾かれる
- 生成は
POST /api/v1/ppt/presentation/generateの1本。レスポンスに返るのはファイルではなくパス - 構成を固定したいなら
contentではなくslides_markdownを使う - 定例バッチは
generate/asyncとwebhook/subscribe。同期のまま束ねると接続を掴み続ける - 進捗は
async-tasks/status/{task_id}。Webhook のパスに/pptは付かない - エンドポイントは v1系だけで106本。ただし
admin/usersは API キーでは呼べない(403) - 保存先はローカル固定。生成物の掃除は自分で仕組みを作る
本記事の内容は、検証環境(presenton-verify)で実際に API を叩いて確かめたものです。実測値は次のとおりです。
| 確認したこと | 結果 |
|---|---|
| 同期生成(3枚) | 33.3秒。返るのはファイルではなくパス |
| 非同期生成(3枚) | 投入0.1秒、完了まで56.7秒 |
| 進捗の問い合わせ | async-tasks/status/{task_id} で pending → completed |
| Webhook 登録 | /api/v1/webhook/subscribe で201。解除は204 |
admin/users | 403 Admin browser session required |
| マウント済みルート数 | 106本 |
LLM の単価だけは公式の価格表で確認してください。改定が入るため、上の計算式は方法を示す例です。
次回は、Presenton に内蔵されている MCP サーバーを使い、Claude Code から直接スライドを作らせる構成を扱います。


コメント