mcpField
C
cloudflare-images

cloudflare-images

github.com/jezwebクラウド・DevOps1.1k328 回インストール3 週間前に更新
リポジトリ

cloudflare-images について

Cloudflare Images を利用する開発者向けに、画像のアップロード、保存、変換を解説するガイドです。アップロード方法、バリアント、署名付き URL、Workers での変換、問題の切り分けを扱います。

主な機能

  1. 01ファイル、URL、直接アップロード
  2. 02名前付き・柔軟なバリアント
  3. 03非公開画像向け署名付き URL
  4. 04URL と Workers による変換
  5. 05トリミング、形式、品質の設定

活用シーン

  1. 01ウェブサイト向け画像のアップロードと配信
  2. 02サムネイルやリサイズ画像の生成
  3. 03署名付き URL による非公開画像の配信

インストール

コマンドをコピーしてターミナルで実行します。

$npx skills add https://github.com/jezweb/claude-skills --skill cloudflare-images

インストール後、Claude Code で/cloudflare-imagesを入力して読み込まれたか確認します。

同梱ファイル

SKILL.md と一緒にインストールされる参考資料やスクリプト。

README.md
.claude-plugin/
plugin.json
references/
api-reference.md
direct-upload-complete-workflow.md
format-optimization.md
responsive-images-patterns.md
signed-urls-guide.md
top-errors.md
transformation-options.md
variants-guide.md
rules/
cloudflare-images.md
scripts/
check-versions.sh
templates/
batch-upload.ts
direct-creator-upload-backend.ts
direct-creator-upload-frontend.html
package.json
responsive-images-srcset.html
signed-urls-generation.ts
transform-via-url.ts
transform-via-workers.ts
upload-api-basic.ts
upload-via-url.ts
variants-management.ts

詳細

Cloudflare Images

ステータス:本番環境対応済み ✅ 最終更新日:2026-01-21 依存関係:Images が有効になっている Cloudflare アカウント 最新バージョン:Cloudflare Images API v2、@cloudflare/[email protected]

最近の更新(2025年):

  • 2025年2月:Content Credentials に対応(C2PA 標準)。画像の来歴チェーンを保持し、変換時に自動で暗号署名を付与します
  • 2025年8月:AI Face Cropping が GA(zoom 制御に対応した gravity=face、GPU ベースの RetinaFace、精度 99.4%)
  • 2025年5月:Media Transformations のオリジン制限(デフォルトは同一ドメインのみ。ダッシュボードから設定可能)
  • 近日提供予定:背景削除、生成アップスケール(計画中の機能)

廃止のお知らせ:Mirage は 2025年9月15日に廃止されました。ストレージや変換には Cloudflare Images に移行するか、遅延読み込みにはネイティブの <img loading="lazy"> を使用してください。


概要

2 つの機能があります。Images API(バリアントを使ったアップロード/保存)と Image Transformations(URL または Workers を使った画像のリサイズ)です。


クイックスタート

1. 有効化:ダッシュボード → Images → アカウント ID と API トークンを取得(Cloudflare Images:Edit 権限)

2. アップロード:

curl -X POST https://api.cloudflare.com/client/v4/accounts/<ACCOUNT_ID>/images/v1 \
  -H 'Authorization: Bearer <API_TOKEN>' \
  -H 'Content-Type: multipart/form-data' \
  -F 'file=@./image.jpg'

3. 配信:https://imagedelivery.net/<ACCOUNT_HASH>/<IMAGE_ID>/public

4. 変換(任意):ダッシュボード → Images → Transformations → ゾーンで有効化

<img src="/cdn-cgi/image/width=800,quality=85/uploads/photo.jpg" />

アップロード方法

1. ファイルアップロード:file(multipart/form-data)を使って /images/v1 に POST します。id、requireSignedURLs、metadata は任意です

2. URL 経由でアップロード:url=https://example.com/image.jpg を指定して POST します(HTTP ベーシック認証に対応)

3. Direct Creator Upload(API キーを公開しないワンタイム URL):

バックエンド:/images/v2/direct_upload に POST → uploadURL を返します フロントエンド:FormData を使ってファイルを uploadURL に POST します

