From f5be5beb42650c2ff2d9fb6d540598315c7a4834 Mon Sep 17 00:00:00 2001 From: cirroskais Date: Mon, 18 Mar 2024 22:39:00 -0400 Subject: [PATCH] testing stuffs --- src/env.d.ts | 1 + src/index.ts | 40 ++++++++++++++++++++++++++++++++++------ src/routes/negotiate.ts | 25 +++++++++++++++++++++++-- src/routes/token.ts | 15 ++++++++++++--- src/routes/user.ts | 3 +++ 5 files changed, 73 insertions(+), 11 deletions(-) create mode 100644 src/routes/user.ts diff --git a/src/env.d.ts b/src/env.d.ts index 8992988..ca972d3 100644 --- a/src/env.d.ts +++ b/src/env.d.ts @@ -2,6 +2,7 @@ declare module "bun" { interface Env { DISCORD_CLIENT_ID: string; DISCORD_CLIENT_SECRET: string; + DISCORD_CLIENT_TOKEN: string; ENCRYPTION_KEY: string; ENCRYPTION_SALT: string; } diff --git a/src/index.ts b/src/index.ts index 5c1b9dd..8a2ecf4 100644 --- a/src/index.ts +++ b/src/index.ts @@ -1,23 +1,51 @@ import token from "./routes/token"; import config from "./routes/config"; +import user from "./routes/user"; import negotiate from "./routes/negotiate"; -Bun.serve({ +type WebSocketData = { + authenticated: boolean; + identity: { + id: string; + username: string; + avatar: string; + }; +}; + +const terryIdentity = { + id: "869016244613951539", + username: "terry218742", + avatar: "", +}; + +const server = Bun.serve({ port: 3000, - async fetch(req) { + async fetch(req, server) { const url = new URL(req.url); console.log(`${new Date().toUTCString()} ${req.method} ${url.pathname}`); if (url.pathname === "/") return await config(req); + if (url.pathname === "/ws") return await negotiate(req, server); if (url.pathname === "/token") return await token(req); - if (url.pathname === "/negotiate") return await negotiate(req); + if (url.pathname === "/user") return await user(req); return new Response("garf dont know what want..."); }, websocket: { - message(ws, message) {}, - open(ws) {}, - close(ws, code, message) {}, + message(ws, message) { + if (!ws.data.authenticated) ws.close(); + server.publish("global", JSON.stringify({ message, identity: ws.data.identity })); + }, + open(ws) { + const message = `${ws.data.identity.username} has joined the channel.`; + server.publish("global", JSON.stringify({ message, identity: terryIdentity })); + ws.subscribe("global"); + }, + close(ws, code, msg) { + const message = `${ws.data.identity.username} has left the channel.`; + server.publish("global", JSON.stringify({ message, identity: terryIdentity })); + ws.unsubscribe("global"); + }, drain(ws) {}, }, }); diff --git a/src/routes/negotiate.ts b/src/routes/negotiate.ts index c180ceb..80f05e3 100644 --- a/src/routes/negotiate.ts +++ b/src/routes/negotiate.ts @@ -1,3 +1,24 @@ -export default async function (req: Request): Promise { - return new Response(); +import type { Server } from "bun"; +import { decrypt } from "../lib/encryption"; +import type { PartialDiscordUser } from "./token"; + +interface NegotiateRequest { + id: string; + iv: string; +} + +export default async function (req: Request, server: Server): Promise { + if (req.method !== "POST") return new Response("garf expected a POST request..."); + if (!req.headers.get("Content-Type")) return new Response("garf expected some jay sawn..."); + if (!req.headers.get("Content-Type")?.includes("application/json")) return new Response("garf expected some jay sawn..."); + + const body = (await req.json()) as NegotiateRequest; + if (!body) return new Response("garf expected some jay sawn..."); + + const decrypted = await decrypt(body.id, body.iv); + if (!decrypted) return new Response("invalid identity!!!!!"); + const identity = JSON.parse(decrypted.decrypted) as PartialDiscordUser; + + const success = server.upgrade(req, { data: { authenticated: true, identity } }); + return success ? undefined : new Response("WebSocket upgrade error", { status: 400 }); } diff --git a/src/routes/token.ts b/src/routes/token.ts index f0271ed..55da48a 100644 --- a/src/routes/token.ts +++ b/src/routes/token.ts @@ -1,3 +1,5 @@ +import { encrypt } from "../lib/encryption"; + interface TokenRequest { code: string; } @@ -10,6 +12,12 @@ interface TokenResponse { scope: string; } +export interface PartialDiscordUser { + id: string; + username: string; + avatar: string; +} + export default async function (req: Request): Promise { if (req.method !== "POST") return new Response("garf expected a POST request..."); if (!req.headers.get("Content-Type")) return new Response("garf expected some jay sawn..."); @@ -30,13 +38,14 @@ export default async function (req: Request): Promise { }); const { access_token } = (await response.json()) as TokenResponse; + const userResponse = await fetch("https://discord.com/api/v10/users/@me", { headers: { Authorization: "Bearer " + access_token }, }); + const user = (await userResponse.json()) as PartialDiscordUser; + const { encrypted, iv } = await encrypt(JSON.stringify(user)); - console.log(await userResponse.json()); - - return new Response(JSON.stringify({ access_token }), { + return new Response(JSON.stringify({ access_token, identity: { id: encrypted, iv } }), { headers: { "Content-Type": "application/json", }, diff --git a/src/routes/user.ts b/src/routes/user.ts new file mode 100644 index 0000000..c180ceb --- /dev/null +++ b/src/routes/user.ts @@ -0,0 +1,3 @@ +export default async function (req: Request): Promise { + return new Response(); +}