本文へスキップ
エラーとクラッシュ

WordPress の画像アップロードで「HTTP エラー」: 原因を本当に突き止める分岐表

WordPress の画像アップロードで出る HTTP エラーの原因を、たった 1 つの確認で切り分ける。ファイアウォール、PHP メモリ、post_max_size、Imagick のどれかを正しく直す手順。

公開

「HTTP エラー」は原因ではありません。メディアアップローダーが「ファイルは送ったが、返ってきたレスポンスを成功として解釈できなかった」と白状しているだけで、まったく無関係な 6 種類以上の失敗が、この同じ文言になります。この区別を当てずっぽうでやるから、本当の原因はファイアウォールのルールなのに upload_max_filesize の値をいじって午後をまるごと溶かす、ということが起きます。

最短ルートは、6 つの原因を 2 つのグループに割るたった 1 つの観察と、そのあと分岐ごとに 1 回ずつの確認です。

まず: 実際のレスポンスを見る

ブラウザーの開発者ツールを開き、ネットワークタブに切り替えて、もう一度ファイルをアップロードします。async-upload.php へのリクエストに注目してください。返ってきたものが、そのまま診断結果です。

見えるもの意味進む先
403 または 406、本文が HTMLファイアウォールか mod_security が拒否した分岐 A
500、空のレスポンス、または途中で切れた本文処理の途中で PHP が停止したかメモリ切れ分岐 B
413リクエスト本文がサーバーの上限を超えた分岐 C
200 だが本文が正しい JSON でないプラグインかテーマがレスポンスより前に出力した分岐 D
リクエストが完了しない・タイムアウトする実行時間の上限。大きいファイルで起きやすい分岐 B

この 1 回の確認だけで、ネット上のアドバイスの大半はふるい落とせます。開発者ツールが使えない場合は、先に wp-config.php でログを有効にしてください。

define( 'WP_DEBUG', true );
define( 'WP_DEBUG_LOG', true );
define( 'WP_DEBUG_DISPLAY', false );

アップロードを再現してから wp-content/debug.log を読みます。致命的エラーの行が、どの分岐かをそのまま教えてくれます。行の内容が難しければ エラーログ解読ツール に貼り付けてください。よくある致命的エラーの型と、実際に何が壊れたのかを対応付けてくれます。

分岐 A — ファイアウォールや mod_security のルール

本文に HTML ページが入った 403 は、リクエストがそもそも WordPress まで届いていないという意味です。その手前にいる何か(mod_security、Cloudflare、Wordfence、Sucuri、あるいはホスティング独自のルールセット)が、その POST を怪しいと判断しています。

確認方法は、セキュリティ系プラグインを一時的に無効化して、もう一度アップロードすること。それで何も変わらなければ、ルールはサーバー側にあります。失敗したアップロードの時刻を伝えて、ホスティングに mod_security の監査ログを見てもらってください。該当するルール ID をホワイトリストに入れてもらえます。

ここで見つかるアドバイスについては、正直になっておきましょう。.htaccess にこれを貼れという断片が出回っています。

SecFilterEngine Off
SecFilterScanPOST Off

これは mod_security 1.x 向けで、ほぼ絶滅しています。現代のサーバーでは、これらのディレクティブは何もしないか、500 を出してサイトをさらに悪化させるかのどちらかです。今の mod_security が使うのは SecRuleEngine で、そもそも多くのマネージドホスティングはディレクトリー単位での上書きを禁止しています。貼り付けるのではなく、ホスティングに聞いてください。

分岐 B — PHP のメモリや実行時間の上限

最も多い分岐であり、手掛かりが最もはっきりしている分岐でもあります。症状が断続的であること です。同じファイルが 3 回目で通る、2MB の写真が失敗するのに 6MB の PDF は素通りする、といった具合です。設定値としての固定上限なら、毎回まったく同じように失敗します。メモリ不足はそうなりません。使える量が、そのときサーバーが他に何をしているかで変わるからです。