重要な CORS 対策:

  • ✅ multipart/form-data を使用します(ヘッダーはブラウザーに設定させます)
  • ✅ フィールド名には file を指定します(image は不可)
  • ✅ /direct_upload の呼び出しはバックエンドからのみ行います
  • ❌ Content-Type: application/json を設定しないでください
  • ❌ /direct_upload をブラウザーから呼び出さないでください

画像変換

URL:/cdn-cgi/image/<OPTIONS>/<SOURCE>

  • サイズ調整:width=800,height=600,fit=cover
  • 品質:quality=85(1~100)
  • 形式:format=auto(WebP/AVIF を自動検出)
  • トリミング:gravity=auto(スマートトリミング)、gravity=face(AI 顔検出、2025年8月に GA)、gravity=center、zoom=0.5(範囲は 0~1、顔トリミングの寄り具合)
  • 効果:blur=10,sharpen=3,brightness=1.2
  • フィット:scale-down、contain、cover、crop、pad

Workers:fetch で cf.image オブジェクトを使用します

fetch(imageURL, {
  cf: {
    image: { width: 800, quality: 85, format: 'auto', gravity: 'face', zoom: 0.8 }
  }
});

バリアント

名前付きバリアント(最大 100 個):事前定義された変換(例:avatar、thumbnail)

  • 作成:id と options を指定して /images/v1/variants に POST します
  • 使用:imagedelivery.net/<HASH>/<ID>/avatar
  • 署名付き URL で使用できます

柔軟なバリアント:URL 内の動的パラメーター(w=400,sharpen=3)

  • 有効化:{"flexible_variants": true} を指定して /images/v1/config に PATCH します
  • ❌ 署名付き URL では使用できません(代わりに名前付きバリアントを使用してください)

署名付き URL

非公開画像用の HMAC-SHA256 トークンを生成します(URL 形式:?exp=<TIMESTAMP>&sig=<HMAC>)。

アルゴリズム:HMAC-SHA256(signingKey, imageId + variant + expiry) → 16 進数の署名

参照:Workers の実装については templates/signed-urls-generation.ts を参照してください


重要なルール

必ず行うこと

✅ Direct Creator Upload には multipart/form-data を使用します ✅ ファイルフィールド名には file を指定します(image など、他の名前は使用しません) ✅ /direct_upload API はバックエンドからのみ呼び出します(ブラウザーからは呼び出しません) ✅ 変換には HTTPS URL を使用します(HTTP はサポートされていません) ✅ 画像パス内の特殊文字を URL エンコードします ✅ /cdn-cgi/image/ を使用する前に、ゾーンで変換を有効にします ✅ 非公開画像(署名付き URL)には名前付きバリアントを使用します ✅ 変換エラーがないか Cf-Resized ヘッダーを確認します ✅ WebP/AVIF への自動変換には format=auto を設定します ✅ 不要な拡大を防ぐには fit=scale-down を使用します

絶対にしないこと

❌ ファイルのアップロードに application/json の Content-Type を使用する ❌ ブラウザーから /direct_upload を呼び出す(CORS エラーが発生します) ❌ requireSignedURLs=true で柔軟なバリアントを使用する ❌ SVG ファイルのサイズを変更する(本質的に拡大縮小可能です) ❌ 変換に HTTP URL を使用する(HTTPS のみ) ❌ URL にスペースやエスケープされていない Unicode を含める ❌ Workers で同じ画像を複数回変換する(9403 ループが発生します) ❌ 画像サイズが 100 メガピクセルを超える ❌ Workers で /cdn-cgi/image/ エンドポイントを使用する(代わりに cf.image を使用してください) ❌ 使用前にゾーンで変換を有効にし忘れる


既知の問題の予防

このスキルは、文書化されている 16 件の問題を防ぎます。

問題 #1:Direct Creator Upload の CORS エラー

エラー:Access to XMLHttpRequest blocked by CORS policy: Request header field content-type is not allowed

情報源:Cloudflare Community #345739、#368114

発生する理由:サーバーの CORS 設定では、Content-Type ヘッダーに multipart/form-data のみが許可されています

予防策:

// ✅ CORRECT
const formData = new FormData();
formData.append('file', fileInput.files[0]);
await fetch(uploadURL, {
  method: 'POST',
  body: formData // Browser sets multipart/form-data automatically
});

