Is there a way to do role based permissions in middleware?
I'm asking this because I was hoping that there would be a way to call getSession in middleware.
Otherwise I would need to implement a helper function hasPermissions(req)
, import it and call it in every single file and I'm trying to avoid that
Thanks
if you do not want to use third party authenticatio server and you want to do on your own, you could write this with using cookeis and jwt.
1- when users logins set a jwt token. In next.js when user logins, make a request to api function and api function should handle the login process:
import jwt from "jsonwebtoken";
const handleLoginWithEmail = async (e) => {
e.preventDefault();
if (email) {
try {
//... add your logic, set state
// make a
const response = await fetch("/api/login", {
method: "POST",
headers: {
// pass this if you are using passwdrdless or other service that needs token
Authorization: `Bearer ${ifToken}`,
"Content-Type": "application/json",
},
});
} catch (error) {
console.error("Something went wrong logging in", error);
}
}
};
your api function should create a jwt
export default async function login(req, res) {
if (req.method === "POST") {
try {
// if there is
const auth = req.headers.authorization;
// add your logic
const token = jwt.sign(
{
...metadata,
iat: Math.floor(Date.now() / 1000),
exp: Math.floor(Date.now() / 1000 + 7 * 24 * 60 * 60),
// I just create a custom object
"roles": {
"allowed-roles": ["user", "admin"],
"default-role": "user",
// you could decide the role based on email or userId. write your logic
"role":"user"
},
},
process.env.JWT_SECRET
);
// set the token
setTokenCookie(token, res);
res.send({ done: true });
} catch (error) {
console.error("Something went wrong logging in", error);
res.status(500).send({ done: false });
}
} else {
res.send({ done: false });
}
}
2- write a set cookie function used in above api function
import cookie from "cookie";
const MAX_AGE = 7 * 24 * 60 * 60;
export const setTokenCookie = (token, res) => {
const setCookie = cookie.serialize("token", token, {
maxAge: MAX_AGE,
expires: new Date(Date.now() + MAX_AGE * 1000),
secure: process.env.NODE_ENV === "production",
path: "/",
});
res.setHeader("Set-Cookie", setCookie);
};
3- write a verify token function
import jwt from "jsonwebtoken";
export async function verifyToken(token) {
if (token) {
const decodedToken = jwt.verify(token, process.env.JWT_SECRET);
console.log("decodedToken",decodedToken)
// get the token role from decodedToken
const userId = decodedToken?.issuer;
return {userId,role};
}
return null;
}
4- Finally in _middleware.js function:
export async function middleware(req, ev) {
console.log("ev in middleware", ev);
const token = req ? req.cookies?.token : null;
const {userId,role} = await verifyToken(token);
// got the role and add logic for role
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With