画像で特に起きやすい理由はこうです。WordPress はファイルを保存するだけでなく、中間サイズを生成するために画像を生のピクセルへ展開します。medium_largeadd_image_size で登録されたサイズ、ショップを運営していれば woocommerce_thumbnail、さらに画像が big_image_size_threshold を超えていれば -scaled のコピーも作られます。1200 万画素の JPEG はディスク上では数 MB でも、メモリ上ではおよそ 48MB です。しかもこれはリサイズ用のバッファーを数える前の話です。128MB の上限はあっという間に消えます。

wp-config.php の「編集を終わり」の行より上で引き上げます。

define( 'WP_MEMORY_LIMIT', '256M' );
define( 'WP_MAX_MEMORY_LIMIT', '512M' );

現実的な制約もあります。WP_MEMORY_LIMIT は、PHP 自体が許している値を超えられません。ホスティングが memory_limit を 128M で固定していれば、この定数は飾りです。自分が書いた値ではなく、ツール → サイトヘルス → 情報 → サーバー で実際の値を確認してください。PHP 側の上限が天井になっているなら、動かせるのはホスティングだけです。

分岐 C — ファイルサイズと POST の上限

実際の数値は ツール → サイトヘルス → 情報 → メディアの取り扱い で確認できます。関係する設定は 2 つですが、たいていの人は片方しか変えません。

  • upload_max_filesize — ファイル 1 個あたりの上限。
  • post_max_size — リクエスト本文 全体 の上限。

POST 全体が post_max_size を超えると、PHP は WordPress のコードが動く前にリクエストを破棄します。返すものが存在しないので、アップローダーは解釈できないレスポンスを受け取って「HTTP エラー」と言います。post_max_size は常に upload_max_filesize より十分大きくしておくべきです。

知っておく価値のある補足があります。upload_max_filesize だけを超えた場合、たいていはブラウザー側でアップローダーが検知し、「最大アップロードサイズを超えています」というもっと明確なメッセージを出します。つまり、素の「HTTP エラー」が指しているのは、みんなが真っ先に上げるあの設定よりも、post_max_size か分岐 B であることのほうが多いのです。

変更場所は環境によります。Apache と mod_php の組み合わせなら .htaccess が効きます。

php_value upload_max_filesize 64M
php_value post_max_size 128M

PHP-FPM、LiteSpeed、NGINX の場合(今どきのホスティングはほぼこれです)、この行は何もしないか、500 を返します。代わりにホスティングの PHP 設定画面か .user.ini を使ってください。NGINX には独自の client_max_body_size もあり、これを上げられるのはホスティングだけです。

分岐 D — 画像処理ライブラリ(Imagick と GD)

WordPress は ImageMagick の PHP 拡張があればそちらを優先し、なければ GD に切り替えます。共有サーバーでは ImageMagick が問題になることがよくあります。ポリシー設定ファイルが処理ごとのメモリ・ディスク・面積を制限していて、リサイズがそのどれかに引っかかるとプロセスは有用なメッセージを残さず死にます。大きい画像でだけ起き、小さい画像は通る、という形で現れることが多く、これは分岐 B に見えますが違います。

仮説を試すには GD を強制します。

add_filter( 'wp_image_editors', function ( $editors ) {
    return array( 'WP_Image_Editor_GD' );
} );

これを functions.php か小さな mu-plugin に置いてアップロードを再試行し、何も変わらなければ削除してください。

正直なトレードオフも書いておきます。GD が単純に優れているわけではありません。GD は展開後のビットマップをまるごと PHP のメモリ上に保持するため、非常に大きなファイルでは memory_limit に当たります。PHP の割り当ての外側でも動く ImageMagick なら通っていたはずの処理が、そこで落ちるわけです。切り替えは失敗の種類を入れ替えるだけになることもあります。まずは診断手段として使い、解決策と見なすのはその次にしてください。

分岐 E — uploads ディレクトリーのパーミッション

マネージドホスティングではまれですが、サーバー移行や手動での引っ越しの直後にはよく起きます。wp-content/uploads に Web サーバーのユーザーが書き込めない、あるいは新しく作られた年月のサブフォルダーが誤った所有者を引き継いだ場合、書き込みが失敗します。

ls -ld wp-content/uploads
ls -ld wp-content/uploads/2026/07

ディレクトリーは通常 755 で、PHP が動いているユーザーの所有であるべきです。掲示板に書いてあったからといって 777 にしてはいけません。それはサーバー上のすべてのアカウントから書き込める状態にして症状を消しているだけで、共有サーバーでは本物のリスクになります。