// ❌ WRONG
await fetch(uploadURL, {
  method: 'POST',
  headers: { 'Content-Type': 'application/json' }, // CORS error
  body: JSON.stringify({ file: base64Image })
});
問題 #2:エラー 5408 - アップロードのタイムアウト

エラー:アップロード開始から約 15 秒後に Error 5408

情報源:Cloudflare Community #571336

発生する理由:Cloudflare のリクエストタイムアウトは 30 秒です。アップロードが遅い場合やファイルが大きい場合、制限を超過します

予防策:

  • アップロード前に画像を圧縮します(Canvas API を使用したクライアント側処理)
  • 適切なファイルサイズ制限を設定します(例:最大 10MB)
  • ユーザーにアップロードの進行状況を表示します
  • タイムアウトエラーを適切に処理します
const MAX_FILE_SIZE = 10 * 1024 * 1024; // 10MB

if (file.size > MAX_FILE_SIZE) {
  alert('File too large. Please select an image under 10MB.');
  return;
}
問題 #3:エラー 400 - 無効なファイルパラメーター

エラー:わかりにくいエラーメッセージを伴う 400 Bad Request

情報源:Cloudflare Community #487629

発生する理由:ファイルフィールドの名前は file にする必要があります(image、photo などは使用できません)

予防策:

// ✅ CORRECT
formData.append('file', imageFile);

// ❌ WRONG
formData.append('image', imageFile); // 400 error
formData.append('photo', imageFile); // 400 error
問題 #4:CORS プリフライトの失敗

エラー:プリフライトの OPTIONS リクエストがブロックされる

情報源:Cloudflare Community #306805

発生する理由:ブラウザーから /direct_upload API を直接呼び出している(バックエンドからのみ呼び出す必要があります)

予防策:

ARCHITECTURE:
Browser → Backend API → POST /direct_upload → Returns uploadURL → Browser uploads to uploadURL

API トークンをブラウザーに公開しないでください。バックエンドでアップロード URL を生成し、フロントエンドに返します。

問題 #5:エラー 9401 - 無効な引数

エラー:Cf-Resized: err=9401 - 必須の cf.image オプションがない、または無効です

情報源:Cloudflare Images Docs - Troubleshooting

発生する理由:必須の変換パラメーターがない、または値が無効です

予防策:

// ✅ CORRECT
fetch(imageURL, {
  cf: {
    image: {
      width: 800,
      quality: 85,
      format: 'auto'
    }
  }
});

// ❌ WRONG
fetch(imageURL, {
  cf: {
    image: {
      width: 'large', // Must be number
      quality: 150 // Max 100
    }
  }
});
問題 #6:エラー 9402 - 画像が大きすぎる

エラー:Cf-Resized: err=9402 - 画像が大きすぎるか、接続が中断されました

情報源:Cloudflare Images Docs - Troubleshooting

発生する理由:画像が最大面積(100 メガピクセル)を超えている、またはダウンロードに失敗しています

予防策:

  • 変換前に画像の寸法を検証します
  • 適切なサイズの元画像を使用します(最大 10000x10000px)
  • ネットワークエラーを適切に処理します
問題 #7:エラー 9403 - リクエストループ

エラー:Cf-Resized: err=9403 - Worker が自身の URL またはすでにサイズ変更された画像を取得しています

情報源:Cloudflare Images Docs - Troubleshooting

発生する理由:すでに変換された画像に変換が適用されている、または Worker が自身を取得しています

予防策:

// ✅ CORRECT
if (url.pathname.startsWith('/images/')) {
  const originalPath = url.pathname.replace('/images/', '');
  const originURL = `https://storage.example.com/${originalPath}`;
  return fetch(originURL, { cf: { image: { width: 800 } } });
}

// ❌ WRONG
if (url.pathname.startsWith('/images/')) {
  // Fetches worker's own URL, causes loop
  return fetch(request, { cf: { image: { width: 800 } } });
}
Issue #8: Error 9406/9419 - 無効な URL 形式

エラー: Cf-Resized: err=9406 または err=9419 - HTTPS 以外の URL、またはスペース/エスケープされていない Unicode を含む URL

出典: Cloudflare Images Docs - トラブルシューティング

発生する理由: 画像 URL が HTTP(HTTPS ではない)を使用しているか、無効な文字を含んでいます

予防策:

// ✅ CORRECT
const imageURL = "https://example.com/images/photo%20name.jpg";

