improve login system on the server
This commit is contained in:
parent
d24929da0c
commit
ee2e192204
6 changed files with 86 additions and 25 deletions
|
@ -2,11 +2,17 @@ import EventEmitter from "events";
|
|||
import zlib from "zlib";
|
||||
import { WebSocket } from "ws";
|
||||
import fetch from "node-fetch";
|
||||
import { logger } from "./common.js";
|
||||
|
||||
const log = logger("log", "DiscordClient");
|
||||
const logError = logger("error", "DiscordClient");
|
||||
const logWarn = logger("warn", "DiscordClient");
|
||||
|
||||
const opcodes = {
|
||||
EVENT: 0,
|
||||
CLIENT_HEARTBEAT: 1,
|
||||
IDENTIFY: 2,
|
||||
RECONNECT: 7,
|
||||
INVALID_SESSION: 9,
|
||||
HELLO: 10,
|
||||
HEARTBEAT_ACK: 11,
|
||||
|
@ -82,7 +88,7 @@ class DiscordClient extends EventEmitter {
|
|||
try {
|
||||
message = JSON.parse(message);
|
||||
} catch(e) {
|
||||
console.error("error: DiscordClient: on 'message': failed to parse incoming message as JSON", e);
|
||||
logError("on 'message': failed to parse incoming message as JSON", e);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -94,7 +100,7 @@ class DiscordClient extends EventEmitter {
|
|||
|
||||
switch (message.op) {
|
||||
case opcodes.HELLO: {
|
||||
console.log(`DiscordClient: HELLO; heartbeat_interval=${payload.heartbeat_interval}`);
|
||||
log(`HELLO; heartbeat_interval=${payload.heartbeat_interval}`);
|
||||
this._setHeartbeat(payload.heartbeat_interval);
|
||||
|
||||
ws.send(JSON.stringify({
|
||||
|
@ -107,7 +113,7 @@ class DiscordClient extends EventEmitter {
|
|||
case opcodes.EVENT: {
|
||||
switch (message.t) {
|
||||
case "READY": {
|
||||
console.log("DiscordClient: READY");
|
||||
log("READY");
|
||||
this.user = payload.user;
|
||||
this.sessionId = payload.session_id;
|
||||
this.guilds = payload.guilds;
|
||||
|
@ -194,22 +200,28 @@ class DiscordClient extends EventEmitter {
|
|||
}
|
||||
|
||||
case opcodes.INVALID_SESSION: {
|
||||
console.error("DiscordClient: INVALID_SESSION - please check your authentication token");
|
||||
console.error("DiscordClient: INVALID_SESSION: will not reconnect");
|
||||
logError("INVALID_SESSION - please check your authentication token");
|
||||
logError("INVALID_SESSION: will not reconnect");
|
||||
break;
|
||||
}
|
||||
|
||||
case opcodes.RECONNECT: {
|
||||
log("gateway is requesting reconnect (payload RECONNECT)");
|
||||
this.connect();
|
||||
break;
|
||||
}
|
||||
|
||||
default: {
|
||||
console.warn(`warn: DiscordClient: got unhandled opcode "${message.op}"`);
|
||||
logWarn(`got unhandled opcode "${message.op}"`);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
connect() {
|
||||
console.log("DiscordClient: connecting...");
|
||||
log("connecting...");
|
||||
if (this.ws) {
|
||||
console.log("DiscordClient: a websocket connection already exists, killing...");
|
||||
log("a websocket connection already exists, killing...");
|
||||
this.ws.removeAllListeners();
|
||||
this.ws.close();
|
||||
this.ws = null;
|
||||
|
@ -233,26 +245,26 @@ class DiscordClient extends EventEmitter {
|
|||
|
||||
|
||||
ws.on("open", () => {
|
||||
console.log("DiscordClient: WebSocket 'open'")
|
||||
log("WebSocket 'open'");
|
||||
});
|
||||
|
||||
ws.on("close", (code, reason) => {
|
||||
reason = reason.toString();
|
||||
console.error(`DiscordClient: on 'close': disconnected from gateway: code '${code}', reason '${reason}'`);
|
||||
logError(`on 'close': disconnected from gateway: code '${code}', reason '${reason}'`);
|
||||
|
||||
this.emit("close", code, reason);
|
||||
this._setHeartbeat(-1);
|
||||
if (skipReconnectFor.includes(code)) {
|
||||
console.error("DiscordClient: on 'close': the exit code above is in skipReconnectFor, and thus the server will not reconnect.");
|
||||
logError("on 'close': the exit code above is in skipReconnectFor, and thus the server will not reconnect.");
|
||||
} else {
|
||||
console.log("DiscordClient: on 'close': the client will now attempt to reconnect...");
|
||||
log("on 'close': the client will now attempt to reconnect...");
|
||||
this.connect();
|
||||
}
|
||||
});
|
||||
|
||||
ws.on("error", (e) => {
|
||||
console.error("DiscordClient: on 'error': websocket error:", e);
|
||||
console.log("DiscordClient: on 'error': reconnecting due to previous websocket error...");
|
||||
logError("on 'error': websocket error:", e);
|
||||
log("on 'error': reconnecting due to previous websocket error...");
|
||||
this._setHeartbeat(-1);
|
||||
this.connect();
|
||||
});
|
||||
|
|
|
@ -99,7 +99,6 @@ class GatewayServer {
|
|||
try {
|
||||
message = JSON.parse(message.toString());
|
||||
} catch (e) {
|
||||
console.error("GatewayServer: payload decode error", e);
|
||||
return ws.close(4000, "Payload error.");
|
||||
}
|
||||
|
||||
|
@ -113,7 +112,6 @@ class GatewayServer {
|
|||
try {
|
||||
user = await decodeToken(message.d.token);
|
||||
} catch(e) {
|
||||
console.error(e);
|
||||
ws.close(4001, "Bad token.");
|
||||
break;
|
||||
}
|
||||
|
|
32
common.js
32
common.js
|
@ -1,4 +1,4 @@
|
|||
import { discordToken, watchedGuildIds } from "./config.js";
|
||||
import { discordToken, logContextMap, watchedGuildIds } from "./config.js";
|
||||
import DiscordClient from "./DiscordClient.js";
|
||||
import WatchedGuild from "./WatchedGuild.js";
|
||||
|
||||
|
@ -13,6 +13,36 @@ export function wait(time, shouldReject=false) {
|
|||
});
|
||||
}
|
||||
|
||||
export function logger(sink, context) {
|
||||
let sinkFunction;
|
||||
switch (sink) {
|
||||
case "log": {
|
||||
sinkFunction = console.log;
|
||||
break;
|
||||
}
|
||||
case "warn": {
|
||||
sinkFunction = console.warn;
|
||||
break;
|
||||
}
|
||||
case "error": {
|
||||
sinkFunction = console.error;
|
||||
break;
|
||||
}
|
||||
default: {
|
||||
sinkFunction = () => {};
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (logContextMap[context] && logContextMap[context][sink]) {
|
||||
return (...e) => {
|
||||
sinkFunction(`[${context}]`, ...e);
|
||||
};
|
||||
} else {
|
||||
return (...e) => {};
|
||||
}
|
||||
}
|
||||
|
||||
bot.once("READY", () => {
|
||||
watchedGuildIds.forEach(id => {
|
||||
const watchedGuild = new WatchedGuild();
|
||||
|
|
17
config.js
17
config.js
|
@ -3,3 +3,20 @@ export const watchedGuildIds = ["822089558886842418", "736292509134749807"];
|
|||
export const jwtSecret = process.env.JWT_SECRET;
|
||||
export const discordToken = process.env.DISCORD_TOKEN;
|
||||
export const dangerousAdminMode = true;
|
||||
export const logContextMap = {
|
||||
DiscordClient: {
|
||||
log: true,
|
||||
warn: true,
|
||||
error: true,
|
||||
},
|
||||
ServerMain: {
|
||||
log: true,
|
||||
warn: true,
|
||||
error: true,
|
||||
},
|
||||
API: {
|
||||
log: true,
|
||||
warn: true,
|
||||
error: true,
|
||||
}
|
||||
};
|
||||
|
|
6
index.js
6
index.js
|
@ -2,9 +2,11 @@ import http from "node:http";
|
|||
import express from "express";
|
||||
import apiRoute from "./routes/api.js";
|
||||
import { mainHttpListenPort } from "./config.js";
|
||||
import { bot } from "./common.js";
|
||||
import { bot, logger } from "./common.js";
|
||||
import GatewayServer from "./GatewayServer.js";
|
||||
|
||||
const log = logger("log", "ServerMain");
|
||||
|
||||
// might introduce bugs and probably a bad idea
|
||||
Object.freeze(Object.prototype);
|
||||
Object.freeze(Object);
|
||||
|
@ -21,6 +23,6 @@ app.use("/", express.static("frontend/public/"));
|
|||
app.use("/api/v1", apiRoute);
|
||||
|
||||
httpServer.listen(mainHttpListenPort, () => {
|
||||
console.log(`server main: listen on ${mainHttpListenPort}`);
|
||||
log(`http listen on ${mainHttpListenPort}`);
|
||||
bot.connect();
|
||||
});
|
|
@ -1,8 +1,10 @@
|
|||
import express from "express";
|
||||
import { guildMap, wait } from "../common.js";
|
||||
import { guildMap, logger } from "../common.js";
|
||||
import { dangerousAdminMode } from "../config.js";
|
||||
import { checkAuth, createToken } from "../tokens.js";
|
||||
|
||||
const error = logger("error", "API");
|
||||
|
||||
const router = express();
|
||||
|
||||
router.get("/", (req, res) => {
|
||||
|
@ -69,7 +71,7 @@ router.post("/guilds/:guildId/channels/:channelId/messages/create", checkAuth(as
|
|||
await guild.discordSendMessage(messageContent, channelId, username, avatarURL);
|
||||
res.status(201).send({ error: false });
|
||||
} catch(e) {
|
||||
console.error("server main: api: message create: error: ", e);
|
||||
error("[message create] [error]", e);
|
||||
res.status(500).send({ error: true, message: "ERROR_MESSAGE_SEND_FAILURE" });
|
||||
}
|
||||
}));
|
||||
|
@ -88,7 +90,7 @@ router.get("/guilds/:guildId/channels", checkAuth(async (req, res) => {
|
|||
try {
|
||||
res.status(200).send({ error: false, channels: guild.userFacingChannelList() });
|
||||
} catch(e) {
|
||||
console.error("server main: api: guild get channels: error: ", e);
|
||||
error("[guild get channels] [error]", e);
|
||||
res.status(500).send({ error: true, message: "ERROR_CHANNELS_FETCH_FAILURE" });
|
||||
}
|
||||
}));
|
||||
|
@ -107,7 +109,7 @@ router.get("/guilds/:guildId", checkAuth(async (req, res) => {
|
|||
try {
|
||||
res.status(200).send({ error: false, guild: guild.guildObject });
|
||||
} catch(e) {
|
||||
console.error("server main: api: guild get info: error: ", e);
|
||||
error("[guild get info]", e);
|
||||
res.status(500).send({ error: true, message: "ERROR_GUILD_INFO_FETCH_FAILURE" });
|
||||
}
|
||||
}));
|
||||
|
@ -133,7 +135,7 @@ router.get("/guilds/:guildId/events/poll", checkAuth(async (req, res) => {
|
|||
guild.holdForEvent(15000)
|
||||
.then(result => res.status(200).send({ error: false, event: result }));
|
||||
} catch(e) {
|
||||
console.error("server main: api: guild poll events: error: ", e);
|
||||
error("[guild poll events]", e);
|
||||
res.status(500).send({ error: true, message: "ERROR_POLL_FAILURE" });
|
||||
}
|
||||
}));
|
||||
|
@ -157,7 +159,7 @@ router.get("/events/poll", checkAuth(async (req, res) => {
|
|||
res.status(200).send({ error: false, event: e })
|
||||
});
|
||||
} catch(e) {
|
||||
console.error("server main: api: guild poll events: error: ", e);
|
||||
error("[guilds poll events]", e);
|
||||
res.status(500).send({ error: true, message: "ERROR_POLL_FAILURE" });
|
||||
}
|
||||
}));
|
||||
|
|
Loading…
Reference in a new issue