internal corporate restructuring

This commit is contained in:
nin0dev 2025-03-15 22:03:19 -04:00
parent 22251c3b2b
commit 6015db1f4f
Signed by: nin0
SSH key fingerprint: SHA256:NOoDnFVvZNFvqfXCIhzr6oCTDImZAbTTuyAysZ8Ufk8
37 changed files with 1207 additions and 348 deletions

View file

@ -1,8 +1,18 @@
{ {
"plugins": ["prettier-plugin-astro"],
"overrides": [
{
"files": "*.astro",
"options": {
"parser": "astro"
}
}
],
"tabWidth": 4, "tabWidth": 4,
"useTabs": true, "useTabs": true,
"singleQuote": false, "singleQuote": false,
"jsxSingleQuote": false, "jsxSingleQuote": false,
"semi": true, "semi": true,
"arrowParens": "avoid" "arrowParens": "avoid",
"trailingComma": "none"
} }

4
.vscode/settings.json vendored Normal file
View file

@ -0,0 +1,4 @@
{
"editor.defaultFormatter": "esbenp.prettier-vscode",
"editor.formatOnSave": true
}

View file

@ -3,8 +3,16 @@ import node from "@astrojs/node";
import cloudflare from "@astrojs/cloudflare"; import cloudflare from "@astrojs/cloudflare";
import react from "@astrojs/react";
// https://astro.build/config // https://astro.build/config
export default defineConfig({ export default defineConfig({
output: "server", output: "server",
adapter: cloudflare() adapter: cloudflare(),
integrations: [react()],
vite: {
server: {
allowedHosts: ["nin0-pc.buri-roach.ts.net"]
}
}
}); });

View file

@ -13,10 +13,18 @@
"7.css": "^0.16.0", "7.css": "^0.16.0",
"@astrojs/cloudflare": "^12.2.4", "@astrojs/cloudflare": "^12.2.4",
"@astrojs/node": "^9.1.3", "@astrojs/node": "^9.1.3",
"@astrojs/react": "^4.2.1",
"@fontsource-variable/noto-emoji": "^5.2.5",
"@fontsource/inter": "^5.2.5",
"@types/react": "^19.0.10",
"@types/react-dom": "^19.0.4",
"astro": "^5.5.2", "astro": "^5.5.2",
"lanyard-wrapper": "^2.0.1" "react": "^19.0.0",
"react-dom": "^19.0.0"
}, },
"devDependencies": { "devDependencies": {
"prettier": "^3.5.3",
"prettier-plugin-astro": "^0.14.1",
"wrangler": "^3.112.0" "wrangler": "^3.112.0"
} }
} }

502
pnpm-lock.yaml generated
View file

