From 0787dfda477d719c53c5644d074a3a89e83aa11c Mon Sep 17 00:00:00 2001 From: Holly Date: Sun, 13 Oct 2024 12:41:45 +0100 Subject: [PATCH] implement protocol versioning and add site specific logos --- client/Terminal-00-Multiuser.user.js | 49 ++++++++++++++++++++++----- client/index.html | 1 - server/config.example.json | 3 ++ server/enums/MessageType.ts | 3 +- server/index.ts | 24 ++++++++++++- server/interfaces/ScriptParameters.ts | 3 +- server/objects/Config.ts | 5 +++ server/scripts | 2 +- 8 files changed, 76 insertions(+), 14 deletions(-) diff --git a/client/Terminal-00-Multiuser.user.js b/client/Terminal-00-Multiuser.user.js index 895814f..9a27a9d 100644 --- a/client/Terminal-00-Multiuser.user.js +++ b/client/Terminal-00-Multiuser.user.js @@ -1,7 +1,7 @@ // ==UserScript== // @name MultiProbe // @namespace https://*.angusnicneven.com/* -// @version 20241013.0 +// @version 20241013.1 // @description Probe with friends! // @author tgpholly // @match https://*.angusnicneven.com/* @@ -49,13 +49,22 @@ const SITE_DEFAULT_HOVER_CURSOR = { "heavenonline.xyz": "https://heavenonline.xyz/core/cursor_hover/frame1.png" }; +const SITE_LOGOS = { + "*.angusnicneven.com": "https://eusv.net/NLuGOZGZtS3BEr", + "multiprobe.eusv.net": "https://eusv.net/NLuGOZGZtS3BEr", + "*.heavenonline.xyz": "https://eusv.net/Iu8kZfgAC8NFdU", + "*.eusv.net": "https://eusv.net/C89X3tb5mtkVI7" +}; + +const PROTOCOL_VERSION = 2; + console.log("[MP] MultiProbe init"); (function() { 'use strict'; // Make sure to change the userscript version too!!!!!!!!!! - const USERSCRIPT_VERSION_RAW = "20241013.0"; + const USERSCRIPT_VERSION_RAW = "20241013.1"; const USERSCRIPT_VERSION = parseInt(USERSCRIPT_VERSION_RAW.replace(".", "")); if (!continueRunningScript) { @@ -76,7 +85,8 @@ console.log("[MP] MultiProbe init"); GroupData: 7, HonkShoe: 8, BadgeUnlock: 9, - DEBUG_UnlockAllBadges: 10 + DEBUG_UnlockAllBadges: 10, + TooOutOfDate: 11 }; let cssCursor = ""; @@ -148,7 +158,7 @@ html { animation: ping 2s linear; animation-iteration-count: 1; image-rendering: pixelated; - background: url("data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAEAAAABACAYAAACqaXHeAAAAAXNSR0IArs4c6QAAAXVJREFUeJztm8ESwyAIRLX//8/2EjKKmhhFUeDN9NbK7kIybaPerSU0vs9PVbGwUGI4hDb/3meypumcsfDtEhsuGCsv8Pw5Us2UiwXnUvEDnaxOTrQmiXaKRRLjk7qVTRVVEKMCA7WglppX4bjusptmLCJc7uF1pIae5HDXl6ePWKqHu+s18DTMKTK7AAHTNJ5gHiDXepJ5gEzzieaBYe0nmwdePfwWijkKCd0HPnuRZB6oerJLACGx+0DRm01AhOTuA5lH9ROgPgBAw/gDiVf1E2ABcAvYAU3XP3B7Vj8BFgC3AG4sAG4B3FgA3AK4sQC4BeyCpm+D9mswxgLgFrATGu4D9qcoRn0AGMmXgT0ZakXiFNjT4a9ImoJuLxJCsD1Co5w8Bar3CqreLap6v/DSHeM7BdG9Xd4OTPQWdfzTwHZkJhGB0qdY87XmVTiu213Tjs2NfBiRBOGcnoOTmKxbdzHhR2dLVDv5xOmHp59ovVMv0/UHCfuPGCq5foYAAAAASUVORK5CYII="); + background: url("https://eusv.net/MA7cm1BBelFHDP"); width: 64px; height: 64px; z-index: -1!important; @@ -161,7 +171,7 @@ html { width: 64px; height: 64px; image-rendering: pixelated; - background: url("data:image/webp;base64,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"); + background: url("https://eusv.net/9ZU5r29lg1yKIi"); z-index: 1; transform: translate(60px, -60px); } @@ -802,8 +812,13 @@ mp_button { } let windowContainer = null; + let preventReconnect = false; function doConnect(apiKey) { + if (preventReconnect) { + return; + } + const Buffer = getBufferClass(); console.log("[MP] Connecting to realtime server..."); @@ -820,11 +835,14 @@ mp_button { selfCursor.element.style.visibility = localStorage["t00mp_cursorStyle"] ?? "hidden"; selfCursor.hasBeenMoved = true; const currentPage = windowLocation.split("/").slice(2).join("/"); + const key = window.ebfohezwACBL8DU8sqvedw ?? ""; ws.send(keepAlivePacket); - ws.send(createWriter(Endian.LE, 4 + apiKey.length + currentPage.length) + ws.send(createWriter(Endian.LE, 8 + apiKey.length + currentPage.length + key.length) .writeUByte(MessageType.ClientDetails) .writeShortString(apiKey) .writeString(currentPage) + .writeUShort(PROTOCOL_VERSION) + .writeString(key) .toBuffer()); pingStartTime = performance.now(); keepAliveInterval = setInterval(() => { @@ -954,6 +972,13 @@ mp_button { const badgeIconUrl = reader.readString16(); createBadgePopup(badgeTitle, badgeDescription, badgeIconUrl); + break; + } + case MessageType.TooOutOfDate: + { + ws.close(); + preventReconnect = true; + break; } } } @@ -986,9 +1011,15 @@ mp_button { const dialog = document.createElement("mp_container"); dialog.style = "position:absolute;top:50%;left:50%;min-width:15rem;background-color:#343434;padding:1rem;transform:translate(-50%,-50%);text-align:center;color:white"; bg.appendChild(dialog); - const title = document.createElement("h4"); - title.innerText = "MultiProbe"; - title.style.marginBottom = "0px"; + const title = document.createElement("img"); + for (const siteKey of Object.keys(SITE_LOGOS)) { + const domain = window.location.href.split("://")[1].split("/")[0]; + if ((siteKey.startsWith("*.") && domain.includes(siteKey.replace("*.", ""))) || domain.startsWith(siteKey)) { + title.src = SITE_LOGOS[siteKey]; + break; + } + } + title.style = "background-color:black;padding:.25rem;margin-bottom:.5rem;border:1px solid white"; dialog.appendChild(title); const subtitle = document.createElement("h5"); subtitle.innerText = `Logged in as ${localStorage["t00mp_username"]}`; diff --git a/client/index.html b/client/index.html index bd495bc..e835713 100644 --- a/client/index.html +++ b/client/index.html @@ -7,7 +7,6 @@ UserScript test page - \ No newline at end of file diff --git a/server/config.example.json b/server/config.example.json index bba38e7..a3356b7 100644 --- a/server/config.example.json +++ b/server/config.example.json @@ -20,5 +20,8 @@ "itterations": 10000, "keylength": 64 } + }, + "badge": { + "key": "hidden :)" } } \ No newline at end of file diff --git a/server/enums/MessageType.ts b/server/enums/MessageType.ts index e6fc974..131f6da 100644 --- a/server/enums/MessageType.ts +++ b/server/enums/MessageType.ts @@ -9,5 +9,6 @@ export enum MessageType { GroupData, HonkShoe, BadgeUnlock, - DEBUG_UnlockAllBadges + DEBUG_UnlockAllBadges, + TooOutOfDate } \ No newline at end of file diff --git a/server/index.ts b/server/index.ts index 1b3fcbb..c342037 100644 --- a/server/index.ts +++ b/server/index.ts @@ -196,6 +196,9 @@ async function updateConnectionMetrics() { } const keepalivePacket = createWriter(Endian.LE, 1).writeByte(MessageType.KeepAlive).toBuffer(); +const outOfDatePacket = createWriter(Endian.LE, 1).writeByte(MessageType.TooOutOfDate).toBuffer(); + +const PROTOCOL_VERSION = 2; websocketServer.on("connection", (socket: any) => { const myUUID = crypto.randomUUID(); @@ -270,6 +273,24 @@ websocketServer.on("connection", (socket: any) => { } const apiKey = reader.readShortString(); const rawURL = reader.readString(); + let key = ""; + + // If there isn't enough bytes for the protocol version + // then we're definitely out of date! + if (reader.readOffset === reader.length) { + socket.send(outOfDatePacket); + return; + } else { + const protocolVersion = reader.readUShort(); + // Procol version is too old + if (protocolVersion < PROTOCOL_VERSION) { + socket.send(outOfDatePacket); + return; + } + // We are the current version if we got here! + key = reader.readString(); + } + const dbUser = await UserService.GetUserByAPIKey(apiKey); if (dbUser == null) { return; @@ -319,7 +340,8 @@ websocketServer.on("connection", (socket: any) => { userParty: dbUserParty, party: dbParty, remoteUser: user, - users: users + users: users, + key: key }; for (const key of goalBadgeKeys) { scriptParams.badge = BadgeCache.GoalBadges.get(key)!; diff --git a/server/interfaces/ScriptParameters.ts b/server/interfaces/ScriptParameters.ts index f796b15..c9b6f83 100644 --- a/server/interfaces/ScriptParameters.ts +++ b/server/interfaces/ScriptParameters.ts @@ -11,5 +11,6 @@ export default interface ScriptParameters { userParty: UserParty | null, party: Party | null, remoteUser: RemoteUser, - users: FunkyArray + users: FunkyArray, + key: string } \ No newline at end of file diff --git a/server/objects/Config.ts b/server/objects/Config.ts index aef4ad3..3dbc96f 100644 --- a/server/objects/Config.ts +++ b/server/objects/Config.ts @@ -7,6 +7,7 @@ export default abstract class Config { public static session:ConfigSession = config.session; public static githost:string = config.githost; public static database:ConfigDatabase = config.database; + public static badge:ConfigBadge = config.badge; } interface ConfigPorts { @@ -33,4 +34,8 @@ interface ConfigDatabase { interface DatabasePbkdf2 { itterations: number, keylength: number +} + +interface ConfigBadge { + key: string } \ No newline at end of file diff --git a/server/scripts b/server/scripts index 7accf5b..8b2408c 160000 --- a/server/scripts +++ b/server/scripts @@ -1 +1 @@ -Subproject commit 7accf5b1c9529490c5713f8dbb9a067cfb2c3d49 +Subproject commit 8b2408c67f98b1a51b35bbfecde1d65e5ea39daf