分岐 F — ファイル名

一覧の中で最も安上がりな確認なので、可能性は最も低くても早めにやってしまいましょう。ファイル名を半角英小文字と数字とハイフンだけに変えて(アクセント記号、アポストロフィ、アンパサンド、#、非ラテン文字は使わない)、もう一度アップロードします。特殊文字がセキュリティルールに引っかかったり、文字コードの食い違うファイルシステムで壊れたりすることが、ときどきあります。10 秒で除外できます。

やってはいけないこと

いきなり全プラグインを無効化しない。 影響が大きいわりに、確かめられるのは分岐 A と分岐 D だけです。ネットワークのレスポンスを見れば 5 秒でもっと多くのことがわかります。

.htaccess にハンドラーの行を適当に足さない。 出回っている SetHandlerAddHandler の断片は、特定のホスティングの PHP 構成を前提にしています。構成が違えば、500 でサイトごと落とします。

「再試行したら通った」を解決とみなさない。 断続的に成功するのは分岐 B の特徴で、サーバーが混んだ瞬間や、誰かがもっと大きいファイルを上げた瞬間に必ず戻ってきます。

それでも解決しない場合

レスポンスがきれいな 200 で JSON も正しいのにアップロードが失敗する場合、壊れているのはファイルが着地したあとの工程です。多くは、添付ファイルの処理チェーンにフックしたプラグインが致命的エラーを投げているか、最適化系プラグインが外部サービスへ独自のリクエストを送ってタイムアウトしているかのどちらかです。WP_DEBUG_LOG を有効にして再現し、出てきた致命的エラーを エラーログ解読ツール にかけて、どのファイルのどのフックが原因なのかを確認してください。

FAQ

よくある質問

WordPress に画像をアップロードするときの「HTTP エラー」とは何ですか?

ブラウザー側のアップローダーがファイルをサーバーに送ったものの、返ってきた内容を成功レスポンスとして解釈できなかった、という意味です。このメッセージは症状を説明しているだけで、原因は何も語っていません。PHP プロセスの停止、ファイアウォールによる遮断、403、空のレスポンス。どれもまったく同じ文言になります。

同じ画像が成功したり失敗したりするのはなぜですか?

断続的な失敗は、設定値の上限よりもメモリや CPU の枯渇を示していることがほとんどです。大きな写真のリサイズには一時的に多くのメモリが必要で、共有サーバーでは使える量がサーバーの混み具合で変わります。post_max_size のような固定の上限であれば、毎回まったく同じように失敗します。

WordPress の画像処理を Imagick から GD に切り替えれば HTTP エラーは直りますか?

直ることもありますが、特定の分岐に限った話です。共有サーバーの ImageMagick はポリシーファイルや低いリソース制限で縛られていることが多く、GD なら通る処理でも失敗します。ただし GD は非常に大きなファイルでより多くのメモリを使うため、メモリが原因の失敗はかえって悪化することがあります。

サーバーのファイアウォールがアップロードを止めているかどうかは、どう判断しますか?

ブラウザーの開発者ツールのネットワークタブを開いてファイルをアップロードし、async-upload.php に返ってきたステータスコードを見てください。HTML の本文を伴う 403 や 406 なら、WAF か mod_security のルールがリクエストを拒否しています。500 や空のレスポンスなら、PHP 側が落ちています。

upload_max_filesize を大きくすれば HTTP エラーは直りますか?

ファイルが本当に上限を超えている場合だけです。しかも多くの場合、効いているのは post_max_size のほうです。リクエスト全体のサイズが post_max_size を超えると、PHP は WordPress が動く前にそれを破棄するため、アップローダーには何も返りません。片方だけ上げても状況は変わりません。

ファイル名が原因で WordPress の HTTP エラーが起きることはありますか?

あります。ただし最も可能性の低い分岐です。アクセント記号、アポストロフィ、アンパサンド、非ラテン文字は、セキュリティルールに引っかかったり、文字コードの食い違うファイルシステムでパスを壊したりすることがあります。半角英小文字と数字とハイフンだけの名前に変えるのはコストゼロで、10 秒ほどでこの分岐を除外できます。