@ -17,13 +17,37 @@ importers:
'@astrojs/node': '@astrojs/node':
specifier: ^9.1.3 specifier: ^9.1.3
version: 9.1.3(astro@5.5.2(rollup@4.34.9)(typescript@5.8.2)) version: 9.1.3(astro@5.5.2(rollup@4.34.9)(typescript@5.8.2))
'@astrojs/react':
specifier: ^4.2.1
version: 4.2.1(@types/react-dom@19.0.4(@types/react@19.0.10))(@types/react@19.0.10)(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
'@fontsource-variable/noto-emoji':
specifier: ^5.2.5
version: 5.2.5
'@fontsource/inter':
specifier: ^5.2.5
version: 5.2.5
'@types/react':
specifier: ^19.0.10
version: 19.0.10
'@types/react-dom':
specifier: ^19.0.4
version: 19.0.4(@types/react@19.0.10)
astro: astro:
specifier: ^5.5.2 specifier: ^5.5.2
version: 5.5.2(rollup@4.34.9)(typescript@5.8.2) version: 5.5.2(rollup@4.34.9)(typescript@5.8.2)
lanyard-wrapper: react:
specifier: ^2.0.1 specifier: ^19.0.0
version: 2.0.1 version: 19.0.0
react-dom:
specifier: ^19.0.0
version: 19.0.0(react@19.0.0)
devDependencies: devDependencies:
prettier:
specifier: ^3.5.3
version: 3.5.3
prettier-plugin-astro:
specifier: ^0.14.1
version: 0.14.1
wrangler: wrangler:
specifier: ^3.112.0 specifier: ^3.112.0
version: 3.112.0(@cloudflare/workers-types@4.20250303.0) version: 3.112.0(@cloudflare/workers-types@4.20250303.0)
@ -33,6 +57,10 @@ packages:
7.css@0.16.0: 7.css@0.16.0:
resolution: {integrity: sha512-qZleAhXgVqtAc8Wb4mAJRczbGBcUMv6i2wNogXzHgf9Dztky0CqrehWOJtzU05tMw9a9xLeyvumnJeD+WjLiNQ==} resolution: {integrity: sha512-qZleAhXgVqtAc8Wb4mAJRczbGBcUMv6i2wNogXzHgf9Dztky0CqrehWOJtzU05tMw9a9xLeyvumnJeD+WjLiNQ==}
'@ampproject/remapping@2.3.0':
resolution: {integrity: sha512-30iZtAPgz+LTIYoeivqYo853f02jBYSd5uGnGpkFV0M3xOt9aN73erkgYAmZU43x4VfqcnLxW9Kpg3R5LC4YYw==}
engines: {node: '>=6.0.0'}
'@astrojs/cloudflare@12.2.4': '@astrojs/cloudflare@12.2.4':
resolution: {integrity: sha512-iFCVNKFpSNoeF1V6ck885uWZvPmbaiJAf2o+Dt6qUb4vYtUwS85nuMOwwwY8MkIc1pg0Zvhx6x6LAp2DWn4HZQ==} resolution: {integrity: sha512-iFCVNKFpSNoeF1V6ck885uWZvPmbaiJAf2o+Dt6qUb4vYtUwS85nuMOwwwY8MkIc1pg0Zvhx6x6LAp2DWn4HZQ==}
peerDependencies: peerDependencies:
@ -56,6 +84,15 @@ packages:
resolution: {integrity: sha512-GilTHKGCW6HMq7y3BUv9Ac7GMe/MO9gi9GW62GzKtth0SwukCu/qp2wLiGpEujhY+VVhaG9v7kv/5vFzvf4NYw==} resolution: {integrity: sha512-GilTHKGCW6HMq7y3BUv9Ac7GMe/MO9gi9GW62GzKtth0SwukCu/qp2wLiGpEujhY+VVhaG9v7kv/5vFzvf4NYw==}
engines: {node: ^18.17.1 || ^20.3.0 || >=22.0.0} engines: {node: ^18.17.1 || ^20.3.0 || >=22.0.0}
'@astrojs/react@4.2.1':
resolution: {integrity: sha512-g0P6zxG7RPHNcbmMB15dJJ83+ApBVFBcgnf6BnMz/PVXM150Pa1vYKeuTcWhERqLNgmpI2uXuch5MecIhrUlqQ==}
engines: {node: ^18.17.1 || ^20.3.0 || >=22.0.0}
peerDependencies:
'@types/react': ^17.0.50 || ^18.0.21 || ^19.0.0
'@types/react-dom': ^17.0.17 || ^18.0.6 || ^19.0.0
react: ^17.0.2 || ^18.0.0 || ^19.0.0
react-dom: ^17.0.2 || ^18.0.0 || ^19.0.0
'@astrojs/telemetry@3.2.0': '@astrojs/telemetry@3.2.0':
resolution: {integrity: sha512-wxhSKRfKugLwLlr4OFfcqovk+LIFtKwLyGPqMsv+9/ibqqnW3Gv7tBhtKEb0gAyUAC4G9BTVQeQahqnQAhd6IQ==} resolution: {integrity: sha512-wxhSKRfKugLwLlr4OFfcqovk+LIFtKwLyGPqMsv+9/ibqqnW3Gv7tBhtKEb0gAyUAC4G9BTVQeQahqnQAhd6IQ==}
engines: {node: ^18.17.1 || ^20.3.0 || >=22.0.0} engines: {node: ^18.17.1 || ^20.3.0 || >=22.0.0}
@ -63,6 +100,40 @@ packages:
'@astrojs/underscore-redirects@0.6.0': '@astrojs/underscore-redirects@0.6.0':
resolution: {integrity: sha512-dnJgFpaM955IFNIkEEmMaaIdWXRdeZs1ID6mlGBqdjh6NiCXfKmOdq7L4fd9Dd/tr18fkLrOJ25IUJSxRAEhjQ==} resolution: {integrity: sha512-dnJgFpaM955IFNIkEEmMaaIdWXRdeZs1ID6mlGBqdjh6NiCXfKmOdq7L4fd9Dd/tr18fkLrOJ25IUJSxRAEhjQ==}
'@babel/code-frame@7.26.2':
resolution: {integrity: sha512-RJlIHRueQgwWitWgF8OdFYGZX328Ax5BCemNGlqHfplnRT9ESi8JkFlvaVYbS+UubVY6dpv87Fs2u5M29iNFVQ==}
engines: {node: '>=6.9.0'}
'@babel/compat-data@7.26.8':
resolution: {integrity: sha512-oH5UPLMWR3L2wEFLnFJ1TZXqHufiTKAiLfqw5zkhS4dKXLJ10yVztfil/twG8EDTA4F/tvVNw9nOl4ZMslB8rQ==}
engines: {node: '>=6.9.0'}
'@babel/core@7.26.10':
resolution: {integrity: sha512-vMqyb7XCDMPvJFFOaT9kxtiRh42GwlZEg1/uIgtZshS5a/8OaduUfCi7kynKgc3Tw/6Uo2D+db9qBttghhmxwQ==}
engines: {node: '>=6.9.0'}
'@babel/generator@7.26.10':
resolution: {integrity: sha512-rRHT8siFIXQrAYOYqZQVsAr8vJ+cBNqcVAY6m5V8/4QqzaPl+zDBe6cLEPRDuNOUf3ww8RfJVlOyQMoSI+5Ang==}
engines: {node: '>=6.9.0'}
'@babel/helper-compilation-targets@7.26.5':
resolution: {integrity: sha512-IXuyn5EkouFJscIDuFF5EsiSolseme1s0CZB+QxVugqJLYmKdxI1VfIBOst0SUu4rnk2Z7kqTwmoO1lp3HIfnA==}
engines: {node: '>=6.9.0'}
'@babel/helper-module-imports@7.25.9':
resolution: {integrity: sha512-tnUA4RsrmflIM6W6RFTLFSXITtl0wKjgpnLgXyowocVPrbYrLUXSBXDgTs8BlbmIzIdlBySRQjINYs2BAkiLtw==}
engines: {node: '>=6.9.0'}
'@babel/helper-module-transforms@7.26.0':
resolution: {integrity: sha512-xO+xu6B5K2czEnQye6BHA7DolFFmS3LB7stHZFaOLb1pAwO1HWLS8fXA+eh0A2yIvltPVmx3eNNDBJA2SLHXFw==}
engines: {node: '>=6.9.0'}
peerDependencies:
'@babel/core': ^7.0.0
'@babel/helper-plugin-utils@7.26.5':
resolution: {integrity: sha512-RS+jZcRdZdRFzMyr+wcsaqOmld1/EqTghfaBGQQd/WnRdzdlvSZ//kF7U8VQTxf1ynZ4cjUcYgjVGx13ewNPMg==}
engines: {node: '>=6.9.0'}
'@babel/helper-string-parser@7.25.9': '@babel/helper-string-parser@7.25.9':
resolution: {integrity: sha512-4A/SCr/2KLd5jrtOMFzaKjVtAei3+2r/NChoBNoZ3EyP/+GlhoaEGoWOZUmFmoITP7zOJyHIMm+DYRd8o3PvHA==} resolution: {integrity: sha512-4A/SCr/2KLd5jrtOMFzaKjVtAei3+2r/NChoBNoZ3EyP/+GlhoaEGoWOZUmFmoITP7zOJyHIMm+DYRd8o3PvHA==}
engines: {node: '>=6.9.0'} engines: {node: '>=6.9.0'}
@ -71,11 +142,39 @@ packages:
resolution: {integrity: sha512-Ed61U6XJc3CVRfkERJWDz4dJwKe7iLmmJsbOGu9wSloNSFttHV0I8g6UAgb7qnK5ly5bGLPd4oXZlxCdANBOWQ==} resolution: {integrity: sha512-Ed61U6XJc3CVRfkERJWDz4dJwKe7iLmmJsbOGu9wSloNSFttHV0I8g6UAgb7qnK5ly5bGLPd4oXZlxCdANBOWQ==}
engines: {node: '>=6.9.0'} engines: {node: '>=6.9.0'}
'@babel/helper-validator-option@7.25.9':
resolution: {integrity: sha512-e/zv1co8pp55dNdEcCynfj9X7nyUKUXoUEwfXqaZt0omVOmDe9oOTdKStH4GmAw6zxMFs50ZayuMfHDKlO7Tfw==}
engines: {node: '>=6.9.0'}
'@babel/helpers@7.26.10':
resolution: {integrity: sha512-UPYc3SauzZ3JGgj87GgZ89JVdC5dj0AoetR5Bw6wj4niittNyFh6+eOGonYvJ1ao6B8lEa3Q3klS7ADZ53bc5g==}
engines: {node: '>=6.9.0'}
'@babel/parser@7.26.10': '@babel/parser@7.26.10':
resolution: {integrity: sha512-6aQR2zGE/QFi8JpDLjUZEPYOs7+mhKXm86VaKFiLP35JQwQb6bwUE+XbvkH0EptsYhbNBSUGaUBLKqxH1xSgsA==} resolution: {integrity: sha512-6aQR2zGE/QFi8JpDLjUZEPYOs7+mhKXm86VaKFiLP35JQwQb6bwUE+XbvkH0EptsYhbNBSUGaUBLKqxH1xSgsA==}
engines: {node: '>=6.0.0'} engines: {node: '>=6.0.0'}
hasBin: true hasBin: true
'@babel/plugin-transform-react-jsx-self@7.25.9':
resolution: {integrity: sha512-y8quW6p0WHkEhmErnfe58r7x0A70uKphQm8Sp8cV7tjNQwK56sNVK0M73LK3WuYmsuyrftut4xAkjjgU0twaMg==}
engines: {node: '>=6.9.0'}
peerDependencies:
'@babel/core': ^7.0.0-0
'@babel/plugin-transform-react-jsx-source@7.25.9':
resolution: {integrity: sha512-+iqjT8xmXhhYv4/uiYd8FNQsraMFZIfxVSqxxVSZP0WbbSAWvBXAul0m/zu+7Vv4O/3WtApy9pmaTMiumEZgfg==}
engines: {node: '>=6.9.0'}
peerDependencies:
'@babel/core': ^7.0.0-0
'@babel/template@7.26.9':
resolution: {integrity: sha512-qyRplbeIpNZhmzOysF/wFMuP9sctmh2cFzRAZOn1YapxBsE1i9bJIY586R/WBLfLcmcBlM8ROBiQURnnNy+zfA==}
engines: {node: '>=6.9.0'}
'@babel/traverse@7.26.10':
resolution: {integrity: sha512-k8NuDrxr0WrPH5Aupqb2LCVURP/S0vBEn5mK6iH+GIYob66U5EtoZvcdudR2jQ4cmTwhEwW1DLB+Yyas9zjF6A==}
engines: {node: '>=6.9.0'}
'@babel/types@7.26.10': '@babel/types@7.26.10':
resolution: {integrity: sha512-emqcG3vHrpxUKTrxcblR36dcrcoRDvKmnL/dCL6ZsHaShW80qxCAcNhzQZrpeM765VzEos+xOi4s+r4IXzTwdQ==} resolution: {integrity: sha512-emqcG3vHrpxUKTrxcblR36dcrcoRDvKmnL/dCL6ZsHaShW80qxCAcNhzQZrpeM765VzEos+xOi4s+r4IXzTwdQ==}
engines: {node: '>=6.9.0'} engines: {node: '>=6.9.0'}
@ -420,6 +519,12 @@ packages:
resolution: {integrity: sha512-vBZP4NlzfOlerQTnba4aqZoMhE/a9HY7HRqoOPaETQcSQuWEIyZMHGfVu6w9wGtGK5fED5qRs2DteVCjOH60sA==} resolution: {integrity: sha512-vBZP4NlzfOlerQTnba4aqZoMhE/a9HY7HRqoOPaETQcSQuWEIyZMHGfVu6w9wGtGK5fED5qRs2DteVCjOH60sA==}
engines: {node: '>=14'} engines: {node: '>=14'}
'@fontsource-variable/noto-emoji@5.2.5':
resolution: {integrity: sha512-p/poFM8KKkBpY/fumf8dKPwclakNNpSpw/ro+TvkEAC4/jESvRJfFpl54LSUmGF8iXpi3w3o8aOc7A3he8c+NA==}
'@fontsource/inter@5.2.5':
resolution: {integrity: sha512-kbsPKj0S4p44JdYRFiW78Td8Ge2sBVxi/PIBwmih+RpSXUdvS9nbs1HIiuUSPtRMi14CqLEZ/fbk7dj7vni1Sg==}
'@img/sharp-darwin-arm64@0.33.5': '@img/sharp-darwin-arm64@0.33.5':
resolution: {integrity: sha512-UT4p+iz/2H4twwAoLCqfA9UH5pI6DggwKEGuaPy7nCVQ8ZsiY5PIcrRvD1DzuY3qYL07NtIQcWnBSY/heikIFQ==} resolution: {integrity: sha512-UT4p+iz/2H4twwAoLCqfA9UH5pI6DggwKEGuaPy7nCVQ8ZsiY5PIcrRvD1DzuY3qYL07NtIQcWnBSY/heikIFQ==}
engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0}
@ -525,13 +630,24 @@ packages:
cpu: [x64] cpu: [x64]
os: [win32] os: [win32]
'@jridgewell/gen-mapping@0.3.8':
resolution: {integrity: sha512-imAbBGkb+ebQyxKgzv5Hu2nmROxoDOXHh80evxdoXNOrvAnVx7zimzc1Oo5h9RlfV4vPXaE2iM5pOFbvOCClWA==}
engines: {node: '>=6.0.0'}
'@jridgewell/resolve-uri@3.1.2': '@jridgewell/resolve-uri@3.1.2':
resolution: {integrity: sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==} resolution: {integrity: sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==}
engines: {node: '>=6.0.0'} engines: {node: '>=6.0.0'}
'@jridgewell/set-array@1.2.1':
resolution: {integrity: sha512-R8gLRTZeyp03ymzP/6Lil/28tGeGEzhx1q2k703KGWRAI1VdvPIXdG70VJc2pAMw3NA6JKL5hhFu1sJX0Mnn/A==}
engines: {node: '>=6.0.0'}
'@jridgewell/sourcemap-codec@1.5.0': '@jridgewell/sourcemap-codec@1.5.0':
resolution: {integrity: sha512-gv3ZRaISU3fjPAgNsriBRqGWQL6quFx04YMPW/zD8XMLsU32mhCCbfbO6KZFLjvYpCZ8zyDEgqsgf+PwPaM7GQ==} resolution: {integrity: sha512-gv3ZRaISU3fjPAgNsriBRqGWQL6quFx04YMPW/zD8XMLsU32mhCCbfbO6KZFLjvYpCZ8zyDEgqsgf+PwPaM7GQ==}
'@jridgewell/trace-mapping@0.3.25':
resolution: {integrity: sha512-vNk6aEwybGtawWmy/PzwnGDOjCkLWSD2wqvjGGAgOAwCGWySYXfYoxt00IJkTF+8Lb57DwOb3Aa0o9CApepiYQ==}
'@jridgewell/trace-mapping@0.3.9': '@jridgewell/trace-mapping@0.3.9':
resolution: {integrity: sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==} resolution: {integrity: sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==}
@ -663,6 +779,18 @@ packages:
'@shikijs/vscode-textmate@10.0.2': '@shikijs/vscode-textmate@10.0.2':
resolution: {integrity: sha512-83yeghZ2xxin3Nj8z1NMd/NCuca+gsYXswywDy5bHvwlWL8tpTQmzGeUuHd9FC3E/SBEMvzJRwWEOz5gGes9Qg==} resolution: {integrity: sha512-83yeghZ2xxin3Nj8z1NMd/NCuca+gsYXswywDy5bHvwlWL8tpTQmzGeUuHd9FC3E/SBEMvzJRwWEOz5gGes9Qg==}
'@types/babel__core@7.20.5':
resolution: {integrity: sha512-qoQprZvz5wQFJwMDqeseRXWv3rqMvhgpbXFfVyWhbx9X47POIA6i/+dXefEmZKoAgOaTdaIgNSMqMIU61yRyzA==}
'@types/babel__generator@7.6.8':
resolution: {integrity: sha512-ASsj+tpEDsEiFr1arWrlN6V3mdfjRMZt6LtK/Vp/kreFLnr5QH5+DhvD5nINYZXzwJvXeGq+05iUXcAzVrqWtw==}
'@types/babel__template@7.4.4':
resolution: {integrity: sha512-h/NUaSyG5EyxBIp8YRxo4RMe2/qQgvyowRwVMzhYhBCONbW8PUsg4lkFMrhgZhUe5z3L3MiLDuvyJ/CaPa2A8A==}
'@types/babel__traverse@7.20.6':
resolution: {integrity: sha512-r1bzfrm0tomOI8g1SzvCaQHo6Lcv6zu0EA+W2kHrt8dyrHQxGzBBL4kdkzIS+jBMV+EYcMAEAqXqYaLJq5rOZg==}
'@types/cookie@0.6.0': '@types/cookie@0.6.0':
resolution: {integrity: sha512-4Kh9a6B2bQciAhf7FSuMRRkUWecJgJu9nPnx3yzpsfXX/c50REIqpHY4C82bXP90qrLtXtkDxTZosYO3UpOwlA==} resolution: {integrity: sha512-4Kh9a6B2bQciAhf7FSuMRRkUWecJgJu9nPnx3yzpsfXX/c50REIqpHY4C82bXP90qrLtXtkDxTZosYO3UpOwlA==}
@ -684,12 +812,26 @@ packages:
'@types/nlcst@2.0.3': '@types/nlcst@2.0.3':
resolution: {integrity: sha512-vSYNSDe6Ix3q+6Z7ri9lyWqgGhJTmzRjZRqyq15N0Z/1/UnVsno9G/N40NBijoYx2seFDIl0+B2mgAb9mezUCA==} resolution: {integrity: sha512-vSYNSDe6Ix3q+6Z7ri9lyWqgGhJTmzRjZRqyq15N0Z/1/UnVsno9G/N40NBijoYx2seFDIl0+B2mgAb9mezUCA==}
'@types/react-dom@19.0.4':
resolution: {integrity: sha512-4fSQ8vWFkg+TGhePfUzVmat3eC14TXYSsiiDSLI0dVLsrm9gZFABjPy/Qu6TKgl1tq1Bu1yDsuQgY3A3DOjCcg==}
peerDependencies:
'@types/react': ^19.0.0
'@types/react@19.0.10':
resolution: {integrity: sha512-JuRQ9KXLEjaUNjTWpzuR231Z2WpIwczOkBEIvbHNCzQefFIT0L8IqE6NV6ULLyC1SI/i234JnDoMkfg+RjQj2g==}
'@types/unist@3.0.2': '@types/unist@3.0.2':
resolution: {integrity: sha512-dqId9J8K/vGi5Zr7oo212BGii5m3q5Hxlkwy3WpYuKPklmBEvsbMYYyLxAQpSffdLl/gdW0XUpKWFvYmyoWCoQ==} resolution: {integrity: sha512-dqId9J8K/vGi5Zr7oo212BGii5m3q5Hxlkwy3WpYuKPklmBEvsbMYYyLxAQpSffdLl/gdW0XUpKWFvYmyoWCoQ==}
'@ungap/structured-clone@1.2.0': '@ungap/structured-clone@1.2.0':
resolution: {integrity: sha512-zuVdFrMJiuCDQUMCzQaD6KL28MjnqqN8XnAqiEq9PNm/hCPTSGfrXCOfwj1ow4LFb/tNymJPwsNbVePc1xFqrQ==} resolution: {integrity: sha512-zuVdFrMJiuCDQUMCzQaD6KL28MjnqqN8XnAqiEq9PNm/hCPTSGfrXCOfwj1ow4LFb/tNymJPwsNbVePc1xFqrQ==}
'@vitejs/plugin-react@4.3.4':
resolution: {integrity: sha512-SCCPBJtYLdE8PX/7ZQAs1QAZ8Jqwih+0VBLum1EGqmCCQal+MIUqLCzj3ZUy8ufbC0cAM4LRlSTm7IQJwWT4ug==}
engines: {node: ^14.18.0 || >=16.0.0}
peerDependencies:
vite: ^4.2.0 || ^5.0.0 || ^6.0.0
acorn-walk@8.3.2: acorn-walk@8.3.2:
resolution: {integrity: sha512-cjkyv4OtNCIeqhHrfS81QWXoCBPExR/J62oyEqepVw8WaQeSqpW2uhuLPh1m9eWhDuOo/jUXVTlifvesOWp/4A==} resolution: {integrity: sha512-cjkyv4OtNCIeqhHrfS81QWXoCBPExR/J62oyEqepVw8WaQeSqpW2uhuLPh1m9eWhDuOo/jUXVTlifvesOWp/4A==}
engines: {node: '>=0.4.0'} engines: {node: '>=0.4.0'}
@ -758,10 +900,18 @@ packages:
resolution: {integrity: sha512-F3PH5k5juxom4xktynS7MoFY+NUWH5LC4CnH11YB8NPew+HLpmBLCybSAEyb2F+4pRXhuhWqFesoQd6DAyc2hw==} resolution: {integrity: sha512-F3PH5k5juxom4xktynS7MoFY+NUWH5LC4CnH11YB8NPew+HLpmBLCybSAEyb2F+4pRXhuhWqFesoQd6DAyc2hw==}
engines: {node: '>=18'} engines: {node: '>=18'}
browserslist@4.24.4:
resolution: {integrity: sha512-KDi1Ny1gSePi1vm0q4oxSF8b4DR44GF4BbmS2YdhPLOEqd8pDviZOGH/GsmRwoWJ2+5Lr085X7naowMwKHDG1A==}
engines: {node: ^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7}
hasBin: true
camelcase@8.0.0: camelcase@8.0.0:
resolution: {integrity: sha512-8WB3Jcas3swSvjIeA2yvCJ+Miyz5l1ZmB6HFb9R1317dt9LCQoswg/BGrmAmkWVEszSrrg4RwmO46qIm2OEnSA==} resolution: {integrity: sha512-8WB3Jcas3swSvjIeA2yvCJ+Miyz5l1ZmB6HFb9R1317dt9LCQoswg/BGrmAmkWVEszSrrg4RwmO46qIm2OEnSA==}
engines: {node: '>=16'} engines: {node: '>=16'}
caniuse-lite@1.0.30001704:
resolution: {integrity: sha512-+L2IgBbV6gXB4ETf0keSvLr7JUrRVbIaB/lrQ1+z8mRcQiisG5k+lG6O4n6Y5q6f5EuNfaYXKgymucphlEXQew==}
ccount@2.0.1: ccount@2.0.1:
resolution: {integrity: sha512-eyrF0jiFpY+3drT6383f1qhkbGsLSifNAjA61IUjZjmLCWjItY6LB9ft9YhoDgwfmclB2zhu51Lc7+95b8NRAg==} resolution: {integrity: sha512-eyrF0jiFpY+3drT6383f1qhkbGsLSifNAjA61IUjZjmLCWjItY6LB9ft9YhoDgwfmclB2zhu51Lc7+95b8NRAg==}
@ -817,6 +967,9 @@ packages:
confbox@0.1.8: confbox@0.1.8:
resolution: {integrity: sha512-RMtmw0iFkeR4YV+fUOSucriAQNb9g8zFR52MWCtl+cCZOFRNL6zeB395vPzFhEjjn4fMxXudmELnl/KF/WrK6w==} resolution: {integrity: sha512-RMtmw0iFkeR4YV+fUOSucriAQNb9g8zFR52MWCtl+cCZOFRNL6zeB395vPzFhEjjn4fMxXudmELnl/KF/WrK6w==}
convert-source-map@2.0.0:
resolution: {integrity: sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==}
cookie-es@1.2.2: cookie-es@1.2.2:
resolution: {integrity: sha512-+W7VmiVINB+ywl1HGXJXmrqkOhpKrIiVZV6tQuV54ZyQC7MMuBt81Vc336GMLoHBq5hV/F9eXgt5Mnx0Rha5Fg==} resolution: {integrity: sha512-+W7VmiVINB+ywl1HGXJXmrqkOhpKrIiVZV6tQuV54ZyQC7MMuBt81Vc336GMLoHBq5hV/F9eXgt5Mnx0Rha5Fg==}
@ -836,6 +989,9 @@ packages:
engines: {node: '>=4'} engines: {node: '>=4'}
hasBin: true hasBin: true
csstype@3.1.3:
resolution: {integrity: sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==}
data-uri-to-buffer@2.0.2: data-uri-to-buffer@2.0.2:
resolution: {integrity: sha512-ND9qDTLc6diwj+Xe5cdAgVTbLVdXbtxTJRXRhli8Mowuaan+0EJOtdqJ0QCHNSSPyoXGx9HX2/VMnKeC34AChA==} resolution: {integrity: sha512-ND9qDTLc6diwj+Xe5cdAgVTbLVdXbtxTJRXRhli8Mowuaan+0EJOtdqJ0QCHNSSPyoXGx9HX2/VMnKeC34AChA==}
@ -906,6 +1062,9 @@ packages:
ee-first@1.1.1: ee-first@1.1.1:
resolution: {integrity: sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==} resolution: {integrity: sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==}
electron-to-chromium@1.5.119:
resolution: {integrity: sha512-Ku4NMzUjz3e3Vweh7PhApPrZSS4fyiCIbcIrG9eKrriYVLmbMepETR/v6SU7xPm98QTqMSYiCwfO89QNjXLkbQ==}
emoji-regex-xs@1.0.0: emoji-regex-xs@1.0.0:
resolution: {integrity: sha512-LRlerrMYoIDrT6jgpeZ2YYl/L8EulRTt5hQcYjy5AInh7HWXKimpqx68aknBFpGL2+/IcogTcaydJEgaTmOpDg==} resolution: {integrity: sha512-LRlerrMYoIDrT6jgpeZ2YYl/L8EulRTt5hQcYjy5AInh7HWXKimpqx68aknBFpGL2+/IcogTcaydJEgaTmOpDg==}
@ -936,6 +1095,10 @@ packages:
engines: {node: '>=18'} engines: {node: '>=18'}
hasBin: true hasBin: true
escalade@3.2.0:
resolution: {integrity: sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==}
engines: {node: '>=6'}
escape-html@1.0.3: escape-html@1.0.3:
resolution: {integrity: sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==} resolution: {integrity: sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==}
@ -991,6 +1154,10 @@ packages:
engines: {node: ^8.16.0 || ^10.6.0 || >=11.0.0} engines: {node: ^8.16.0 || ^10.6.0 || >=11.0.0}
os: [darwin] os: [darwin]
gensync@1.0.0-beta.2:
resolution: {integrity: sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg==}
engines: {node: '>=6.9.0'}
get-east-asian-width@1.2.0: get-east-asian-width@1.2.0:
resolution: {integrity: sha512-2nk+7SIVb14QrgXFHcm84tD4bKQz0RxPuMT8Ag5KPOq7J5fEmAg0UbXdTOSHqNuHSU28k55qnceesxXRZGzKWA==} resolution: {integrity: sha512-2nk+7SIVb14QrgXFHcm84tD4bKQz0RxPuMT8Ag5KPOq7J5fEmAg0UbXdTOSHqNuHSU28k55qnceesxXRZGzKWA==}
engines: {node: '>=18'} engines: {node: '>=18'}
@ -1004,6 +1171,10 @@ packages:
glob-to-regexp@0.4.1: glob-to-regexp@0.4.1:
resolution: {integrity: sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw==} resolution: {integrity: sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw==}
globals@11.12.0:
resolution: {integrity: sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==}
engines: {node: '>=4'}
h3@1.15.1: h3@1.15.1:
resolution: {integrity: sha512-+ORaOBttdUm1E2Uu/obAyCguiI7MbBvsLTndc3gyK3zU+SYLoZXlyCP9Xgy0gikkGufFLTZXCXD6+4BsufnmHA==} resolution: {integrity: sha512-+ORaOBttdUm1E2Uu/obAyCguiI7MbBvsLTndc3gyK3zU+SYLoZXlyCP9Xgy0gikkGufFLTZXCXD6+4BsufnmHA==}
@ -1090,10 +1261,23 @@ packages:
resolution: {integrity: sha512-UcVfVfaK4Sc4m7X3dUSoHoozQGBEFeDC+zVo06t98xe8CzHSZZBekNXH+tu0NalHolcJ/QAGqS46Hef7QXBIMw==} resolution: {integrity: sha512-UcVfVfaK4Sc4m7X3dUSoHoozQGBEFeDC+zVo06t98xe8CzHSZZBekNXH+tu0NalHolcJ/QAGqS46Hef7QXBIMw==}
engines: {node: '>=16'} engines: {node: '>=16'}
js-tokens@4.0.0:
resolution: {integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==}
js-yaml@4.1.0: js-yaml@4.1.0:
resolution: {integrity: sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==} resolution: {integrity: sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==}
hasBin: true hasBin: true
jsesc@3.1.0:
resolution: {integrity: sha512-/sM3dO2FOzXjKQhJuo0Q173wf2KOo8t4I8vHy6lF9poUp7bKT0/NHE8fPX23PwfhnykfqnC2xRxOnVw5XuGIaA==}
engines: {node: '>=6'}
hasBin: true
json5@2.2.3:
resolution: {integrity: sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==}
engines: {node: '>=6'}
hasBin: true
kleur@3.0.3: kleur@3.0.3:
resolution: {integrity: sha512-eTIzlVOSUR+JxdDFepEYcBMtZ9Qqdef+rnzWdRZuMbOywu5tO2w2N7rqjoANZ5k9vywhL6Br1VRjUIgTQx4E8w==} resolution: {integrity: sha512-eTIzlVOSUR+JxdDFepEYcBMtZ9Qqdef+rnzWdRZuMbOywu5tO2w2N7rqjoANZ5k9vywhL6Br1VRjUIgTQx4E8w==}
engines: {node: '>=6'} engines: {node: '>=6'}
@ -1102,15 +1286,15 @@ packages:
resolution: {integrity: sha512-o+NO+8WrRiQEE4/7nwRJhN1HWpVmJm511pBHUxPLtp0BUISzlBplORYSmTclCnJvQq2tKu/sgl3xVpkc7ZWuQQ==} resolution: {integrity: sha512-o+NO+8WrRiQEE4/7nwRJhN1HWpVmJm511pBHUxPLtp0BUISzlBplORYSmTclCnJvQq2tKu/sgl3xVpkc7ZWuQQ==}
engines: {node: '>=6'} engines: {node: '>=6'}
lanyard-wrapper@2.0.1:
resolution: {integrity: sha512-wDMqGTEzc1AXvs3i2JaVkDHCzA7FCkpsdlJIpypOiDhhkIYJhhnDzOo91FQ3E6u5fQiF1Q8vfOOKm3kZ3peQSw==}
longest-streak@3.1.0: longest-streak@3.1.0:
resolution: {integrity: sha512-9Ri+o0JYgehTaVBBDoMqIl8GXtbWg711O3srftcHhZ0dqnETqLaoIK0x17fUw9rFSlK/0NlsKe0Ahhyl5pXE2g==} resolution: {integrity: sha512-9Ri+o0JYgehTaVBBDoMqIl8GXtbWg711O3srftcHhZ0dqnETqLaoIK0x17fUw9rFSlK/0NlsKe0Ahhyl5pXE2g==}
lru-cache@10.4.3: lru-cache@10.4.3:
resolution: {integrity: sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==} resolution: {integrity: sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==}
lru-cache@5.1.1:
resolution: {integrity: sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w==}
magic-string@0.25.9: magic-string@0.25.9:
resolution: {integrity: sha512-RmF0AsMzgt25qzqqLc1+MbHmhdx0ojF2Fvs4XnOqz2ZOBXzzkEwc/dJQZCYHAn7v1jbVOjAZfK8msRn4BxO4VQ==} resolution: {integrity: sha512-RmF0AsMzgt25qzqqLc1+MbHmhdx0ojF2Fvs4XnOqz2ZOBXzzkEwc/dJQZCYHAn7v1jbVOjAZfK8msRn4BxO4VQ==}
@ -1299,6 +1483,9 @@ packages:
node-mock-http@1.0.0: node-mock-http@1.0.0:
resolution: {integrity: sha512-0uGYQ1WQL1M5kKvGRXWQ3uZCHtLTO8hln3oBjIusM75WoesZ909uQJs/Hb946i2SS+Gsrhkaa6iAO17jRIv6DQ==} resolution: {integrity: sha512-0uGYQ1WQL1M5kKvGRXWQ3uZCHtLTO8hln3oBjIusM75WoesZ909uQJs/Hb946i2SS+Gsrhkaa6iAO17jRIv6DQ==}
node-releases@2.0.19:
resolution: {integrity: sha512-xxOWJsBKtzAq7DY0J+DTzuz58K8e7sJbdgwkbMWQe8UYB6ekmsQ45q0M/tJDsGaZmbC+l7n57UV8Hl5tHxO9uw==}
normalize-path@3.0.0: normalize-path@3.0.0:
resolution: {integrity: sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==} resolution: {integrity: sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==}
engines: {node: '>=0.10.0'} engines: {node: '>=0.10.0'}
@ -1364,6 +1551,15 @@ packages:
resolution: {integrity: sha512-dle9A3yYxlBSrt8Fu+IpjGT8SY8hN0mlaA6GY8t0P5PjIOZemULz/E2Bnm/2dcUOena75OTNkHI76uZBNUUq3A==} resolution: {integrity: sha512-dle9A3yYxlBSrt8Fu+IpjGT8SY8hN0mlaA6GY8t0P5PjIOZemULz/E2Bnm/2dcUOena75OTNkHI76uZBNUUq3A==}
engines: {node: ^10 || ^12 || >=14} engines: {node: ^10 || ^12 || >=14}
prettier-plugin-astro@0.14.1:
resolution: {integrity: sha512-RiBETaaP9veVstE4vUwSIcdATj6dKmXljouXc/DDNwBSPTp8FRkLGDSGFClKsAFeeg+13SB0Z1JZvbD76bigJw==}
engines: {node: ^14.15.0 || >=16.0.0}
prettier@3.5.3:
resolution: {integrity: sha512-QQtaxnoDJeAkDvDKWCLiwIXkTgRhwYDEQCghU9Z6q03iyek/rxRh/2lC3HB7P8sWT2xC/y5JDctPLBIGzHKbhw==}
engines: {node: '>=14'}
hasBin: true
printable-characters@1.0.42: printable-characters@1.0.42:
resolution: {integrity: sha512-dKp+C4iXWK4vVYZmYSd0KBH5F/h1HoZRsbJ82AVKRO3PEo8L4lBS/vLwhVtpwwuYcoIsVY+1JYKR268yn480uQ==} resolution: {integrity: sha512-dKp+C4iXWK4vVYZmYSd0KBH5F/h1HoZRsbJ82AVKRO3PEo8L4lBS/vLwhVtpwwuYcoIsVY+1JYKR268yn480uQ==}
@ -1388,6 +1584,19 @@ packages:
resolution: {integrity: sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==} resolution: {integrity: sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==}
engines: {node: '>= 0.6'} engines: {node: '>= 0.6'}
react-dom@19.0.0:
resolution: {integrity: sha512-4GV5sHFG0e/0AD4X+ySy6UJd3jVl1iNsNHdpad0qhABJ11twS3TTBnseqsKurKcsNqCEFeGL3uLpVChpIO3QfQ==}
peerDependencies:
react: ^19.0.0
react-refresh@0.14.2:
resolution: {integrity: sha512-jCvmsr+1IUSMUyzOkRcvnVbX3ZYC6g9TDrDbFuFmRDq7PD4yaGbLKNQL6k2jnArV8hjYxh7hVhAZB6s9HDGpZA==}
engines: {node: '>=0.10.0'}
react@19.0.0:
resolution: {integrity: sha512-V8AVnmPIICiWpGfm6GLzCR/W5FXLchHop40W4nXBmdlEceh16rCN8O8LNWm5bh5XUX91fh7KpA+W0TgMKmgTpQ==}
engines: {node: '>=0.10.0'}
readdirp@4.1.2: readdirp@4.1.2:
resolution: {integrity: sha512-GDhwkLfywWL2s6vEjyhri+eXmfH6j1L7JE27WhqLeYzoh/A3DBaYGEj2H/HFZCn/kMfim73FXxEJTw06WtxQwg==} resolution: {integrity: sha512-GDhwkLfywWL2s6vEjyhri+eXmfH6j1L7JE27WhqLeYzoh/A3DBaYGEj2H/HFZCn/kMfim73FXxEJTw06WtxQwg==}
engines: {node: '>= 14.18.0'} engines: {node: '>= 14.18.0'}
@ -1459,6 +1668,19 @@ packages:
engines: {node: '>=18.0.0', npm: '>=8.0.0'} engines: {node: '>=18.0.0', npm: '>=8.0.0'}
hasBin: true hasBin: true
s.color@0.0.15:
resolution: {integrity: sha512-AUNrbEUHeKY8XsYr/DYpl+qk5+aM+DChopnWOPEzn8YKzOhv4l2zH6LzZms3tOZP3wwdOyc0RmTciyi46HLIuA==}
sass-formatter@0.7.9:
resolution: {integrity: sha512-CWZ8XiSim+fJVG0cFLStwDvft1VI7uvXdCNJYXhDvowiv+DsbD1nXLiQ4zrE5UBvj5DWZJ93cwN0NX5PMsr1Pw==}
scheduler@0.25.0:
resolution: {integrity: sha512-xFVuu11jh+xcO7JOAGJNOXld8/TcEHK/4CituBUeUb5hqxJLj9YuemAEuvm9gQ/+pgXYfbQuqAkiYu+u7YEsNA==}
semver@6.3.1:
resolution: {integrity: sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==}
hasBin: true
semver@7.7.1: semver@7.7.1:
resolution: {integrity: sha512-hlq8tAfn0m/61p4BVRcPzIGr6LKiMwo4VM6dGi6pt4qcRkmNzTcWq6eCEjEh+qXjkMDvPlOFFSGwQjoEa6gyMA==} resolution: {integrity: sha512-hlq8tAfn0m/61p4BVRcPzIGr6LKiMwo4VM6dGi6pt4qcRkmNzTcWq6eCEjEh+qXjkMDvPlOFFSGwQjoEa6gyMA==}
engines: {node: '>=10'} engines: {node: '>=10'}
@ -1536,6 +1758,9 @@ packages:
resolution: {integrity: sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==} resolution: {integrity: sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==}
engines: {node: '>=12'} engines: {node: '>=12'}
suf-log@2.5.3:
resolution: {integrity: sha512-KvC8OPjzdNOe+xQ4XWJV2whQA0aM1kGVczMQ8+dStAO6KfEB140JEVQ9dE76ONZ0/Ylf67ni4tILPJB41U0eow==}
tinyexec@0.3.2: tinyexec@0.3.2:
resolution: {integrity: sha512-KQQR9yN7R5+OSwaK0XQoj22pwHoTlgYqmUscPYoknOoWCWfj/5/ABTMRi69FrKU5ffPVh5QcFikpWJI/P1ocHA==} resolution: {integrity: sha512-KQQR9yN7R5+OSwaK0XQoj22pwHoTlgYqmUscPYoknOoWCWfj/5/ABTMRi69FrKU5ffPVh5QcFikpWJI/P1ocHA==}
@ -1680,6 +1905,12 @@ packages:
uploadthing: uploadthing:
optional: true optional: true
update-browserslist-db@1.1.3:
resolution: {integrity: sha512-UxhIZQ+QInVdunkDAaiazvvT/+fXL5Osr0JZlJulepYu6Jd7qJtDZjlur0emRlT71EN3ScPoE7gvsuIKKNavKw==}
hasBin: true
peerDependencies:
browserslist: '>= 4.21.0'
vfile-location@5.0.3: vfile-location@5.0.3:
resolution: {integrity: sha512-5yXvWDEgqeiYiBe1lbxYF7UMAIm/IcopxMHrMQDq3nvKcjPKIhZklUKL+AE7J7uApI4kwe2snsK+eI6UTj9EHg==} resolution: {integrity: sha512-5yXvWDEgqeiYiBe1lbxYF7UMAIm/IcopxMHrMQDq3nvKcjPKIhZklUKL+AE7J7uApI4kwe2snsK+eI6UTj9EHg==}
@ -1822,6 +2053,9 @@ packages:
xxhash-wasm@1.1.0: xxhash-wasm@1.1.0:
resolution: {integrity: sha512-147y/6YNh+tlp6nd/2pWq38i9h6mz/EuQ6njIrmW8D1BS5nCqs0P6DG+m6zTGnNz5I+uhZ0SHxBs9BsPrwcKDA==} resolution: {integrity: sha512-147y/6YNh+tlp6nd/2pWq38i9h6mz/EuQ6njIrmW8D1BS5nCqs0P6DG+m6zTGnNz5I+uhZ0SHxBs9BsPrwcKDA==}
yallist@3.1.1:
resolution: {integrity: sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==}
yargs-parser@21.1.1: yargs-parser@21.1.1:
resolution: {integrity: sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==} resolution: {integrity: sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==}
engines: {node: '>=12'} engines: {node: '>=12'}
@ -1865,6 +2099,11 @@ snapshots:
7.css@0.16.0: {} 7.css@0.16.0: {}
'@ampproject/remapping@2.3.0':
dependencies:
'@jridgewell/gen-mapping': 0.3.8
'@jridgewell/trace-mapping': 0.3.25
'@astrojs/cloudflare@12.2.4(astro@5.5.2(rollup@4.34.9)(typescript@5.8.2))': '@astrojs/cloudflare@12.2.4(astro@5.5.2(rollup@4.34.9)(typescript@5.8.2))':
dependencies: dependencies:
'@astrojs/internal-helpers': 0.6.1 '@astrojs/internal-helpers': 0.6.1
@ -1936,6 +2175,29 @@ snapshots:
dependencies: dependencies:
prismjs: 1.29.0 prismjs: 1.29.0
'@astrojs/react@4.2.1(@types/react-dom@19.0.4(@types/react@19.0.10))(@types/react@19.0.10)(react-dom@19.0.0(react@19.0.0))(react@19.0.0)':
dependencies:
'@types/react': 19.0.10
'@types/react-dom': 19.0.4(@types/react@19.0.10)
'@vitejs/plugin-react': 4.3.4(vite@6.2.2)
react: 19.0.0
react-dom: 19.0.0(react@19.0.0)
ultrahtml: 1.5.3
vite: 6.2.2
transitivePeerDependencies:
- '@types/node'
- jiti
- less
- lightningcss
- sass
- sass-embedded
- stylus
- sugarss
- supports-color
- terser
- tsx
- yaml
'@astrojs/telemetry@3.2.0': '@astrojs/telemetry@3.2.0':
dependencies: dependencies:
ci-info: 4.2.0 ci-info: 4.2.0
@ -1950,14 +2212,111 @@ snapshots:
'@astrojs/underscore-redirects@0.6.0': {} '@astrojs/underscore-redirects@0.6.0': {}
'@babel/code-frame@7.26.2':
dependencies:
'@babel/helper-validator-identifier': 7.25.9
js-tokens: 4.0.0
picocolors: 1.1.1
'@babel/compat-data@7.26.8': {}
'@babel/core@7.26.10':
dependencies:
'@ampproject/remapping': 2.3.0
'@babel/code-frame': 7.26.2
'@babel/generator': 7.26.10
'@babel/helper-compilation-targets': 7.26.5
'@babel/helper-module-transforms': 7.26.0(@babel/core@7.26.10)
'@babel/helpers': 7.26.10
'@babel/parser': 7.26.10
'@babel/template': 7.26.9
'@babel/traverse': 7.26.10
'@babel/types': 7.26.10
convert-source-map: 2.0.0
debug: 4.4.0
gensync: 1.0.0-beta.2
json5: 2.2.3
semver: 6.3.1
transitivePeerDependencies:
- supports-color
'@babel/generator@7.26.10':
dependencies:
'@babel/parser': 7.26.10
'@babel/types': 7.26.10
'@jridgewell/gen-mapping': 0.3.8
'@jridgewell/trace-mapping': 0.3.25
jsesc: 3.1.0
'@babel/helper-compilation-targets@7.26.5':
dependencies:
'@babel/compat-data': 7.26.8
'@babel/helper-validator-option': 7.25.9
browserslist: 4.24.4
lru-cache: 5.1.1
semver: 6.3.1
'@babel/helper-module-imports@7.25.9':
dependencies:
'@babel/traverse': 7.26.10
'@babel/types': 7.26.10
transitivePeerDependencies:
- supports-color
'@babel/helper-module-transforms@7.26.0(@babel/core@7.26.10)':
dependencies:
'@babel/core': 7.26.10
'@babel/helper-module-imports': 7.25.9
'@babel/helper-validator-identifier': 7.25.9
'@babel/traverse': 7.26.10
transitivePeerDependencies:
- supports-color
'@babel/helper-plugin-utils@7.26.5': {}
'@babel/helper-string-parser@7.25.9': {} '@babel/helper-string-parser@7.25.9': {}
'@babel/helper-validator-identifier@7.25.9': {} '@babel/helper-validator-identifier@7.25.9': {}
'@babel/helper-validator-option@7.25.9': {}
'@babel/helpers@7.26.10':
dependencies:
'@babel/template': 7.26.9
'@babel/types': 7.26.10
'@babel/parser@7.26.10': '@babel/parser@7.26.10':
dependencies: dependencies:
'@babel/types': 7.26.10 '@babel/types': 7.26.10
'@babel/plugin-transform-react-jsx-self@7.25.9(@babel/core@7.26.10)':
dependencies:
'@babel/core': 7.26.10
'@babel/helper-plugin-utils': 7.26.5
'@babel/plugin-transform-react-jsx-source@7.25.9(@babel/core@7.26.10)':
dependencies:
'@babel/core': 7.26.10
'@babel/helper-plugin-utils': 7.26.5
'@babel/template@7.26.9':
dependencies:
'@babel/code-frame': 7.26.2
'@babel/parser': 7.26.10
'@babel/types': 7.26.10
'@babel/traverse@7.26.10':
dependencies:
'@babel/code-frame': 7.26.2
'@babel/generator': 7.26.10
'@babel/parser': 7.26.10
'@babel/template': 7.26.9
'@babel/types': 7.26.10
debug: 4.4.0
globals: 11.12.0
transitivePeerDependencies:
- supports-color
'@babel/types@7.26.10': '@babel/types@7.26.10':
dependencies: dependencies:
'@babel/helper-string-parser': 7.25.9 '@babel/helper-string-parser': 7.25.9
@ -2146,6 +2505,10 @@ snapshots:
'@fastify/busboy@2.1.1': {} '@fastify/busboy@2.1.1': {}
'@fontsource-variable/noto-emoji@5.2.5': {}
'@fontsource/inter@5.2.5': {}
'@img/sharp-darwin-arm64@0.33.5': '@img/sharp-darwin-arm64@0.33.5':
optionalDependencies: optionalDependencies:
'@img/sharp-libvips-darwin-arm64': 1.0.4 '@img/sharp-libvips-darwin-arm64': 1.0.4
@ -2221,10 +2584,23 @@ snapshots:
'@img/sharp-win32-x64@0.33.5': '@img/sharp-win32-x64@0.33.5':
optional: true optional: true
'@jridgewell/gen-mapping@0.3.8':
dependencies:
'@jridgewell/set-array': 1.2.1
'@jridgewell/sourcemap-codec': 1.5.0
'@jridgewell/trace-mapping': 0.3.25
'@jridgewell/resolve-uri@3.1.2': {} '@jridgewell/resolve-uri@3.1.2': {}
'@jridgewell/set-array@1.2.1': {}
'@jridgewell/sourcemap-codec@1.5.0': {} '@jridgewell/sourcemap-codec@1.5.0': {}
'@jridgewell/trace-mapping@0.3.25':
dependencies:
'@jridgewell/resolve-uri': 3.1.2
'@jridgewell/sourcemap-codec': 1.5.0
'@jridgewell/trace-mapping@0.3.9': '@jridgewell/trace-mapping@0.3.9':
dependencies: dependencies:
'@jridgewell/resolve-uri': 3.1.2 '@jridgewell/resolve-uri': 3.1.2
@ -2332,6 +2708,27 @@ snapshots:
'@shikijs/vscode-textmate@10.0.2': {} '@shikijs/vscode-textmate@10.0.2': {}
'@types/babel__core@7.20.5':
dependencies:
'@babel/parser': 7.26.10
'@babel/types': 7.26.10
'@types/babel__generator': 7.6.8
'@types/babel__template': 7.4.4
'@types/babel__traverse': 7.20.6
'@types/babel__generator@7.6.8':
dependencies:
'@babel/types': 7.26.10
'@types/babel__template@7.4.4':
dependencies:
'@babel/parser': 7.26.10
'@babel/types': 7.26.10
'@types/babel__traverse@7.20.6':
dependencies:
'@babel/types': 7.26.10
'@types/cookie@0.6.0': {} '@types/cookie@0.6.0': {}
'@types/debug@4.1.12': '@types/debug@4.1.12':
@ -2354,10 +2751,29 @@ snapshots:
dependencies: dependencies:
'@types/unist': 3.0.2 '@types/unist': 3.0.2
'@types/react-dom@19.0.4(@types/react@19.0.10)':
dependencies:
'@types/react': 19.0.10
'@types/react@19.0.10':
dependencies:
csstype: 3.1.3
'@types/unist@3.0.2': {} '@types/unist@3.0.2': {}
'@ungap/structured-clone@1.2.0': {} '@ungap/structured-clone@1.2.0': {}
'@vitejs/plugin-react@4.3.4(vite@6.2.2)':
dependencies:
'@babel/core': 7.26.10
'@babel/plugin-transform-react-jsx-self': 7.25.9(@babel/core@7.26.10)
'@babel/plugin-transform-react-jsx-source': 7.25.9(@babel/core@7.26.10)
'@types/babel__core': 7.20.5
react-refresh: 0.14.2
vite: 6.2.2
transitivePeerDependencies:
- supports-color
acorn-walk@8.3.2: {} acorn-walk@8.3.2: {}
acorn@8.14.0: {} acorn@8.14.0: {}
@ -2504,8 +2920,17 @@ snapshots:
widest-line: 5.0.0 widest-line: 5.0.0
wrap-ansi: 9.0.0 wrap-ansi: 9.0.0
browserslist@4.24.4:
dependencies:
caniuse-lite: 1.0.30001704
electron-to-chromium: 1.5.119
node-releases: 2.0.19
update-browserslist-db: 1.1.3(browserslist@4.24.4)
camelcase@8.0.0: {} camelcase@8.0.0: {}
caniuse-lite@1.0.30001704: {}
ccount@2.0.1: {} ccount@2.0.1: {}
chalk@5.3.0: {} chalk@5.3.0: {}
@ -2552,6 +2977,8 @@ snapshots:
confbox@0.1.8: {} confbox@0.1.8: {}
convert-source-map@2.0.0: {}
cookie-es@1.2.2: {} cookie-es@1.2.2: {}
cookie@0.5.0: {} cookie@0.5.0: {}
@ -2564,6 +2991,8 @@ snapshots:
cssesc@3.0.0: {} cssesc@3.0.0: {}
csstype@3.1.3: {}
data-uri-to-buffer@2.0.2: {} data-uri-to-buffer@2.0.2: {}
debug@4.3.6: debug@4.3.6:
@ -2609,6 +3038,8 @@ snapshots:
ee-first@1.1.1: {} ee-first@1.1.1: {}
electron-to-chromium@1.5.119: {}
emoji-regex-xs@1.0.0: {} emoji-regex-xs@1.0.0: {}
emoji-regex@10.3.0: {} emoji-regex@10.3.0: {}
@ -2674,6 +3105,8 @@ snapshots:
'@esbuild/win32-ia32': 0.25.0 '@esbuild/win32-ia32': 0.25.0
'@esbuild/win32-x64': 0.25.0 '@esbuild/win32-x64': 0.25.0
escalade@3.2.0: {}
escape-html@1.0.3: {} escape-html@1.0.3: {}
escape-string-regexp@4.0.0: {} escape-string-regexp@4.0.0: {}
@ -2707,6 +3140,8 @@ snapshots:
fsevents@2.3.3: fsevents@2.3.3:
optional: true optional: true
gensync@1.0.0-beta.2: {}
get-east-asian-width@1.2.0: {} get-east-asian-width@1.2.0: {}
get-source@2.0.12: get-source@2.0.12:
@ -2718,6 +3153,8 @@ snapshots:
glob-to-regexp@0.4.1: {} glob-to-regexp@0.4.1: {}
globals@11.12.0: {}
h3@1.15.1: h3@1.15.1:
dependencies: dependencies:
cookie-es: 1.2.2 cookie-es: 1.2.2
@ -2878,20 +3315,28 @@ snapshots:
dependencies: dependencies:
is-inside-container: 1.0.0 is-inside-container: 1.0.0
js-tokens@4.0.0: {}
js-yaml@4.1.0: js-yaml@4.1.0:
dependencies: dependencies:
argparse: 2.0.1 argparse: 2.0.1
jsesc@3.1.0: {}
json5@2.2.3: {}
kleur@3.0.3: {} kleur@3.0.3: {}
kleur@4.1.5: {} kleur@4.1.5: {}
lanyard-wrapper@2.0.1: {}
longest-streak@3.1.0: {} longest-streak@3.1.0: {}
lru-cache@10.4.3: {} lru-cache@10.4.3: {}
lru-cache@5.1.1:
dependencies:
yallist: 3.1.1
magic-string@0.25.9: magic-string@0.25.9:
dependencies: dependencies:
sourcemap-codec: 1.4.8 sourcemap-codec: 1.4.8
@ -3270,6 +3715,8 @@ snapshots:
node-mock-http@1.0.0: {} node-mock-http@1.0.0: {}
node-releases@2.0.19: {}
normalize-path@3.0.0: {} normalize-path@3.0.0: {}
ofetch@1.4.1: ofetch@1.4.1:
@ -3340,6 +3787,14 @@ snapshots:
picocolors: 1.1.1 picocolors: 1.1.1
source-map-js: 1.2.1 source-map-js: 1.2.1
prettier-plugin-astro@0.14.1:
dependencies:
'@astrojs/compiler': 2.11.0
prettier: 3.5.3
sass-formatter: 0.7.9
prettier@3.5.3: {}
printable-characters@1.0.42: {} printable-characters@1.0.42: {}
prismjs@1.29.0: {} prismjs@1.29.0: {}
@ -3357,6 +3812,15 @@ snapshots:
range-parser@1.2.1: {} range-parser@1.2.1: {}
react-dom@19.0.0(react@19.0.0):
dependencies:
react: 19.0.0
scheduler: 0.25.0
react-refresh@0.14.2: {}
react@19.0.0: {}
readdirp@4.1.2: {} readdirp@4.1.2: {}
regex-recursion@5.1.1: regex-recursion@5.1.1:
@ -3506,6 +3970,16 @@ snapshots:
'@rollup/rollup-win32-x64-msvc': 4.34.9 '@rollup/rollup-win32-x64-msvc': 4.34.9
fsevents: 2.3.3 fsevents: 2.3.3
s.color@0.0.15: {}
sass-formatter@0.7.9:
dependencies:
suf-log: 2.5.3
scheduler@0.25.0: {}
semver@6.3.1: {}
semver@7.7.1: {} semver@7.7.1: {}
send@1.1.0: send@1.1.0:
@ -3618,6 +4092,10 @@ snapshots:
dependencies: dependencies:
ansi-regex: 6.0.1 ansi-regex: 6.0.1
suf-log@2.5.3:
dependencies:
s.color: 0.0.15
tinyexec@0.3.2: {} tinyexec@0.3.2: {}
tinyglobby@0.2.12: tinyglobby@0.2.12:
@ -3723,6 +4201,12 @@ snapshots:
ofetch: 1.4.1 ofetch: 1.4.1
ufo: 1.5.4 ufo: 1.5.4
update-browserslist-db@1.1.3(browserslist@4.24.4):
dependencies:
browserslist: 4.24.4
escalade: 3.2.0
picocolors: 1.1.1
vfile-location@5.0.3: vfile-location@5.0.3:
dependencies: dependencies:
'@types/unist': 3.0.2 '@types/unist': 3.0.2
@ -3803,6 +4287,8 @@ snapshots:
xxhash-wasm@1.1.0: {} xxhash-wasm@1.1.0: {}
yallist@3.1.1: {}
yargs-parser@21.1.1: {} yargs-parser@21.1.1: {}
yocto-queue@1.1.1: {} yocto-queue@1.1.1: {}

BIN
public/background.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 283 KiB

View file

@ -1,9 +0,0 @@
---
const {position, text, url, id} = Astro.props;
---
<style>
button, a {
width: 100%;
}
</style>
{url ? <a href={url}><button id={id}>{text}</button></a> : <button id={id}>{text}</button>}

View file

@ -1,11 +0,0 @@
<style>
div {
display: grid;
grid-auto-flow: row;
row-gap: 5px;
}
</style>
<div class="button-collection">
<slot />
</div>

View file

@ -1,10 +0,0 @@
---
import Social from "./Social.astro"
const contacts: any = Object.values(import.meta.glob("../../info/contacts/*.md", {
eager: true
}));
---
<ul>
{contacts.map(contact => <Social platform={contact.frontmatter.platform} url={contact.frontmatter.url} name={contact.frontmatter.name} note={contact.frontmatter.note}/>)}
</ul>

View file

@ -1,23 +0,0 @@
<style>
div {
color: black;
background-color: lightcoral;
padding: 10px;
margin-bottom: 20px;
border-radius: 10px;
}
a {
color: blue;
}
</style>
<noscript>
<div>
<p>
<h4>ENABLE JAVASCRIPT OR I WILL KILL YOU</h4>
I will not. However, you seem to be living in fear of technology, as you have JavaScript disabled. This means that some features (eg. dragging, submitting forms) will not work. Enable JS to fully enjoy this website!
<br/>
Rest assured, there's no external tracking. You can check this site's source code on the <a href="https://git.nin0.dev/nin0/website">nin0/website</a> repository on my Forgejo.
</p>
</div>
</noscript>

View file

@ -1,16 +0,0 @@
---
const {name} = Astro.props
---
<style>
fieldset {
margin-top: 10px;
margin-bottom: 0px;
padding: 0px 15px;
}
</style>
<fieldset>
<legend>{name}</legend>
<slot />
</fieldset>

View file

@ -1,31 +0,0 @@
---
import Contacts from "../components/Contacts.astro";
import GroupBox from "../components/GroupBox.astro";
import Me from "../components/Me.astro";
import Presence from "../components/Presence.astro";
import Window from "../components/Window.astro";
import Button from "./Button.astro";
import ButtonCollection from "./ButtonCollection.astro";
import Spacer from "./Spacer.astro";
---
<Window title="Home" maxWidth="600px" showClose={true}>
<Me />
<Presence />
<GroupBox name="About me">
<p>
I'm a Canadian self-taught software developer.
<br/>
I also make things that some people use with varying degrees of usefulness.
</p>
</GroupBox>
<GroupBox name="Reach out">
<Contacts />
</GroupBox>
<ButtonCollection>
<Button position="left" text="Projects (soon)" url="/projects"/>
<Spacer />
<Button position="left" text="Code (soon)" url="/code"/>
<Spacer />
<Button position="left" text="Blog (ETA: 100 years)" url="/code"/>
</ButtonCollection>
</Window>

View file

@ -1,45 +0,0 @@
---
import {fetchUserData, type DiscordStatus} from "lanyard-wrapper";
const rawUserData = await fetchUserData("886685857560539176");
const statusColor = () => {
switch (rawUserData.discord_status) {
case "online":
return "#23a55a";
case "idle":
return "#f0b232";
case "dnd":
return "#f23f43";
case "offline":
return "#80848e";
default:
return "#80848e";
}
};
---
<style define:vars={{statusColor: statusColor()}}>
div {
display: flex;
}
h3 {
font-weight: 400;
margin-left: 20px;
margin-top: auto;
margin-bottom: auto;
}
img {
width: 90px;
height: 90px;
border-radius: 6px;
box-shadow: 10px black;
border-color: var(--statusColor);
border-style: solid;
border-width: 2px;
}
</style>
<div>
<img src="logo.png" alt="the nin0dev logo">
<h3>nin0 <span style="font-size: 0.4em;">(he/him)</span></h3>
</div>

View file

@ -1,55 +0,0 @@
---
import {fetchUserData} from "lanyard-wrapper";
const rawUserData = await fetchUserData("886685857560539176");
const activity = (() => {
let finalActivity = {
type: undefined,
name: undefined,
artist: undefined
};
rawUserData.activities.some((activity => {
if(activity.type === 0) {
finalActivity = {
type: "playing",
name: activity.name,
artist: undefined
};
return;
}
}));
if(finalActivity.type !== undefined) return finalActivity;
if(rawUserData.listening_to_spotify) {
finalActivity = {
type: "listening",
name: rawUserData.spotify.song,
artist: rawUserData.spotify.artist
};
};
return finalActivity;
})();
---
<style>
div {
margin-top: 10px;
display: flex;
}
p {
margin-top: auto;
margin-bottom: auto;
margin-left: 10px;
}
img {
width: 30px;
height: 30px;
}
</style>
{
activity.type !== undefined &&
<div>
<img src={activity.type === "playing" ? "/game.ico" : "/music.ico"}>
<p>{`${activity.type === "playing" ? "Playing" : "Listening to"} ${activity.name}${activity.type === "listening" ? ` - ${activity.artist}` : ""}`}</p>
</div>
}

View file

@ -1,16 +0,0 @@
---
const {platform, name, url, note} = Astro.props;
---
<style>
bl {
font-weight: 500;
}
it {
font-style: italic;
}
</style>
<li>
<bl>{platform}</bl>: {url ? <a href={url}>{name}</a> : name}{note && <it> ({note})</it>}
</li>

View file

@ -1 +0,0 @@
<span />

View file

@ -1,39 +0,0 @@
---
const {title, showClose, maxWidth} = Astro.props
---
<style define:vars={{ maxWidth }}>
.window {
max-width: var(--maxWidth);
position: absolute;
}
.window-body {
padding: 20px !important;
}
@media (pointer:coarse) {
.window {
position: absolute;
top: 0px;
left: 0px;
margin: 5%;
width: 90%;
}
}
</style>
<div class="background" class="window">
<div class="window glass active" style="max-width: 100%">
<div class="title-bar">
<div class="title-bar-text">{title}</div>
{
showClose &&
<div class="title-bar-controls">
<button aria-label="Close" onclick="window.close()"></button>
</div>
}
</div>
<div class="window-body has-space">
<slot />
</div>
</div>
</div>

View file

@ -0,0 +1,29 @@
---
const { position, text, url, id, onClick } = Astro.props;
---
<style>
button,
a {
width: 100%;
}
button {
background-color: #45475a;
border: 1px var(--text) solid;
border-radius: 10px;
color: var(--text);
padding: 8px 20px;
}
button:hover {
background-color: #585b70;
}
</style>
{
url ? (
<a href={url}>
<button id={id}>{text}</button>
</a>
) : (
<button id={id}>{text}</button>
)
}

View file

@ -0,0 +1,11 @@
<style>
div {
display: grid;
grid-auto-flow: row;
row-gap: 8px;
margin-top: 15px;
}
</style>
<div class="button-collection">
<slot />
</div>

View file

@ -0,0 +1,19 @@
---
const { name } = Astro.props;
---
<style>
div {
margin-top: 15px;
margin-bottom: 0px;
padding: 0px 15px;
border-radius: 15px;
border: 1px solid #313244;
background-color: #313244;
}
</style>
<div>
<h3>{name}</h3>
<slot />
</div>

View file

@ -0,0 +1 @@
<span></span>

View file

@ -0,0 +1,89 @@
---
const { title, showClose, maxWidth, hideByDefault, customClass, offset } =
Astro.props;
const randomID = customClass || Math.random().toString().replace(".", "");
---
<style define:vars={{ maxWidth, offset }}>
.window {
width: var(--maxWidth);
top: var(--offset);
left: var(--offset);
position: absolute;
}
.title-bar {
.title-bar-text {
margin-top: 2.5px !important;
}
display: flex;
justify-content: space-between;
background-color: #313244;
border-radius: 15px 15px 0 0;
padding: 9px 18px 9px 18px;
}
svg {
fill: var(--text);
margin: 0;
padding: 0;
height: 24px !important;
}
#close {
background: none;
color: inherit;
border: none;
padding: 0;
margin: 0;
height: 24px !important;
font: inherit;
cursor: pointer;
outline: inherit;
}
.window-body {
padding: 20px !important;
background-color: #1e1e2e;
border-radius: 0 0 20px 20px;
}
@media (pointer: coarse) {
.window {
position: absolute;
top: 0px;
left: 0px;
margin: 5%;
width: 90%;
}
}
</style>
<div
class="background"
id={`window-${randomID}`}
class="window"
style={hideByDefault && "display: none;"}
>
<div class="window" style="max-width: 100%">
<div class="title-bar">
<div class="title-bar-text">{title}</div>
{
showClose && (
<button
id="close"
aria-label="Close"
onclick={`document.querySelector("#window-${randomID}").style.display = "none";`}
>
<svg
xmlns="http://www.w3.org/2000/svg"
height="24px"
viewBox="0 -960 960 960"
>
<path d="m256-200-56-56 224-224-224-224 56-56 224 224 224-224 56 56-224 224 224 224-56 56-224-224-224 224Z" />
</svg>
</button>
)
}
</div>
<div class="window-body">
<slot />
</div>
</div>
</div>

