Nuxt Authentication API calls strategies - vue.js

I have some unfamiliar API calls in the current app I'm building. It needs a couple of parameters to setup the following api's. Currently based on subdomain in window it picks up the url parameter to create the first API call. After that I use Vuex store to store the relevant information for the organization data.
I'm currently trying to setup authorization and unfortunately due to it being inside nuxt.config.js I can't dynamically add data from the vuex store. Here is an example of the strategies I've set up. I'm currently using the local default strategies, but wan't to make the url requests dynamic:
nuxt.config.js
/*
** Nuxt.js modules
*/
modules: ['#nuxtjs/axios', '#nuxtjs/auth'],
/*
** Axios configuration
*/
axios: {
baseURL: 'https://api.getconflux.com',
headers: {
common: {
Accept: 'application/json, text/plain, */*'
}
}
},
/*
** Auth configuration
*/
auth: {
strategies: {
local: {
endpoints: {
login: {
method: 'post',
propertyName: 'token'
},
logout: {
url: '/logout',
method: 'post'
},
user: {
url: '/supporters/me',
headers: {
'organization-id': getters.companyId,
// Authorization Bearer needs to be automatically called from login
},
method: 'get',
propertyName: 'voter'
},
}
}
},
customStrategy: {
user: '~/schemas/user'
},
redirect: {
home: '/'
}
}
The current login I manually setup, with no url as I call that when my index page loads. This is the first api call to build out my state with the required data I need to call for my subsequent api calls after that.
For my auth api request to work, especially the fetchUser() call in the user strategy I need to get the companyId getter/state from my store. I have no idea how to do this here?
Does anyone have an idea of how I can best implement that?
Any help will be appreciated!
Thanks in advance!