// ❌ WRONG
const imageURL = "http://example.com/images/photo.jpg"; // HTTP not allowed
const imageURL = "https://example.com/images/photo name.jpg"; // Space not encoded

URL パスには必ず encodeURIComponent() を使用してください:

const filename = "photo name.jpg";
const imageURL = `https://example.com/images/${encodeURIComponent(filename)}`;
Issue #9: Error 9412 - 画像以外のレスポンス

エラー: Cf-Resized: err=9412 - オリジンサーバーが画像ではなく HTML を返しました

出典: Cloudflare Images Docs - トラブルシューティング

発生する理由: オリジンサーバーが画像ではなく、404 ページやエラーページ(HTML)を返しています

予防策:

// Verify URL before transforming
const originResponse = await fetch(imageURL, { method: 'HEAD' });
const contentType = originResponse.headers.get('content-type');

if (!contentType?.startsWith('image/')) {
  return new Response('Not an image', { status: 400 });
}

return fetch(imageURL, { cf: { image: { width: 800 } } });
Issue #10: Error 9413 - 画像の最大面積超過

エラー: Cf-Resized: err=9413 - 画像が 100 メガピクセルを超えています

出典: Cloudflare Images Docs - トラブルシューティング

発生する理由: 元画像の寸法が 100 メガピクセルを超えています(例:10000x10000px)

予防策:

  • アップロード前に画像の寸法を検証する
  • 大きすぎる画像を事前に処理する
  • しきい値を超える画像を拒否する
const MAX_MEGAPIXELS = 100;

if (width * height > MAX_MEGAPIXELS * 1_000_000) {
  return new Response('Image too large', { status: 413 });
}
Issue #11: Flexible Variants と Signed URLs の非互換性

エラー: Flexible Variants はプライベート画像では機能しません

出典: Cloudflare Images Docs - Enable flexible variants

発生する理由: requireSignedURLs=true の場合、Flexible Variants は使用できません

予防策:

// ✅ CORRECT - Use named variants for private images
await uploadImage({
  file: imageFile,
  requireSignedURLs: true // Use named variants: /public, /avatar, etc.
});

// ❌ WRONG - Flexible variants don't support signed URLs
// Cannot use: /w=400,sharpen=3 with requireSignedURLs=true
Issue #12: SVG のリサイズ制限

エラー: SVG ファイルは変換によってリサイズできません

出典: Cloudflare Images Docs - SVG files

発生する理由: SVG は本質的に拡大縮小可能なベクター形式であり、リサイズは適用できません

予防策:

// SVGs can be served but not resized
// Use any variant name as placeholder
// https://imagedelivery.net/<HASH>/<SVG_ID>/public

// SVG will be served at original size regardless of variant settings
Issue #13: 形式によって EXIF メタデータが削除される

エラー: アップロードした画像から GPS データやカメラ設定が削除されます

出典: Cloudflare Images Docs - Transform via URL

発生する理由: デフォルトでは、著作権情報を除くすべてのメタデータが削除されます。重要: WebP と PNG の出力形式では、設定にかかわらずメタデータが必ず破棄されます。メタデータの保持をサポートしているのは JPEG のみです。

予防策:

// ✅ CORRECT - JPEG preserves metadata
fetch(imageURL, {
  cf: {
    image: {
      width: 800,
      format: 'jpeg', // or 'auto' (may become jpeg)
      metadata: 'keep' // Preserves most EXIF including GPS
    }
  }
});

// ❌ WRONG - WebP/PNG ignore metadata setting
fetch(imageURL, {
  cf: {
    image: {
      format: 'webp',
      metadata: 'keep' // NO EFFECT - always stripped for WebP/PNG
    }
  }
});

メタデータのオプション(JPEG のみ):

  • none:すべてのメタデータを削除する
  • copyright:著作権タグのみを保持する(JPEG のデフォルト)
  • keep:GPS を含む EXIF メタデータの大部分を保持する

形式のサポート:

  • ✅ JPEG:すべてのメタデータオプションが機能します
  • ❌ WebP:メタデータを常に削除します(none と同じ動作)
  • ❌ PNG:メタデータを常に削除します(none と同じ動作)
Issue #14: AVIF の解像度上限に関する不明確さ

