#Next 14 route handler and spotify access token

1 messages · Page 1 of 1 (latest)

crisp vigil
#

I made a musical quizz using the spotify API without user auth, just the API access token (it uses the tracks preview).
I kinda make it simple with just a service file where I put my API calls, it was as long as it was in dev.
When I deployed it on vercel, I realized I kinda forget to handle the client key and secret as it should,.
I need to be able to read them directly as env variables.
So I found out I can achieve that on next 14 by using route handlers.
Problem is, it's a new feature and all the examples I've found are not that helpful for my special case, like it's quite theoretical, they're not a lot of it calling functions, it's directly fetch, etc... Cause I still want to use my service functions and such to handle and modify my data on the server side.
I tried to understand how it works, my only problem is I'm not sure how am I supposed to get my accessToken. I found something that works, but it's a bit odd. I've messed around a lot, so I came to understand that in my POST function maybe all I need to do is to declare which header my post request on this route should have? Then on the same route I've got a GET function that call a getPlaylist in which I call the getAccessToken, and it's when I guess it took the header I declare in my route handler?
I still need to declare the headers in getAccessToken, that's one of the think that makes me thing my solution is a bit odd, but I think I'm close to the real solution?
Here is my code (I'm also thinking about moving the getShuffledPlaylist in a controller file?) :

#

the service file :

const getAccessToken = async () => {
    return fetch("https://accounts.spotify.com/api/token", {
        method: "POST",
        headers: {
            "Content-Type": "application/x-www-form-urlencoded",
            Authorization: `Basic ${btoa(
                `${process.env.REACT_APP_CLIENT_KEY}:${process.env.REACT_APP_CLIENT_SECRET}`
            )}`,
        },
        body: new URLSearchParams({
            grant_type: "client_credentials",
        }),
    })
        .then((response) => {
            if (!response.ok) {
                return response.json().then((data) => {
                    throw new Error(data.error || "Failed to get access token");
                });
            }
            return response.json();
        })
        .then((data) => {
            return data.access_token;
        })
        .catch((error) => {
            console.error("Error getting access token:", error);
            throw error;
        });
};

const getPlaylist = async (offsetNumber: string) => {
    return getAccessToken()
        .then((accessToken) =>
            fetch(
                `https://api.spotify.com/v1/playlists/niubn67898YHBUI8O9J8HJ9H/tracks?offset=${offsetNumber}`,
                {
                    method: "GET",
                    headers: {
                        Authorization: `Bearer ${accessToken}`,
                    },
                }
            )
        )
        .then((response) => response.json())
        .then((data) => {
            return data.items;
        })
        .catch((error) => console.error("Error getting track infos", error));
};
#
const getShuffledPlaylist = async () => {
    return Promise.all([getPlaylist("0"), getPlaylist("100")])
        .then(([playlist1, playlist2]) => {
            const combinedPlaylists = [...playlist1, ...playlist2];
            const shuffledPlaylist = shuffle(combinedPlaylists);
            return shuffledPlaylist;
        })
        .catch((error) => {
            console.error(error);
        });
};```
#

and here the route handler file :

export async function POST(request: NextRequest, response: NextResponse) {
    const req = new Request("", {
        headers: {
            "Content-Type": "application/x-www-form-urlencoded",
            Authorization: `Basic ${btoa(
                `${process.env.REACT_APP_CLIENT_KEY}:${process.env.REACT_APP_CLIENT_SECRET}`
            )}`,
        },
    });
}

export async function GET(request: NextRequest, response: NextResponse) {
    const playlist = await getShuffledPlaylist();
    return Response.json({ playlist });
}