View file

@ -0,0 +1,34 @@
---
import GroupBox from "@components/GroupBox.astro";
import Window from "@components/Window.astro";
---
<Window
title="Code"
maxWidth="400px"
showClose={true}
hideByDefault={true}
customClass="code-window"
offset="55px"
>
<p>
As mentioned in the main page, I write code. Some used by a lot, some
not as much. You can find it on:
<GroupBox name="GitHub (@nin0-dev)">
Here, you'll find most of my external contributions. I rarely start
personal projects on GitHub.
<br />
<a href="https://gh.nin0.dev">Go!</a>
<br />
<br />
</GroupBox>
<GroupBox name="Forgejo (@nin0)">
Some more personal/niche projects can be found on my own instance
(git.nin0.dev), which will probably be down.
<br />
<a href="https://git.nin0.dev/nin0">Go!</a>
<br />
<br />
</GroupBox>
</p>
</Window>

View file

@ -0,0 +1,22 @@
---
import Social from "./Social.astro";
const contacts: any = Object.values(
import.meta.glob("../../../../info/contacts/*.md", {
eager: true
})
);
---
<ul>
{
contacts.map(contact => (
<Social
platform={contact.frontmatter.platform}
url={contact.frontmatter.url}
name={contact.frontmatter.name}
note={contact.frontmatter.note}
/>
))
}
</ul>