エラー: AVIF の大きな画像変換が失敗するか、低い解像度に劣化します

出典: Cloudflare Docs + コミュニティからの報告

発生する理由: 公式ドキュメントでは format=avif の上限を 1,600px としていますが、コミュニティからは 2024 年後半時点で実際には最長辺の上限が 1200px であるという報告があります。注:公式ドキュメント(1600px)と報告された動作(1200px)に食い違いがあり、検証が必要です。

予防策:

// ✅ RECOMMENDED - Use format=auto instead of explicit avif
fetch(imageURL, {
  cf: {
    image: {
      width: 2000,
      format: 'auto' // Cloudflare chooses best format
    }
  }
});

// ⚠️ MAY FAIL - Explicit AVIF with large dimensions
fetch(imageURL, {
  cf: {
    image: {
      width: 2000,
      format: 'avif' // May fail if >1200px
    }
  }
});

// ✅ WORKAROUND - Use WebP for larger images
if (width > 1200) {
  format = 'webp'; // WebP supports larger dimensions
} else {
  format = 'avif'; // AVIF for smaller images
}
Issue #15:デバイスタイプ別の画像キャッシュ(コミュニティからの報告)

エラー:デスクトップとモバイルで異なるキャッシュ済みバージョンが表示され、予期しないキャッシュミスが発生します

出典:Cloudflare Community

発生する理由:キャッシュルールでこの動作を無効にする設定がないにもかかわらず、画像が予期せずデバイスタイプ別にキャッシュされます。複数のユーザーが、2024年12月時点でこの動作を確認しています。

予防策:

  • キャッシュのパージには、デバイスタイプごとのパージが必要であることを理解する
  • 必要に応じて、Cloudflare ダッシュボードからデバイスタイプごとに手動でキャッシュをパージする
  • キャッシュ無効化の戦略に、デバイス固有のキャッシュを考慮する

解決策/回避策: 必要に応じて、Cloudflare ダッシュボードからデバイスタイプごとに手動でキャッシュをパージします。

Issue #16:PNG はデフォルトでキャッシュされない

エラー:ほかの画像形式は機能するのに、PNG 画像がキャッシュされません

出典:Cloudflare Community

発生する理由:Cloudflare がデフォルトでキャッシュするファイル拡張子に .png は含まれていません。デフォルトでキャッシュされる拡張子は .jpg、.jpeg、.gif、.webp、.bmp、.ico、.svg、.tif、.tiff です(PNG は含まれていません)。

予防策: PNG ファイル用の明示的なキャッシュルールを作成します。

  1. ダッシュボード → Caching → Cache Rules
  2. ルールを追加:URI Path ends with .png → Cache Everything

バンドルされたリソースの使用

テンプレート(templates/)

よく使われるパターン向けの、コピーしてすぐ使えるコードです。

  1. wrangler-images-binding.jsonc - Wrangler の設定(バインディングは不要)
  2. upload-api-basic.ts - Images API へのファイルのアップロード
  3. upload-via-url.ts - 外部 URL からの画像の取り込み
  4. direct-creator-upload-backend.ts - 1 回限りのアップロード URL の生成
  5. direct-creator-upload-frontend.html - ユーザー向けアップロードフォーム
  6. transform-via-url.ts - URL 変換の例
  7. transform-via-workers.ts - Workers での変換パターン
  8. variants-management.ts - バリアントの作成/一覧表示/削除
  9. signed-urls-generation.ts - HMAC-SHA256 署名付き URL の生成
  10. responsive-images-srcset.html - レスポンシブ画像のパターン
  11. batch-upload.ts - 大量アップロード向けのバッチ API

使用方法:

cp templates/upload-api-basic.ts src/upload.ts
# Edit with your account ID and API token
リファレンス(references/)

必要に応じて Claude が読み込める詳細なドキュメントです。

  1. api-reference.md - API エンドポイントの全一覧(アップロード、一覧表示、削除、バリアント)
  2. transformation-options.md - 変換パラメーターのすべてと例
  3. variants-guide.md - 名前付きバリアントと柔軟なバリアント、それぞれの使いどころ
  4. signed-urls-guide.md - HMAC-SHA256 の実装の詳細
  5. direct-upload-complete-workflow.md - アーキテクチャとフローの全体
  6. responsive-images-patterns.md - srcset、sizes、アートディレクション
  7. format-optimization.md - WebP/AVIF への自動変換戦略
  8. top-errors.md - 13 件以上のエラーと詳細なトラブルシューティング