You could disable the user endpoint in the nuxt.config.js file and then manually call the endpoint in Vuex to fetch the user details then pass it on to the setUser method of the auth NuxtJS module. So in your nuxt.config.js file, you should have this:
/*
** Nuxt.js modules
*/
modules: ['#nuxtjs/axios', '#nuxtjs/auth'],
/*
** Axios configuration
*/
axios: {
baseURL: 'https://api.getconflux.com',
headers: {
common: {
Accept: 'application/json, text/plain, */*'
}
}
},
/*
** Auth configuration
*/
auth: {
strategies: {
local: {
endpoints: {
login: {
method: 'post',
propertyName: 'token'
},
logout: {
url: '/logout',
method: 'post'
},
user: false
},
customStrategy: {
user: '~/schemas/user'
},
redirect: {
home: '/'
}
}
Then in your store, you have an action(or a mutation making the API request to get the user details). Then you call setUser as described here

Related

CSRF token and Nuxt-auth

I'm now trying to code a login functionality using nuxt-auth.
I've got a FastAPI server that is set to work with HTTPOnly cookies, thus it needs a csrf token for throwing a user to my client. I can't handle the token because it's HTTPOnly so no LocalStorage
Login works fine but I can't manage to get the stored user. I made that after request to my /login endpoint, Nuxt also requests a user on /me endpoint. But I'm getting the 401 response and
Missing cookie access_token_cookie
error on /me. I don't know how to handle it.
my login request method
async userLogin() {
await this.$auth.loginWith('cookie', {
data: `grant_type=&username=${this.emailInput}&password=${this.passwordInput}&scope=&client_id=&client_secret=&`,
method: 'POST',
headers: {'Content-Type': 'application/x-www-form-urlencoded'},
})
await this.$router.push('/account')
}
I read that nuxt-auth is bad at cookie patterns but the post was from 2018 and we have a 'cookie' strategy now. So is there a workaround of it's better to handle authentication manually?
my auth key in nuxt.config.js
auth: {
strategies: {
cookie: {
endpoints: {
login: {
url: "/api/v1/login/login",
method: "post",
withCredentials: true
},
logout: { url: "/api/v1/login/logout", method: "post" },
user: {
url: "/api/v1/users/me",
method: "get"
}
},
tokenType: "bearer"
}
}
}
I have a working http-only cookie based setup on Nuxt + Django.
My Nuxt application reverse proxies API requests to backend. So, it can read cookies on server side.
So, I create auth-ssr.ts middleware to check is user loggedIn
import { Context, Middleware } from '#nuxt/types'
import { parse as parseCookie } from 'cookie' // this is lib https://github.com/jshttp/cookie
/**
* This middleware is needed when running with SSR
* it checks if the token in cookie is set and injects it into the nuxtjs/auth module
* otherwise it will redirect to login
* #param context
*/
const authMiddleware: Middleware = async (context: Context) => {
if (process.server && context.req.headers.cookie != null) {
const cookies = parseCookie(context.req.headers.cookie)
const token = cookies['session'] || '' // here your cookie name
if (token) {
context.$auth.$state.loggedIn = true
}
}
}
export default authMiddleware
And here my nuxt.config.js
auth: {
strategies: {
cookie: {
user: {
property: 'user',
},
endpoints: {
login: {
url: '/api/v2/auth/login/',
method: 'post',
},
user: {
url: '/api/v2/auth/user/',
method: 'get',
},
logout: {
url: '/api/v2/auth/logout/',
method: 'post',
},
},
},
},
redirect: {
login: '/login',
},
plugins: ['#plugins/axios.ts'],
},
router: {
middleware: ['auth-ssr', 'auth'],
},
// Axios module configuration: https://go.nuxtjs.dev/config-axios
axios: {
proxy: true,
},
proxy: {
'/api': {
target: 'https://backend.com/',
},
},
...

Nuxt Auth Module c5 doesn't refresh token automatically when token expires

Version
module: 5.0.0-1624817847.21691f1
nuxt: 2.15.8
Nuxt configuration
Universal
Nuxt configuration
// Auth: https://auth.nuxtjs.org/ (v5)
auth: {
redirect: {
login: '/account/login/',
logout: '/account/login/',
callback: '/account/login/',
home: '/account/beams/'
},
strategies: {
local: {
scheme: 'refresh',
token: {
property: 'access_token',
maxAge: 120, // seconds, 2 minutes
global: true
},
refreshToken: {
property: 'refresh_token',
data: 'refresh_token',
maxAge: 1209600 // seconds, 2 weeks
},
user: {
property: 'user',
autoFetch: true
},
endpoints: {
login: { url: '/api/account/login', method: 'post', propertyName: 'token' },
refresh: { url: '/api/account/refresh', method: 'post', },
logout: { url: '/api/account/logout', method: 'post' },
user: { url: '/api/account', method: 'get' }
},
autoLogout: false
}
}
},
Additional information
Checklist
[x] I have tested with the latest Nuxt version and the issue still occurs
[x] I have tested with the latest module version and the issue still occurs
[x] I have searched the issue tracker and this issue hasn't been reported yet
Steps to reproduce
What is expected?
When a user's token expires and refresh scheme is implemented, a user shouldn't be logged out and redirected back to the login screen, the refresh token should be used to obtain a new token and the transition should be seamless allowing any authenticated route to continue to work.
What is actually happening?
In my Nuxt project with the Auth module I've implemented the refresh scheme, however, when my token expires I don't see any request in my network being made to the refresh route after my token expires and I navigate to a protected page via the auth middleware.
I expect I'm missing some simple configuration?
My current token has an expiry of 1 minute for testing, and my refresh token has an expiry of 14 days for testing.
However, when adding:
scheme: 'refresh'
refresh: { url: '/api/account/refresh', method: 'post', }
the functionality appears to not be fetching my user and automatically logging me in.
My /api/account/refresh endpoint in my API returns the following:
{
refresh_token: 'my refresh token',
token_type: 'bearer',
expired_in: 5000
}
My /api/account/login endpoint in my API returns the following:
{
access_token: 'my token',
token_type: 'bearer',
expired_in: 1000
}
What am I missing?
You need to return refresh token from /api/account/login. And then set in conf property name of it.
I have same issue with very similar comfiguration. This is my result from API (I added refresh token to the result):
{
"access_token": "XXX",
"refresh_token": "XXX",
"expired_in": 3600,
"token_type": "bearer"
}
If I inspect cookies, I can see acces token, but refresh token does not set:
I try to manually set refresh token after login, but with same result:
const result = await this.$auth.loginWith('local', {
data: this.login,
})
this.$auth.setUserToken(result.data.accessToken, result.data.refreshToken)

How to prevent nuxt auth to go to error page if the pass or email is wrong

I'm using NuxtJs v2.13 with its auth module and Laravel with passport for my backend. for login i use the documented method:
async signIn(formData){
await this.$auth.loginWith('local',{
data: formData
})
if(this.$auth.user.depth > 1){
this.goTo('/cms/product')
}else{
this.goTo('/')
}
}
when the email or password is wrong it send me too nuxt error page! i should remain on login page.
what should i do!!?
BTW, i gonna use vee-validate on my form too. and this is my auth config on nuxt.config.js:
auth: {
strategies: {
local: {
endpoints: {
login: { url: 'auth/login', method: 'post', propertyName: '' },
logout: { url: 'auth/logout', method: 'post' },
user: { url: 'auth/info', method: 'get', propertyName: 'data' }
}
}
},
redirect: {
login: '/login',
logout: '/',
callback: '/login',
home: '/'
},
cookie: {
prefix: 'auth.',
options: {
path: '/',
maxAge: process.env.AUTH_COOKIE_MAX_AGE
}
}
},
Nuxt is redirecting because the error isn't being handled. You can simply wrap this code in an error handler. It's also good to put this code near the login component or page so you can use the status code of the error to display some meaningful response to the user, e.g. that the credentials were invalid.
try {
await this.$auth.loginWith('local', {
data: formData,
})
if (this.$auth.user.depth > 1) {
this.goTo('/cms/product')
} else {
this.goTo('/')
}
} catch (error) {
if (error.response) {
// Get the error status, inform the user of the error.
}
// Unexpected error, tell the user to try again later.
}
Since the #nuxtjs/auth package requires the #nuxtjs/axios package you can also read about intercepting errors on a global level with Axios Interceptors. I personally use try/catch blocks at the method level and use interceptors for catching 401 Unauthenticated errors and deleting the user information from Vuex.

Single user login to multiple Nuxt.js websites with Nuxt Auth

Hello I'm creating a group of small websites based on Vue.js with the Nuxt.js framework
All sites use the same API (different parts of it but for example the auth is the same for all sites)
Now my client asked me to do a single login for all sites and I'm a little bit lost on how to handle this
Currently I'm using the nuxt-auth module to handle the users but I won't mind dropping it if I need to code this manually
Right now my configuration in nuxt.config.js for the Auth looks like this:
auth: {
strategies: {
local: {
endpoints: {
login: { url: 'Account/Login', method: 'post', propertyName: 'data.token' },
user: { url: 'Account/GetBasicUserInformation', method: 'get', propertyName: null },
logout: { url: 'Account/Logout', method: 'post' }
},
tokenType: null
}
}
}
Maybe I can store the token info or similar in a cookie and make other sites check for it before doing the session check?

How can I login and access to my Django-Rest-Framework while running my Nuxt project local?

I use Django-Rest-Framework for my API. It is on a remote server in the internet.
Locally I have a Nuxt-JS application running which should consume the REST-API.
How can I access this API from my local machine?
1) I would like to get the CSRF token from my login page with axios. For example from: /accounts/login/
For this I would like to make a "GET" call and geht from the HTTP-HEADER my CSRF tocken. But how?
You can install #nuxt/auth module after which you can update your nuxt.config.js file as follows:
auth: {
redirect: {
login: 'your-login-redirect-path',
logout: 'your-logout-redirect-path',
home: 'your-home-path'
},
strategies: {
local: {
endpoints: {
login: { url: 'your-django-login-endpoint', method: 'post', propertyName: 'token' },
logout: { url: 'your-django-logout-endpoint', method: 'post' },
user: { url: 'your-django-userinfo-endpoint', method: 'get', propertyName: 'user' }
}
}
}
},
Check out Nuxt Auth for more info