Bonjour gars,
J'ai crĂ©Ă© une nouvelle instance de l'axios que j'utilise pour les ressources api protĂ©gĂ©es et j'y ai attachĂ© un en-tĂȘte d'authentification avec un jeton, mais le problĂšme est que si je vais Ă la console et supprime le tokem de localStorage, axios l'envoie toujours en tant qu'instance n'a pas Ă©tĂ© mis Ă jour.
Existe-t-il une solution pour que mes en-tĂȘtes d'authentification dans l'instance puissent vĂ©rifier le jeton dans localStorage dans chaque demande ?
Merci!
J'ai un cas d'utilisation similaire oĂč ce serait formidable si les en-tĂȘtes transmis Ă©taient Ă©valuĂ©s paresseusement pour chaque demande.
Pensée:
Au lieu de passer le hachage des en-tĂȘtes avec empressement en tant qu'objet ( axios.create({headers: {...}})
nous pourrions passer une fonction qui renvoie les en-tĂȘtes ( axios.create({headers: () => {...}}
) qui seraient Ă©valuĂ©s avant l'envoi de la requĂȘte.
Qu'en penses-tu?
Edit : Ceci est une proposition, je ne pense pas que cela fonctionne pour le moment.
Je suis tombĂ© sur le mĂȘme cas d'utilisation. Ce que j'ai fini par faire Ă court terme, c'est d'utiliser la fonction transformRequest
. Certainement un hack et j'adorerais aider Ă mettre en Ćuvre une approche de chargement paresseux appropriĂ©e dans la base de code.
Voir ci-dessous pour l'extrait de code. auth()
obtient le jeton de l'utilisateur connecté s'il est disponible.
let HTTP = axios.create({
baseURL: baseurl,
transformRequest: [function (data, headers) {
headers['Authorization'] = auth()
return JSON.stringify(data)
}],
headers: {
'Content-Type': 'application/json'
}
})
J'ai utilisĂ© des intercepteurs Ă cette fin. Si l'URL de base de la demande correspond Ă mon API, j'ajoute l'en-tĂȘte auth (pour empĂȘcher l'envoi d'informations d'identification Ă des tiers). Ceci est exĂ©cutĂ© Ă chaque demande, donc si le jeton change (par exemple Ă la suite d'une actualisation du jeton), la demande suivante rĂ©cupĂšre le nouveau jeton. Je m'assure Ă©galement de vĂ©rifier les valeurs existantes dans la demande pour permettre le remplacement de l'en-tĂȘte du site d'appel si cela s'avĂ©rait nĂ©cessaire pour une raison quelconque.
axios.interceptors.request.use(
config => {
if (config.baseURL === baseApiAddress && !config.headers.Authorization) {
const token = getToken();
if (token) {
config.headers.Authorization = `Bearer ${token}`;
}
}
return config;
},
error => Promise.reject(error)
);
@mattstrayer pouvez-vous me montrer la méthode getToken() ? Stockez-vous votre jeton dans localStorage ou AsyncStorage (React Native) ? Merci d'avance!
J'ai fini avec ça.
axios.create({
baseURL: '<your-api>',
headers: {
Authorization: {
toString () {
return `Bearer ${localStorage.getItem('token')}`
}
}
}
})
Je ne sais pas si cela fonctionne dans tous les cas.
Mon fichier http.js
 :
import axios from 'axios';
import {store} from './store';
const http = axios.create ({
baseURL: process.env.VUE_APP_ROOT_API,
timeout: 1000,
headers: {'Content-Type': 'application/json'},
});
http.interceptors.request.use (
function (config) {
const token = store.token;
if (token) config.headers.Authorization = `Bearer ${token}`;
return config;
},
function (error) {
return Promise.reject (error);
}
);
export default http;
Mon magasin, une simple "classe" get/set
export const store = {
_username: '',
_email: '',
_token: '',
isLogged () {
return this.token
},
set username (str) {
this._username = str
localStorage.setItem('username',str)
},
get username () {
return this._username || localStorage.getItem('username')
},
set email (str) {
this._email = str
localStorage.setItem('email',str)
},
get email () {
return this._email || localStorage.getItem('email')
},
set token (str) {
this._token = str
localStorage.setItem('token',str)
},
get token () {
return this._token || localStorage.getItem('token')
}
}
Mon service utilisateur "classe":
import http from './http'
export const user = {
ping: () => http.get('/users/ping'),
save: (user) => http.post('/users', user)
}
et enfin, mon implémentation :
import {user} from '@/services'
user.ping().then( r => {
console.log(r.data)
})
d'ailleurs,
process.env.VUE_APP_ROOT_API
et@/services
sont des choses de Vue...
RĂ©sultat:
@danielschmitz merci pour cet exemple !!
On dirait que vous avez tous compris cela et que ce n'est pas un bug, alors je ferme ça đ
J'ai trouvé utile d'envelopper l'intercepteur dans async/wait pour m'assurer que mon jeton était défini avant le déclenchement de l'appel d'API :
http.interceptors.request.use (
async (config) => {
const token = await getToken(); // slightly longer running function than example above
if (token) config.headers.Authorization = `Bearer ${token}`;
return config;
},
(error) => {
return Promise.reject (error);
}
);
J'ai utilisĂ© des intercepteurs Ă cette fin. Si l'URL de base de la demande correspond Ă mon API, j'ajoute l'en-tĂȘte auth (pour empĂȘcher l'envoi d'informations d'identification Ă des tiers). Ceci est exĂ©cutĂ© Ă chaque demande, donc si le jeton change (par exemple Ă la suite d'une actualisation du jeton), la demande suivante rĂ©cupĂšre le nouveau jeton. Je m'assure Ă©galement de vĂ©rifier les valeurs existantes dans la demande pour permettre le remplacement de l'en-tĂȘte du site d'appel si cela s'avĂ©rait nĂ©cessaire pour une raison quelconque.
axios.interceptors.request.use( config => { if (config.baseURL === baseApiAddress && !config.headers.Authorization) { const token = getToken(); if (token) { config.headers.Authorization = `Bearer ${token}`; } } return config; }, error => Promise.reject(error) );
Interceptor semble ĂȘtre la solution la plus Ă©lĂ©gante
Commentaire le plus utile
J'ai utilisĂ© des intercepteurs Ă cette fin. Si l'URL de base de la demande correspond Ă mon API, j'ajoute l'en-tĂȘte auth (pour empĂȘcher l'envoi d'informations d'identification Ă des tiers). Ceci est exĂ©cutĂ© Ă chaque demande, donc si le jeton change (par exemple Ă la suite d'une actualisation du jeton), la demande suivante rĂ©cupĂšre le nouveau jeton. Je m'assure Ă©galement de vĂ©rifier les valeurs existantes dans la demande pour permettre le remplacement de l'en-tĂȘte du site d'appel si cela s'avĂ©rait nĂ©cessaire pour une raison quelconque.