読み込むタイミング:

  • 特定の機能を詳しく調べるとき
  • 複雑な問題のトラブルシューティングを行うとき
  • API の詳細を理解するとき
  • 高度なパターンを実装するとき
スクリプト(scripts/)

check-versions.sh - API エンドポイントが最新か確認します


高度なトピック

カスタムドメイン:/cdn-cgi/imagedelivery/<HASH>/<ID>/<VARIANT> を使用して、自分のドメインから配信できます(Cloudflare 上でドメインがプロキシされている必要があります)。カスタムパスには Transform Rules を使用します。

Batch API:バッチトークンを使用して、batch.imagedelivery.net 経由で大量のアップロードを行えます(Dashboard → Images → Batch API)。

Webhooks:Direct Creator Upload の通知を設定できます(Dashboard → Notifications → Webhooks)。ペイロードには imageId、status、metadata が含まれます。

Content Credentials(C2PA):Cloudflare Images は画像のプロベナンスチェーンを保持し、署名します。Content Credentials を含む画像を変換する場合、Cloudflare は変換内容をマニフェストに自動で追加し、DigiCert の証明書を使用して暗号学的に署名します。Dashboard → Images → Transformations → Preserve Content Credentials から有効にできます。注:ソース画像に C2PA メタデータがすでに含まれている場合にのみ機能します(一部のカメラ、DALL-E、対応する編集ソフトウェアなど)。contentcredentials.org/verify で確認できます。

ブラウザーキャッシュ TTL:ブラウザーキャッシュ TTL のデフォルトは 2 日(172,800 秒)です。1 時間から 1 年までカスタマイズできます(アカウント単位またはバリアント単位)。重要:プライベート画像(署名付き URL)では TTL 設定は適用されません。同じ Custom ID を使って画像を再アップロードすると問題が発生し、ユーザーには最大 2 日間、古いバージョンが表示されることがあります。解決策:一意の画像 ID を使用する(タイムスタンプやハッシュを追加する)か、再アップロード後にキャッシュを手動でパージします。

製品統合に伴う移行(2023 年 11 月):Cloudflare は Image Resizing を Images 製品に統合し、新しい料金体系を導入しました。月間の一意な変換 1,000 件につき $0.50 です(一意な変換ごとに 30 日に 1 回課金)。移行時の注意点:従来の Image Resizing はキャッシュされていないリクエスト数に基づいて課金されていました(キャッシュ動作の変動により、コストが予測しにくくなります)。新しい課金方式では、リクエスト数ではなく「一意な変換」(画像 ID とパラメーターの組み合わせ)ごとに課金されます。同じ変換を月に 1,000 回リクエストしても、課金は 1 回です。既存の顧客は従来版を引き続き使用することも、任意で移行することもできます。

コスト最適化のための R2 連携:Cloudflare Images は R2 と Image Resizing を基盤としています。コストを抑えるには、元画像を R2 に保存し、Image Transformations をオンデマンドで使用します。

  1. 画像を R2 バケットにアップロードします
  2. カスタムドメインと /cdn-cgi/image/ 変換を使用して配信します
  3. バリアントは保存されません(変換は一時的に生成され、キャッシュされます)

コスト比較:

  • R2:10GB のストレージと無制限の帯域幅(無料枠)
  • Cloudflare Images:月額 $5(画像 100,000 枚)+ 変換 100,000 件につき $1
  • R2 + Transformations:R2 のストレージ料金 + 一意な変換 1,000 件につき $0.50

ユースケース:名前付きバリアント、バッチアップロード、Direct Creator Upload 機能が不要な場合は、R2 のほうが費用対効果に優れています。

R2 を使用する Workers の実装パターン例:

export default {
  async fetch(request, env) {
    const url = new URL(request.url);
    const imageKey = url.pathname.replace('/images/', '');
    const originURL = `https://r2-bucket.example.com/${imageKey}`;

    return fetch(originURL, {
      cf: {
        image: {
          width: 800,
          quality: 85,
          format: 'auto'
        }
      }
    });
  }
};

参考:Cloudflare Reference Architecture


トラブルシューティング

