import { Request, Response } from "express"; import RequestError, { HttpStatusCode } from "../../helper/request_error"; import User from "../../models/user"; import Client from "../../models/client"; import getOAuthJWT from "../../helper/jwt"; import Stacker from "../middlewares/stacker"; import { GetClientAuthMiddleware } from "../middlewares/client" import ClientCode from "../../models/client_code"; import Mail from "../../models/mail"; import { randomBytes } from "crypto"; import moment = require("moment"); import { JWTExpDur } from "../../keys"; import RefreshToken from "../../models/refresh_token"; import { getEncryptionKey } from "../../helper/user_key"; const RefreshTokenRoute = Stacker(GetClientAuthMiddleware(false, false, true), async (req: Request, res: Response) => { let grant_type = req.query.grant_type || req.body.grant_type; if (!grant_type || grant_type === "authorization_code") { let code = req.query.code || req.body.code; let c = await ClientCode.findOne({ code: code }) if (!c) { throw new RequestError(req.__("Invalid code"), HttpStatusCode.BAD_REQUEST); } let client = await Client.findById(c.client); let user = await User.findById(c.user); let mails = await Promise.all(user.mails.map(m => Mail.findOne(m))); let token = RefreshToken.new({ user: c.user, client: c.client, permissions: c.permissions, token: randomBytes(16).toString("hex"), valid: true, validTill: moment().add(6, "months").toDate() }); await RefreshToken.save(token); await ClientCode.delete(c); let mail = mails.find(e => e.primary); if (!mail) mail = mails[0]; res.json({ refresh_token: token.token, token: token.token, access_token: await getOAuthJWT({ client: client, user: user, permissions: c.permissions }), token_type: "bearer", expires_in: JWTExpDur.asSeconds(), profile: { uid: user.uid, email: mail ? mail.mail : "", name: user.name, enc_key: getEncryptionKey(user, client) } }); } else if (grant_type === "refresh_token") { let refresh_token = req.query.refresh_token || req.body.refresh_token; if (!refresh_token) throw new RequestError(req.__("refresh_token not set"), HttpStatusCode.BAD_REQUEST); let token = await RefreshToken.findOne({ token: refresh_token }); if (!token) throw new RequestError(req.__("Invalid token"), HttpStatusCode.BAD_REQUEST); let user = await User.findById(token.user); let client = await Client.findById(token.client) let jwt = await getOAuthJWT({ user, client, permissions: token.permissions }); res.json({ access_token: jwt, expires_in: JWTExpDur.asSeconds() }); } else { throw new RequestError("invalid grant_type", HttpStatusCode.BAD_REQUEST); } }) export default RefreshTokenRoute;