React 前端和 Node 后端的 Spotify API CORS 错误

时间:2021-02-22 01:36:50

标签: javascript node.js reactjs express spotify

我有一个使用 Spotify API 的普通 JavaScript 网络应用程序,它运行良好。我正在将它移植到 React 前端和 NodeJS/Express 后端,但我收到了这个问题。 当用户单击“登录”按钮时,它会在浏览器控制台中显示此错误(已编辑私人信息):

Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote resource at 
https://accounts.spotify.com/authorize?response_type=code&client_id=xxx&
scope=playlist-modify-public%20playlist-modify-private
&redirect_uri=http%3A%2F%2Flocalhost%3A8888%2Fcallback%2F&state=xxxxx&show_dialog=true. 
(Reason: CORS header ‘Access-Control-Allow-Origin’ missing).

这是主页中的按钮(React):

<button
    onClick={login}
    type="button"
    className="btn btn-primary login-btn col-sm-12 col-lg-6">
    Login with Spotify
</button>

async function login() {
    console.log("Sent Login Request");
    await fetch(`/api/login`, {
      method: "GET",
      headers: { "Content-Type": "application/json" },
    });
  }

在前端 package.json 我已经设置了代理:

"proxy": "http://localhost:8888"

这是(我认为)与此问题相关的 app.js(后端)代码:

app
  .use(express.static(directoryPath))
  .use(helmet())
  .use(compression())
  .use(cors())
  .use(cookieParser());

app.use(function (req, res, next) {
  res.header("Access-Control-Allow-Origin", "localhost"); // update to match the domain you will make the request from
  res.header(
    "Access-Control-Allow-Headers",
    "Origin, X-Requested-With, Content-Type, Accept"
  );
  next();
});

app.get("/api/login", function (req, res) {
  console.log("Started LOGIN flow");
  let state = generateRandomString(16);
  res.clearCookie(stateKey);
  res.cookie(stateKey, state);

  let scope = "playlist-modify-public playlist-modify-private";
  res.redirect(
    "https://accounts.spotify.com/authorize?" +
      querystring.stringify({
        response_type: "code",
        client_id: _client_id,
        scope: scope,
        redirect_uri: _redirect_uri,
        state: state,
        show_dialog: true, // show dialog to allow users to log out
      })
  );
});

app.get("/callback", function (req, res) {
  let code = req.query.code || null;
  let state = req.query.state || null;
  let storedState = req.cookies ? req.cookies[stateKey] : null;

  if (state === null || state !== storedState) {
    res.redirect(
      "/#" +
        querystring.stringify({
          error: "State mismatch",
        })
    );
  } else {
    res.clearCookie(stateKey);
    // request auth
    const params = {
      client_id: _client_id,
      client_secret: _client_secret,
      redirect_uri: _redirect_uri,
      code,
      grant_type: "authorization_code",
    };

    ax({
      method: "post",
      url: "https://accounts.spotify.com/api/token",
      params,
      headers: {
        "Content-Type": "application/x-www-form-urlencoded",
      },
    })
      .then((response) => {
        let token = response.data.access_token;
        res.redirect(
          "/#" +
            querystring.stringify({
              authorized: "access_granted",
              token: token,
            })
        );
      })
      .catch((error) => {
        console.log("Failed to login: " + error);
        res.redirect(
          "/#" + querystring.stringify({ authorized: "access_denied" })
        );
      });
  }
});

0 个答案:

没有答案
相关问题