View file

@ -0,0 +1,28 @@
<style>
div {
color: black;
background-color: lightcoral;
padding: 10px;
margin-bottom: 20px;
border-radius: 10px;
}
a {
color: blue;
}
</style>
<noscript>
<div>
<p>
<h4>ENABLE JAVASCRIPT OR I WILL KILL YOU</h4>
I will not. However, you seem to be living in fear of technology, as
you have JavaScript disabled. This means that some features (eg. dragging,
submitting forms) will not work. Enable JS to fully enjoy this website!
<br />
Rest assured, there's no external tracking. You can check this site's
source code on the <a href="https://git.nin0.dev/nin0/website"
>nin0/website</a
> repository on my Forgejo.
</p>
</div>
</noscript>

View file

@ -0,0 +1,36 @@
---
import Contacts from "./Contacts.astro";
import GroupBox from "@components/GroupBox.astro";
import Me from "./Me";
import Window from "@components/Window.astro";
import Button from "@components/Button.astro";
import ButtonCollection from "@components/ButtonCollection.astro";
import Spacer from "@components/Spacer.astro";
---
<script>
document
.querySelector("#show-code-window")
.addEventListener("click", () => {
// @ts-ignore
document.querySelector("#window-code-window").style.display =
"block";
});
</script>
<Window title="Home" maxWidth="600px" showClose={false}>
<Me client:only />
<ButtonCollection>
<Button position="left" text="My code" id="show-code-window" />
</ButtonCollection>
<GroupBox name="About me">
<p>
I'm a Canadian self-taught software developer.
<br />
I also make things that some people use with varying degrees of usefulness.
</p>
</GroupBox>
<GroupBox name="Reach out">
<Contacts />
</GroupBox>
</Window>

