112 lines
3.8 KiB
TypeScript
112 lines
3.8 KiB
TypeScript
import jwt from "jsonwebtoken";
|
|
import { JWTData, JWTToken } from "../type/jwtTypes";
|
|
import { JWT_SECRET, JWT_EXPIRATION } from "../env.defaults";
|
|
import InternalException from "../exceptions/internalException";
|
|
import RolePermissionService from "../service/user/rolePermissionService";
|
|
import UserPermissionService from "../service/user/userPermissionService";
|
|
import UserService from "../service/user/userService";
|
|
import PermissionHelper from "./permissionHelper";
|
|
import WebapiService from "../service/user/webapiService";
|
|
import WebapiPermissionService from "../service/user/webapiPermissionService";
|
|
import ms from "ms";
|
|
|
|
export abstract class JWTHelper {
|
|
static validate(token: string): Promise<string | jwt.JwtPayload> {
|
|
return new Promise<string | jwt.JwtPayload>((resolve, reject) => {
|
|
jwt.verify(token, JWT_SECRET, (err, decoded) => {
|
|
if (err) reject(err.message);
|
|
else resolve(decoded);
|
|
});
|
|
});
|
|
}
|
|
|
|
static create(
|
|
data: JWTData,
|
|
{ expOverwrite, useExpiration }: { expOverwrite?: number; useExpiration?: boolean } = { useExpiration: true }
|
|
): Promise<string> {
|
|
return new Promise<string>((resolve, reject) => {
|
|
jwt.sign(
|
|
data,
|
|
JWT_SECRET,
|
|
{
|
|
...(useExpiration ?? true ? { expiresIn: expOverwrite ?? JWT_EXPIRATION } : {}),
|
|
},
|
|
(err, token) => {
|
|
if (err) reject(err.message);
|
|
else resolve(token);
|
|
}
|
|
);
|
|
});
|
|
}
|
|
|
|
static decode(token: string): Promise<string | jwt.JwtPayload> {
|
|
return new Promise<string | jwt.JwtPayload>((resolve, reject) => {
|
|
try {
|
|
let decoded = jwt.decode(token);
|
|
resolve(decoded);
|
|
} catch (err) {
|
|
reject(err.message);
|
|
}
|
|
});
|
|
}
|
|
|
|
static async buildToken(id: number): Promise<string> {
|
|
let { firstname, lastname, mail, username, isOwner } = await UserService.getById(id);
|
|
let userPermissions = await UserPermissionService.getByUser(id);
|
|
let userPermissionStrings = userPermissions.map((e) => e.permission);
|
|
let userRoles = await UserService.getAssignedRolesByUserId(id);
|
|
let rolePermissions =
|
|
userRoles.length != 0 ? await RolePermissionService.getByRoles(userRoles.map((e) => e.id)) : [];
|
|
let rolePermissionStrings = rolePermissions.map((e) => e.permission);
|
|
let permissionObject = PermissionHelper.convertToObject([...userPermissionStrings, ...rolePermissionStrings]);
|
|
|
|
let jwtData: JWTToken = {
|
|
userId: id,
|
|
mail: mail,
|
|
username: username,
|
|
firstname: firstname,
|
|
lastname: lastname,
|
|
isOwner: isOwner,
|
|
permissions: permissionObject,
|
|
};
|
|
|
|
return await JWTHelper.create(jwtData)
|
|
.then((result) => {
|
|
return result;
|
|
})
|
|
.catch((err) => {
|
|
throw new InternalException("Failed accessToken creation", err);
|
|
});
|
|
}
|
|
|
|
static async buildWebapiToken(token: string, expiration?: Date): Promise<string> {
|
|
let { id, title } = await WebapiService.getByToken(token);
|
|
let webapiPermissions = await WebapiPermissionService.getByApi(id);
|
|
let webapiPermissionStrings = webapiPermissions.map((e) => e.permission);
|
|
let permissionObject = PermissionHelper.convertToObject(webapiPermissionStrings);
|
|
|
|
let jwtData: JWTToken = {
|
|
userId: id,
|
|
mail: "",
|
|
username: title,
|
|
firstname: "",
|
|
lastname: "",
|
|
isOwner: false,
|
|
permissions: permissionObject,
|
|
sub: "webapi_access_token",
|
|
};
|
|
|
|
let overwriteExpiration =
|
|
ms(JWT_EXPIRATION) < new Date().getTime() - new Date(expiration).getTime()
|
|
? null
|
|
: Date.now() - new Date(expiration).getTime();
|
|
|
|
return await JWTHelper.create(jwtData, { expOverwrite: overwriteExpiration, useExpiration: true })
|
|
.then((result) => {
|
|
return result;
|
|
})
|
|
.catch((err) => {
|
|
throw new InternalException("Failed webapi accessToken creation", err);
|
|
});
|
|
}
|
|
}
|