import { Request as ExpressRequest, Response as ExpressResponse } from "express"; import { DiscordAPI } from "src/utils/util"; import { Option, tryDo } from "@shared/common/async_utils"; import { eventLogger, logger } from "src/utils/logging"; import { rpcClient } from "src/utils/rpc"; import { ENV } from "src/utils/environment"; export const get = async (req: ExpressRequest, res: ExpressResponse): Promise => { res.redirect(DiscordAPI.getAuthUrl({ client_id: ENV.BOT_CLIENT_ID, redirect_url: ENV.WEB_AUTH_URI, response_type: "code", scope: "identify", })); }; type AuthResult = Option; export const post = async (req: ExpressRequest, res: ExpressResponse): Promise> => { if (!req.session) { logger.warn("WEB: req.session is not set up correctly!"); return res.json({ ok: false, error: "No session is set up. This is a server error!", }); } if (!req.session.authTokenCode) { logger.warn("WEB: attempted to join with no authTokenCode set!"); eventLogger.warn("IP %s attempted to join with no authTokenCode set", req.ip); return res.json({ ok: false, error: "Authentication token is missing. Please try logging in again.", }); } const tokenResult = await DiscordAPI.getToken({ client_id: ENV.BOT_CLIENT_ID, client_secret: ENV.BOT_CLIENT_SECRET, grant_type: "authorization_code", code: req.session.authTokenCode, scope: "identify", redirect_uri: ENV.WEB_AUTH_URI, }); if (!tokenResult.ok) { return res.json(tokenResult); } const userResult = await DiscordAPI.getCurrentUser(tokenResult.access_token); if (!userResult.ok) { return res.json(userResult); } const userInServerResult = await tryDo(rpcClient.userInServer({ userId: userResult.id })); if (!userInServerResult.ok) { logger.error("WEB: failed to auth user %s: %s", userResult.id, userInServerResult.error); return res.json({ ok: false, error: "Couldn't determine if user joined the server, please try again later" }); } eventLogger.info("%s#%s authed from %s", userResult.username, userResult.discriminator, req.ip); logger.verbose("Logged in as %s#%s (%s); user in server: (%s)", userResult.username, userResult.discriminator, userResult.id, userInServerResult.result.exists); if (!userInServerResult.result.exists) { return res.json({ ok: false, error: "You haven't joined any servers NoctBot manages! Please join first and try again!" }); } req.session.authTokenCode = undefined; req.session.userId = userResult.id; req.session.avatarId = userResult.avatar; req.session.username = `${userResult.username}#${userResult.discriminator}`; req.sessionOptions.maxAge = tokenResult.expires_in; return res.json({ ok: true, }); };