diff --git a/.husky/pre-commit b/.husky/pre-commit index a282f31f54..1ccfeab6a9 100755 --- a/.husky/pre-commit +++ b/.husky/pre-commit @@ -1,8 +1,6 @@ -#!/usr/bin/env sh -. "$(dirname -- "$0")/_/husky.sh" +# Husky v10 compatible pre-commit (removed deprecated husky.sh sourcing) +# Ensure PATH includes typical Node locations if needed (optional on most setups) +export PATH="$PATH" -# Add PATH setup to ensure npx is found -export PATH="/usr/local/bin:$HOME/.npm-global/bin:$HOME/.nvm/versions/node/$(node -v)/bin:$PATH" - -# Then run lint-staged if tests pass +# Run lint-staged tasks npx lint-staged diff --git a/__mocks__/jose.js b/__mocks__/jose.js new file mode 100644 index 0000000000..81f36f295b --- /dev/null +++ b/__mocks__/jose.js @@ -0,0 +1,8 @@ +// Minimal mock of jose for tests +export const base64url = { + encode: (input) => Buffer.from(String(input)).toString("base64url"), + decode: (input) => Buffer.from(String(input), "base64url").toString("utf8"), +}; +export const jwtVerify = async () => ({ payload: {}, protectedHeader: {} }); +export const decodeJwt = () => ({ sub: "test" }); +export const JWK = {}; diff --git a/eslint.config.js b/eslint.config.js index 3caf4b48d0..9e7e1f9a48 100644 --- a/eslint.config.js +++ b/eslint.config.js @@ -25,6 +25,7 @@ export default [ projectService: { allowDefaultProject: [ "__mocks__/fileMock.js", + "__mocks__/jose.js", "eslint.config.js", "jest.config.ts", "postcss.config.js", diff --git a/jest.config.ts b/jest.config.ts index b69aa53386..06548a8579 100644 --- a/jest.config.ts +++ b/jest.config.ts @@ -5,6 +5,7 @@ export default { extensionsToTreatAsEsm: [".ts"], moduleNameMapper: { "^(\\.{1,2}/.*)\\.js$": "$1", + "^jose$": "/__mocks__/jose.js", "\\.(jpg|jpeg|png|gif|eot|otf|webp|svg|ttf|woff|woff2|mp4|webm|wav|mp3|m4a|aac|oga)$": "/__mocks__/fileMock.js", "\\.(css|less)$": "/__mocks__/fileMock.js", diff --git a/package-lock.json b/package-lock.json index 236574ed45..ee9648f718 100644 --- a/package-lock.json +++ b/package-lock.json @@ -32,6 +32,7 @@ "js-yaml": "^4.1.1", "nanoid": "^3.3.6", "obscenity": "^0.4.3", + "pixi-filters": "^6.1.4", "seedrandom": "^3.0.5", "ts-node": "^10.9.2", "uuid": "^11.1.0", @@ -91,7 +92,6 @@ "lit": "^3.3.1", "lit-markdown": "^1.3.2", "mrmime": "^2.0.0", - "pixi-filters": "^6.1.4", "pixi.js": "^8.11.0", "postcss": "^8.5.1", "postcss-loader": "^8.1.1", @@ -1049,7 +1049,6 @@ "integrity": "sha512-bXYxrXFubeYdvB0NhD/NBB3Qi6aZeV20GOWVI47t2dkecCEoneR4NPVcb7abpXDEvejgrUfFtG6vG/zxAKmg+g==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "@ampproject/remapping": "^2.2.0", "@babel/code-frame": "^7.27.1", @@ -2922,7 +2921,6 @@ } ], "license": "MIT", - "peer": true, "engines": { "node": ">=18" }, @@ -2946,7 +2944,6 @@ } ], "license": "MIT", - "peer": true, "engines": { "node": ">=18" } @@ -5101,7 +5098,6 @@ "resolved": "https://registry.npmjs.org/@opentelemetry/api/-/api-1.9.0.tgz", "integrity": "sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg==", "license": "Apache-2.0", - "peer": true, "engines": { "node": ">=8.0.0" } @@ -5486,7 +5482,6 @@ "version": "2.9.6", "resolved": "https://registry.npmjs.org/@pixi/colord/-/colord-2.9.6.tgz", "integrity": "sha512-nezytU2pw587fQstUu1AsJZDVEynjskwOL+kibwcdxsMBFqPsFFNA7xl0ii/gXuDi6M0xj3mfRJj8pBSc2jCfA==", - "dev": true, "license": "MIT" }, "node_modules/@pkgjs/parseargs": { @@ -6420,6 +6415,7 @@ "os": [ "darwin" ], + "peer": true, "engines": { "node": ">=10" } @@ -6436,6 +6432,7 @@ "os": [ "darwin" ], + "peer": true, "engines": { "node": ">=10" } @@ -6452,6 +6449,7 @@ "os": [ "linux" ], + "peer": true, "engines": { "node": ">=10" } @@ -6468,6 +6466,7 @@ "os": [ "linux" ], + "peer": true, "engines": { "node": ">=10" } @@ -6484,6 +6483,7 @@ "os": [ "linux" ], + "peer": true, "engines": { "node": ">=10" } @@ -6500,6 +6500,7 @@ "os": [ "linux" ], + "peer": true, "engines": { "node": ">=10" } @@ -6516,6 +6517,7 @@ "os": [ "linux" ], + "peer": true, "engines": { "node": ">=10" } @@ -6532,6 +6534,7 @@ "os": [ "win32" ], + "peer": true, "engines": { "node": ">=10" } @@ -6548,6 +6551,7 @@ "os": [ "win32" ], + "peer": true, "engines": { "node": ">=10" } @@ -6564,6 +6568,7 @@ "os": [ "win32" ], + "peer": true, "engines": { "node": ">=10" } @@ -6599,6 +6604,7 @@ "integrity": "sha512-u1iIVZV9Q0jxY+yM2vw/hZGDNudsN85bBpTqzAQ9rzkxW9D+e3aEM4Han+ow518gSewkXgjmEK0BD79ZcNVgPw==", "devOptional": true, "license": "Apache-2.0", + "peer": true, "dependencies": { "@swc/counter": "^0.1.3" } @@ -6751,7 +6757,6 @@ "version": "0.0.12", "resolved": "https://registry.npmjs.org/@types/css-font-loading-module/-/css-font-loading-module-0.0.12.tgz", "integrity": "sha512-x2tZZYkSxXqWvTDgveSynfjq/T2HyiZHXb00j/+gy19yp70PHCizM48XFdjBCWH7eHBD0R5i/pw9yMBP/BH5uA==", - "dev": true, "license": "MIT" }, "node_modules/@types/d3": { @@ -7038,13 +7043,6 @@ "@types/d3-selection": "*" } }, - "node_modules/@types/earcut": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/@types/earcut/-/earcut-3.0.0.tgz", - "integrity": "sha512-k/9fOUGO39yd2sCjrbAJvGDEQvRwRnQIZlBz43roGwUZo5SHAmyVvSFyaVVZkicRVCaDXPKlbxrUcBuJoSWunQ==", - "dev": true, - "license": "MIT" - }, "node_modules/@types/eslint": { "version": "9.6.1", "resolved": "https://registry.npmjs.org/@types/eslint/-/eslint-9.6.1.tgz", @@ -7116,7 +7114,6 @@ "version": "0.1.5", "resolved": "https://registry.npmjs.org/@types/gradient-parser/-/gradient-parser-0.1.5.tgz", "integrity": "sha512-r7K3NkJz3A95WkVVmjs0NcchhHstC2C/VIYNX4JC6tieviUNo774FFeOHjThr3Vw/WCeMP9kAT77MKbIRlO/4w==", - "dev": true, "license": "MIT" }, "node_modules/@types/hammerjs": { @@ -7253,7 +7250,6 @@ "resolved": "https://registry.npmjs.org/@types/node/-/node-22.15.32.tgz", "integrity": "sha512-3jigKqgSjsH6gYZv2nEsqdXfZqIFGAV36XYYjf9KGZ3PSG+IhLecqPnI310RvjutyMwifE2hhhNEklOUrvx/wA==", "license": "MIT", - "peer": true, "dependencies": { "undici-types": "~6.21.0" } @@ -7488,7 +7484,6 @@ "integrity": "sha512-4O3idHxhyzjClSMJ0a29AcoK0+YwnEqzI6oz3vlRf3xw0zbzt15MzXwItOlnr5nIth6zlY2RENLsOPvhyrKAQA==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "@typescript-eslint/scope-manager": "8.34.1", "@typescript-eslint/types": "8.34.1", @@ -8151,10 +8146,9 @@ } }, "node_modules/@webgpu/types": { - "version": "0.1.61", - "resolved": "https://registry.npmjs.org/@webgpu/types/-/types-0.1.61.tgz", - "integrity": "sha512-w2HbBvH+qO19SB5pJOJFKs533CdZqxl3fcGonqL321VHkW7W/iBo6H8bjDy6pr/+pbMwIu5dnuaAxH7NxBqUrQ==", - "dev": true, + "version": "0.1.66", + "resolved": "https://registry.npmjs.org/@webgpu/types/-/types-0.1.66.tgz", + "integrity": "sha512-YA2hLrwLpDsRueNDXIMqN9NTzD6bCDkuXbOSe0heS+f8YE8usA6Gbv1prj81pzVHrbaAma7zObnIC+I6/sXJgA==", "license": "BSD-3-Clause" }, "node_modules/@webpack-cli/configtest": { @@ -8205,10 +8199,9 @@ } }, "node_modules/@xmldom/xmldom": { - "version": "0.8.10", - "resolved": "https://registry.npmjs.org/@xmldom/xmldom/-/xmldom-0.8.10.tgz", - "integrity": "sha512-2WALfTl4xo2SkGCYRt6rDTFfk9R1czmBvUQy12gK2KuRKIpWEhcbbzy8EZXtz/jkRqHX8bFEc6FC1HjX4TUWYw==", - "dev": true, + "version": "0.8.11", + "resolved": "https://registry.npmjs.org/@xmldom/xmldom/-/xmldom-0.8.11.tgz", + "integrity": "sha512-cQzWCtO6C8TQiYl1ruKNn2U6Ao4o4WBBcbL61yJl84x+j5sOWWFU9X7DpND8XZG3daDppSsigMdfAIl2upQBRw==", "license": "MIT", "engines": { "node": ">=10.0.0" @@ -8259,7 +8252,6 @@ "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.15.0.tgz", "integrity": "sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==", "license": "MIT", - "peer": true, "bin": { "acorn": "bin/acorn" }, @@ -8318,7 +8310,6 @@ "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "fast-deep-equal": "^3.1.1", "fast-json-stable-stringify": "^2.0.0", @@ -8884,7 +8875,6 @@ } ], "license": "MIT", - "peer": true, "dependencies": { "caniuse-lite": "^1.0.30001718", "electron-to-chromium": "^1.5.160", @@ -9063,7 +9053,6 @@ "dev": true, "hasInstallScript": true, "license": "MIT", - "peer": true, "dependencies": { "node-addon-api": "^7.0.0", "prebuild-install": "^7.1.1" @@ -9085,7 +9074,6 @@ "integrity": "sha512-mCuXncKXk5iCLhfhwTc0izo0gtEmpz5CtG2y8GiOINBlMVS6v8TMRc5TaLWKS6692m9+dVVfzgeVxR5UxWHTYw==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "assertion-error": "^2.0.1", "check-error": "^2.1.1", @@ -9690,7 +9678,6 @@ "integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "fast-deep-equal": "^3.1.3", "fast-uri": "^3.0.1", @@ -10278,7 +10265,6 @@ "integrity": "sha512-fmTRWbNMmsmWq6xJV8D19U/gw/bwrHfNXxrIN+HfZgnzqTHp9jOmKMhsTUjXOJnZOdZY9Q28y4yebKzqDKlxlQ==", "dev": true, "license": "ISC", - "peer": true, "engines": { "node": ">=12" } @@ -10753,13 +10739,6 @@ "node": ">= 0.4" } }, - "node_modules/earcut": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/earcut/-/earcut-3.0.1.tgz", - "integrity": "sha512-0l1/0gOjESMeQyYaK5IDiPNvFeu93Z/cO0TjZh9eZ1vyCtZnA7KMZ8rQggpsJHIbGSdrqYq9OhuveadOVHCshw==", - "dev": true, - "license": "ISC" - }, "node_modules/eastasianwidth": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/eastasianwidth/-/eastasianwidth-0.2.0.tgz", @@ -11021,7 +11000,6 @@ "integrity": "sha512-GsGizj2Y1rCWDu6XoEekL3RLilp0voSePurjZIkxL3wlm5o5EC9VpgaP7lrCvjnkuLvzFBQWB3vWB3K5KQTveQ==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "@eslint-community/eslint-utils": "^4.2.0", "@eslint-community/regexpp": "^4.12.1", @@ -11191,7 +11169,6 @@ "integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "fast-deep-equal": "^3.1.3", "fast-uri": "^3.0.1", @@ -11393,7 +11370,6 @@ "version": "5.0.1", "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-5.0.1.tgz", "integrity": "sha512-GWkBvjiSZK87ELrYOSESUYeVIc9mvLLf/nXalMOS5dYrgZq9o5OVkbZAVM06CVxYsCwH9BDZFPlQTlPA1j4ahA==", - "dev": true, "license": "MIT" }, "node_modules/events": { @@ -11550,7 +11526,6 @@ "resolved": "https://registry.npmjs.org/express/-/express-4.21.2.tgz", "integrity": "sha512-28HqgMZAmih1Czt9ny7qr6ek2qddF4FclbMzwhCREB6OFfH+rXAnuNCwo1/wFvrtbgsQDb4kSbX9de9lFbrXnA==", "license": "MIT", - "peer": true, "dependencies": { "accepts": "~1.3.8", "array-flatten": "1.1.1", @@ -12135,7 +12110,6 @@ "version": "2.1.2", "resolved": "https://registry.npmjs.org/gifuct-js/-/gifuct-js-2.1.2.tgz", "integrity": "sha512-rI2asw77u0mGgwhV3qA+OEgYqaDn5UNqgs+Bx0FGwSpuqfYn+Ir6RQY5ENNQ8SbIiG/m5gVa7CD5RriO4f4Lsg==", - "dev": true, "license": "MIT", "dependencies": { "js-binary-schema-parser": "^2.0.3" @@ -12451,7 +12425,6 @@ "integrity": "sha512-QSf1yjtSAsmf7rYBV7XX86uua4W/vkhIt0xNXKbsi2foEeW7vjJQz4bhnpL3xH+l1ryl1680uNv968Z+X6jSYg==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "@types/html-minifier-terser": "^6.0.0", "html-minifier-terser": "^6.0.2", @@ -13084,7 +13057,6 @@ "version": "1.1.1", "resolved": "https://registry.npmjs.org/ismobilejs/-/ismobilejs-1.1.1.tgz", "integrity": "sha512-VaFW53yt8QO61k2WJui0dHf4SlL8lxBofUuUmwBo0ljPk0Drz2TiuDW4jo3wDcv41qy/SxrJ+VAzJ/qYqsmzRw==", - "dev": true, "license": "MIT" }, "node_modules/isobject": { @@ -14953,7 +14925,6 @@ "version": "2.0.3", "resolved": "https://registry.npmjs.org/js-binary-schema-parser/-/js-binary-schema-parser-2.0.3.tgz", "integrity": "sha512-xezGJmOb4lk/M1ZZLTR/jaBHQ4gG/lqQnJqdIv4721DMggsa1bDVlHXNeHYogaIEHD9vCRv0fcL4hMA+Coarkg==", - "dev": true, "license": "MIT" }, "node_modules/js-tokens": { @@ -14981,7 +14952,6 @@ "integrity": "sha512-Cvc9WUhxSMEo4McES3P7oK3QaXldCfNWp7pl2NNeiIFlCoLr3kfq9kb1fxftiwk1FLV7CvpvDfonxtzUDeSOPg==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "cssstyle": "^4.2.1", "data-urls": "^5.0.0", @@ -16463,7 +16433,6 @@ "version": "0.1.2", "resolved": "https://registry.npmjs.org/parse-svg-path/-/parse-svg-path-0.1.2.tgz", "integrity": "sha512-JyPSBnkTJ0AI8GGJLfMXvKq42cj5c006fnLz6fXy6zfoVjJizi8BNTpu8on8ziI1cKy9d9DGNuY17Ce7wuejpQ==", - "dev": true, "license": "MIT" }, "node_modules/parse5": { @@ -16680,7 +16649,6 @@ "version": "6.1.4", "resolved": "https://registry.npmjs.org/pixi-filters/-/pixi-filters-6.1.4.tgz", "integrity": "sha512-6QdkhR8hZ/jXyV7GZG8R0UKkRy9jPeZsOnHaQiKSFEe4tGJ4PfUG90vaC9eyi7g+YKxhKLpNOXu6tmO1+R2tpQ==", - "dev": true, "license": "MIT", "dependencies": { "@types/gradient-parser": "^0.1.2" @@ -16693,9 +16661,7 @@ "version": "8.11.0", "resolved": "https://registry.npmjs.org/pixi.js/-/pixi.js-8.11.0.tgz", "integrity": "sha512-dyuThzncsgEgJZnvd/A/5x6IkUERbK+phXqUQrI+0C6WE+8xqGH5VChRTLecemhgZF0kQ+gZOM3tJTX9937xpg==", - "dev": true, "license": "MIT", - "peer": true, "dependencies": { "@pixi/colord": "^2.9.6", "@types/css-font-loading-module": "^0.0.12", @@ -16713,6 +16679,18 @@ "url": "https://opencollective.com/pixijs" } }, + "node_modules/pixi.js/node_modules/@types/earcut": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/@types/earcut/-/earcut-3.0.0.tgz", + "integrity": "sha512-k/9fOUGO39yd2sCjrbAJvGDEQvRwRnQIZlBz43roGwUZo5SHAmyVvSFyaVVZkicRVCaDXPKlbxrUcBuJoSWunQ==", + "license": "MIT" + }, + "node_modules/pixi.js/node_modules/earcut": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/earcut/-/earcut-3.0.2.tgz", + "integrity": "sha512-X7hshQbLyMJ/3RPhyObLARM2sNxxmRALLKx1+NVFFnQ9gKzmCrxm9+uLIAdBcvc8FNLpctqlQ2V6AE92Ol9UDQ==", + "license": "ISC" + }, "node_modules/pkg-dir": { "version": "4.2.0", "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-4.2.0.tgz", @@ -16753,7 +16731,6 @@ } ], "license": "MIT", - "peer": true, "dependencies": { "nanoid": "^3.3.11", "picocolors": "^1.1.1", @@ -17092,7 +17069,6 @@ "integrity": "sha512-QQtaxnoDJeAkDvDKWCLiwIXkTgRhwYDEQCghU9Z6q03iyek/rxRh/2lC3HB7P8sWT2xC/y5JDctPLBIGzHKbhw==", "dev": true, "license": "MIT", - "peer": true, "bin": { "prettier": "bin/prettier.cjs" }, @@ -18362,7 +18338,6 @@ "integrity": "sha512-TOgRcwFPbfGtpqvZw+hyqJDvqfapr1qUlOizROIk4bBLjlsjlB00Pg6wMFXNtJRpu+eCZuVOaLatG7M8105kAw==", "dev": true, "license": "BSD-3-Clause", - "peer": true, "dependencies": { "@sinonjs/commons": "^3.0.1", "@sinonjs/fake-timers": "^13.0.5", @@ -19075,7 +19050,6 @@ "integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "fast-deep-equal": "^3.1.3", "fast-uri": "^3.0.1", @@ -19307,7 +19281,6 @@ "integrity": "sha512-M7BAV6Rlcy5u+m6oPhAPFgJTzAioX/6B0DxyvDlo9l8+T3nLKbrczg2WLUyzd45L8RqfUMyGPzekbMvX2Ldkwg==", "dev": true, "license": "MIT", - "peer": true, "engines": { "node": ">=12" }, @@ -19495,7 +19468,6 @@ "resolved": "https://registry.npmjs.org/ts-node/-/ts-node-10.9.2.tgz", "integrity": "sha512-f0FFpIdcHgn8zcPSbf1dRevwt047YMnaiJM3u2w2RewrB+fob/zePZcrOyQoLMMO7aBIddLcQIEK5dYjkLnGrQ==", "license": "MIT", - "peer": true, "dependencies": { "@cspotcode/source-map-support": "^0.8.0", "@tsconfig/node10": "^1.0.7", @@ -19578,8 +19550,7 @@ "version": "2.8.1", "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.8.1.tgz", "integrity": "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w==", - "license": "0BSD", - "peer": true + "license": "0BSD" }, "node_modules/tsx": { "version": "4.20.3", @@ -19668,7 +19639,6 @@ "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.8.3.tgz", "integrity": "sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ==", "license": "Apache-2.0", - "peer": true, "bin": { "tsc": "bin/tsc", "tsserver": "bin/tsserver" @@ -19963,7 +19933,6 @@ "integrity": "sha512-QaNKAvGCDRh3wW1dsDjeMdDXwZm2vqq3zn6Pvq4rHOEOGSaUMgOOjG2Y9ZbIGzpfkJk9ZYTHpDqgDfeBDcnLaw==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "@types/eslint-scope": "^3.7.7", "@types/estree": "^1.0.8", @@ -20013,7 +19982,6 @@ "integrity": "sha512-MfwFQ6SfwinsUVi0rNJm7rHZ31GyTcpVE5pgVA3hwFRb7COD4TzjUUwhGWKfO50+xdc2MQPuEBBJoqIMGt3JDw==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "@discoveryjs/json-ext": "^0.6.1", "@webpack-cli/configtest": "^3.0.1", @@ -20097,7 +20065,6 @@ "integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "fast-deep-equal": "^3.1.3", "fast-uri": "^3.0.1", @@ -20213,7 +20180,6 @@ "integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "fast-deep-equal": "^3.1.3", "fast-uri": "^3.0.1", @@ -20306,7 +20272,6 @@ "integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "fast-deep-equal": "^3.1.3", "fast-uri": "^3.0.1", diff --git a/resources/lang/en.json b/resources/lang/en.json index 2953d70111..6434fda794 100644 --- a/resources/lang/en.json +++ b/resources/lang/en.json @@ -507,6 +507,12 @@ "stop_trading": "Stop trading with [P1]!" } }, + "lobby_chat": { + "title": "Lobby Chat", + "placeholder": "Type a message...", + "enable": "Enable Lobby Chat", + "send": "Send" + }, "build_menu": { "desc": { "atom_bomb": "Small explosion", diff --git a/src/client/ClientGameRunner.ts b/src/client/ClientGameRunner.ts index c3c093426d..5f47302c51 100644 --- a/src/client/ClientGameRunner.ts +++ b/src/client/ClientGameRunner.ts @@ -74,6 +74,17 @@ export function joinLobby( `joining lobby: gameID: ${lobbyConfig.gameID}, clientID: ${lobbyConfig.clientID}`, ); + // Expose EventBus for lightweight components (e.g., LobbyChatPanel) + (window as any).__eventBus = eventBus; + // Expose current clientID for UI alignment decisions + (window as any).__clientID = lobbyConfig.clientID; + // Expose username for message identification + (window as any).__username = lobbyConfig.playerName; + // Notify components that the EventBus is ready + document.dispatchEvent( + new CustomEvent("event-bus:ready", { bubbles: true, composed: true }), + ); + const userSettings: UserSettings = new UserSettings(); startGame(lobbyConfig.gameID, lobbyConfig.gameStartInfo?.config ?? {}); @@ -136,6 +147,19 @@ export function joinLobby( ); } } + if (message.type === "lobby_chat") { + document.dispatchEvent( + new CustomEvent("lobby-chat:message", { + detail: { + username: message.username, + isHost: message.isHost, + text: message.text, + }, + bubbles: true, + composed: true, + }), + ); + } }; transport.connect(onconnect, onmessage); return () => { diff --git a/src/client/HostLobbyModal.ts b/src/client/HostLobbyModal.ts index 5d94324e92..a672936413 100644 --- a/src/client/HostLobbyModal.ts +++ b/src/client/HostLobbyModal.ts @@ -25,6 +25,7 @@ import { import { generateID } from "../core/Util"; import "./components/baseComponents/Modal"; import "./components/Difficulties"; +import "./components/LobbyChatPanel"; import "./components/LobbyTeamView"; import "./components/Maps"; import { JoinLobbyEvent } from "./Main"; @@ -51,6 +52,7 @@ export class HostLobbyModal extends LitElement { @state() private instantBuild: boolean = false; @state() private randomSpawn: boolean = false; @state() private compactMap: boolean = false; + @state() private chatEnabled: boolean = false; @state() private lobbyId = ""; @state() private copySuccess = false; @state() private clients: ClientInfo[] = []; @@ -410,6 +412,28 @@ export class HostLobbyModal extends LitElement { + + +