2026年5月20日

2026年5月20日

WordPressのCORS(クロスオリジン)エラーを解決する方法

はじめに

ブラウザの開発者ツールに「Access to XMLHttpRequest has been blocked by CORS policy」と表示され、外部サイトやReactアプリからWordPressのデータが取得できない。CORSエラーはセキュリティ機能の一つですが、正しく設定すれば安全に解決できます。

症状・原因

ブラウザコンソールに以下のようなエラーが出ます。

Access to fetch at 'https://yoursite.com/wp-json/wp/v2/posts'
from origin 'https://other-domain.com' has been blocked by CORS policy:
No 'Access-Control-Allow-Origin' header is present on the target resource.

CORSエラーが発生する主な状況:

  • ヘッドレスWordPress構成:ReactやVue.jsなど別ドメインのフロントエンドからREST APIを呼び出す
  • サブドメイン間通信api.yoursite.comyoursite.com などのリクエスト
  • 外部サービス連携:別サイトのJavaScriptからWordPressのデータを取得する
  • プラグインの設定不足:CORS対応していないAPIエンドポイントを呼び出す

解決手順

ステップ1:CORSヘッダーをfunctions.phpで追加する

最も確実な方法はWordPress側でCORSヘッダーを追加することです。

// functions.php または カスタムプラグイン
add_action('init', function() {
    // 特定のオリジンのみ許可(推奨)
    $allowed_origins = [
        'https://frontend.yoursite.com',
        'https://app.yoursite.com',
    ];
    
    $origin = $_SERVER['HTTP_ORIGIN'] ?? '';
    
    if (in_array($origin, $allowed_origins, true)) {
        header('Access-Control-Allow-Origin: ' . $origin);
        header('Access-Control-Allow-Methods: GET, POST, OPTIONS');
        header('Access-Control-Allow-Headers: Authorization, Content-Type, X-WP-Nonce');
        header('Access-Control-Allow-Credentials: true');
    }
    
    // OPTIONSリクエスト(プリフライト)に即座に応答
    if ($_SERVER['REQUEST_METHOD'] === 'OPTIONS') {
        status_header(200);
        exit();
    }
});

ステップ2:REST APIのCORSヘッダーを設定する

REST APIのレスポンスに対してCORSヘッダーを追加するにはフィルターを使います。

add_filter('rest_pre_serve_request', function($served, $result, $request, $server) {
    $origin = get_http_origin();
    
    if ($origin) {
        header('Access-Control-Allow-Origin: ' . esc_url_raw($origin));
        header('Access-Control-Allow-Methods: GET, POST, PUT, DELETE, OPTIONS');
        header('Access-Control-Allow-Credentials: true');
    }
    
    return $served;
}, 10, 4);

ステップ3:.htaccessでApacheレベルで設定する

<IfModule mod_headers.c>
    # 特定のドメインのみ許可
    SetEnvIf Origin "^https://(frontend|app)\.yoursite\.com$" ALLOWED_ORIGIN=$0
    Header always set Access-Control-Allow-Origin "%{ALLOWED_ORIGIN}e" env=ALLOWED_ORIGIN
    Header always set Access-Control-Allow-Methods "GET, POST, OPTIONS"
    Header always set Access-Control-Allow-Headers "Authorization, Content-Type, X-WP-Nonce"
    Header always set Access-Control-Max-Age "3600"
    
    # OPTIONSリクエストを処理
    RewriteEngine On
    RewriteCond %{REQUEST_METHOD} OPTIONS
    RewriteRule ^(.*)$ $1 [R=200,L]
</IfModule>

ステップ4:Nginxで設定する

location ~* \.(php)$ {
    add_header 'Access-Control-Allow-Origin' 'https://frontend.yoursite.com' always;
    add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS' always;
    add_header 'Access-Control-Allow-Headers' 'Authorization, Content-Type, X-WP-Nonce' always;
    
    if ($request_method = 'OPTIONS') {
        add_header 'Access-Control-Max-Age' 1728000;
        add_header 'Content-Type' 'text/plain; charset=utf-8';
        add_header 'Content-Length' 0;
        return 204;
    }
}

ステップ5:WordPress REST API認証設定

フロントエンドからnonce認証を使う場合:

// フロントエンド側のfetch例
const response = await fetch('https://yoursite.com/wp-json/wp/v2/posts', {
    method: 'GET',
    headers: {
        'X-WP-Nonce': wpApiSettings.nonce,  // WordPressがlocalize_scriptで提供
        'Content-Type': 'application/json',
    },
    credentials: 'include',  // Cookieを送信する場合
});

注意事項

  • Access-Control-Allow-Origin: *(全ドメイン許可)はセキュリティリスクがあります。本番環境では必ず許可するオリジンを明示してください。
  • Access-Control-Allow-Credentials: true を設定する場合、* は使えず特定のオリジンを指定する必要があります。
  • 変更後はブラウザのキャッシュをクリアしてテストしてください。

まとめ

CORSエラーはWordPress側でCORSヘッダーを返すことで解決できます。functions.phpのREST APIフィルターが最も柔軟で推奨の方法です。許可するオリジンは必要最小限に絞り、セキュリティを保ちましょう。関連記事:REST APIのエラー対処法ヘッドレスWordPress構築

お気軽にご相談ください

お見積りへ お問い合わせへ