I’m having trouble with Spotify API authentication in my React application
I’m pretty new to React and Express.js development. I’m building an app that needs to connect to Spotify’s Web API to get user data. I found some example code online that worked perfectly when using a simple HTML page with buttons, but now I’m trying to integrate it into my React frontend and I keep running into CORS issues.
When I try to make the authentication request from my React component, I get this CORS error message:
Access to XMLHttpRequest at 'https://accounts.spotify.com/authorize?response_type=code&client_id=...' has been blocked by CORS policy: Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin' header is present on the requested resource.
My React component code:
import React from 'react';
import './SpotifyAuth.scss';
import axios from 'axios';
export default class SpotifyLogin extends React.Component {
authenticateUser() {
axios
.get('http://localhost:9000/authenticate', {
headers: {
'Access-Control-Allow-Origin': '*',
}
})
.then(response => {
console.log('Success:', response);
})
.catch(error => {
console.error('Authentication failed:', error);
});
}
render() {
return (
<div className="auth-container">
<div className="content">
<div className="header"><h2>Music Player</h2></div>
<button
className="auth-button"
type="button"
onClick={() => this.authenticateUser()}>
Connect to Spotify
</button>
</div>
</div>
);
}
}
My Express server code:
const express = require('express');
const request = require('request');
const cors = require('cors');
const querystring = require('querystring');
const cookieParser = require('cookie-parser');
const SpotifyAPI = require('spotify-web-api-node');
const server = express();
server.use(express.json());
server.use(express.urlencoded({ extended: true }));
server.use(cors());
server.use(cookieParser());
let currentUserId = '';
const authStateKey = 'auth_state_spotify';
const appClientId = 'your_client_id_here';
const appClientSecret = 'your_client_secret_here';
const callbackURL = 'http://localhost:9000/auth-callback';
const spotifyClient = new SpotifyAPI({
clientId: appClientId,
clientSecret: appClientSecret,
redirectUri: callbackURL
});
function createRandomString(len) {
let result = '';
const characters = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
for (let i = 0; i < len; i++) {
result += characters.charAt(Math.floor(Math.random() * characters.length));
}
return result;
}
server.get('/authenticate', function(req, res) {
const randomState = createRandomString(16);
res.cookie(authStateKey, randomState);
const permissions = 'user-read-private user-read-email';
res.redirect('https://accounts.spotify.com/authorize?' +
querystring.stringify({
response_type: 'code',
client_id: appClientId,
scope: permissions,
redirect_uri: callbackURL,
state: randomState
}));
});
server.get('/auth-callback', function(req, res) {
const authCode = req.query.code || null;
const stateParam = req.query.state || null;
const savedState = req.cookies ? req.cookies[authStateKey] : null;
if (stateParam === null || stateParam !== savedState) {
res.redirect('/#' + querystring.stringify({ error: 'state_mismatch' }));
} else {
res.clearCookie(authStateKey);
const tokenRequest = {
url: 'https://accounts.spotify.com/api/token',
form: {
code: authCode,
redirect_uri: callbackURL,
grant_type: 'authorization_code'
},
headers: {
'Authorization': 'Basic ' + Buffer.from(appClientId + ':' + appClientSecret).toString('base64')
},
json: true
};
request.post(tokenRequest, function(err, response, data) {
if (!err && response.statusCode === 200) {
const userToken = data.access_token;
const refreshToken = data.refresh_token;
spotifyClient.setAccessToken(userToken);
const userDataRequest = {
url: 'https://api.spotify.com/v1/me',
headers: { 'Authorization': 'Bearer ' + userToken },
json: true
};
request.get(userDataRequest, function(err, response, userData) {
console.log('User data:', userData);
currentUserId = userData.id;
});
res.redirect('/#' + querystring.stringify({
access_token: userToken,
refresh_token: refreshToken
}));
} else {
res.redirect('/#' + querystring.stringify({ error: 'invalid_token' }));
}
});
}
});
server.listen(9000, () => {
console.log('Server running on port 9000');
});
I have CORS enabled on my Express server but I’m still getting this error. How can I fix this issue and make the authentication work properly from my React app?