Skip to content

Commit b7ee8df

Browse files
committed
Merge branch 'main' into DRY
2 parents 2ec02db + 7d0b42f commit b7ee8df

File tree

6 files changed

+47
-7
lines changed

6 files changed

+47
-7
lines changed

Dockerfile

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ COPY package.json ./
1818
COPY package-lock.json ./
1919

2020
# Setup the application itself
21-
RUN npm install --silent
21+
RUN npm install
2222

2323
COPY . ./
2424

@@ -28,4 +28,4 @@ RUN npm run build
2828
ENTRYPOINT [ "npm", "run", "start" ]
2929

3030
# For debugging.
31-
# ENTRYPOINT ["tail", "-f", "/dev/null"]
31+
# ENTRYPOINT ["tail", "-f", "/dev/null"]

config/.env-example

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,5 +18,3 @@ WEBHOOK_UPDATE_SECRET = ""
1818
# https://profile.intra.42.fr/oauth/applications/8540
1919
INTRA_UID = ""
2020
INTRA_SECRET = ""
21-
22-
SENTRY_SECRET = ""

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@
2626
"ts-node-dev": "^1.1.6"
2727
},
2828
"scripts": {
29-
"prepare": "[ -d .git ] && (P=.git/hooks/pre-commit; echo \"#!/bin/sh\\nnpm run lint:check\" > $P; chmod 777 $P)",
29+
"prepare": "[ -d .git ] && (P=.git/hooks/pre-commit; echo \"#!/bin/sh\\nnpm run lint:check\" > $P; chmod 777 $P) || true",
3030
"dev": "ts-node-dev --quiet --rs --respawn --clear --transpile-only src/app.ts",
3131
"init-db": "sqlite3 ./db/peerdb.sqlite < ./sql/default.sql",
3232
"build": "tsc",

sql/default.sql

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ CREATE TABLE IF NOT EXISTS expiredTeam(
55
created_at INTEGER DEFAULT (datetime('now', 'localtime'))
66
);
77

8+
-- Students that want to receive notifcations.
89
CREATE TABLE IF NOT EXISTS evaluators(
910
intraUID INTEGER PRIMARY KEY NOT NULL,
1011
slackUID varchar(512) NOT NULL,
@@ -16,3 +17,9 @@ CREATE TABLE IF NOT EXISTS evaluators(
1617

1718
notifyOfNewLock BOOLEAN NOT NULL
1819
);
20+
21+
-- Avoid duplicate deliveries.
22+
CREATE TABLE IF NOT EXISTS webhookDeliveries(
23+
delivery varchar(1024) PRIMARY KEY NOT NULL,
24+
body varchar(65535) NOT NULL
25+
)

src/bots/webhook.ts

Lines changed: 29 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,9 +14,35 @@ import { IntraWebhook } from "../utils/types";
1414
import Logger, { LogType } from "../utils/logger";
1515
import { Request, Response, NextFunction } from "express";
1616
import * as Checks from "../checks/evaluators";
17+
import db from "../db";
1718

1819
/*============================================================================*/
1920

21+
// Intra, like many distributed systems will sometimes deliver the same webhook > 1 times
22+
// This is where we filter those situations
23+
async function filterAlreadyDeliveredWebhook(req: Request) {
24+
const headerKey = "x-delivery";
25+
const id = req.headers[headerKey];
26+
if (!id || typeof id !== "string") {
27+
Logger.log(`WEBHOOK: Request header "${headerKey}" has invalid value of: "${id}"`);
28+
return false;
29+
}
30+
31+
const hasDelivery = await db.hasWebhookDelivery(id).catch((e) => {
32+
Logger.log(`WEBHOOK: Could not load from db: ${e}`);
33+
return false;
34+
});
35+
if (hasDelivery) {
36+
return true;
37+
}
38+
39+
await db.addWebhookDelivery(id, JSON.stringify(req.body)).catch((e) => {
40+
Logger.log(`WEBHOOK: Could not add webhook delivery: ${e}`);
41+
});
42+
43+
return false;
44+
}
45+
2046
/**
2147
* Filters for requests and sends back corresponding error.
2248
* @param req The incoming request.
@@ -161,6 +187,7 @@ webhookApp.post("/create", filterHook(Env.WEBHOOK_CREATE_SECRET), async (req: Re
161187
});
162188
if (yeetEval != undefined) {
163189
await Intra.deleteEvaluation(yeetEval);
190+
res.status(200).send();
164191
return Logger.log(`Evaluation cancelled: These users shouldn't evaluate each other, yikes.`);
165192
}
166193
}
@@ -198,7 +225,7 @@ webhookApp.post("/create", filterHook(Env.WEBHOOK_CREATE_SECRET), async (req: Re
198225
webhookApp.post("/delete", filterHook(Env.WEBHOOK_DELETE_SECRET), async (req: Request, res: Response) => {
199226
const hook: IntraWebhook.Root = req.body;
200227

201-
Logger.log(`Evaluation destroyed: ${hook.team.name} -> ${hook.project.name}`);
228+
Logger.log(`Evaluation destroyed: ${hook.team.name} -> ${hook.project.name} -> ID: ${req.headers["x-delivery"]}`);
202229
if (hook.user && hook.user.id != Config.botID) {
203230
res.status(204).send();
204231
return Logger.log("Ignored: Webhook does not concern bot.");
@@ -232,7 +259,7 @@ webhookApp.post("/delete", filterHook(Env.WEBHOOK_DELETE_SECRET), async (req: Re
232259
webhookApp.post("/update", filterHook(Env.WEBHOOK_UPDATE_SECRET), async (req: Request, res: Response) => {
233260
const hook: IntraWebhook.Root = req.body;
234261

235-
Logger.log(`Evaluation update: ${hook.team.name} -> ${hook.project.name}`);
262+
Logger.log(`Evaluation update: ${hook.team.name} -> ${hook.project.name} -> ID: ${req.headers["x-delivery"]}`);
236263

237264
try {
238265
const check = await DB.exists(hook.team.id);

src/db.ts

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -58,6 +58,14 @@ namespace DB {
5858
return team.amount > 0;
5959
}
6060

61+
export async function hasWebhookDelivery(id: string): Promise<boolean> {
62+
return !!(await dbGet<any>(`SELECT delivery FROM webhookDeliveries WHERE delivery = '${id}'`));
63+
}
64+
65+
export async function addWebhookDelivery(id: string, body: string): Promise<void> {
66+
await dbRun(`INSERT INTO webhookDeliveries(delivery, body) VALUES('${id}', '${body}')`);
67+
}
68+
6169
export async function saveEvaluator(user: User, notify: boolean): Promise<void> {
6270
const { intraUID, intraLogin, slackUID, email, level, campusID } = user;
6371
const staff = user.staff ? 1 : 0;

0 commit comments

Comments
 (0)