Open1

CORS設定について

MygMyg

参考記事

https://qiita.com/toki_dev/items/8fecf48f618e786fa01b

https://study-diary.hatenadiary.jp/entry/2022/02/05/161328

不具合発生手順

前提条件

Frontend:React
Backend:NestJS
・NestJSで作成したAPIをReactから叩いている。

エラー

以下のようなエラーが発生する

Access to fetch at 'http://localhost:3000/item' from origin 'http://localhost:4000' has been blocked by CORS policy:
No 'Access-Control-Allow-Origin' header is present on the requested resource. 
If an opaque response serves your needs, set the request's mode to 'no-cors' to fetch the resource with CORS disabled.

原因

localhost:3000からlocalhost:4000へのリクエストはCORSポリシーによりブロックされている

CORSポリシーとは

https://developer.mozilla.org/ja/docs/Web/HTTP/CORS

CORS(Cross-Origin Resource Sharing)とは、異なるオリジン間でリソースを共有するための仕組みです。具体的には、ウェブページが自分のオリジンとは異なるドメインからリソース(画像、スクリプト、スタイルシートなど)を安全にリクエストできるようにするためのHTTPヘッダーを使用します。

CORSの基本概念

同一オリジンポリシー: CORSの背景には、同一オリジンポリシーがあります。これは、ウェブページが自分が読み込まれたオリジン(スキーム、ホスト、ポートが同じ)以外のリソースにアクセスすることを制限するセキュリティ機能です。このポリシーは、悪意のあるスクリプトが他のドメインのデータにアクセスするのを防ぐために設けられています。

CORSの仕組み: CORSは、サーバーが特定のオリジンからのリクエストを許可するために、HTTPレスポンスヘッダーを使用します。これにより、ブラウザはリクエストが許可されているかどうかを判断します。例えば、Access-Control-Allow-Originヘッダーを使用して、どのオリジンがリソースにアクセスできるかを指定します。

CORSの重要性

CORSは、以下のような理由から重要です:

セキュリティの向上: CORSを使用することで、ウェブアプリケーションは他のオリジンからのリソースを安全に利用できるようになります。これにより、開発者はより柔軟で強力なアプリケーションを構築できます。

リソースの共有: CORSを利用することで、異なるドメイン間でのデータやリソースの共有が可能になります。これにより、例えば、外部APIからデータを取得したり、他のドメインの画像やスクリプトを埋め込むことができます。

CORSの設定とベストプラクティス

CORSを適切に設定することは非常に重要です。以下は、CORSを安全に実装するためのベストプラクティスです:

明示的なオリジンの指定: ワイルドカード(*)を使用するのではなく、許可するオリジンを明示的に指定することが推奨されます。これにより、悪意のあるサイトからのアクセスを防ぐことができます。

HTTPメソッドとヘッダーの制限: Access-Control-Allow-MethodsやAccess-Control-Allow-Headersを使用して、許可するHTTPメソッドやカスタムヘッダーを明示的に指定します。

プリフライトリクエストの理解: 特定の条件下では、ブラウザがサーバーに対してプリフライトリクエストを送信し、実際のリクエストが許可されているかを確認します。このプロセスを理解し、適切に設定することが重要です。

CORSは、現代のウェブ開発において不可欠な要素であり、適切に実装することで、セキュリティを維持しつつ、リソースの柔軟な利用を可能にします。

CORSの設定

app.enableCors({
  origin: ['http://localhost:5173', 'http://localhost:3000'],
  allowedHeaders: 'Origin, X-Requested-With, Content-Type, Accept',
});

URLの末尾にスラッシュがあるかどうか('http://localhost:3000')が影響する場合があるため気を付ける

CORS設定では、特定のHTTPメソッド(GET, POST, PUT, DELETEなど)を許可する必要があります。デフォルトでは、GETとPOSTは許可されていますが、他のメソッドを使用する場合は、methodsオプションを追加する必要があります。

app.enableCors({
  origin: ['http://localhost:5173', 'http://localhost:3000'],
  allowedHeaders: 'Origin, X-Requested-With, Content-Type, Accept',
  methods: 'GET,HEAD,PUT,PATCH,POST,DELETE',
});

フロントエンド側では、mode:"cors"をつける必要がある。

await fetch(`http://localhost:3000//${id}`, {
      mode: "cors",