Announcements

Help Wizard

Step 1

NEXT STEP

Receiving a 403 status when getting user's top items

Solved!

Receiving a 403 status when getting user's top items

From what I am reading it is a bad OAuth request, but I cannot identify what I am doing wrong. TIA!


 

import { useEffect, useState } from "react";
import "./App.css";
import axios from "axios";

function App() {
  const CLIENT_ID = "501594440ad341babe6b49b9db06b908";
  const REDIRECT_URI = "http://localhost:3002";
  const AUTH_ENDPOINT = "https://accounts.spotify.com/authorize";
  const RESPONSE_TYPE = "token";

  const [token, setToken] = useState("");
  const [data, setData] = useState([]);

  // on login
  useEffect(() => {
    const hash = window.location.hash;
    let token = window.localStorage.getItem("token");
    if (!token && hash) {
      token = hash
        .substring(1)
        .split("&")
        .find((elem) => elem.startsWith("access_token"))
        .split("=")[1];

      window.location.hash = "";
      window.localStorage.setItem("token", token);
    }

    setToken(token);

    // getTopArtists();
  }, []);

  const getTopArtists = async () => {
    console.log(token);
    const { data } = await axios.get(
      "https://api.spotify.com/v1/me/top/artists",
      {
        headers: {
          Authorization: `Bearer ${token}`,
        },
      }
    );

    console.log(token);
    console.log(data);
    // setData(data);
  };

  return (
    <div className="App">
      <header className="App-header">
        <h1>Spotify React</h1>
        {!token && (
          <a
            href={`${AUTH_ENDPOINT}?client_id=${CLIENT_ID}&redirect_uri=${REDIRECT_URI}&response_type=${RESPONSE_TYPE}`}
          >
            Login to Spotify
          </a>
        )}
        <button onClick={getTopArtists}>Get Top Artists</button>
      </header>
    </div>
  );
}

export default App;

 

 

Reply

Accepted Solutions
Marked as solution

I was not setting the correct scope as referenced here:

https://community.spotify.com/t5/Spotify-for-Developers/Receiving-a-Only-valid-bearer-authentication...

Marking as done, cheers Ximzend.

View solution in original post

6 Replies

A 403 status indicates that the server is refusing to fulfill the request. In this case, it could be because the OAuth request is missing or has invalid parameters.

One possible cause of this error is that the token variable is not being set correctly. In the code you provided, token is set to the value of the access_token query parameter in the URL hash, but this value is not being passed to the getTopArtists function.

To fix this, you can pass the token variable to the getTopArtists function as a parameter:

 

const getTopArtists = async (token) => {
  const { data } = await axios.get(
    "https://api.spotify.com/v1/me/top/artists",
    {
      headers: {
        Authorization: `Bearer ${token}`,
      },
    }
  );

  console.log(token);
  console.log(data);
  // setData(data);
};

 

Then, when calling the getTopArtists function, you can pass the token variable as an argument:

 

<button onClick={() => getTopArtists(token)}>Get Top Artists</button>

 

This should ensure that the correct token value is passed to the getTopArtists function and included in the request to the Spotify API.

I tried your solution but am still experiencing a 403. I am setting the token in state and am not sure of the merit of putting that state value in the function as a parameter and argument. I am able to get a successful request when using the search endpoint which I have shared below.

 

import { useEffect, useState } from "react";
import "./App.css";
import axios from "axios";

function App() {
  const CLIENT_ID = "501594440ad341babe6b49b9db06b908";
  const REDIRECT_URI = "http://localhost:3002";
  const AUTH_ENDPOINT = "https://accounts.spotify.com/authorize";
  const RESPONSE_TYPE = "token";

  const [token, setToken] = useState("");
  const [data, setData] = useState([]);

  // on login
  useEffect(() => {
    const hash = window.location.hash;
    let token = window.localStorage.getItem("token");
    if (!token && hash) {
      token = hash
        .substring(1)
        .split("&")
        .find((elem) => elem.startsWith("access_token"))
        .split("=")[1];

      window.location.hash = "";
      window.localStorage.setItem("token", token);
    }

    setToken(token);

    // getTopArtists();
  }, []);

  const getTopArtists = async () => {
    const { data } = await axios.get("https://api.spotify.com/v1/search", {
      headers: {
        Authorization: `Bearer ${token}`,
      },
      params: {
        q: "Childish Gambino",
        type: "artist",
      },
    });

    console.log(data);
  };

  return (
    <div className="App">
      <header className="App-header">
        <h1>Spotify React</h1>
        {!token && (
          <a
            href={`${AUTH_ENDPOINT}?client_id=${CLIENT_ID}&redirect_uri=${REDIRECT_URI}&response_type=${RESPONSE_TYPE}`}
          >
            Login to Spotify
          </a>
        )}
        <button onClick={getTopArtists}>Get Top Artists</button>
      </header>
    </div>
  );
}

export default App;

 

 

 

Screen Shot 2022-12-06 at 7.47.26 PM.png

Receiving a 401 now with the original endpoint, added params for testing 😞

 

 

import { useEffect, useState } from "react";
import "./App.css";
import axios from "axios";

function App() {
  const CLIENT_ID = "501594440ad341babe6b49b9db06b908";
  const REDIRECT_URI = "http://localhost:3002";
  const AUTH_ENDPOINT = "https://accounts.spotify.com/authorize";
  const RESPONSE_TYPE = "token";

  const [token, setToken] = useState("");
  const [data, setData] = useState([]);

  // on login
  useEffect(() => {
    const hash = window.location.hash;
    let token = window.localStorage.getItem("token");
    if (!token && hash) {
      token = hash
        .substring(1)
        .split("&")
        .find((elem) => elem.startsWith("access_token"))
        .split("=")[1];

      window.location.hash = "";
      window.localStorage.setItem("token", token);
    }

    setToken(token);

    getTopArtists();
  }, []);

  const getTopArtists = async () => {
    const { data } = await axios.get("https://api.spotify.com/v1/me/top/type", {
      headers: {
        Authorization: `Bearer ${token}`,
        "Content-Type": "application/json",
      },
      params: {
        type: "artist",
        limit: 20,
        offset: 5,
        time_range: "medium_term",
      },
    });

    console.log(data);
  };

  return (
    <div className="App">
      <header className="App-header">
        <h1>Spotify React</h1>
        {!token && (
          <a
            href={`${AUTH_ENDPOINT}?client_id=${CLIENT_ID}&redirect_uri=${REDIRECT_URI}&response_type=${RESPONSE_TYPE}`}
          >
            Login to Spotify
          </a>
        )}
        <button>Get Top Artists</button>
      </header>
    </div>
  );
}

export default App;

 

 

 

Screen Shot 2022-12-06 at 8.15.54 PM.png

After looking again, I see you are missing a step to get an Access Token. You can read how to get one here: https://developer.spotify.com/documentation/general/guides/authorization/code-flow/

Marked as solution

I was not setting the correct scope as referenced here:

https://community.spotify.com/t5/Spotify-for-Developers/Receiving-a-Only-valid-bearer-authentication...

Marking as done, cheers Ximzend.

I try to get the json with postman, when i use for artist, everything is good, but when i try to get the top users, i got 403 forbidden

Suggested posts