Next-auth: difference between session token and access token?

Created on 19 Sep 2020  路  4Comments  路  Source: nextauthjs/next-auth

Got a document in the sessions collection for a logged in user in my test MongoDB database

image

What's the difference between sessionToken and accessToken and why is only accessToken being returned to session variable in const [ session, loading ] = useSession() .

{user: {鈥, accessToken: "e25f790f00e553b82592626a2a948a643e90a6f3b7c3b0d7b4574e94437e52cc", expires: "2020-10-18T02:58:39.561Z"}
accessToken: "e25f790f00e553b82592626a2a948a643e90a6f3b7c3b0d7b4574e94437e52cc"
expires: "2020-10-18T02:58:39.561Z"
user: {email: "[email protected]"}

In what cases would you use the access token vs the session token and is there an example of how you would use these tokens?

question

Most helpful comment

Great question! This isn't really covered anywhere in the documentation.

A Session Token is usually used to identify a session in a browser (or other client). Typically Session Tokens are fixed and do not change unless a user signs out, but in some applications they can rotate. For optimal security, they should not be readable by client side JavaScript (i.e. they are server side only cookies).

An Access Token is usually used as a way of providing a way for clients to make requests using a token that uniquely identifies a user / session, sometimes - but not always - with less privileges (e.g. it might be read only, or may perform create and update operations, but not delete operations). Typically Access Tokens do rotate. This is done to limit the risk of exposing a token to client side JavaScript, where it could be hijacked by third party scripts.

For example, Google Access Tokens are only valid for 1 hour and you must make a request using a Refresh Token (which does not rotate, and functions like a Session Token) to request a new Access Token every hour.

NextAuth.js implements Access Tokens in sessions as a way to provide an identifier for client side operations that can be tracked by to a session, without exposing the Session Token itself (so that a Session cannot be hijacked by a third party script).

However, it is currently only a basic implementation in that the Access Token it exposes does not change / expire and it is not used for anything internally - it's more a placeholder around which you can build on and extend on to add your own functionality, to discourage people from exposing the Session Token client side.

In practice, if you have /api/ endpoints in a Next.js app you should be able to access the session directly from them (or JWT directly, if you are using JSON Web Tokens to store session data) so you _probably_ don't need to use the accessToken.

An example of how you might want to use it, is to pass it to another service to allow it to make API requests to your service (e.g. as callback) so that it could do so securely on behalf of your user, without exposing information about the user or their session.

All 4 comments

Great question! This isn't really covered anywhere in the documentation.

A Session Token is usually used to identify a session in a browser (or other client). Typically Session Tokens are fixed and do not change unless a user signs out, but in some applications they can rotate. For optimal security, they should not be readable by client side JavaScript (i.e. they are server side only cookies).

An Access Token is usually used as a way of providing a way for clients to make requests using a token that uniquely identifies a user / session, sometimes - but not always - with less privileges (e.g. it might be read only, or may perform create and update operations, but not delete operations). Typically Access Tokens do rotate. This is done to limit the risk of exposing a token to client side JavaScript, where it could be hijacked by third party scripts.

For example, Google Access Tokens are only valid for 1 hour and you must make a request using a Refresh Token (which does not rotate, and functions like a Session Token) to request a new Access Token every hour.

NextAuth.js implements Access Tokens in sessions as a way to provide an identifier for client side operations that can be tracked by to a session, without exposing the Session Token itself (so that a Session cannot be hijacked by a third party script).

However, it is currently only a basic implementation in that the Access Token it exposes does not change / expire and it is not used for anything internally - it's more a placeholder around which you can build on and extend on to add your own functionality, to discourage people from exposing the Session Token client side.

In practice, if you have /api/ endpoints in a Next.js app you should be able to access the session directly from them (or JWT directly, if you are using JSON Web Tokens to store session data) so you _probably_ don't need to use the accessToken.

An example of how you might want to use it, is to pass it to another service to allow it to make API requests to your service (e.g. as callback) so that it could do so securely on behalf of your user, without exposing information about the user or their session.

@iaincollins thanks for the explanation! Just want a little bit more clarification on something.

I was looking through the cookies for my site in the browser, and I noticed a logged in user's session token exposed under the field next-auth.session-token. Is this expected since it has to match the session token stored in the database? Or should this value be the access token value? You mentioned that session tokens are server side cookies so just wondering why I see it in the browser.

image

Also, getServerSideProps has access to the session token next-auth.session-token stored in the request headers, should this token be used on the server side or should it not be used? I don't see the acccess token available in getServerSideProps

@kevinmachstudio It's a http-only cookie! It's only "accessible" when you make a http call! So is all cool!

awesome thanks guys

Was this page helpful?
0 / 5 - 0 ratings