Express サーバで CORS を許可する・PUT や DELETE メソッドの通信を許可する

Express で作った Web API サーバに対し、SPA なアプリから GET 通信を試みたら、以下のようなエラーがブラウザコンソールに出てしまった。

Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin' header is present on the requested resource.

異なるドメインへの Ajax 通信を制限する、クロスドメイン制約に引っかかっているようだ。

コレを解消するには、Express サーバの起動時に以下のように CORS を許可するヘッダを設定してやれば良い。

const express = require('express');

// サーバをインスタンス化する
const app = express();

// CORS を許可する
app.use((req, res, next) => {
  res.header('Access-Control-Allow-Origin', '*');
  res.header('Access-Control-Allow-Headers', 'Origin, X-Requested-With, Content-Type, Accept');
  next();
});

// サーバを起動する
app.listen(port);

GET・POST メソッドの通信についてはコレで上手く行っていたのだが、PUT や DELETE メソッドでの通信時に、次のようなエラーが出た。

Method PUT is not allowed by Access-Control-Allow-Methods in preflight response.

調べてみると、CORS を許可するメソッドを別途指定しないと、PUT や DELETE に対応してくれないようだ。

先程のコードの // CORS を許可する 部分に、以下の1行を追加すると解決した。

// CORS を許可する
app.use((req, res, next) => {
  res.header('Access-Control-Allow-Origin', '*');
  res.header('Access-Control-Allow-Headers', 'Origin, X-Requested-With, Content-Type, Accept');
  res.header('Access-Control-Allow-Methods', 'GET, POST, PUT, DELETE, OPTIONS');  // ← コレを追加
  next();
});

以前作った node-js-rest-api-sqlite-db にも反映しておいたので、SPA なアプリからアクセスして使ってもらえるであろう。

その他参考