View file

@ -0,0 +1,161 @@
import "@css/me.css";
import { initLanyard } from "@js/lanyard/lanyard";
import { type LanyardPresence } from "../../../js/lanyard/types";
import { useEffect, useState } from "react";
export default function Me() {
// me-e-eeeee
const [presence, setPresence] = useState<LanyardPresence | undefined>();
const [currentlyPlaying, setCurrentlyPlaying] = useState<
| {
title: string;
artist: string;
album: string;
albumArt: string;
loved: boolean;
streak: number;
}
| undefined
>();
useEffect(() => {
initLanyard(presence => {
console.log(presence);
setPresence(presence);
});
async function getLastFmTracks() {
const params = new URLSearchParams({
method: "user.getrecenttracks",
api_key: "3c5623fa1abbd11c49f53ca18e992ead",
user: "nin0dev",
limit: "50",
format: "json",
extended: "true"
});
const res = await (
await fetch(`https://ws.audioscrobbler.com/2.0/?${params}`)
).json();
if (
res.recenttracks.track.some(t => {
try {
return t["@attr"].nowplaying === "true";
} catch (e) {
return false;
}
})
) {
const currentlyPlayingTrack = res.recenttracks.track[0];
setCurrentlyPlaying({
title: currentlyPlayingTrack.name,
artist: currentlyPlayingTrack.artist.name,
album: currentlyPlayingTrack.album["#text"],
albumArt: currentlyPlayingTrack.image[1]["#text"],
loved: currentlyPlayingTrack.loved === "1",
streak: (() => {
let current = 0;
for (const track of res.recenttracks.track) {
if (track.name === currentlyPlayingTrack.name)
current++;
else return current;
}
})()
});
} else {
setCurrentlyPlaying(undefined);
}
}
getLastFmTracks();
setInterval(getLastFmTracks, 10000);
}, []);
return (
<>
<div className="me-container">
<img src="logo.png" alt="the nin0 logo" />
<h3>
nin0 <span style={{ fontSize: "0.9rem" }}>(he/him)</span>
</h3>
</div>
{currentlyPlaying && (
<div className="spotify-card">
<h3>Listening to</h3>
<div
className="spotify-card-background"
style={{
backgroundImage: `url(${currentlyPlaying.albumArt})`
}}
></div>
<div
className="spotify-card-content"
style={{
display: "flex",
alignItems: "center",
marginBottom: "10px"
}}
>
<img
src={currentlyPlaying.albumArt}
style={{
marginRight: "10px",
width: "50px",
borderRadius: "5px"
}}
/>
<div>
<p style={{ margin: "0", fontWeight: "600" }}>
{currentlyPlaying.title}
</p>
<p style={{ margin: "0" }}>
<span className="prefix">by </span>
{currentlyPlaying.artist}
</p>
<p style={{ margin: "0" }}>
<span className="prefix">on </span>
{currentlyPlaying.album}
</p>
</div>
</div>
<p style={{ fontSize: "0.9rem" }} className="emoji">
{(() => {
const flags: {
color: string;
data: string;
}[] = [];
if (currentlyPlaying.loved)
flags.push({
color: "#f38ba8",
data: "💞 Loved track"
});
if (currentlyPlaying.streak > 1) {
flags.push({
color: "#f9e2af",
data: `⚡ Played ${currentlyPlaying.streak} times in a row`
});
}
return flags.map(flag => (
<span
style={{ color: flag.color }}
className="emoji"
key={flag.color}
>
{flag.data}{" "}
{flags.indexOf(flag) !==
flags.length - 1 && (
<span style={{ color: "white" }}>
{" "}{" "}
</span>
)}
</span>
));
})()}
</p>
</div>
)}
</>
);
}