問題:画像が変換されない

症状:/cdn-cgi/image/... が元画像を返すか、404 を返します

解決策:

  1. ゾーンで変換を有効にします:Dashboard → Images → Transformations → Enable for zone
  2. ゾーンが Cloudflare 経由でプロキシされていることを確認します(オレンジ色の雲)
  3. ソース画像に公開アクセスできることを確認します
  4. 設定が反映されるまで 5~10 分待ちます
問題:直接アップロードで CORS エラーが返される

症状:ブラウザーコンソールに Access-Control-Allow-Origin エラーが表示されます

解決策:

  1. multipart/form-data エンコーディングを使用します(ブラウザーに Content-Type を設定させます)
  2. ブラウザーから /direct_upload を呼び出さず、バックエンドから呼び出します
  3. ファイルフィールドには file と名前を付けます(image ではありません)
  4. Content-Type ヘッダーを手動で設定しないでください
問題:Worker の変換で 9403 ループエラーが返される

症状:レスポンスヘッダーに Cf-Resized: err=9403 が表示されます

解決策:

  1. Worker 自身の URL をフェッチしないでください(外部オリジンを使用します)
  2. すでにリサイズされた画像を変換しないでください
  3. ループを避けるため、URL のルーティングロジックを確認します
問題:署名付き URL が機能しない

症状:署名付き URL へのアクセス時に 403 Forbidden が発生する

解決策:

  1. requireSignedURLs=true を指定して画像をアップロードしたことを確認します
  2. 署名の生成方法(HMAC-SHA256)を確認します
  3. 有効期限のタイムスタンプが未来の時刻であることを確認します
  4. 署名キーがダッシュボード(Images → Keys)のものと一致することを確認します
  5. 署名付き URL ではフレキシブルバリアントを使用できません(名前付きバリアントを使用してください)
問題:画像はアップロードされたが、表示されない

症状:アップロードは 200 OK を返すが、画像がダッシュボードに表示されない

解決策:

  1. レスポンスに draft: true が含まれていないか確認します(Direct Creator Upload)
  2. アップロードの完了を待ちます(GET /images/v1/{id} で確認します)
  3. アカウント ID が一致することを確認します
  4. Webhook にアップロードエラーがないか確認します
問題:画像を再アップロードしても古いバージョンが表示される

症状:ページに一度もアクセスしたことがないユーザーにも、再アップロード後に古い画像が表示される

解決策:

  1. アップロードごとに一意の画像 ID を使用します:const imageId = \${baseId}-${Date.now()}`;`
  2. Cache-Control ヘッダーの有効期間を短くします(例:30 日ではなく、1 日の max-age=86400 を指定します)
  3. 同じ ID で再アップロードした後、ダッシュボードから手動でキャッシュをパージします
  4. デフォルトの Browser Cache TTL は 2 日です。ユーザーにキャッシュ済みのバージョンが表示される場合があります

根本原因:Cloudflare はオリジンの Cache-Control ヘッダーに従います。オリジンが長い max-age(例:30 日)を設定すると、同じ ID で再アップロードした後も画像がキャッシュに残ります。

問題:PNG 画像がキャッシュされない

症状:他の形式(JPEG、WebP)は正しくキャッシュされるが、PNG 画像はキャッシュを通過しない

解決策:

  1. 明示的なキャッシュルールを作成します:ダッシュボード → Caching → Cache Rules
  2. ルールを追加します:URI Path ends with .png → Cache Everything
  3. デフォルトのキャッシュ対象拡張子に .png は含まれていません(.jpg、.jpeg、.gif、.webp、.bmp、.ico、.svg、.tif、.tiff のみ)

公式ドキュメント


パッケージのバージョン

最終確認日:2026-01-21 API バージョン:v2(直接アップロード)、v1(標準アップロード) オプション:@cloudflare/[email protected]


スキルのバージョン:2.1.0 | 変更点:新たに 3 つの問題(AVIF の制限、デバイス別キャッシュ、PNG のキャッシュ)を追加し、メタデータの問題に形式の詳細を追加。Content Credentials、Browser Cache TTL、Product Merge に関する注意事項、R2 統合パターン、Mirage の非推奨に関する通知、キャッシュのトラブルシューティングガイダンスを追加。エラー数:13 → 16。

コメント