How can we implement an Axios interceptor to automatically refresh the token in Next-Auth?

After setting up Next-Auth and Axios for my NextJs project, I utilized the getSession() method from Next-Auth to set the axios header as follows:

export const ApiAuth = () => {
  const instance = axios.create({
    baseURL: API_URL,
  });

  instance.interceptors.request.use(async (request) => {
    const session = await getSession();
    console.log(session);

    if (session) {
      request.headers["Authorization"] = `Bearer ${session.tokens.accessToken}`;
    }
    return request;
  });

  instance.interceptors.response.use(
    (response) => {
      return response;
    },
    (error) => {
      console.log(`error`, error);
      if (error.response.status === 401) {
        console.log("Let refresh Here");
        console.log("And update Next-Auth session data");
      }
    }
  );

  return instance;
};

However, I am unsure of how to update Next-Auth session data from the axios interceptor. Can anyone guide me on this?

I am considering creating an api endpoint like /api/auth/refresh that would handle updating the new access token and refresh token for Next-Auth, while also returning the new access token for axios.

Answer №1

My curiosity was piqued by the same query, as I am partial to the interceptor method for jwt refresh. The issue appears to lie in next-auth only providing a hook for session updates:

const { update } = useSession()

To update with your new accessToken, you would simply invoke this update like so:

update({ accessToken })

The way to handle this is outlined in [...nextauth] (taken directly from the documentation):

jwt({ token, trigger, session }) {
      if (trigger === "update" && session?.accessToken) {
        // set the new accesstoken
        token.accessToken = session.accessToken
      }
      return token
}

In the session callback, it would still be necessary to include (not clear from your code)

async session({ session, token }) {
    session.accessToken = token.accessToken;
    session.refreshToken = token.refreshToken; // I included this for completeness, but it may be redundant
    return session;
}

This is how I tackled the problem, opting to move away from interceptors and utilize a react hook along with interval. It could potentially still function using interceptors by passing the update method to ApiAuth and initializing the api client within the react app. Alternatively, you could pass the session at that point and eliminate the need for await getSession().

export const ApiAuth = ({ update }) => { ... }

If this approach doesn't suit your needs, debugging the update call itself might be beneficial, which involves a POST to api/auth/session with the body and csrf token in the headers.

For further reference, check out the documentation:

https://next-auth.js.org/getting-started/client#updating-the-session

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

What are the steps to create a Node.js application and publish it on a local LAN without using Nodemon?

When working on a Node.js application, I often use the following commands to build and serve it locally: //package.json "build": "react-scripts build", To serve it on my local LAN, I typically use: serve -s build However, I have been wondering how I ...

Discovering an element within an HTML response using jQuery AJAX

Check out the code snippet below: ajax_obj = $.ajax( { data: data, success: function(answer) { console.log(answer); console.log($('#table_conferences_tbody', answer).html()); ...

execute a setTimeout function in ReactJs to render a component after a specified amount of time

Is there a way to render a component inside my App.Js after a certain amount of time using setTimeout? I've tried, but nothing seems to be happening... This is my code: function App() { return ( <Router> <GlobalStyle /> ...

I successfully executed my first node.js http request, but it is now encountering an error

Utilizing the 'request' module in node.js for sending http requests has been successful initially. However, it is now returning an error. var request = require('request'); request('http://www.google.com', function (error, res ...

``Can you provide step-by-step instructions on how to delete a particular item from

Currently, I am in the process of developing a simple comment list application using JavaScript and local storage. I have completed all the necessary details, but now I need to figure out how to remove a specific item that was created by the application ...

Upgraded my computer, and suddenly I'm unable to get Next.js running on my local server

ISSUE After switching from a MacBook Pro to a MacBook Air, I encountered an error when trying to run my Next.js repos using the command npx run dev. The terminal displayed the following message: Error: Cannot find module '/Users/briangrieco/Code Proje ...

Error encounter when loading the chunk for FusionCharts's overlappedbar2d.js in React.js: fusioncharts.overlapped

Currently, I am working on a web application that utilizes next.js and FusionCharts. Within the app, various FusionChart types have already been set up. My task now is to integrate the Overlapping Bars chart as outlined in the following documentation: How ...

Can you explain the purpose and function of stub.callsArg(index) feature in Sinon.JS?

Confusion has set in as I try to make sense of this. According to the documentation: stub.callsArg(index) - This command prompts the stub to execute the callback function found at the specified index. For instance, using stub.callsArg(0); will trigger the ...

Ways to change a value in an array within MongoDb

My array value is being overridden by $set, how can I update it properly? var obj = // contains some other data to update as well obj.images=images; // updating obj with images [] Units.update({_id: 'id', {$set: obj}); Ultimately, my MongoDB ...

How can jQuery retrieve a string from a URL?

If I have a URL like http://www.mysite.com/index.php?=332, can jQuery be used to extract the string after ?=? I've searched on Google but only found information about Ajax and URL variables that hasn't been helpful. if (url.indexOf("?=") > 0) ...

Fading Out with JQuery

My page contains about 30 same-sized divs with different classes, such as: .mosaic-block, .events, .exhibitions, .gallery, .sponsors, .hospitality, .workshops, .lectures { background:rgba(0, 0, 0, .30); float:left; position:relative; overf ...

Using jqgrid to generate a hyperlink that corresponds to the data's value

I am working with a grid setup similar to the one below: $("#list").jqGrid({ url:'listOpenQueryInXML.php', datatype: 'xml', colNames:['Id','name1', 'name2', 'status', 'type' ...

Prisma is throwing an error because it is unable to access properties of an undefined variable

When attempting to configure Prisma in my Next.js 13 application, I encountered an error while trying to insert data. You can view the error image here. Below is the model code I am working with: generator client { provider = "prisma-client-js" } datas ...

Steps for implementing a select all feature with jQuery

I'm currently working on a jQuery function that is acting as a select-all option. Everything is functioning correctly except that when I deselect any of the child elements from select all, the option remains enabled. My goal is to enable or disable th ...

Update google maps markers and infoBubbles dynamically with ajax

I am currently using asp mvc in conjunction with jquery and the google maps api to showcase and update various locations on a map. Main Objective: Utilize markers to mark multiple locations Display brief information about these locations using info ...

What is the best way to generate an array by extracting items from various nested values?

The structure of the array I'm working with is as follows (with variable objects inside): this.selected_sum_version may contain multiple groups: this.selected_sum_version.sum_item_groups = [ { "id": 1, "name": "GROUP 1", " ...

"Server request with ajax did not yield a response in JSON format

http://jsfiddle.net/0cp2v9od/ Can anyone help me figure out what's wrong with my code? I'm unable to see my data in console.log, even though the network tab in Chrome shows that my data has been successfully retrieved. Here is my code snippet: ...

Setting the default type of an array in props in Vue 2 is a common need for many developers

My Vue component relies on an array of objects as a prop and I always make use of prop validation, especially for setting default values. In this case, my current setup is: props: { items: Array } However, I would prefer it to resemble something lik ...

Exploring the use of the "++" operator in Regular

Is there a way to detect the presence of ++, --, // or ** signs in a string? Any help would be greatly appreciated. var str = document.getElementById('screen').innerHTML; var res = str.substring(0, str.length); var patt1 = ++,--,//,**; var resul ...

Leveraging TipTap.dev for building a joint editing platform -

I have integrated the collaboration feature from tiptap.dev into my NextJS application. Initially, I used their CLI command for the Hocuspocus server which worked well on port 1234 locally and synchronized text editing across browsers seamlessly. However, ...