View file

@ -0,0 +1,18 @@
---
const { platform, name, url, note } = Astro.props;
---
<style>
bl {
font-weight: 500;
}
it {
font-style: italic;
}
</style>
<li>
<bl>{platform}</bl>: {url ? <a href={url}>{name}</a> : name}{
note && <it> ({note})</it>
}
</li>

48
src/css/me.css Normal file
View file

@ -0,0 +1,48 @@
.me-container {
display: flex;
h3 {
color: #89b4fa;
font-weight: 400;
font-size: 2rem;
margin-left: 20px;
margin-top: auto;
margin-bottom: auto;
}
img {
width: 80px;
height: 80px;
border-radius: 6px;
box-shadow: 10px black;
border-style: solid;
border-width: 2px;
}
}
.spotify-card {
h3 {
margin: 13px 0;
}
.prefix {
color: #a6adc8 !important;
}
.spotify-card-background {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
z-index: -1;
border-radius: 15px;
filter: brightness(0.3) blur(8px);
background-size: cover;
background-position: center;
overflow: hidden;
}
position: relative;
background-color: transparent;
padding: 5px 15px;
margin-top: 15px;
border-radius: 15px;
border: 2px solid #cdd6f4;
z-index: 0;
overflow: hidden;
}

View file

@ -1,11 +1,26 @@
:root {
--background: url("/background.png");
--text: #cdd6f4;
}
* {
font-family: Inter, sans-serif;
}
body { body {
background-color: #56a0d1; background: var(--background);
font-size: 0.95rem;
color: var(--text);
padding: 30px; padding: 30px;
font-family: sans-serif !important;
overflow: hidden; overflow: hidden;
} }
a {
color: #89b4fa;
}
@media (pointer: coarse) { @media (pointer: coarse) {
body { body {
overflow: scroll; overflow: scroll;
} }
} }
.emoji {
font-family: "Inter", "Noto Emoji Variable";
}

