Cleanup
parent
1b36a24409
commit
dbb1e78429
@ -1,62 +0,0 @@
|
||||
# Criterion A: Planning
|
||||
|
||||
## The Programmer's Hangout Unban System
|
||||
|
||||
### Defining the Problem
|
||||
|
||||
veksen is a senior moderator of TPH (The Programmer's Hangout), an online
|
||||
community with over 55,000 members from all over the world. The community is on
|
||||
Discord, a very popular chatting platform where people can hang out. veksen,
|
||||
alongside with the rest of the TPH staff team have a rather clunky way of
|
||||
handling those who misbehave, manage to get themselves *banned* from the
|
||||
server, and want a second chance. Usually, they either have to create a new
|
||||
account and join the server in an attempt to get in touch with the staff team,
|
||||
or have to get a friend to help them out.
|
||||
|
||||
In September, veksen approached me and discussed the issue at hand, wanting an
|
||||
unban system with an online interface, so that it is accessible for those who
|
||||
can't join the community anymore. The online interface would authenticate you
|
||||
with the very open Discord API, be able to validate, that a user is in fact
|
||||
banned from the server, and allow users to fill out a form to appeal their
|
||||
punishment(s). This seemed like a fantastic project for me to complete for my
|
||||
Internal Assessment, as I would be able to solve a programming-related problem,
|
||||
the actual implementation isn't going to be completely non-trivial and simple
|
||||
to solve, and I would be helping out a community that has been so helpful and
|
||||
useful to not only myself, but thousands of others alike.
|
||||
|
||||
In order to get more details, I decided to hop in a call with veksen on
|
||||
September 11th, and get more information about how the system would work.
|
||||
|
||||
### Rationale for Proposed Solution
|
||||
|
||||
There is going to be three main parts to the system. Firstly, there is going to
|
||||
be a REST API that their current website will hook into. This API will have
|
||||
access to information about users who authorize themselves with Discord, so
|
||||
that those who are appealing can be identified when filling out the request.
|
||||
Next, their current website will hook up with the backend API. Finally, there
|
||||
will be a "bot" on the community itself. when a request is processed, will
|
||||
allow the users to rejoin with limited access, so that the staff team can
|
||||
further look into their case and ask more questions.
|
||||
|
||||
I have decided to write the bot, as well as the backend REST API in TypeScript
|
||||
because
|
||||
|
||||
- The rest of the staff team at TPH have experience with it
|
||||
- Easy to write and maintain, especially in comparison with JavaScript, which
|
||||
is purely dynamically typed
|
||||
- Has great libraries available to create REST APIs, as well as Discord bots
|
||||
|
||||
The frontend will be written with React/Gatsby, as that's what the current
|
||||
website is using, and rewriting it all from scratch will be undesirable.
|
||||
|
||||
### The Success Criteria
|
||||
|
||||
1. Allows users to authorize themselves with Discord's OAuth Api
|
||||
1. Identifies whether or not users are banned on the server
|
||||
1. Interfaces with the backend REST API to submit an appeal request
|
||||
1. Uses an email client to inform users information about their appeal request
|
||||
1. Connects with the Discord Bot (known as Contrition) to allow users limited
|
||||
access on TPH
|
||||
1. Has a logging system to keep track of misuse and errors
|
||||
1. Has a flexible configuration system to stay flexible if the TPH server setup
|
||||
is changed
|
@ -1,28 +1,48 @@
|
||||
import base64url from "base64url";
|
||||
// Module crypto gives an RNG source that is more secure (slower, more
|
||||
// entropy), and better for security.
|
||||
import * as crypto from "crypto";
|
||||
import { Request, Response } from "express";
|
||||
import { OAUTH_SCOPE } from "../config/Constants";
|
||||
import { StateToken } from "../entity/StateToken";
|
||||
import { respond } from "./Util";
|
||||
|
||||
/**
|
||||
* genOauth is the endpoint for users to visit and authorize themselves with Discord.
|
||||
* No passwords are exchanged with our servers, only receiving acknowledgement
|
||||
* and identification of users, meaning that we can access their basic
|
||||
* information in a safe manner.
|
||||
*
|
||||
* @route /api/oauth
|
||||
*
|
||||
*/
|
||||
export const genOAuth = async (req: Request, res: Response) => {
|
||||
// Get application core configuration
|
||||
const { api } = req.app.get("config");
|
||||
|
||||
// Generate secure token with package crypto. Make sure the token doesn't
|
||||
// already exist using a simple do while {}. If the token exists, simply
|
||||
// regenerate. Should not take more than 1 iteration in almost all
|
||||
// situations.
|
||||
let token: string;
|
||||
do {
|
||||
token = base64url(crypto.randomBytes(18));
|
||||
} while ((await StateToken.count({ where: { token } })) !== 0);
|
||||
|
||||
// Save the generated token to the database, so it can be validated when we
|
||||
// get the response back from Discord.
|
||||
new StateToken(token).save();
|
||||
|
||||
// Generate the redirect URL with the relevant information for the OAuth2
|
||||
// Auth flow.
|
||||
let url =
|
||||
"https://discord.com/api/oauth2/authorize" +
|
||||
"https://canary.discord.com/api/oauth2/authorize" +
|
||||
`?response_type=code` +
|
||||
`&prompt=consent` +
|
||||
`&client_id=${api.client_id}` +
|
||||
`&scope=${encodeURIComponent(OAUTH_SCOPE)}` +
|
||||
`&state=${token}` +
|
||||
`&redirect_uri=${encodeURIComponent(api.redirect_uri)}`;
|
||||
`&scope=${encodeURIComponent(OAUTH_SCOPE)}` + // Only get the relevant info - identity
|
||||
`&state=${token}` + // Prevent impersonation with temporary state token
|
||||
`&redirect_uri=${encodeURIComponent(api.redirect_uri)}`; // {baseurl}/authorize
|
||||
|
||||
respond(res, { redirectURL: url });
|
||||
};
|
||||
|
Loading…
Reference in New Issue