PDF圧縮API: APIコール1回でPDFファイルサイズを削減する方法
メールでPDFが弾かれる。ダウンロードリンクがタイムアウトする。ストレージコストが積み上がる。PDFが重すぎる場合、最も手軽な解決策はサイズ圧縮です。APIで処理すれば、追加ライブラリもローカルツールも不要です。
FUNBREW PDFの圧縮エンドポイント(POST /api/pdf/compress)は、FUNBREWサーバー上に保存済みのPDFをGhostscriptで圧縮し、新しいダウンロードURLを返します。POSTリクエスト1回だけです。
このガイドではAPIの仕様、品質プリセットの使い分け、cURL・Node.js・Python・PHPのコード例、そして圧縮率を最大化するための実践的なヒントを解説します。
PDFの生成方法についてはPDF APIクイックスタートを、複数PDFの結合はPDFマージAPIガイドを参照してください。
仕組み
圧縮パイプラインは3ステップです。
- アカウント内に存在する
filename(以前のFUNBREW PDF API呼び出しで生成されたファイル)を指定してPOST /api/pdf/compressを呼び出す。 - サーバーが選択した
-dPDFSETTINGSプリセットでGhostscriptを実行する。 - 圧縮後のサイズが元より小さければ圧縮済みファイルを、そうでなければ元ファイルを返す。どちらの場合も有効なダウンロードURLが返ります。
このエンドポイントはSaaSエディションでpdf.feature:compressフィーチャーゲートが有効なプランが必要です。
API仕様
POST /api/pdf/compress
Content-Type: application/json
Authorization: Bearer {APIキー}
リクエストパラメータ
| パラメータ | 型 | 必須 | 説明 |
|---|---|---|---|
filename |
string | Yes | アカウント内の既存PDFのファイル名 |
quality |
string | No | 圧縮プリセット: low、medium、high(デフォルト: medium) |
expiration_hours |
integer | No | 圧縮済みファイルの有効期限(時間)(0〜168、デフォルト 24) |
max_downloads |
integer | No | 有効期限前の最大ダウンロード数(0〜100、デフォルト 10) |
品質プリセット
qualityパラメータはGhostscriptの-dPDFSETTINGSフラグに対応します。
| 値 | Ghostscript設定 | 代表的な用途 |
|---|---|---|
low |
/screen |
メール添付・プレビュー — 最大サイズ削減 |
medium |
/ebook |
Web配信・業務文書 — バランス重視(デフォルト) |
high |
/printer |
印刷用途 — 品質低下を最小化 |
成功レスポンス
{
"success": true,
"data": {
"filename": "compressed-abc123.pdf",
"download_url": "https://pdf.funbrew.cloud/api/pdf/download/compressed-abc123.pdf",
"original_size": 4194304,
"compressed_size": 1048576,
"savings_percent": 75.0,
"expires_at": "2026-05-19T10:00:00Z"
}
}
savings_percentはoriginal_sizeに対する削減率(%)です。値が0の場合、元ファイルが既に最適化されており変更なしで返ったことを意味します。
エラーレスポンス
| ステータス | 原因 |
|---|---|
| 422 | filenameがアカウント内に見つからない、またはファイルの有効期限切れ |
| 422 | ストレージ上にファイルが存在しない(削除済み) |
| 500 | Ghostscriptの実行失敗 |
コード例
cURL
デフォルトのmedium品質で圧縮する最小構成:
curl -X POST https://pdf.funbrew.cloud/api/pdf/compress \
-H "Authorization: Bearer $FUNBREW_PDF_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"filename": "report-abc123.pdf",
"quality": "medium"
}'
low品質・有効期限48時間で圧縮:
curl -X POST https://pdf.funbrew.cloud/api/pdf/compress \
-H "Authorization: Bearer $FUNBREW_PDF_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"filename": "report-abc123.pdf",
"quality": "low",
"expiration_hours": 48,
"max_downloads": 5
}'
Node.js
const fs = require('fs');
async function compressPdf(filename, quality = 'medium') {
const response = await fetch('https://pdf.funbrew.cloud/api/pdf/compress', {
method: 'POST',
headers: {
'Authorization': `Bearer ${process.env.FUNBREW_PDF_API_KEY}`,
'Content-Type': 'application/json',
},
body: JSON.stringify({ filename, quality }),
});
if (!response.ok) {
const error = await response.json();
throw new Error(`Compress APIエラー ${response.status}: ${error.message}`);
}
const result = await response.json();
const { download_url, original_size, compressed_size, savings_percent } = result.data;
console.log(`元サイズ: ${(original_size / 1024).toFixed(1)} KB`);
console.log(`圧縮後: ${(compressed_size / 1024).toFixed(1)} KB`);
console.log(`削減率: ${savings_percent}%`);
console.log(`ダウンロード: ${download_url}`);
return result.data;
}
// 生成 → 圧縮の2ステップ例
async function generateAndCompress() {
// Step 1: PDF生成
const genResponse = await fetch('https://pdf.funbrew.cloud/api/pdf/generate-from-html', {
method: 'POST',
headers: {
'Authorization': `Bearer ${process.env.FUNBREW_PDF_API_KEY}`,
'Content-Type': 'application/json',
},
body: JSON.stringify({
html: '<h1>年次レポート</h1><p>2026年度のサマリー...</p>',
engine: 'quality',
format: 'A4',
return_type: 'filename',
}),
});
const genResult = await genResponse.json();
const filename = genResult.data.filename;
// Step 2: 圧縮
const compressed = await compressPdf(filename, 'low');
return compressed.download_url;
}
generateAndCompress().then(url => console.log('最終URL:', url));
Python
import os
import requests
FUNBREW_API_KEY = os.environ["FUNBREW_PDF_API_KEY"]
BASE_URL = "https://pdf.funbrew.cloud/api/pdf"
def compress_pdf(filename: str, quality: str = "medium") -> dict:
"""FUNBREWに保存済みのPDFを圧縮してメタデータを返す。"""
response = requests.post(
f"{BASE_URL}/compress",
headers={"Authorization": f"Bearer {FUNBREW_API_KEY}"},
json={"filename": filename, "quality": quality},
timeout=60,
)
response.raise_for_status()
result = response.json()["data"]
print(f"元サイズ: {result['original_size'] / 1024:.1f} KB")
print(f"圧縮後: {result['compressed_size'] / 1024:.1f} KB")
print(f"削減率: {result['savings_percent']}%")
return result
def generate_and_compress(html: str, quality: str = "medium") -> str:
"""HTMLからPDFを生成して圧縮し、ダウンロードURLを返す。"""
# Step 1: PDF生成(filenameを返す)
gen_response = requests.post(
f"{BASE_URL}/generate-from-html",
headers={"Authorization": f"Bearer {FUNBREW_API_KEY}"},
json={
"html": html,
"engine": "quality",
"format": "A4",
"return_type": "filename",
},
timeout=60,
)
gen_response.raise_for_status()
filename = gen_response.json()["data"]["filename"]
# Step 2: 圧縮
result = compress_pdf(filename, quality)
return result["download_url"]
if __name__ == "__main__":
html = """
<html><body>
<h1>四半期レポート</h1>
<p>高解像度の画像と詳細なグラフを含むレポートです。</p>
</body></html>
"""
url = generate_and_compress(html, quality="low")
print(f"ダウンロードURL: {url}")
PHP
cURL(フレームワーク不問)
function compressPdf(string $filename, string $quality = 'medium'): array
{
$ch = curl_init('https://pdf.funbrew.cloud/api/pdf/compress');
curl_setopt_array($ch, [
CURLOPT_POST => true,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_HTTPHEADER => [
'Authorization: Bearer ' . getenv('FUNBREW_PDF_API_KEY'),
'Content-Type: application/json',
],
CURLOPT_POSTFIELDS => json_encode([
'filename' => $filename,
'quality' => $quality,
]),
]);
$body = curl_exec($ch);
$httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);
if ($httpCode !== 200) {
throw new RuntimeException("Compress API returned HTTP $httpCode: $body");
}
$result = json_decode($body, true)['data'];
printf(
"元サイズ: %.1f KB | 圧縮後: %.1f KB | 削減率: %s%%\n",
$result['original_size'] / 1024,
$result['compressed_size'] / 1024,
$result['savings_percent']
);
return $result;
}
// 使用例
$result = compressPdf('report-abc123.pdf', 'low');
echo $result['download_url'];
Laravel(Httpファサード)
use Illuminate\Support\Facades\Http;
$response = Http::withToken(config('services.funbrew.api_key'))
->post('https://pdf.funbrew.cloud/api/pdf/compress', [
'filename' => 'report-abc123.pdf',
'quality' => 'medium',
'expiration_hours' => 48,
'max_downloads' => 20,
]);
if ($response->successful()) {
$data = $response->json('data');
logger()->info('PDF圧縮完了', [
'savings_percent' => $data['savings_percent'],
'download_url' => $data['download_url'],
]);
}
生成 → 圧縮の2ステップパターン
圧縮エンドポイントが受け付けるのは、FUNBREWアカウントにすでに保存されているファイルのみです。PDF生成エンドポイントでreturn_type: "filename"を指定すると、生成されたPDFはサーバー上に保持されてファイル名がレスポンスに含まれます。そのファイル名を/api/pdf/compressにそのまま渡せます。
POST /api/pdf/generate-from-html → { filename: "gen-abc.pdf" }
POST /api/pdf/compress → { filename: "compressed-xyz.pdf", savings_percent: 68.3 }
このパターンが有効な場面:
- レポート生成パイプライン: 複雑なHTMLレポートをqualityエンジンで生成し、メール送信前に圧縮する。
- 証明書バッチ処理: 証明書を一括生成・圧縮してからPDFを結合する。詳細はPDF証明書自動化ガイドを参照。
- ストレージ効率化: S3やWasabiへのアーカイブ前に圧縮してストレージコストを削減する。
実践的なヒント
プリセットの選び方
- low(
/screen): 画像を72dpiに積極的にダウンサンプル。メール配信やプレビューなど、ファイルサイズ最優先の場面に最適。精細なグラフや小さな文字を含む文書には不向き。 - medium(
/ebook): 150dpiにダウンサンプル。WebからのPDFダウンロードやSaaSのドキュメントエクスポートに適した標準設定。 - high(
/printer): 300dpiにダウンサンプル。印刷用途や画像の鮮明さが重要な場合に使用する。
圧縮効果が低いケース
スキャン画像のみのPDFや、すでにGhostscriptで処理済みのPDFは、追加の圧縮効果がほとんど得られない場合があります。APIはこれを自動的に処理し、出力が元より大きくなる場合は元のコンテンツをそのまま返します(savings_percent: 0)。
200KB以下の小さなファイルに対して圧縮APIを呼び出しても効果が薄いため、直前のAPIレスポンスのファイルサイズを確認してから判断することをお勧めします。
有効期限とダウンロード制限
デフォルトでは24時間・最大10ダウンロードで期限切れになります。バッチパイプラインでファイルを即時ダウンロードまたは外部ストレージへ転送する場合はこのデフォルトで問題ありません。メールでリンクを送る場合など、長期間有効なリンクが必要な場合はexpiration_hoursを最大168(7日間)に設定してください。
次のステップ
- APIリファレンス — 圧縮エンドポイント: 全パラメータの詳細仕様
- Playground: PDF生成とダウンロードリンクをブラウザで事前確認
- PDFマージAPIガイド: 圧縮後のPDFを1ファイルに結合
- PDF APIバッチ処理ガイド: 並行処理を使った大量ファイルの処理
- PDF証明書自動化ガイド: 証明書の一括生成と圧縮
関連リンク
- PDF APIクイックスタート: Node.js・Python・PHP — 最初のAPIコールを5分以内に
- PDFマージAPIガイド — 複数のPDFを1ファイルに統合
- ユースケース一覧 — 実際のPDF自動化パターン