View file

@ -1,6 +1,6 @@
// wow i love being fake programmer // wow i love being fake programmer
// source: https://jams.hackclub.com/batch/webOS/part-3 // source: https://jams.hackclub.com/batch/webOS/part-3
function dragElement(element) { export function dragElement(element) {
var initialX = 0; var initialX = 0;
var initialY = 0; var initialY = 0;
var currentX = 0; var currentX = 0;
@ -26,8 +26,6 @@ function dragElement(element) {
currentY = initialY - e.clientY; currentY = initialY - e.clientY;
initialX = e.clientX; initialX = e.clientX;
initialY = e.clientY; initialY = e.clientY;
console.log(element.offsetTop);
console.log(currentX);
element.style.top = element.offsetTop - currentY + "px"; element.style.top = element.offsetTop - currentY + "px";
element.style.left = element.offsetLeft - currentX + "px"; element.style.left = element.offsetLeft - currentX + "px";
} }
@ -35,7 +33,5 @@ function dragElement(element) {
function stopDragging() { function stopDragging() {
document.onmouseup = null; document.onmouseup = null;
document.onmousemove = null; document.onmousemove = null;
console.log(element.offsetTop - currentY);
console.log(element.offsetLeft - currentX);
} }
} }

1
src/js/lanyard/lanyard.d.ts vendored Normal file
View file

