I make web application using react js, node, express
when I login the error message appear says "No token attached"
now I need to put a jwt token into header how can I do that
this is my code:
import { webToken } from "../crypto/web_token.js";
import { responses } from "../classes/responses.js";
export const verifyRequest = (req, res, nex) => {
try {
if (!req.headers.authorization) {
throw Error("no token attached");
}
const token = req.headers.authorization.split(" ")[1];
const payload = webToken.verify(token);
req.user = payload;
nex();
} catch (error) {
res.json(new responses.Error(error.message));
}
};
another code: web_token.js
import jsonwebtoken from "jsonwebtoken";
import { errors } from "../classes/errors.js";
const secret = "#########";
export const webToken = Object.freeze({
generate: (data, expiry = "1hr") => {
try {
return jsonwebtoken.sign(data, secret, { expiresIn: expiry });
} catch (error) {
throw new errors.Logic("Internal error from the bcrypt hashing", "jwt");
}
},
verify: (token) => {
try {
const data = jsonwebtoken.verify(token, secret);
return data;
} catch (error) {
throw new errors.Authentication(
error.message.replace("jwt", "Token"),
"jwt"
);
}
},
});
here is the template, take a look
var axios = require('axios');
var data = JSON.stringify({
"value1": "val1"
});
var config = {
method: 'post',
url: 'http://localhost:3000/GetText',
headers: {
'Authorization': `Bearer ${token}`,
'Content-Type': 'application/json'
},
data : data
};
axios(config)
.then(function (response) {
console.log(JSON.stringify(response.data));
})
.catch(function (error) {
console.log(error);
});
Related
Trying to store jwt token on login using rxjs behavioursubject
Then creating a http request with Authorization: Bearer ${user.jwtToken} in the
I believe I need to have
a) initial value,
b) a source that can be turned into an observable
c) a public variable that can be subscribed
On log in the user is correctly added to the user subject here "userSubject.next(user);"
But whenever I try to create the bearer token its always null
// The Accounts Service
// initialise and set initial value
const userSubject = new BehaviorSubject(null);
const authApiUrl = "https:testApi";
export const accountService = {
` user: userSubject.asObservable(), get userValue() { return userSubject.value },
login,
getAllUsers
};
function login(email, password) {
return fetchWrapper.post(process.env.AuthApiUrl + '/accounts/authenticate', { email, password })
.then(user => {
userSubject.next(user);
localStorage.setItem('user', JSON.stringify(user));
return user;
});
}
function getAllUsers() {
return await fetchWrapper.get(process.env.AuthApiUrl + '/accounts/get-all-users');
}
}
// The fetchwrapper
export const fetchWrapper = {
get,
post
};
function post(url, body) {
const requestOptions = {
method: 'POST',
headers: { 'Content-Type': 'application/json', ...authHeader(url) },
credentials: 'include',
body: JSON.stringify(body)
};
return fetch(url, requestOptions).then(handleResponse);
}
function get(url) {
const requestOptions = {
method: 'GET',
headers: authHeader(url)
};
return fetch(url, requestOptions).then(handleResponse);
}
function authHeader(url) {
// return auth header with basic auth credentials if user is logged in and request is to the api url
// THE accountService.userValue IS ALWAYS NULL???
const user = accountService.userValue;
const isLoggedIn = user && user.jwtToken;
const isApiUrl = url.startsWith(process.env.AuthApiUrl);
if (isLoggedIn && isApiUrl) {
return { Authorization: `Bearer ${user.jwtToken}` };
} else {
return {};
}
}
function handleResponse(response) {
return response.text().then(text => {
const data = text && JSON.parse(text);
if (!response.ok) {
if ([401, 403].includes(response.status) && accountService.userValue) {
// auto logout if 401 Unauthorized or 403 Forbidden response returned from api
accountService.logout();
}
const error = (data && data.message) || response.statusText;
return Promise.reject(error);
}
return data;
});
}
Can someone tell me what mistake I am making or tell me how to set the header in axios patch request. when I am running the API through postman, everything is working fine but when I connect it with the front end, an error comes up saying that the JWT is not provided on the backend
here is the frond end code :
import React, { useEffect } from 'react';
import { useParams } from 'react-router';
import axios from 'axios';
const Loader = () => {
const parmas = useParams();
const { id } = parmas;
console.log(id);
useEffect(() => {
const fetchBags = async () => {
try {
const res = await axios.patch('http://localhost:4001/public/verify', {
headers: {
'Content-Type': 'application/json',
Token: id,
},
});
console.log(res);
console.log('CBM', { res });
} catch (error) {
console.log(error);
}
};
fetchBags();
}, []);
return <div>this is loader</div>;
};
export default Loader;
below is my backend code:
export const verifyUser = async (data) => {
const token1 = data.header("Token");
try {
const verified = jwt.verify(token1, getTokenSecret());
console.log(verified)
await userModel.verifyUser(verified);
return {
message: "success",
};
} catch (error) {
console.log(`Auth Service > verifyUser > ${error.toString()}`);
throw error;
}
};
this error is comming:
Error
From docs
axios.patch(url[, data[, config]])
As you can see you pass config in 3rd argument not 2nd.
const res = await axios.patch(
'http://localhost:4001/public/verify',
{}, // data (2nd argument)
{
headers: {
'Content-Type': 'application/json',
Token: id,
},
} // config (3rd argument)
)
Access to XMLHttpRequest at 'http://localhost:3030/socket.io/?EIO=3&transport=polling&t=NHnZ9gy' from origin 'http://localhost:3000' has been blocked by CORS policy: The value of the 'Access-Control-Allow-Origin' header in the response must not be the wildcard '*' when the request's credentials mode is 'include'. The credentials mode of requests initiated by the XMLHttpRequest is controlled by the withCredentials attribute.
============================== node socket code
import socketIO from 'socket.io';
import jwt from 'jsonwebtoken';
import { get } from 'lodash';
async function authMiddleware(app, socket, next) {
try {
const token = get(socket.request.headers, 'authorization', null);
if (!token) {
return next(new Error('Invalid authentication token'));
}
// Validate access token
const appSecret = app.get('config').appSecret;
// Invalid authorization header
const tokenValues = token.split(' ');
if (tokenValues.length !== 2) { throw new Error('Invalid token'); }
if (tokenValues[0] !== appSecret.tokenType) { throw new Error('Invalid token'); }
// Decode token and inject user data in request
const payload = await jwt.verify(tokenValues[1], appSecret.key);
// Find user
const User = app.get('models').user;
const userQuery = { where: { id: payload.id } };
const user = await User.findOne(userQuery);
if (!user) { throw new Error('No user found'); }
// Set user instance to socket
socket.user = user;
return next();
} catch (err) {
return next(err);
}
}
export default function (app) {
const io = socketIO(app.server, {
handlePreflightRequest(req, res) {
const headers = {
'Access-Control-Allow-Headers': 'Content-Type, Authorization',
'Access-Control-Allow-Origin': req.headers.origin,
'Access-Control-Allow-Credentials': true,
'Access-Control-Allow-Origin': '*',
'Access-Control-Allow-Methods': 'GET,PUT,POST,DELETE,PATCH,OPTIONS'
//'Access-Control-Allow-Origin': '*://*'
};
res.writeHead(200, headers);
res.end();
}
});
// const io = socketIO(app.server);
//io.origins('*:*')
io.use((socket, next) => authMiddleware(app, socket, next));
console.log("Socket call");
io.on('connection', socket => {
// On connect, join the socket to user room
const user = socket.user;
if(user.type == 'Processor'){
socket.join("Processor-"+user.companyId);
} else if(user.type == 'Admin'){
socket.join("Processor-"+user.companyId);
}
else{
socket.join("Customer-");
}
console.log(socket.id,"Joins",user.type+"-"+user.companyId);
if (user) {
socket.on(`syncDriverLocation-${user.id}`, payload => {
const { tripId, isDbUpdate, latitude, longitude } = payload;
socket.broadcast.emit(`syncDriverToTrip-${tripId}`, payload);
// if (isDbUpdate) {
const driverLocation = {
type: 'Point',
coordinates: [longitude, latitude]
};
console.log('driverLocation',driverLocation)
const Trip = app.get('models').trip;
Trip.findOne({ where: { id: tripId }}).then((trip) => {
trip.update({ driverLocation }).then();
});
console.log('Trip',Trip)
const TripLocation = app.get('models').tripLocation;
TripLocation.create({
tripId,
driverLocation: {
type: 'Point',
coordinates: [longitude, latitude]
},
}).then();
// }
});
}
});
app.set('io', io);
}
===================================
this is my initialize code in react
this.socket = io('http://localhost:3030'
, {
reconnect: true,
transportOptions: {
polling: { extraHeaders: {
authorization: getAccessHeader()
} }
}
}
);
this.socket.on("connect", () => {
console.log(`===============Socket Connected(${this.socket.id})===============`);
}).on("error",(err) => {
console.log(
`===============Socket error===============`,err
);
})
this.socket.on("disconnect", () => {
console.log(`===============Socket Disconnected===============`);
});
This is React native expo mobile app. I'm using NodeJs Server to get data from Firestore. Postman api fetch data properly.
Cannot fetch data from react native mobile app.
Postman Output
"customer": [
{
"phone":12345,
"username": "customer1",
},
]
Redux action.js
import { SET_CUSTOMERS } from "../types";
import { create } from "axios";
import { auth } from "../../firebase";
const baseURL = "https://...../api/";
const API = create({
baseURL: baseURL,
timeout: 60000,
"Content-Type": "application/json",
});
export const getCustomers = () => {
return async (dispatch) => {
try {
const token = await auth.currentUser.getIdToken();
console.log("token ", token); //Working Well
const response = API({
url: "customers",
headers: {
Authorization: `Bearer ${token}`,
},
});
console.log(response); //NOT Working
dispatch({ type: SET_CUSTOMERS, payload: response.data });
} catch (error) {
console.log(error);
throw error;
}
};
};
Redux reducer.js
import { SET_CUSTOMERS } from "../types";
const initialState = {
customers: [],
};
export default (state = initialState, action) => {
switch (action.type) {
case SET_CUSTOMERS:
return {
...state,
customers: action.payload,
};
default:
return state;
}
};
import React, { useState, useEffect, useCallback } from "react";
import { useSelector, useDispatch } from "react-redux";
import { getCustomers } from "../store/actions/data";
const UserProfileView = (props) => {
const [error, setError] = useState();
const customers = useSelector((state) => state.data.customers);
const dispatch = useDispatch();
const loadCustomers = useCallback(async () => {
setError(null);
try {
await dispatch(getCustomers());
} catch (err) {
setError(err.message);
}
}, [dispatch, setError]);
useEffect(() => {
loadCustomers;
}, [loadCustomers]);
return (
<View>
<Text>Customer Details</Text>
</View>
);
};
Expected Output payload: response.data pass response.data array
export const getCustomers = () => {
return async (dispatch) => {
try {
const token = await auth.currentUser.getIdToken();
console.log("token ", token); //Working Well
const response = API({
url: "customers",
headers: {
Authorization: `Bearer ${token}`,
},
});
console.log(response); //NOT Working
dispatch({ type: SET_CUSTOMERS, payload: response.data });
} catch (error) {
console.log(error);
throw error;
}
};
};
I am working on a web-app using node.js and vue.js, I am doing authentication and maintaining session using jwt and passport.js using passport-jwtstrategy
I have done all the things from creating jwt to protecting routes all the things now my issue is while generating jwt I am passing expiresIn:3600 so I want to auto-logout my user from Ui and remove token from localStorage once it has been one hour
On decoding my jwt I am getting
{
"name": "Dheeraj",
"iat": 1571896207,
"exp": 1571899807
}
So how can I get the real-time when to logout
In my auth.js vue store file my logout code when user clicks on logout is
logout({ commit }) {
return new Promise((resolve, reject) => {
localStorage.removeItem('jwt-token')
localStorage.removeItem('user-name')
commit('setAuthUser', null)
resolve(true)
})
},
In the same file, I have a method getAuthUser which is running whenever a page is loading or reloading to check to protect rout and guestUser
getAuthUser({ commit, getters }) {
const authUser = getters['authUser']
const token = localStorage.getItem('jwt-token')
const isTokenValid = checkTokenValidity(token)
if (authUser && isTokenValid) {
return Promise.resolve(authUser)
}
commit('setAuthUser', token)
commit('setAuthState', true)
debugger
return token
}
So how can I logout once my token is expired
Anyone out here please guide me how can I logout once the token is expired
Edit
In my router.js file
router.beforeEach((to, from, next) => {
store.dispatch('auth/getAuthUser')
.then((authUser) => {
const isAuthenticated = store.getters['auth/isAuthenticated']
if (to.meta.onlyAuthUser) {
if (isAuthenticated) {
next()
} else {
next({ name: 'login' })
}
} else if (to.meta.onlyGuestUser) {
if (isAuthenticated) {
next({ name: 'welcome' })
} else {
next()
}
} else {
next()
}
})
})
from my auth file I am calling get authUser which I have already mention above
for checking token validity I am using this code
function checkTokenValidity(token) {
if (token) {
const decodedToken = jwt.decode(token)
return decodedToken && (decodedToken.exp * 1000) > new Date().getTime()
}
return false
}
but it returns false when I am on login page and there is no token there but once I am loged in it shows null
My global api file
import axios from 'axios';
export default () => {
let headers = {
'cache-control': 'no-cache'
};
let accessToken = localStorage.getItem('jwt-token');
if (accessToken && accessToken !== '') {
headers.Authorization = accessToken;
};
return axios.create({
baseURL: 'http://localhost:8086/',
headers: headers
});
}
Refer to the axios documentataion: https://github.com/axios/axios
import axios from 'axios';
export default () => {
let headers = {
'cache-control': 'no-cache'
};
let accessToken = localStorage.getItem('jwt-token');
if (accessToken && accessToken !== '') {
headers.Authorization = accessToken;
};
const instance = axios.create({
baseURL: 'http://localhost:8086/',
headers: headers
});
instance.interceptors.response.use((response) => {
if(response.status === 401) {
//add your code
alert("You are not authorized");
}
return response;
}, (error) => {
if (error.response && error.response.data) {
//add your code
return Promise.reject(error.response.data);
}
return Promise.reject(error.message);
});
return instance;
}