@ -0,0 +1 @@
declare module "@js/lanyard/lanyard";

56
src/js/lanyard/lanyard.ts Normal file
View file

@ -0,0 +1,56 @@
import type {
AnyLanyardPayload,
LanyardInitStatePayload,
LanyardPayload,
LanyardPresence,
LanyardPresenceUpdatePayload
} from "./types";
function sendToSocket(socket: WebSocket, data: AnyLanyardPayload) {
socket.send(JSON.stringify(data));
}
export function initLanyard(
updateCallback: (presence: LanyardPresence) => void
) {
const socket = new WebSocket("wss://api.lanyard.rest/socket");
socket.onmessage = data => {
const payload: LanyardPayload = JSON.parse(data.data);
switch (payload.op) {
case 1: {
// Initialize
sendToSocket(socket, {
op: 2,
d: {
subscribe_to_ids: ["886685857560539176"]
}
});
sendToSocket(socket, {
op: 3
});
setInterval(
() => {
sendToSocket(socket, {
op: 3
});
},
"heartbeat_interval" in payload.d
? payload.d.heartbeat_interval
: 30000
);
break;
}
case 0: {
const typedPayload = payload as
| LanyardInitStatePayload
| LanyardPresenceUpdatePayload;
updateCallback(
typedPayload.t === "INIT_STATE"
? typedPayload.d["886685857560539176"]
: typedPayload.d
);
}
}
};
}

65
src/js/lanyard/types.ts Normal file
View file

@ -0,0 +1,65 @@
export interface LanyardPresence {
listening_to_spotify: boolean;
spotify: {
track_id: string;
timestamps: {
start: number;
end: number;
};
song: string;
artist: string;
album_art_url: string;
album: string;
};
discord_status: string;
activities: {
type: number;
timestamps: {
start: number;
end: number;
};
state: string;
name: string;
id: string;
details: string;
assets: {
small_text: string;
small_image: string;
large_text: string;
large_image: string;
};
application_id: string;
}[];
}
export interface AnyLanyardPayload {
op: 0 | 1 | 2 | 3;
d?: object;
}
export interface LanyardHelloPayload {
op: 1;
d: {
heartbeat_interval: number;
};
}
export interface LanyardInitStatePayload {
op: 0;
t: "INIT_STATE";
d: {
[user_id: string]: LanyardPresence;
};
}
export interface LanyardPresenceUpdatePayload {
op: 0;
t: "PRESENCE_UPDATE";
d: LanyardPresence;
}
export type LanyardPayload =
| LanyardHelloPayload
| LanyardInitStatePayload
| LanyardPresenceUpdatePayload
| AnyLanyardPayload;

View file

@ -1,76 +1,29 @@
--- ---
import "7.css/dist/7.css";
import "../css/style.css"; import "../css/style.css";
import "@fontsource/inter";
import "@fontsource-variable/noto-emoji";
const {tabTitle} = Astro.props; const { tabTitle } = Astro.props;
--- ---
<html lang="en"> <html lang="en">
<head> <head>
<meta charset="utf-8" /> <meta charset="utf-8" />
<link rel="icon" type="image/svg+xml" href="/favicon.svg" /> <link rel="icon" type="image/svg+xml" href="/favicon.svg" />
<meta name="viewport" content="width=device-width" /> <meta name="viewport" content="width=device-width" />
<meta name="generator" content={Astro.generator} /> <meta name="generator" content={Astro.generator} />
<title>{tabTitle}</title> <title>{tabTitle}</title>
</head> </head>
<body> <body>
<slot /> <slot />
<script> <script>
function dragElement(element) { import { dragElement } from "@js/drag";
// Step 2: Set up variables to keep track of the element's position.
var initialX = 0; document.addEventListener("DOMContentLoaded", () => {
var initialY = 0; document.querySelectorAll(".window").forEach(window => {
var currentX = 0; dragElement(window);
var currentY = 0; });
// Step 3: Check if there is a special header element associated with the draggable element.
if (document.getElementById("title-bar")) {
// Step 4: If present, assign the `dragMouseDown` function to the header's `onmousedown` event.
// This allows you to drag the window around by its header.
document.getElementById("title-bar").onmousedown = startDragging;
} else {
// Step 5: If not present, assign the function directly to the draggable element's `onmousedown` event.
// This allows you to drag the window by holding down anywhere on the window.
element.onmousedown = startDragging;
}
// Step 6: Define the `startDragging` function to capture the initial mouse position and set up event listeners.
function startDragging(e) {
e = e || window.event;
e.preventDefault();
// Step 7: Get the mouse cursor position at startup.
initialX = e.clientX;
initialY = e.clientY;
// Step 8: Set up event listeners for mouse movement (`elementDrag`) and mouse button release (`closeDragElement`).
document.onmouseup = stopDragging;
document.onmousemove = dragElement;
}
// Step 9: Define the `elementDrag` function to calculate the new position of the element based on mouse movement.
function dragElement(e) {
e = e || window.event;
e.preventDefault();
// Step 10: Calculate the new cursor position.
currentX = initialX - e.clientX;
currentY = initialY - e.clientY;
initialX = e.clientX;
initialY = e.clientY;
// Step 11: Update the element's new position by modifying its `top` and `left` CSS properties.
element.style.top = (element.offsetTop - currentY) + "px";
element.style.left = (element.offsetLeft - currentX) + "px";
}
// Step 12: Define the `stopDragging` function to stop tracking mouse movement by removing the event listeners.
function stopDragging() {
document.onmouseup = null;
document.onmousemove = null;
}
}
document.addEventListener("DOMContentLoaded", () => {
document.querySelectorAll(".window").forEach(window => {
dragElement(window);
}); });
}); </script>
</script> </body>
</body>
</html> </html>

View file

@ -1,10 +1,13 @@
--- ---
import FearOfTechnology from "../components/FearOfTechnology.astro"; import FearOfTechnology from "@windows/mainWindow/FearOfTechnology.astro";
import MainWindow from "../components/MainWindow.astro"; import MainWindow from "@windows/mainWindow/MainWindow.astro";
import BaseLayout from "../layouts/BaseLayout.astro"; import BaseLayout from "../layouts/BaseLayout.astro";
import Window from "@components/Window.astro";
import CodeWindow from "@windows/code/CodeWindow.astro";
--- ---
<BaseLayout tabTitle="Home - nin0dev"> <BaseLayout tabTitle="nin0.dev">
<FearOfTechnology /> <FearOfTechnology />
<MainWindow /> <MainWindow />
<CodeWindow />
</BaseLayout> </BaseLayout>

View file

@ -1,3 +1,17 @@
{ {
"extends": "astro/tsconfigs/base" "extends": "astro/tsconfigs/base",
} "compilerOptions": {
"baseUrl": "./src/",
"paths": {
"@components/*": ["components/commonComponents/*"],
"@windows/*": ["components/windows/*"],
"@layouts/*": ["layouts/*"],
"@css/*": ["css/*"],
"@js/*": ["js/*"],
"@info/*": ["info/*"]
},
"jsx": "react-jsx",
"jsxImportSource": "react"
},
"include": ["src/**/*.d.ts", "src/**/*.ts", "src/**/*.astro"]
}