diff --git a/package.json b/package.json index b404945..deda336 100644 --- a/package.json +++ b/package.json @@ -9,8 +9,8 @@ "qwilight-fe" ], "scripts": { - "start": "turbo start", - "start:taehui-www": "pnpm --filter taehui-www start", + "dev": "turbo dev", + "start:taehui-fe": "pnpm --filter taehui-fe dev", "build": "turbo build", "build:taehui-ts": "pnpm --filter taehui-ts build", "deploy": "turbo deploy && taehui.cmd" diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 805c77b..94b24f2 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -58,7 +58,7 @@ version: 4.0.6(mobx@6.12.0)(react-dom@18.2.0)(react@18.2.0) next: specifier: ^14.1.3 - version: 14.1.3(@babel/core@7.22.9)(react-dom@18.2.0)(react@18.2.0)(sass@1.72.0) + version: 14.1.3(react-dom@18.2.0)(react@18.2.0)(sass@1.72.0) next-intl: specifier: ^3.9.5 version: 3.9.5(next@14.1.3)(react@18.2.0) @@ -108,9 +108,6 @@ '@types/react-dom': specifier: ^18.2.22 version: 18.2.22 - '@types/react-router-dom': - specifier: ^5.3.3 - version: 5.3.3 eslint-config-next: specifier: ^14.1.3 version: 14.1.3(eslint@8.57.0)(typescript@5.4.2) @@ -146,7 +143,7 @@ version: 4.0.6(mobx@6.12.0)(react-dom@18.2.0)(react@18.2.0) next: specifier: ^14.1.3 - version: 14.1.3(@babel/core@7.22.9)(react-dom@18.2.0)(react@18.2.0)(sass@1.72.0) + version: 14.1.3(react-dom@18.2.0)(react@18.2.0)(sass@1.72.0) next-intl: specifier: ^3.9.5 version: 3.9.5(next@14.1.3)(react@18.2.0) @@ -165,9 +162,6 @@ react-infinite-scroll-component: specifier: ^6.1.0 version: 6.1.0(react@18.2.0) - react-scripts: - specifier: 5.0.1 - version: 5.0.1(@babel/plugin-syntax-flow@7.23.3)(@babel/plugin-transform-react-jsx@7.23.4)(eslint@8.57.0)(react@18.2.0)(sass@1.72.0)(typescript@5.4.2) react-textarea-autosize: specifier: ^8.5.3 version: 8.5.3(@types/react@18.2.65)(react@18.2.0) @@ -177,9 +171,6 @@ reactstrap: specifier: ^9.2.2 version: 9.2.2(react-dom@18.2.0)(react@18.2.0) - sprintf-js: - specifier: ^1.1.3 - version: 1.1.3 sweetalert2: specifier: ^11.10.6 version: 11.10.6 @@ -208,9 +199,6 @@ '@types/showdown': specifier: ^2.0.6 version: 2.0.6 - '@types/sprintf-js': - specifier: ^1.1.4 - version: 1.1.4 eslint-config-next: specifier: ^14.1.3 version: 14.1.3(eslint@8.57.0)(typescript@5.4.2) @@ -237,7 +225,7 @@ version: 14.1.3(eslint@8.57.0)(typescript@5.4.2) next: specifier: ^14.1.3 - version: 14.1.3(@babel/core@7.22.9)(react-dom@18.2.0)(react@18.2.0)(sass@1.72.0) + version: 14.1.3(react-dom@18.2.0)(react@18.2.0)(sass@1.72.0) next-intl: specifier: ^3.9.5 version: 3.9.5(next@14.1.3)(react@18.2.0) @@ -317,303 +305,19 @@ /@aashutoshrathi/word-wrap@1.2.6: resolution: {integrity: sha512-1Yjs2SvM8TflER/OD3cOjhWWOZb58A2t7wpE2S9XfBYTiIl+XFhQG2bjy4Pu1I+EAlCNUzRDYDdFwFYUKvXcIA==} engines: {node: '>=0.10.0'} - - /@alloc/quick-lru@5.2.0: - resolution: {integrity: sha512-UrcABB+4bUrFABwbluTIBErXwvbsU/V7TZWfmbgJfbkwiBuziS9gxdODUyuiecfdGQ85jglMW6juS3+z5TsKLw==} - engines: {node: '>=10'} - dev: false - - /@ampproject/remapping@2.2.1: - resolution: {integrity: sha512-lFMjJTrFL3j7L9yBxwYfCq2k6qqwHyzuUl/XBnif78PWTJYyL/dfowQHWE3sp6U6ZzqWiiIZnpTMO96zhkjwtg==} - engines: {node: '>=6.0.0'} - dependencies: - '@jridgewell/gen-mapping': 0.3.3 - '@jridgewell/trace-mapping': 0.3.18 - - /@apideck/better-ajv-errors@0.3.6(ajv@8.12.0): - resolution: {integrity: sha512-P+ZygBLZtkp0qqOAJJVX4oX/sFo5JR3eBWwwuqHHhK0GIgQOKWrAfiAaWX0aArHkRWHMuggFEgAZNxVPwPZYaA==} - engines: {node: '>=10'} - peerDependencies: - ajv: '>=8' - dependencies: - ajv: 8.12.0 - json-schema: 0.4.0 - jsonpointer: 5.0.1 - leven: 3.1.0 - dev: false + dev: true /@babel/code-frame@7.22.5: resolution: {integrity: sha512-Xmwn266vad+6DAqEB2A6V/CcZVp62BbwVmcOJc2RPuwih1kw02TjQvWVWlcKGbBPd+8/0V5DEkOcizRGYsspYQ==} engines: {node: '>=6.9.0'} dependencies: '@babel/highlight': 7.22.5 - - /@babel/compat-data@7.22.9: - resolution: {integrity: sha512-5UamI7xkUcJ3i9qVDS+KFDEK8/7oJ55/sJMB1Ge7IEapr7KfdfV/HErR+koZwOfd+SgtFKOKRhRakdg++DcJpQ==} - engines: {node: '>=6.9.0'} - - /@babel/core@7.22.9: - resolution: {integrity: sha512-G2EgeufBcYw27U4hhoIwFcgc1XU7TlXJ3mv04oOv1WCuo900U/anZSPzEqNjwdjgffkk2Gs0AN0dW1CKVLcG7w==} - engines: {node: '>=6.9.0'} - dependencies: - '@ampproject/remapping': 2.2.1 - '@babel/code-frame': 7.22.5 - '@babel/generator': 7.22.9 - '@babel/helper-compilation-targets': 7.22.9(@babel/core@7.22.9) - '@babel/helper-module-transforms': 7.22.9(@babel/core@7.22.9) - '@babel/helpers': 7.22.6 - '@babel/parser': 7.22.7 - '@babel/template': 7.22.5 - '@babel/traverse': 7.22.8 - '@babel/types': 7.22.5 - convert-source-map: 1.9.0 - debug: 4.3.4(supports-color@5.5.0) - gensync: 1.0.0-beta.2 - json5: 2.2.3 - semver: 6.3.1 - transitivePeerDependencies: - - supports-color - - /@babel/eslint-parser@7.22.9(@babel/core@7.22.9)(eslint@8.57.0): - resolution: {integrity: sha512-xdMkt39/nviO/4vpVdrEYPwXCsYIXSSAr6mC7WQsNIlGnuxKyKE7GZjalcnbSWiC4OXGNNN3UQPeHfjSC6sTDA==} - engines: {node: ^10.13.0 || ^12.13.0 || >=14.0.0} - peerDependencies: - '@babel/core': '>=7.11.0' - eslint: ^7.5.0 || ^8.0.0 - dependencies: - '@babel/core': 7.22.9 - '@nicolo-ribaudo/eslint-scope-5-internals': 5.1.1-v1 - eslint: 8.57.0 - eslint-visitor-keys: 2.1.0 - semver: 6.3.1 - dev: false - - /@babel/generator@7.22.9: - resolution: {integrity: sha512-KtLMbmicyuK2Ak/FTCJVbDnkN1SlT8/kceFTiuDiiRUUSMnHMidxSCdG4ndkTOHHpoomWe/4xkvHkEOncwjYIw==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.22.5 - '@jridgewell/gen-mapping': 0.3.3 - '@jridgewell/trace-mapping': 0.3.18 - jsesc: 2.5.2 - - /@babel/helper-annotate-as-pure@7.22.5: - resolution: {integrity: sha512-LvBTxu8bQSQkcyKOU+a1btnNFQ1dMAd0R6PyW3arXes06F6QLWLIrd681bxRPIXlrMGR3XYnW9JyML7dP3qgxg==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.22.5 - dev: false - - /@babel/helper-builder-binary-assignment-operator-visitor@7.22.5: - resolution: {integrity: sha512-m1EP3lVOPptR+2DwD125gziZNcmoNSHGmJROKoy87loWUQyJaVXDgpmruWqDARZSmtYQ+Dl25okU8+qhVzuykw==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.22.5 - dev: false - - /@babel/helper-compilation-targets@7.22.9(@babel/core@7.22.9): - resolution: {integrity: sha512-7qYrNM6HjpnPHJbopxmb8hSPoZ0gsX8IvUS32JGVoy+pU9e5N0nLr1VjJoR6kA4d9dmGLxNYOjeB8sUDal2WMw==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0 - dependencies: - '@babel/compat-data': 7.22.9 - '@babel/core': 7.22.9 - '@babel/helper-validator-option': 7.22.5 - browserslist: 4.21.9 - lru-cache: 5.1.1 - semver: 6.3.1 - - /@babel/helper-create-class-features-plugin@7.22.9(@babel/core@7.22.9): - resolution: {integrity: sha512-Pwyi89uO4YrGKxL/eNJ8lfEH55DnRloGPOseaA8NFNL6jAUnn+KccaISiFazCj5IolPPDjGSdzQzXVzODVRqUQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-annotate-as-pure': 7.22.5 - '@babel/helper-environment-visitor': 7.22.5 - '@babel/helper-function-name': 7.22.5 - '@babel/helper-member-expression-to-functions': 7.22.5 - '@babel/helper-optimise-call-expression': 7.22.5 - '@babel/helper-replace-supers': 7.22.9(@babel/core@7.22.9) - '@babel/helper-skip-transparent-expression-wrappers': 7.22.5 - '@babel/helper-split-export-declaration': 7.22.6 - semver: 6.3.1 - dev: false - - /@babel/helper-create-regexp-features-plugin@7.22.9(@babel/core@7.22.9): - resolution: {integrity: sha512-+svjVa/tFwsNSG4NEy1h85+HQ5imbT92Q5/bgtS7P0GTQlP8WuFdqsiABmQouhiFGyV66oGxZFpeYHza1rNsKw==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-annotate-as-pure': 7.22.5 - regexpu-core: 5.3.2 - semver: 6.3.1 - dev: false - - /@babel/helper-define-polyfill-provider@0.4.1(@babel/core@7.22.9): - resolution: {integrity: sha512-kX4oXixDxG197yhX+J3Wp+NpL2wuCFjWQAr6yX2jtCnflK9ulMI51ULFGIrWiX1jGfvAxdHp+XQCcP2bZGPs9A==} - peerDependencies: - '@babel/core': ^7.4.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-compilation-targets': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - debug: 4.3.4(supports-color@5.5.0) - lodash.debounce: 4.0.8 - resolve: 1.22.2 - transitivePeerDependencies: - - supports-color - dev: false - - /@babel/helper-environment-visitor@7.22.5: - resolution: {integrity: sha512-XGmhECfVA/5sAt+H+xpSg0mfrHq6FzNr9Oxh7PSEBBRUb/mL7Kz3NICXb194rCqAEdxkhPT1a88teizAFyvk8Q==} - engines: {node: '>=6.9.0'} - - /@babel/helper-function-name@7.22.5: - resolution: {integrity: sha512-wtHSq6jMRE3uF2otvfuD3DIvVhOsSNshQl0Qrd7qC9oQJzHvOL4qQXlQn2916+CXGywIjpGuIkoyZRRxHPiNQQ==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/template': 7.22.5 - '@babel/types': 7.22.5 - - /@babel/helper-hoist-variables@7.22.5: - resolution: {integrity: sha512-wGjk9QZVzvknA6yKIUURb8zY3grXCcOZt+/7Wcy8O2uctxhplmUPkOdlgoNhmdVee2c92JXbf1xpMtVNbfoxRw==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.22.5 - - /@babel/helper-member-expression-to-functions@7.22.5: - resolution: {integrity: sha512-aBiH1NKMG0H2cGZqspNvsaBe6wNGjbJjuLy29aU+eDZjSbbN53BaxlpB02xm9v34pLTZ1nIQPFYn2qMZoa5BQQ==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.22.5 - dev: false - - /@babel/helper-module-imports@7.22.15: - resolution: {integrity: sha512-0pYVBnDKZO2fnSPCrgM/6WMc7eS20Fbok+0r88fp+YtWVLZrp4CkafFGIp+W0VKw4a22sgebPT99y+FDNMdP4w==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.23.9 - dev: false - - /@babel/helper-module-imports@7.22.5: - resolution: {integrity: sha512-8Dl6+HD/cKifutF5qGd/8ZJi84QeAKh+CEe1sBzz8UayBBGg1dAIJrdHOcOM5b2MpzWL2yuotJTtGjETq0qjXg==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.22.5 - - /@babel/helper-module-transforms@7.22.9(@babel/core@7.22.9): - resolution: {integrity: sha512-t+WA2Xn5K+rTeGtC8jCsdAH52bjggG5TKRuRrAGNM/mjIbO4GxvlLMFOEz9wXY5I2XQ60PMFsAG2WIcG82dQMQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-environment-visitor': 7.22.5 - '@babel/helper-module-imports': 7.22.5 - '@babel/helper-simple-access': 7.22.5 - '@babel/helper-split-export-declaration': 7.22.6 - '@babel/helper-validator-identifier': 7.22.5 - - /@babel/helper-optimise-call-expression@7.22.5: - resolution: {integrity: sha512-HBwaojN0xFRx4yIvpwGqxiV2tUfl7401jlok564NgB9EHS1y6QT17FmKWm4ztqjeVdXLuC4fSvHc5ePpQjoTbw==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.22.5 - dev: false - - /@babel/helper-plugin-utils@7.22.5: - resolution: {integrity: sha512-uLls06UVKgFG9QD4OeFYLEGteMIAa5kpTPcFL28yuCIIzsf6ZyKZMllKVOCZFhiZ5ptnwX4mtKdWCBE/uT4amg==} - engines: {node: '>=6.9.0'} - dev: false - - /@babel/helper-remap-async-to-generator@7.22.9(@babel/core@7.22.9): - resolution: {integrity: sha512-8WWC4oR4Px+tr+Fp0X3RHDVfINGpF3ad1HIbrc8A77epiR6eMMc6jsgozkzT2uDiOOdoS9cLIQ+XD2XvI2WSmQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-annotate-as-pure': 7.22.5 - '@babel/helper-environment-visitor': 7.22.5 - '@babel/helper-wrap-function': 7.22.9 - dev: false - - /@babel/helper-replace-supers@7.22.9(@babel/core@7.22.9): - resolution: {integrity: sha512-LJIKvvpgPOPUThdYqcX6IXRuIcTkcAub0IaDRGCZH0p5GPUp7PhRU9QVgFcDDd51BaPkk77ZjqFwh6DZTAEmGg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-environment-visitor': 7.22.5 - '@babel/helper-member-expression-to-functions': 7.22.5 - '@babel/helper-optimise-call-expression': 7.22.5 - dev: false - - /@babel/helper-simple-access@7.22.5: - resolution: {integrity: sha512-n0H99E/K+Bika3++WNL17POvo4rKWZ7lZEp1Q+fStVbUi8nxPQEBOlTmCOxW/0JsS56SKKQ+ojAe2pHKJHN35w==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.22.5 - - /@babel/helper-skip-transparent-expression-wrappers@7.22.5: - resolution: {integrity: sha512-tK14r66JZKiC43p8Ki33yLBVJKlQDFoA8GYN67lWCDCqoL6EMMSuM9b+Iff2jHaM/RRFYl7K+iiru7hbRqNx8Q==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.22.5 - dev: false - - /@babel/helper-split-export-declaration@7.22.6: - resolution: {integrity: sha512-AsUnxuLhRYsisFiaJwvp1QF+I3KjD5FOxut14q/GzovUe6orHLesW2C7d754kRm53h5gqrz6sFl6sxc4BVtE/g==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.22.5 - - /@babel/helper-string-parser@7.22.5: - resolution: {integrity: sha512-mM4COjgZox8U+JcXQwPijIZLElkgEpO5rsERVDJTc2qfCDfERyob6k5WegS14SX18IIjv+XD+GrqNumY5JRCDw==} - engines: {node: '>=6.9.0'} - - /@babel/helper-string-parser@7.23.4: - resolution: {integrity: sha512-803gmbQdqwdf4olxrX4AJyFBV/RTr3rSmOj0rKwesmzlfhYNDEs+/iOcznzpNWlJlIlTJC2QfPFcHB6DlzdVLQ==} - engines: {node: '>=6.9.0'} - dev: false - - /@babel/helper-validator-identifier@7.22.20: - resolution: {integrity: sha512-Y4OZ+ytlatR8AI+8KZfKuL5urKp7qey08ha31L8b3BwewJAoJamTzyvxPR/5D+KkdJCGPq/+8TukHBlY10FX9A==} - engines: {node: '>=6.9.0'} - dev: false + dev: true /@babel/helper-validator-identifier@7.22.5: resolution: {integrity: sha512-aJXu+6lErq8ltp+JhkJUfk1MTGyuA4v7f3pA+BJ5HLfNC6nAQ0Cpi9uOquUj8Hehg0aUiHzWQbOVJGao6ztBAQ==} engines: {node: '>=6.9.0'} - - /@babel/helper-validator-option@7.22.5: - resolution: {integrity: sha512-R3oB6xlIVKUnxNUxbmgq7pKjxpru24zlimpE8WK47fACIlM0II/Hm1RS8IaOI7NgCr6LNS+jl5l75m20npAziw==} - engines: {node: '>=6.9.0'} - - /@babel/helper-wrap-function@7.22.9: - resolution: {integrity: sha512-sZ+QzfauuUEfxSEjKFmi3qDSHgLsTPK/pEpoD/qonZKOtTPTLbf59oabPQ4rKekt9lFcj/hTZaOhWwFYrgjk+Q==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/helper-function-name': 7.22.5 - '@babel/template': 7.22.5 - '@babel/types': 7.22.5 - dev: false - - /@babel/helpers@7.22.6: - resolution: {integrity: sha512-YjDs6y/fVOYFV8hAf1rxd1QvR9wJe1pDBZ2AREKq/SDayfPzgk0PBnVuTCE5X1acEpMMNOVUqoe+OwiZGJ+OaA==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/template': 7.22.5 - '@babel/traverse': 7.22.8 - '@babel/types': 7.22.5 - transitivePeerDependencies: - - supports-color + dev: true /@babel/highlight@7.22.5: resolution: {integrity: sha512-BSKlD1hgnedS5XRnGOljZawtag7H1yPfQp0tdNJCHoH6AZ+Pcm9VvkrK59/Yy593Ypg0zMxH2BxD1VPYUQ7UIw==} @@ -622,1162 +326,7 @@ '@babel/helper-validator-identifier': 7.22.5 chalk: 2.4.2 js-tokens: 4.0.0 - - /@babel/parser@7.22.7: - resolution: {integrity: sha512-7NF8pOkHP5o2vpmGgNGcfAeCvOYhGLyA3Z4eBQkT1RJlWu47n63bCs93QfJ2hIAFCil7L5P2IWhs1oToVgrL0Q==} - engines: {node: '>=6.0.0'} - hasBin: true - dependencies: - '@babel/types': 7.22.5 - - /@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-NP1M5Rf+u2Gw9qfSO4ihjcTGW5zXTi36ITLd4/EoAcEhIZ0yjMqmftDNl3QC19CX7olhrjpyU454g/2W7X0jvQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-31Bb65aZaUwqCbWMnZPduIZxCBngHFlzyN6Dq6KAJjtx+lx6ohKHubc61OomYi7XwVD4Ol0XCVz4h+pYFR048g==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.13.0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-skip-transparent-expression-wrappers': 7.22.5 - '@babel/plugin-transform-optional-chaining': 7.22.6(@babel/core@7.22.9) - dev: false - - /@babel/plugin-proposal-class-properties@7.18.6(@babel/core@7.22.9): - resolution: {integrity: sha512-cumfXOF0+nzZrrN8Rf0t7M+tF6sZc7vhQwYQck9q1/5w2OExlD+b4v4RpMJFaV1Z7WcDRgO6FqvxqxGlwo+RHQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-create-class-features-plugin': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-proposal-decorators@7.22.7(@babel/core@7.22.9): - resolution: {integrity: sha512-omXqPF7Onq4Bb7wHxXjM3jSMSJvUUbvDvmmds7KI5n9Cq6Ln5I05I1W2nRlRof1rGdiUxJrxwe285WF96XlBXQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-create-class-features-plugin': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-replace-supers': 7.22.9(@babel/core@7.22.9) - '@babel/helper-split-export-declaration': 7.22.6 - '@babel/plugin-syntax-decorators': 7.22.5(@babel/core@7.22.9) - dev: false - - /@babel/plugin-proposal-nullish-coalescing-operator@7.18.6(@babel/core@7.22.9): - resolution: {integrity: sha512-wQxQzxYeJqHcfppzBDnm1yAY0jSRkUXR2z8RePZYrKwMKgMlE8+Z6LUno+bd6LvbGh8Gltvy74+9pIYkr+XkKA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-nullish-coalescing-operator': 7.8.3(@babel/core@7.22.9) - dev: false - - /@babel/plugin-proposal-numeric-separator@7.18.6(@babel/core@7.22.9): - resolution: {integrity: sha512-ozlZFogPqoLm8WBr5Z8UckIoE4YQ5KESVcNudyXOR8uqIkliTEgJ3RoketfG6pmzLdeZF0H/wjE9/cCEitBl7Q==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-numeric-separator': 7.10.4(@babel/core@7.22.9) - dev: false - - /@babel/plugin-proposal-optional-chaining@7.21.0(@babel/core@7.22.9): - resolution: {integrity: sha512-p4zeefM72gpmEe2fkUr/OnOXpWEf8nAgk7ZYVqqfFiyIG7oFfVZcCrU64hWn5xp4tQ9LkV4bTIa5rD0KANpKNA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-skip-transparent-expression-wrappers': 7.22.5 - '@babel/plugin-syntax-optional-chaining': 7.8.3(@babel/core@7.22.9) - dev: false - - /@babel/plugin-proposal-private-methods@7.18.6(@babel/core@7.22.9): - resolution: {integrity: sha512-nutsvktDItsNn4rpGItSNV2sz1XwS+nfU0Rg8aCx3W3NOKVzdMjJRu0O5OkgDp3ZGICSTbgRpxZoWsxoKRvbeA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-create-class-features-plugin': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-proposal-private-property-in-object@7.21.0-placeholder-for-preset-env.2(@babel/core@7.22.9): - resolution: {integrity: sha512-SOSkfJDddaM7mak6cPEpswyTRnuRltl429hMraQEglW+OkovnCzsiszTmsrlY//qLFjCpQDFRvjdm2wA5pPm9w==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - dev: false - - /@babel/plugin-proposal-private-property-in-object@7.21.11(@babel/core@7.22.9): - resolution: {integrity: sha512-0QZ8qP/3RLDVBwBFoWAwCtgcDZJVwA5LUJRZU8x2YFfKNuFq161wK3cuGrALu5yiPu+vzwTAg/sMWVNeWeNyaw==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-annotate-as-pure': 7.22.5 - '@babel/helper-create-class-features-plugin': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-private-property-in-object': 7.14.5(@babel/core@7.22.9) - dev: false - - /@babel/plugin-proposal-unicode-property-regex@7.18.6(@babel/core@7.22.9): - resolution: {integrity: sha512-2BShG/d5yoZyXZfVePH91urL5wTG6ASZU9M4o03lKK8u8UW1y08OMttBSOADTcJrnPMpvDXRG3G8fyLh4ovs8w==} - engines: {node: '>=4'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-create-regexp-features-plugin': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-async-generators@7.8.4(@babel/core@7.22.9): - resolution: {integrity: sha512-tycmZxkGfZaxhMRbXlPXuVFpdWlXpir2W4AMhSJgRKzk/eDlIXOhb2LHWoLpDF7TEHylV5zNhykX6KAgHJmTNw==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-bigint@7.8.3(@babel/core@7.22.9): - resolution: {integrity: sha512-wnTnFlG+YxQm3vDxpGE57Pj0srRU4sHE/mDkt1qv2YJJSeUAec2ma4WLUnUPeKjyrfntVwe/N6dCXpU+zL3Npg==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-class-properties@7.12.13(@babel/core@7.22.9): - resolution: {integrity: sha512-fm4idjKla0YahUNgFNLCB0qySdsoPiZP3iQE3rky0mBUtMZ23yDJ9SJdg6dXTSDnulOVqiF3Hgr9nbXvXTQZYA==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-class-static-block@7.14.5(@babel/core@7.22.9): - resolution: {integrity: sha512-b+YyPmr6ldyNnM6sqYeMWE+bgJcJpO6yS4QD7ymxgH34GBPNDM/THBh8iunyvKIZztiwLH4CJZ0RxTk9emgpjw==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-decorators@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-avpUOBS7IU6al8MmF1XpAyj9QYeLPuSDJI5D4pVMSMdL7xQokKqJPYQC67RCT0aCTashUXPiGwMJ0DEXXCEmMA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-dynamic-import@7.8.3(@babel/core@7.22.9): - resolution: {integrity: sha512-5gdGbFon+PszYzqs83S3E5mpi7/y/8M9eC90MRTZfduQOYW76ig6SOSPNe41IG5LoP3FGBn2N0RjVDSQiS94kQ==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-export-namespace-from@7.8.3(@babel/core@7.22.9): - resolution: {integrity: sha512-MXf5laXo6c1IbEbegDmzGPwGNTsHZmEy6QGznu5Sh2UCWvueywb2ee+CCE4zQiZstxU9BMoQO9i6zUFSY0Kj0Q==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-flow@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-9RdCl0i+q0QExayk2nOS7853w08yLucnnPML6EN9S8fgMPVtdLDCdx/cOQ/i44Lb9UeQX9A35yaqBBOMMZxPxQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-flow@7.23.3(@babel/core@7.22.9): - resolution: {integrity: sha512-YZiAIpkJAwQXBJLIQbRFayR5c+gJ35Vcz3bg954k7cd73zqjvhacJuL9RbrzPz8qPmZdgqP6EUKwy0PCNhaaPA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-import-assertions@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-rdV97N7KqsRzeNGoWUOK6yUsWarLjE5Su/Snk9IYPU9CwkWHs4t+rTGOvffTR8XGkJMTAdLfO0xVnXm8wugIJg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-import-attributes@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-KwvoWDeNKPETmozyFE0P2rOLqh39EoQHNjqizrI5B8Vt0ZNS7M56s7dAiAqbYfiAYOuIzIh96z3iR2ktgu3tEg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-import-meta@7.10.4(@babel/core@7.22.9): - resolution: {integrity: sha512-Yqfm+XDx0+Prh3VSeEQCPU81yC+JWZ2pDPFSS4ZdpfZhp4MkFMaDC1UqseovEKwSUpnIL7+vK+Clp7bfh0iD7g==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-json-strings@7.8.3(@babel/core@7.22.9): - resolution: {integrity: sha512-lY6kdGpWHvjoe2vk4WrAapEuBR69EMxZl+RoGRhrFGNYVK8mOPAW8VfbT/ZgrFbXlDNiiaxQnAtgVCZ6jv30EA==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-jsx@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-gvyP4hZrgrs/wWMaocvxZ44Hw0b3W8Pe+cMxc8V1ULQ07oh8VNbIRaoD1LRZVTvD+0nieDKjfgKg89sD7rrKrg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-jsx@7.23.3(@babel/core@7.22.9): - resolution: {integrity: sha512-EB2MELswq55OHUoRZLGg/zC7QWUKfNLpE57m/S2yr1uEneIgsTgrSzXP3NXEsMkVn76OlaVVnzN+ugObuYGwhg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-logical-assignment-operators@7.10.4(@babel/core@7.22.9): - resolution: {integrity: sha512-d8waShlpFDinQ5MtvGU9xDAOzKH47+FFoney2baFIoMr952hKOLp1HR7VszoZvOsV/4+RRszNY7D17ba0te0ig==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-nullish-coalescing-operator@7.8.3(@babel/core@7.22.9): - resolution: {integrity: sha512-aSff4zPII1u2QD7y+F8oDsz19ew4IGEJg9SVW+bqwpwtfFleiQDMdzA/R+UlWDzfnHFCxxleFT0PMIrR36XLNQ==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-numeric-separator@7.10.4(@babel/core@7.22.9): - resolution: {integrity: sha512-9H6YdfkcK/uOnY/K7/aA2xpzaAgkQn37yzWUMRK7OaPOqOpGS1+n0H5hxT9AUw9EsSjPW8SVyMJwYRtWs3X3ug==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-object-rest-spread@7.8.3(@babel/core@7.22.9): - resolution: {integrity: sha512-XoqMijGZb9y3y2XskN+P1wUGiVwWZ5JmoDRwx5+3GmEplNyVM2s2Dg8ILFQm8rWM48orGy5YpI5Bl8U1y7ydlA==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-optional-catch-binding@7.8.3(@babel/core@7.22.9): - resolution: {integrity: sha512-6VPD0Pc1lpTqw0aKoeRTMiB+kWhAoT24PA+ksWSBrFtl5SIRVpZlwN3NNPQjehA2E/91FV3RjLWoVTglWcSV3Q==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-optional-chaining@7.8.3(@babel/core@7.22.9): - resolution: {integrity: sha512-KoK9ErH1MBlCPxV0VANkXW2/dw4vlbGDrFgz8bmUsBGYkFRcbRwMh6cIJubdPrkxRwuGdtCk0v/wPTKbQgBjkg==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-private-property-in-object@7.14.5(@babel/core@7.22.9): - resolution: {integrity: sha512-0wVnp9dxJ72ZUJDV27ZfbSj6iHLoytYZmh3rFcxNnvsJF3ktkzLDZPy/mA17HGsaQT3/DQsWYX1f1QGWkCoVUg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-top-level-await@7.14.5(@babel/core@7.22.9): - resolution: {integrity: sha512-hx++upLv5U1rgYfwe1xBQUhRmU41NEvpUvrp8jkrSCdvGSnM5/qdRMtylJ6PG5OFkBaHkbTAKTnd3/YyESRHFw==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-typescript@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-1mS2o03i7t1c6VzH6fdQ3OA8tcEIxwG18zIPRp+UY1Ihv6W+XZzBCVxExF9upussPXJ0xE9XRHwMoNs1ep/nRQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-unicode-sets-regex@7.18.6(@babel/core@7.22.9): - resolution: {integrity: sha512-727YkEAPwSIQTv5im8QHz3upqp92JTWhidIC81Tdx4VJYIte/VndKf1qKrfnnhPLiPghStWfvC/iFaMCQu7Nqg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-create-regexp-features-plugin': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-arrow-functions@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-26lTNXoVRdAnsaDXPpvCNUq+OVWEVC6bx7Vvz9rC53F2bagUWW4u4ii2+h8Fejfh7RYqPxn+libeFBBck9muEw==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-async-generator-functions@7.22.7(@babel/core@7.22.9): - resolution: {integrity: sha512-7HmE7pk/Fmke45TODvxvkxRMV9RazV+ZZzhOL9AG8G29TLrr3jkjwF7uJfxZ30EoXpO+LJkq4oA8NjO2DTnEDg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-environment-visitor': 7.22.5 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-remap-async-to-generator': 7.22.9(@babel/core@7.22.9) - '@babel/plugin-syntax-async-generators': 7.8.4(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-async-to-generator@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-b1A8D8ZzE/VhNDoV1MSJTnpKkCG5bJo+19R4o4oy03zM7ws8yEMK755j61Dc3EyvdysbqH5BOOTquJ7ZX9C6vQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-module-imports': 7.22.5 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-remap-async-to-generator': 7.22.9(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-block-scoped-functions@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-tdXZ2UdknEKQWKJP1KMNmuF5Lx3MymtMN/pvA+p/VEkhK8jVcQ1fzSy8KM9qRYhAf2/lV33hoMPKI/xaI9sADA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-block-scoping@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-EcACl1i5fSQ6bt+YGuU/XGCeZKStLmyVGytWkpyhCLeQVA0eu6Wtiw92V+I1T/hnezUv7j74dA/Ro69gWcU+hg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-class-properties@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-nDkQ0NfkOhPTq8YCLiWNxp1+f9fCobEjCb0n8WdbNUBc4IB5V7P1QnX9IjpSoquKrXF5SKojHleVNs2vGeHCHQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-create-class-features-plugin': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-class-static-block@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-SPToJ5eYZLxlnp1UzdARpOGeC2GbHvr9d/UV0EukuVx8atktg194oe+C5BqQ8jRTkgLRVOPYeXRSBg1IlMoVRA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.12.0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-create-class-features-plugin': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-class-static-block': 7.14.5(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-classes@7.22.6(@babel/core@7.22.9): - resolution: {integrity: sha512-58EgM6nuPNG6Py4Z3zSuu0xWu2VfodiMi72Jt5Kj2FECmaYk1RrTXA45z6KBFsu9tRgwQDwIiY4FXTt+YsSFAQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-annotate-as-pure': 7.22.5 - '@babel/helper-compilation-targets': 7.22.9(@babel/core@7.22.9) - '@babel/helper-environment-visitor': 7.22.5 - '@babel/helper-function-name': 7.22.5 - '@babel/helper-optimise-call-expression': 7.22.5 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-replace-supers': 7.22.9(@babel/core@7.22.9) - '@babel/helper-split-export-declaration': 7.22.6 - globals: 11.12.0 - dev: false - - /@babel/plugin-transform-computed-properties@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-4GHWBgRf0krxPX+AaPtgBAlTgTeZmqDynokHOX7aqqAB4tHs3U2Y02zH6ETFdLZGcg9UQSD1WCmkVrE9ErHeOg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/template': 7.22.5 - dev: false - - /@babel/plugin-transform-destructuring@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-GfqcFuGW8vnEqTUBM7UtPd5A4q797LTvvwKxXTgRsFjoqaJiEg9deBG6kWeQYkVEL569NpnmpC0Pkr/8BLKGnQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-dotall-regex@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-5/Yk9QxCQCl+sOIB1WelKnVRxTJDSAIxtJLL2/pqL14ZVlbH0fUQUZa/T5/UnQtBNgghR7mfB8ERBKyKPCi7Vw==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-create-regexp-features-plugin': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-duplicate-keys@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-dEnYD+9BBgld5VBXHnF/DbYGp3fqGMsyxKbtD1mDyIA7AkTSpKXFhCVuj/oQVOoALfBs77DudA0BE4d5mcpmqw==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-dynamic-import@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-0MC3ppTB1AMxd8fXjSrbPa7LT9hrImt+/fcj+Pg5YMD7UQyWp/02+JWpdnCymmsXwIx5Z+sYn1bwCn4ZJNvhqQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-dynamic-import': 7.8.3(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-exponentiation-operator@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-vIpJFNM/FjZ4rh1myqIya9jXwrwwgFRHPjT3DkUA9ZLHuzox8jiXkOLvwm1H+PQIP3CqfC++WPKeuDi0Sjdj1g==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-builder-binary-assignment-operator-visitor': 7.22.5 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-export-namespace-from@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-X4hhm7FRnPgd4nDA4b/5V280xCx6oL7Oob5+9qVS5C13Zq4bh1qq7LU0GgRU6b5dBWBvhGaXYVB4AcN6+ol6vg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-export-namespace-from': 7.8.3(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-flow-strip-types@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-tujNbZdxdG0/54g/oua8ISToaXTFBf8EnSb5PgQSciIXWOWKX3S4+JR7ZE9ol8FZwf9kxitzkGQ+QWeov/mCiA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-flow': 7.22.5(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-for-of@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-3kxQjX1dU9uudwSshyLeEipvrLjBCVthCgeTp6CzE/9JYrlAIaeekVxRpCWsDDfYTfRZRoCeZatCQvwo+wvK8A==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-function-name@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-UIzQNMS0p0HHiQm3oelztj+ECwFnj+ZRV4KnguvlsD2of1whUeM6o7wGNj6oLwcDoAXQ8gEqfgC24D+VdIcevg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-compilation-targets': 7.22.9(@babel/core@7.22.9) - '@babel/helper-function-name': 7.22.5 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-json-strings@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-DuCRB7fu8MyTLbEQd1ew3R85nx/88yMoqo2uPSjevMj3yoN7CDM8jkgrY0wmVxfJZyJ/B9fE1iq7EQppWQmR5A==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-json-strings': 7.8.3(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-literals@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-fTLj4D79M+mepcw3dgFBTIDYpbcB9Sm0bpm4ppXPaO+U+PKFFyV9MGRvS0gvGw62sd10kT5lRMKXAADb9pWy8g==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-logical-assignment-operators@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-MQQOUW1KL8X0cDWfbwYP+TbVbZm16QmQXJQ+vndPtH/BoO0lOKpVoEDMI7+PskYxH+IiE0tS8xZye0qr1lGzSA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-logical-assignment-operators': 7.10.4(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-member-expression-literals@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-RZEdkNtzzYCFl9SE9ATaUMTj2hqMb4StarOJLrZRbqqU4HSBE7UlBw9WBWQiDzrJZJdUWiMTVDI6Gv/8DPvfew==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-modules-amd@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-R+PTfLTcYEmb1+kK7FNkhQ1gP4KgjpSO6HfH9+f8/yfp2Nt3ggBjiVpRwmwTlfqZLafYKJACy36yDXlEmI9HjQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-module-transforms': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-modules-commonjs@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-B4pzOXj+ONRmuaQTg05b3y/4DuFz3WcCNAXPLb2Q0GT0TrGKGxNKV4jwsXts+StaM0LQczZbOpj8o1DLPDJIiA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-module-transforms': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-simple-access': 7.22.5 - dev: false - - /@babel/plugin-transform-modules-systemjs@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-emtEpoaTMsOs6Tzz+nbmcePl6AKVtS1yC4YNAeMun9U8YCsgadPNxnOPQ8GhHFB2qdx+LZu9LgoC0Lthuu05DQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-hoist-variables': 7.22.5 - '@babel/helper-module-transforms': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-validator-identifier': 7.22.5 - dev: false - - /@babel/plugin-transform-modules-umd@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-+S6kzefN/E1vkSsKx8kmQuqeQsvCKCd1fraCM7zXm4SFoggI099Tr4G8U81+5gtMdUeMQ4ipdQffbKLX0/7dBQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-module-transforms': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-named-capturing-groups-regex@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-YgLLKmS3aUBhHaxp5hi1WJTgOUb/NCuDHzGT9z9WTt3YG+CPRhJs6nprbStx6DnWM4dh6gt7SU3sZodbZ08adQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-create-regexp-features-plugin': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-new-target@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-AsF7K0Fx/cNKVyk3a+DW0JLo+Ua598/NxMRvxDnkpCIGFh43+h/v2xyhRUYf6oD8gE4QtL83C7zZVghMjHd+iw==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-nullish-coalescing-operator@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-6CF8g6z1dNYZ/VXok5uYkkBBICHZPiGEl7oDnAx2Mt1hlHVHOSIKWJaXHjQJA5VB43KZnXZDIexMchY4y2PGdA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-nullish-coalescing-operator': 7.8.3(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-numeric-separator@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-NbslED1/6M+sXiwwtcAB/nieypGw02Ejf4KtDeMkCEpP6gWFMX1wI9WKYua+4oBneCCEmulOkRpwywypVZzs/g==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-numeric-separator': 7.10.4(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-object-rest-spread@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-Kk3lyDmEslH9DnvCDA1s1kkd3YWQITiBOHngOtDL9Pt6BZjzqb6hiOlb8VfjiiQJ2unmegBqZu0rx5RxJb5vmQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/compat-data': 7.22.9 - '@babel/core': 7.22.9 - '@babel/helper-compilation-targets': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-object-rest-spread': 7.8.3(@babel/core@7.22.9) - '@babel/plugin-transform-parameters': 7.22.5(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-object-super@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-klXqyaT9trSjIUrcsYIfETAzmOEZL3cBYqOYLJxBHfMFFggmXOv+NYSX/Jbs9mzMVESw/WycLFPRx8ba/b2Ipw==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-replace-supers': 7.22.9(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-optional-catch-binding@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-pH8orJahy+hzZje5b8e2QIlBWQvGpelS76C63Z+jhZKsmzfNaPQ+LaW6dcJ9bxTpo1mtXbgHwy765Ro3jftmUg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-optional-catch-binding': 7.8.3(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-optional-chaining@7.22.6(@babel/core@7.22.9): - resolution: {integrity: sha512-Vd5HiWml0mDVtcLHIoEU5sw6HOUW/Zk0acLs/SAeuLzkGNOPc9DB4nkUajemhCmTIz3eiaKREZn2hQQqF79YTg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-skip-transparent-expression-wrappers': 7.22.5 - '@babel/plugin-syntax-optional-chaining': 7.8.3(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-parameters@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-AVkFUBurORBREOmHRKo06FjHYgjrabpdqRSwq6+C7R5iTCZOsM4QbcB27St0a4U6fffyAOqh3s/qEfybAhfivg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-private-methods@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-PPjh4gyrQnGe97JTalgRGMuU4icsZFnWkzicB/fUtzlKUqvsWBKEpPPfr5a2JiyirZkHxnAqkQMO5Z5B2kK3fA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-create-class-features-plugin': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-private-property-in-object@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-/9xnaTTJcVoBtSSmrVyhtSvO3kbqS2ODoh2juEU72c3aYonNF0OMGiaz2gjukyKM2wBBYJP38S4JiE0Wfb5VMQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-annotate-as-pure': 7.22.5 - '@babel/helper-create-class-features-plugin': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-private-property-in-object': 7.14.5(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-property-literals@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-TiOArgddK3mK/x1Qwf5hay2pxI6wCZnvQqrFSqbtg1GLl2JcNMitVH/YnqjP+M31pLUeTfzY1HAXFDnUBV30rQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-react-constant-elements@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-BF5SXoO+nX3h5OhlN78XbbDrBOffv+AxPP2ENaJOVqjWCgBDeOY3WcaUcddutGSfoap+5NEQ/q/4I3WZIvgkXA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-react-display-name@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-PVk3WPYudRF5z4GKMEYUrLjPl38fJSKNaEOkFuoprioowGuWN6w2RKznuFNSlJx7pzzXXStPUnNSOEO0jL5EVw==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-react-jsx-development@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-bDhuzwWMuInwCYeDeMzyi7TaBgRQei6DqxhbyniL7/VG4RSS7HtSL2QbY4eESy1KJqlWt8g3xeEBGPuo+XqC8A==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/plugin-transform-react-jsx': 7.22.5(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-react-jsx@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-rog5gZaVbUip5iWDMTYbVM15XQq+RkUKhET/IHR6oizR+JEoN6CAfTTuHcK4vwUyzca30qqHqEpzBOnaRMWYMA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-annotate-as-pure': 7.22.5 - '@babel/helper-module-imports': 7.22.5 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-jsx': 7.22.5(@babel/core@7.22.9) - '@babel/types': 7.22.5 - dev: false - - /@babel/plugin-transform-react-jsx@7.23.4(@babel/core@7.22.9): - resolution: {integrity: sha512-5xOpoPguCZCRbo/JeHlloSkTA8Bld1J/E1/kLfD1nsuiW1m8tduTA1ERCgIZokDflX/IBzKcqR3l7VlRgiIfHA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-annotate-as-pure': 7.22.5 - '@babel/helper-module-imports': 7.22.15 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-jsx': 7.23.3(@babel/core@7.22.9) - '@babel/types': 7.23.9 - dev: false - - /@babel/plugin-transform-react-pure-annotations@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-gP4k85wx09q+brArVinTXhWiyzLl9UpmGva0+mWyKxk6JZequ05x3eUcIUE+FyttPKJFRRVtAvQaJ6YF9h1ZpA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-annotate-as-pure': 7.22.5 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-regenerator@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-rR7KePOE7gfEtNTh9Qw+iO3Q/e4DEsoQ+hdvM6QUDH7JRJ5qxq5AA52ZzBWbI5i9lfNuvySgOGP8ZN7LAmaiPw==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - regenerator-transform: 0.15.1 - dev: false - - /@babel/plugin-transform-reserved-words@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-DTtGKFRQUDm8svigJzZHzb/2xatPc6TzNvAIJ5GqOKDsGFYgAskjRulbR/vGsPKq3OPqtexnz327qYpP57RFyA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-runtime@7.22.9(@babel/core@7.22.9): - resolution: {integrity: sha512-9KjBH61AGJetCPYp/IEyLEp47SyybZb0nDRpBvmtEkm+rUIwxdlKpyNHI1TmsGkeuLclJdleQHRZ8XLBnnh8CQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-module-imports': 7.22.5 - '@babel/helper-plugin-utils': 7.22.5 - babel-plugin-polyfill-corejs2: 0.4.4(@babel/core@7.22.9) - babel-plugin-polyfill-corejs3: 0.8.2(@babel/core@7.22.9) - babel-plugin-polyfill-regenerator: 0.5.1(@babel/core@7.22.9) - semver: 6.3.1 - transitivePeerDependencies: - - supports-color - dev: false - - /@babel/plugin-transform-shorthand-properties@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-vM4fq9IXHscXVKzDv5itkO1X52SmdFBFcMIBZ2FRn2nqVYqw6dBexUgMvAjHW+KXpPPViD/Yo3GrDEBaRC0QYA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-spread@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-5ZzDQIGyvN4w8+dMmpohL6MBo+l2G7tfC/O2Dg7/hjpgeWvUx8FzfeOKxGog9IimPa4YekaQ9PlDqTLOljkcxg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-skip-transparent-expression-wrappers': 7.22.5 - dev: false - - /@babel/plugin-transform-sticky-regex@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-zf7LuNpHG0iEeiyCNwX4j3gDg1jgt1k3ZdXBKbZSoA3BbGQGvMiSvfbZRR3Dr3aeJe3ooWFZxOOG3IRStYp2Bw==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-template-literals@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-5ciOehRNf+EyUeewo8NkbQiUs4d6ZxiHo6BcBcnFlgiJfu16q0bQUw9Jvo0b0gBKFG1SMhDSjeKXSYuJLeFSMA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-typeof-symbol@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-bYkI5lMzL4kPii4HHEEChkD0rkc+nvnlR6+o/qdqR6zrm0Sv/nodmyLhlq2DO0YKLUNd2VePmPRjJXSBh9OIdA==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-typescript@7.22.9(@babel/core@7.22.9): - resolution: {integrity: sha512-BnVR1CpKiuD0iobHPaM1iLvcwPYN2uVFAqoLVSpEDKWuOikoCv5HbKLxclhKYUXlWkX86DoZGtqI4XhbOsyrMg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-annotate-as-pure': 7.22.5 - '@babel/helper-create-class-features-plugin': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-typescript': 7.22.5(@babel/core@7.22.9) - dev: false - - /@babel/plugin-transform-unicode-escapes@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-biEmVg1IYB/raUO5wT1tgfacCef15Fbzhkx493D3urBI++6hpJ+RFG4SrWMn0NEZLfvilqKf3QDrRVZHo08FYg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-unicode-property-regex@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-HCCIb+CbJIAE6sXn5CjFQXMwkCClcOfPCzTlilJ8cUatfzwHlWQkbtV0zD338u9dZskwvuOYTuuaMaA8J5EI5A==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-create-regexp-features-plugin': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-unicode-regex@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-028laaOKptN5vHJf9/Arr/HiJekMd41hOEZYvNsrsXqJ7YPYuX2bQxh31fkZzGmq3YqHRJzYFFAVYvKfMPKqyg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-create-regexp-features-plugin': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-transform-unicode-sets-regex@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-lhMfi4FC15j13eKrh3DnYHjpGj6UKQHtNKTbtc1igvAhRy4+kLhV07OpLcsN0VgDEw/MjAvJO4BdMJsHwMhzCg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-create-regexp-features-plugin': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/preset-env@7.22.9(@babel/core@7.22.9): - resolution: {integrity: sha512-wNi5H/Emkhll/bqPjsjQorSykrlfY5OWakd6AulLvMEytpKasMVUpVy8RL4qBIBs5Ac6/5i0/Rv0b/Fg6Eag/g==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/compat-data': 7.22.9 - '@babel/core': 7.22.9 - '@babel/helper-compilation-targets': 7.22.9(@babel/core@7.22.9) - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-validator-option': 7.22.5 - '@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-proposal-private-property-in-object': 7.21.0-placeholder-for-preset-env.2(@babel/core@7.22.9) - '@babel/plugin-syntax-async-generators': 7.8.4(@babel/core@7.22.9) - '@babel/plugin-syntax-class-properties': 7.12.13(@babel/core@7.22.9) - '@babel/plugin-syntax-class-static-block': 7.14.5(@babel/core@7.22.9) - '@babel/plugin-syntax-dynamic-import': 7.8.3(@babel/core@7.22.9) - '@babel/plugin-syntax-export-namespace-from': 7.8.3(@babel/core@7.22.9) - '@babel/plugin-syntax-import-assertions': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-syntax-import-attributes': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-syntax-import-meta': 7.10.4(@babel/core@7.22.9) - '@babel/plugin-syntax-json-strings': 7.8.3(@babel/core@7.22.9) - '@babel/plugin-syntax-logical-assignment-operators': 7.10.4(@babel/core@7.22.9) - '@babel/plugin-syntax-nullish-coalescing-operator': 7.8.3(@babel/core@7.22.9) - '@babel/plugin-syntax-numeric-separator': 7.10.4(@babel/core@7.22.9) - '@babel/plugin-syntax-object-rest-spread': 7.8.3(@babel/core@7.22.9) - '@babel/plugin-syntax-optional-catch-binding': 7.8.3(@babel/core@7.22.9) - '@babel/plugin-syntax-optional-chaining': 7.8.3(@babel/core@7.22.9) - '@babel/plugin-syntax-private-property-in-object': 7.14.5(@babel/core@7.22.9) - '@babel/plugin-syntax-top-level-await': 7.14.5(@babel/core@7.22.9) - '@babel/plugin-syntax-unicode-sets-regex': 7.18.6(@babel/core@7.22.9) - '@babel/plugin-transform-arrow-functions': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-async-generator-functions': 7.22.7(@babel/core@7.22.9) - '@babel/plugin-transform-async-to-generator': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-block-scoped-functions': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-block-scoping': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-class-properties': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-class-static-block': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-classes': 7.22.6(@babel/core@7.22.9) - '@babel/plugin-transform-computed-properties': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-destructuring': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-dotall-regex': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-duplicate-keys': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-dynamic-import': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-exponentiation-operator': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-export-namespace-from': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-for-of': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-function-name': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-json-strings': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-literals': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-logical-assignment-operators': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-member-expression-literals': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-modules-amd': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-modules-commonjs': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-modules-systemjs': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-modules-umd': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-named-capturing-groups-regex': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-new-target': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-nullish-coalescing-operator': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-numeric-separator': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-object-rest-spread': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-object-super': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-optional-catch-binding': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-optional-chaining': 7.22.6(@babel/core@7.22.9) - '@babel/plugin-transform-parameters': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-private-methods': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-private-property-in-object': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-property-literals': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-regenerator': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-reserved-words': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-shorthand-properties': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-spread': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-sticky-regex': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-template-literals': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-typeof-symbol': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-unicode-escapes': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-unicode-property-regex': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-unicode-regex': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-unicode-sets-regex': 7.22.5(@babel/core@7.22.9) - '@babel/preset-modules': 0.1.5(@babel/core@7.22.9) - '@babel/types': 7.22.5 - babel-plugin-polyfill-corejs2: 0.4.4(@babel/core@7.22.9) - babel-plugin-polyfill-corejs3: 0.8.2(@babel/core@7.22.9) - babel-plugin-polyfill-regenerator: 0.5.1(@babel/core@7.22.9) - core-js-compat: 3.31.1 - semver: 6.3.1 - transitivePeerDependencies: - - supports-color - dev: false - - /@babel/preset-modules@0.1.5(@babel/core@7.22.9): - resolution: {integrity: sha512-A57th6YRG7oR3cq/yt/Y84MvGgE0eJG2F1JLhKuyG+jFxEgrd/HAMJatiFtmOiZurz+0DkrvbheCLaV5f2JfjA==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-proposal-unicode-property-regex': 7.18.6(@babel/core@7.22.9) - '@babel/plugin-transform-dotall-regex': 7.22.5(@babel/core@7.22.9) - '@babel/types': 7.22.5 - esutils: 2.0.3 - dev: false - - /@babel/preset-react@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-M+Is3WikOpEJHgR385HbuCITPTaPRaNkibTEa9oiofmJvIsrceb4yp9RL9Kb+TE8LznmeyZqpP+Lopwcx59xPQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-validator-option': 7.22.5 - '@babel/plugin-transform-react-display-name': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-react-jsx': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-react-jsx-development': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-react-pure-annotations': 7.22.5(@babel/core@7.22.9) - dev: false - - /@babel/preset-typescript@7.22.5(@babel/core@7.22.9): - resolution: {integrity: sha512-YbPaal9LxztSGhmndR46FmAbkJ/1fAsw293tSU+I5E5h+cnJ3d4GTwyUgGYmOXJYdGA+uNePle4qbaRzj2NISQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-validator-option': 7.22.5 - '@babel/plugin-syntax-jsx': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-modules-commonjs': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-typescript': 7.22.9(@babel/core@7.22.9) - dev: false - - /@babel/regjsgen@0.8.0: - resolution: {integrity: sha512-x/rqGMdzj+fWZvCOYForTghzbtqPDZ5gPwaoNGHdgDfF2QA/XZbCBp4Moo5scrkAMPhB7z26XM/AaHuIJdgauA==} - dev: false - - /@babel/runtime@7.22.6: - resolution: {integrity: sha512-wDb5pWm4WDdF6LFUde3Jl8WzPA+3ZbxYqkC6xAXuD3irdEHN1k0NfTRrJD8ZD378SJ61miMLCqIOXYhd8x+AJQ==} - engines: {node: '>=6.9.0'} - dependencies: - regenerator-runtime: 0.13.11 - dev: false + dev: true /@babel/runtime@7.23.2: resolution: {integrity: sha512-mM8eg4yl5D6i3lu2QKPuPH4FArvJ8KhTofbE7jwMUv9KX5mBvwPAqnV3MlyBNqdp9RyRKP6Yck8TrfYrPvX3bg==} @@ -1792,52 +341,6 @@ dependencies: regenerator-runtime: 0.14.0 - /@babel/template@7.22.5: - resolution: {integrity: sha512-X7yV7eiwAxdj9k94NEylvbVHLiVG1nvzCV2EAowhxLTwODV1jl9UzZ48leOC0sH7OnuHrIkllaBgneUykIcZaw==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/code-frame': 7.22.5 - '@babel/parser': 7.22.7 - '@babel/types': 7.22.5 - - /@babel/traverse@7.22.8: - resolution: {integrity: sha512-y6LPR+wpM2I3qJrsheCTwhIinzkETbplIgPBbwvqPKc+uljeA5gP+3nP8irdYt1mjQaDnlIcG+dw8OjAco4GXw==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/code-frame': 7.22.5 - '@babel/generator': 7.22.9 - '@babel/helper-environment-visitor': 7.22.5 - '@babel/helper-function-name': 7.22.5 - '@babel/helper-hoist-variables': 7.22.5 - '@babel/helper-split-export-declaration': 7.22.6 - '@babel/parser': 7.22.7 - '@babel/types': 7.22.5 - debug: 4.3.4(supports-color@5.5.0) - globals: 11.12.0 - transitivePeerDependencies: - - supports-color - - /@babel/types@7.22.5: - resolution: {integrity: sha512-zo3MIHGOkPOfoRXitsgHLjEXmlDaD/5KU1Uzuc9GNiZPhSqVxVRtxuPaSBZDsYZ9qV88AjtMtWW7ww98loJ9KA==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/helper-string-parser': 7.22.5 - '@babel/helper-validator-identifier': 7.22.5 - to-fast-properties: 2.0.0 - - /@babel/types@7.23.9: - resolution: {integrity: sha512-dQjSq/7HaSjRM43FFGnv5keM2HsxpmyV1PfaSVm0nzzjwwTmjOe6J4bC8e3+pTEIgHaHj+1ZlLThRJ2auc/w1Q==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/helper-string-parser': 7.23.4 - '@babel/helper-validator-identifier': 7.22.20 - to-fast-properties: 2.0.0 - dev: false - - /@bcoe/v8-coverage@0.2.3: - resolution: {integrity: sha512-0hYQ8SB4Db5zvZB4axdMHGwEaQjkZzFjQiN9LVYvIFB2nSUHW9tYpxWriPrWDASIxiaXax83REcLxuSdnGPZtw==} - dev: false - /@colors/colors@1.5.0: resolution: {integrity: sha512-ooWCrlZP11i8GImSjTHYHLkvFDP48nS4+204nGb1RiX/WXYHmJA2III9/e2DWVabCESdW7hBAEzHRqUn9OUVvQ==} engines: {node: '>=0.1.90'} @@ -1848,163 +351,6 @@ engines: {node: '>=0.1.90'} dev: false - /@csstools/normalize.css@12.0.0: - resolution: {integrity: sha512-M0qqxAcwCsIVfpFQSlGN5XjXWu8l5JDZN+fPt1LeW5SZexQTgnaEvgXAY+CeygRw0EeppWHi12JxESWiWrB0Sg==} - dev: false - - /@csstools/postcss-cascade-layers@1.1.1(postcss@8.4.26): - resolution: {integrity: sha512-+KdYrpKC5TgomQr2DlZF4lDEpHcoxnj5IGddYYfBWJAKfj1JtuHUIqMa+E1pJJ+z3kvDViWMqyqPlG4Ja7amQA==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - '@csstools/selector-specificity': 2.2.0(postcss-selector-parser@6.0.13) - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /@csstools/postcss-color-function@1.1.1(postcss@8.4.26): - resolution: {integrity: sha512-Bc0f62WmHdtRDjf5f3e2STwRAl89N2CLb+9iAwzrv4L2hncrbDwnQD9PCq0gtAt7pOI2leIV08HIBUd4jxD8cw==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - '@csstools/postcss-progressive-custom-properties': 1.3.0(postcss@8.4.26) - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /@csstools/postcss-font-format-keywords@1.0.1(postcss@8.4.26): - resolution: {integrity: sha512-ZgrlzuUAjXIOc2JueK0X5sZDjCtgimVp/O5CEqTcs5ShWBa6smhWYbS0x5cVc/+rycTDbjjzoP0KTDnUneZGOg==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /@csstools/postcss-hwb-function@1.0.2(postcss@8.4.26): - resolution: {integrity: sha512-YHdEru4o3Rsbjmu6vHy4UKOXZD+Rn2zmkAmLRfPet6+Jz4Ojw8cbWxe1n42VaXQhD3CQUXXTooIy8OkVbUcL+w==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /@csstools/postcss-ic-unit@1.0.1(postcss@8.4.26): - resolution: {integrity: sha512-Ot1rcwRAaRHNKC9tAqoqNZhjdYBzKk1POgWfhN4uCOE47ebGcLRqXjKkApVDpjifL6u2/55ekkpnFcp+s/OZUw==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - '@csstools/postcss-progressive-custom-properties': 1.3.0(postcss@8.4.26) - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /@csstools/postcss-is-pseudo-class@2.0.7(postcss@8.4.26): - resolution: {integrity: sha512-7JPeVVZHd+jxYdULl87lvjgvWldYu+Bc62s9vD/ED6/QTGjy0jy0US/f6BG53sVMTBJ1lzKZFpYmofBN9eaRiA==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - '@csstools/selector-specificity': 2.2.0(postcss-selector-parser@6.0.13) - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /@csstools/postcss-nested-calc@1.0.0(postcss@8.4.26): - resolution: {integrity: sha512-JCsQsw1wjYwv1bJmgjKSoZNvf7R6+wuHDAbi5f/7MbFhl2d/+v+TvBTU4BJH3G1X1H87dHl0mh6TfYogbT/dJQ==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /@csstools/postcss-normalize-display-values@1.0.1(postcss@8.4.26): - resolution: {integrity: sha512-jcOanIbv55OFKQ3sYeFD/T0Ti7AMXc9nM1hZWu8m/2722gOTxFg7xYu4RDLJLeZmPUVQlGzo4jhzvTUq3x4ZUw==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /@csstools/postcss-oklab-function@1.1.1(postcss@8.4.26): - resolution: {integrity: sha512-nJpJgsdA3dA9y5pgyb/UfEzE7W5Ka7u0CX0/HIMVBNWzWemdcTH3XwANECU6anWv/ao4vVNLTMxhiPNZsTK6iA==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - '@csstools/postcss-progressive-custom-properties': 1.3.0(postcss@8.4.26) - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /@csstools/postcss-progressive-custom-properties@1.3.0(postcss@8.4.26): - resolution: {integrity: sha512-ASA9W1aIy5ygskZYuWams4BzafD12ULvSypmaLJT2jvQ8G0M3I8PRQhC0h7mG0Z3LI05+agZjqSR9+K9yaQQjA==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.3 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /@csstools/postcss-stepped-value-functions@1.0.1(postcss@8.4.26): - resolution: {integrity: sha512-dz0LNoo3ijpTOQqEJLY8nyaapl6umbmDcgj4AD0lgVQ572b2eqA1iGZYTTWhrcrHztWDDRAX2DGYyw2VBjvCvQ==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /@csstools/postcss-text-decoration-shorthand@1.0.0(postcss@8.4.26): - resolution: {integrity: sha512-c1XwKJ2eMIWrzQenN0XbcfzckOLLJiczqy+YvfGmzoVXd7pT9FfObiSEfzs84bpE/VqfpEuAZ9tCRbZkZxxbdw==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /@csstools/postcss-trigonometric-functions@1.0.2(postcss@8.4.26): - resolution: {integrity: sha512-woKaLO///4bb+zZC2s80l+7cm07M7268MsyG3M0ActXXEFi6SuhvriQYcb58iiKGbjwwIU7n45iRLEHypB47Og==} - engines: {node: ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /@csstools/postcss-unset-value@1.0.2(postcss@8.4.26): - resolution: {integrity: sha512-c8J4roPBILnelAsdLr4XOAR/GsTm0GJi4XpcfvoWk3U6KiTCqiFYc63KhRMQQX35jYMp4Ao8Ij9+IZRgMfJp1g==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - dev: false - - /@csstools/selector-specificity@2.2.0(postcss-selector-parser@6.0.13): - resolution: {integrity: sha512-+OJ9konv95ClSTOJCmMZqpd5+YGsB2S+x6w3E1oaM8UuR5j8nTNHYSz8c9BEPGDOCMQYIEEGlVPj/VY64iTbGw==} - engines: {node: ^14 || ^16 || >=18} - peerDependencies: - postcss-selector-parser: ^6.0.10 - dependencies: - postcss-selector-parser: 6.0.13 - dev: false - /@dabh/diagnostics@2.0.3: resolution: {integrity: sha512-hrlQOIi7hAfzsMqlGSFyVucrx38O+j6wiGOf//H2ecvIEqYN4ADBSS2iLMh5UFyDunCNniUIPk/q3riFv45xRA==} dependencies: @@ -2236,10 +582,12 @@ dependencies: eslint: 8.57.0 eslint-visitor-keys: 3.4.3 + dev: true /@eslint-community/regexpp@4.6.2: resolution: {integrity: sha512-pPTNuaAG3QMH+buKyBIGJs3g/S5y0caxw0ygM3YyE6yJFySwiGGSzA+mM3KJ8QQvzeLh3blwgSonkFjgQdxzMw==} engines: {node: ^12.0.0 || ^14.0.0 || >=16.0.0} + dev: true /@eslint/eslintrc@2.1.4: resolution: {integrity: sha512-269Z39MS6wVJtsoUl10L60WdkhJVdPG24Q4eZTH3nnF6lpvSShEK3wQjDX9JRWAUPvPh7COouPpU9IrqaZFvtQ==} @@ -2256,10 +604,12 @@ strip-json-comments: 3.1.1 transitivePeerDependencies: - supports-color + dev: true /@eslint/js@8.57.0: resolution: {integrity: sha512-Ys+3g2TaW7gADOJzPt83SJtCDhMjndcDMFVQ/Tj9iA1BfJzFKD9mAUXT3OenpuPHbI6P/myECxRJrofUsDx/5g==} engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + dev: true /@formatjs/ecma402-abstract@1.11.4: resolution: {integrity: sha512-EBikYFp2JCdIfGEb5G9dyCkTGDmC57KSHhRQOC3aYxoPWVZvfWCDjZwkGYHN7Lis/fmuWl906bnNTJifDQ3sXw==} @@ -2315,13 +665,16 @@ minimatch: 3.1.2 transitivePeerDependencies: - supports-color + dev: true /@humanwhocodes/module-importer@1.0.1: resolution: {integrity: sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==} engines: {node: '>=12.22'} + dev: true /@humanwhocodes/object-schema@2.0.2: resolution: {integrity: sha512-6EwiSjwWYP7pTckG6I5eyFANjPhmPjUX9JRLUSfNPC7FX7zK9gyZAfUEaECL6ALTpGX5AjnBq3C9XmVWPitNpw==} + dev: true /@img/sharp-darwin-arm64@0.33.2: resolution: {integrity: sha512-itHBs1rPmsmGF9p4qRe++CzCgd+kFYktnsoR1sbIAfsRMrJZau0Tt1AH9KVnufc2/tU02Gf6Ibujx+15qRE03w==} @@ -2523,101 +876,6 @@ wrap-ansi-cjs: /wrap-ansi@7.0.0 dev: true - /@istanbuljs/load-nyc-config@1.1.0: - resolution: {integrity: sha512-VjeHSlIzpv/NyD3N0YuHfXOPDIixcA1q2ZV98wsMqcYlPmv2n3Yb2lYP9XMElnaFVXg5A7YLTeLu6V84uQDjmQ==} - engines: {node: '>=8'} - dependencies: - camelcase: 5.3.1 - find-up: 4.1.0 - get-package-type: 0.1.0 - js-yaml: 3.14.1 - resolve-from: 5.0.0 - dev: false - - /@istanbuljs/schema@0.1.3: - resolution: {integrity: sha512-ZXRY4jNvVgSVQ8DL3LTcakaAtXwTVUxE81hslsyD2AtoXW/wVob10HkOJ1X/pAlcI7D+2YoZKg5do8G/w6RYgA==} - engines: {node: '>=8'} - dev: false - - /@jest/console@27.5.1: - resolution: {integrity: sha512-kZ/tNpS3NXn0mlXXXPNuDZnb4c0oZ20r4K5eemM2k30ZC3G0T02nXUvyhf5YdbXWHPEJLc9qGLxEZ216MdL+Zg==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/types': 27.5.1 - '@types/node': 20.11.27 - chalk: 4.1.2 - jest-message-util: 27.5.1 - jest-util: 27.5.1 - slash: 3.0.0 - dev: false - - /@jest/console@28.1.3: - resolution: {integrity: sha512-QPAkP5EwKdK/bxIr6C1I4Vs0rm2nHiANzj/Z5X2JQkrZo6IqvC4ldZ9K95tF0HdidhA8Bo6egxSzUFPYKcEXLw==} - engines: {node: ^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0} - dependencies: - '@jest/types': 28.1.3 - '@types/node': 20.11.27 - chalk: 4.1.2 - jest-message-util: 28.1.3 - jest-util: 28.1.3 - slash: 3.0.0 - dev: false - - /@jest/core@27.5.1: - resolution: {integrity: sha512-AK6/UTrvQD0Cd24NSqmIA6rKsu0tKIxfiCducZvqxYdmMisOYAsdItspT+fQDQYARPf8XgjAFZi0ogW2agH5nQ==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - peerDependencies: - node-notifier: ^8.0.1 || ^9.0.0 || ^10.0.0 - peerDependenciesMeta: - node-notifier: - optional: true - dependencies: - '@jest/console': 27.5.1 - '@jest/reporters': 27.5.1 - '@jest/test-result': 27.5.1 - '@jest/transform': 27.5.1 - '@jest/types': 27.5.1 - '@types/node': 20.11.27 - ansi-escapes: 4.3.2 - chalk: 4.1.2 - emittery: 0.8.1 - exit: 0.1.2 - graceful-fs: 4.2.11 - jest-changed-files: 27.5.1 - jest-config: 27.5.1 - jest-haste-map: 27.5.1 - jest-message-util: 27.5.1 - jest-regex-util: 27.5.1 - jest-resolve: 27.5.1 - jest-resolve-dependencies: 27.5.1 - jest-runner: 27.5.1 - jest-runtime: 27.5.1 - jest-snapshot: 27.5.1 - jest-util: 27.5.1 - jest-validate: 27.5.1 - jest-watcher: 27.5.1 - micromatch: 4.0.5 - rimraf: 3.0.2 - slash: 3.0.0 - strip-ansi: 6.0.1 - transitivePeerDependencies: - - bufferutil - - canvas - - supports-color - - ts-node - - utf-8-validate - dev: false - - /@jest/environment@27.5.1: - resolution: {integrity: sha512-/WQjhPJe3/ghaol/4Bq480JKXV/Rfw8nQdN7f41fM8VDHLcxKXou6QyXAh3EFr9/bVG3x74z1NWDkP87EiY8gA==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/fake-timers': 27.5.1 - '@jest/types': 27.5.1 - '@types/node': 20.11.27 - jest-mock: 27.5.1 - dev: false - /@jest/expect-utils@29.6.1: resolution: {integrity: sha512-o319vIf5pEMx0LmzSxxkYYxo4wrRLKHq9dP1yJU7FoPTB0LfAKSz8SWD6D/6U3v/O52t9cF5t+MeJiRsfk7zMw==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} @@ -2625,72 +883,6 @@ jest-get-type: 29.4.3 dev: true - /@jest/fake-timers@27.5.1: - resolution: {integrity: sha512-/aPowoolwa07k7/oM3aASneNeBGCmGQsc3ugN4u6s4C/+s5M64MFo/+djTdiwcbQlRfFElGuDXWzaWj6QgKObQ==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/types': 27.5.1 - '@sinonjs/fake-timers': 8.1.0 - '@types/node': 20.11.27 - jest-message-util: 27.5.1 - jest-mock: 27.5.1 - jest-util: 27.5.1 - dev: false - - /@jest/globals@27.5.1: - resolution: {integrity: sha512-ZEJNB41OBQQgGzgyInAv0UUfDDj3upmHydjieSxFvTRuZElrx7tXg/uVQ5hYVEwiXs3+aMsAeEc9X7xiSKCm4Q==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/environment': 27.5.1 - '@jest/types': 27.5.1 - expect: 27.5.1 - dev: false - - /@jest/reporters@27.5.1: - resolution: {integrity: sha512-cPXh9hWIlVJMQkVk84aIvXuBB4uQQmFqZiacloFuGiP3ah1sbCxCosidXFDfqG8+6fO1oR2dTJTlsOy4VFmUfw==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - peerDependencies: - node-notifier: ^8.0.1 || ^9.0.0 || ^10.0.0 - peerDependenciesMeta: - node-notifier: - optional: true - dependencies: - '@bcoe/v8-coverage': 0.2.3 - '@jest/console': 27.5.1 - '@jest/test-result': 27.5.1 - '@jest/transform': 27.5.1 - '@jest/types': 27.5.1 - '@types/node': 20.11.27 - chalk: 4.1.2 - collect-v8-coverage: 1.0.2 - exit: 0.1.2 - glob: 7.2.3 - graceful-fs: 4.2.11 - istanbul-lib-coverage: 3.2.0 - istanbul-lib-instrument: 5.2.1 - istanbul-lib-report: 3.0.0 - istanbul-lib-source-maps: 4.0.1 - istanbul-reports: 3.1.5 - jest-haste-map: 27.5.1 - jest-resolve: 27.5.1 - jest-util: 27.5.1 - jest-worker: 27.5.1 - slash: 3.0.0 - source-map: 0.6.1 - string-length: 4.0.2 - terminal-link: 2.1.1 - v8-to-istanbul: 8.1.1 - transitivePeerDependencies: - - supports-color - dev: false - - /@jest/schemas@28.1.3: - resolution: {integrity: sha512-/l/VWsdt/aBXgjshLWOFyFt3IVdYypu5y2Wn2rOO1un6nkqIn8SLXzgIMYXFyYsRWDyF5EthmKJMIdJvk08grg==} - engines: {node: ^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0} - dependencies: - '@sinclair/typebox': 0.24.51 - dev: false - /@jest/schemas@29.6.0: resolution: {integrity: sha512-rxLjXyJBTL4LQeJW3aKo0M/+GkCOXsO+8i9Iu7eDb6KwtP65ayoDsitrdPBtujxQ88k4wI2FNYfa6TOGwSn6cQ==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} @@ -2698,93 +890,6 @@ '@sinclair/typebox': 0.27.8 dev: true - /@jest/source-map@27.5.1: - resolution: {integrity: sha512-y9NIHUYF3PJRlHk98NdC/N1gl88BL08aQQgu4k4ZopQkCw9t9cV8mtl3TV8b/YCB8XaVTFrmUTAJvjsntDireg==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - callsites: 3.1.0 - graceful-fs: 4.2.11 - source-map: 0.6.1 - dev: false - - /@jest/test-result@27.5.1: - resolution: {integrity: sha512-EW35l2RYFUcUQxFJz5Cv5MTOxlJIQs4I7gxzi2zVU7PJhOwfYq1MdC5nhSmYjX1gmMmLPvB3sIaC+BkcHRBfag==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/console': 27.5.1 - '@jest/types': 27.5.1 - '@types/istanbul-lib-coverage': 2.0.4 - collect-v8-coverage: 1.0.2 - dev: false - - /@jest/test-result@28.1.3: - resolution: {integrity: sha512-kZAkxnSE+FqE8YjW8gNuoVkkC9I7S1qmenl8sGcDOLropASP+BkcGKwhXoyqQuGOGeYY0y/ixjrd/iERpEXHNg==} - engines: {node: ^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0} - dependencies: - '@jest/console': 28.1.3 - '@jest/types': 28.1.3 - '@types/istanbul-lib-coverage': 2.0.4 - collect-v8-coverage: 1.0.2 - dev: false - - /@jest/test-sequencer@27.5.1: - resolution: {integrity: sha512-LCheJF7WB2+9JuCS7VB/EmGIdQuhtqjRNI9A43idHv3E4KltCTsPsLxvdaubFHSYwY/fNjMWjl6vNRhDiN7vpQ==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/test-result': 27.5.1 - graceful-fs: 4.2.11 - jest-haste-map: 27.5.1 - jest-runtime: 27.5.1 - transitivePeerDependencies: - - supports-color - dev: false - - /@jest/transform@27.5.1: - resolution: {integrity: sha512-ipON6WtYgl/1329g5AIJVbUuEh0wZVbdpGwC99Jw4LwuoBNS95MVphU6zOeD9pDkon+LLbFL7lOQRapbB8SCHw==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@babel/core': 7.22.9 - '@jest/types': 27.5.1 - babel-plugin-istanbul: 6.1.1 - chalk: 4.1.2 - convert-source-map: 1.9.0 - fast-json-stable-stringify: 2.1.0 - graceful-fs: 4.2.11 - jest-haste-map: 27.5.1 - jest-regex-util: 27.5.1 - jest-util: 27.5.1 - micromatch: 4.0.5 - pirates: 4.0.6 - slash: 3.0.0 - source-map: 0.6.1 - write-file-atomic: 3.0.3 - transitivePeerDependencies: - - supports-color - dev: false - - /@jest/types@27.5.1: - resolution: {integrity: sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@types/istanbul-lib-coverage': 2.0.4 - '@types/istanbul-reports': 3.0.1 - '@types/node': 20.11.27 - '@types/yargs': 16.0.5 - chalk: 4.1.2 - dev: false - - /@jest/types@28.1.3: - resolution: {integrity: sha512-RyjiyMUZrKz/c+zlMFO1pm70DcIlST8AeWTkoUdZevew44wcNZQHsEVOiCVtgVnlFFD82FPaXycys58cf2muVQ==} - engines: {node: ^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0} - dependencies: - '@jest/schemas': 28.1.3 - '@types/istanbul-lib-coverage': 2.0.4 - '@types/istanbul-reports': 3.0.1 - '@types/node': 20.11.27 - '@types/yargs': 17.0.24 - chalk: 4.1.2 - dev: false - /@jest/types@29.6.1: resolution: {integrity: sha512-tPKQNMPuXgvdOn2/Lg9HNfUvjYVGolt04Hp03f5hAk878uwOLikN+JzeLY0HcVgKgFl9Hs3EIqpu3WX27XNhnw==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} @@ -2797,49 +902,10 @@ chalk: 4.1.2 dev: true - /@jridgewell/gen-mapping@0.3.3: - resolution: {integrity: sha512-HLhSWOLRi875zjjMG/r+Nv0oCW8umGb0BgEhyX3dDX3egwZtB8PqLnjz3yedt8R5StBrzcg4aBpnh8UA9D1BoQ==} - engines: {node: '>=6.0.0'} - dependencies: - '@jridgewell/set-array': 1.1.2 - '@jridgewell/sourcemap-codec': 1.4.15 - '@jridgewell/trace-mapping': 0.3.18 - - /@jridgewell/resolve-uri@3.1.0: - resolution: {integrity: sha512-F2msla3tad+Mfht5cJq7LSXcdudKTWCVYUgw6pLFOOHSTtZlj6SWNYAp+AhuqLmWdBO2X5hPrLcu8cVP8fy28w==} - engines: {node: '>=6.0.0'} - - /@jridgewell/set-array@1.1.2: - resolution: {integrity: sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==} - engines: {node: '>=6.0.0'} - - /@jridgewell/source-map@0.3.5: - resolution: {integrity: sha512-UTYAUj/wviwdsMfzoSJspJxbkH5o1snzwX0//0ENX1u/55kkZZkcTZP6u9bwKGkv+dkk9at4m1Cpt0uY80kcpQ==} - dependencies: - '@jridgewell/gen-mapping': 0.3.3 - '@jridgewell/trace-mapping': 0.3.18 - dev: false - - /@jridgewell/sourcemap-codec@1.4.14: - resolution: {integrity: sha512-XPSJHWmi394fuUuzDnGz1wiKqWfo1yXecHQMRf2l6hztTO+nPru658AyDngaBe7isIxEkRsPR3FZh+s7iVa4Uw==} - - /@jridgewell/sourcemap-codec@1.4.15: - resolution: {integrity: sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg==} - - /@jridgewell/trace-mapping@0.3.18: - resolution: {integrity: sha512-w+niJYzMHdd7USdiH2U6869nqhD2nbfZXND5Yp93qIbEmnDNk7PD48o+YchRVpzMU7M6jVCbenTR7PA1FLQ9pA==} - dependencies: - '@jridgewell/resolve-uri': 3.1.0 - '@jridgewell/sourcemap-codec': 1.4.14 - /@kurkle/color@0.3.2: resolution: {integrity: sha512-fuscdXJ9G1qb7W8VdHi+IwRqij3lBkosAm4ydQtEmbY58OzHXqQhvlxqEkoz0yssNVn38bcpRWgA9PP+OGoisw==} dev: false - /@leichtgewicht/ip-codec@2.0.4: - resolution: {integrity: sha512-Hcv+nVC0kZnQ3tD9GVu5xSMR4VVYOteQIr/hwFPVEvPdlXqgGEuRjiheChHgdM+JyqdgNcmzZOX/tnl0JOiI7A==} - dev: false - /@next/env@14.1.3: resolution: {integrity: sha512-VhgXTvrgeBRxNPjyfBsDIMvgsKDxjlpw4IAUsHCX8Gjl1vtHUYRT3+xfQ/wwvLPDd/6kqfLqk9Pt4+7gysuCKQ==} @@ -2921,27 +987,18 @@ requiresBuild: true optional: true - /@nicolo-ribaudo/eslint-scope-5-internals@5.1.1-v1: - resolution: {integrity: sha512-54/JRvkLIzzDWshCWfuhadfrfZVPiElY8Fcgmg1HroEly/EDSszzhBAsarCux+D/kOslTRquNzuyGSmUSTTHGg==} - dependencies: - eslint-scope: 5.1.1 - dev: false - - /@nicolo-ribaudo/semver-v6@6.3.3: - resolution: {integrity: sha512-3Yc1fUTs69MG/uZbJlLSI3JISMn2UV2rg+1D/vROUqZyh3l6iYHCs7GMp+M40ZD7yOdDbYjJcU1oTJhrc+dGKg==} - hasBin: true - dev: false - /@nodelib/fs.scandir@2.1.5: resolution: {integrity: sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==} engines: {node: '>= 8'} dependencies: '@nodelib/fs.stat': 2.0.5 run-parallel: 1.2.0 + dev: true /@nodelib/fs.stat@2.0.5: resolution: {integrity: sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==} engines: {node: '>= 8'} + dev: true /@nodelib/fs.walk@1.2.8: resolution: {integrity: sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==} @@ -2949,6 +1006,7 @@ dependencies: '@nodelib/fs.scandir': 2.1.5 fastq: 1.15.0 + dev: true /@pkgjs/parseargs@0.11.0: resolution: {integrity: sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg==} @@ -2957,92 +1015,10 @@ dev: true optional: true - /@pmmmwh/react-refresh-webpack-plugin@0.5.10(react-refresh@0.11.0)(webpack-dev-server@4.15.1)(webpack@5.88.1): - resolution: {integrity: sha512-j0Ya0hCFZPd4x40qLzbhGsh9TMtdb+CJQiso+WxLOPNasohq9cc5SNUcwsZaRH6++Xh91Xkm/xHCkuIiIu0LUA==} - engines: {node: '>= 10.13'} - peerDependencies: - '@types/webpack': 4.x || 5.x - react-refresh: '>=0.10.0 <1.0.0' - sockjs-client: ^1.4.0 - type-fest: '>=0.17.0 <4.0.0' - webpack: '>=4.43.0 <6.0.0' - webpack-dev-server: 3.x || 4.x - webpack-hot-middleware: 2.x - webpack-plugin-serve: 0.x || 1.x - peerDependenciesMeta: - '@types/webpack': - optional: true - sockjs-client: - optional: true - type-fest: - optional: true - webpack-dev-server: - optional: true - webpack-hot-middleware: - optional: true - webpack-plugin-serve: - optional: true - dependencies: - ansi-html-community: 0.0.8 - common-path-prefix: 3.0.0 - core-js-pure: 3.31.1 - error-stack-parser: 2.1.4 - find-up: 5.0.0 - html-entities: 2.4.0 - loader-utils: 2.0.4 - react-refresh: 0.11.0 - schema-utils: 3.3.0 - source-map: 0.7.4 - webpack: 5.88.1 - webpack-dev-server: 4.15.1(webpack@5.88.1) - dev: false - /@popperjs/core@2.11.8: resolution: {integrity: sha512-P1st0aksCrn9sGZhp8GMYwBnQsbvAWsZAX44oXNNvLHGqAOcoVxmjZiohstwQ7SqKnbR47akdNi+uleWD8+g6A==} dev: false - /@rollup/plugin-babel@5.3.1(@babel/core@7.22.9)(rollup@2.79.1): - resolution: {integrity: sha512-WFfdLWU/xVWKeRQnKmIAQULUI7Il0gZnBIH/ZFO069wYIfPu+8zrfp/KMW0atmELoRDq8FbiP3VCss9MhCut7Q==} - engines: {node: '>= 10.0.0'} - peerDependencies: - '@babel/core': ^7.0.0 - '@types/babel__core': ^7.1.9 - rollup: ^1.20.0||^2.0.0 - peerDependenciesMeta: - '@types/babel__core': - optional: true - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-module-imports': 7.22.5 - '@rollup/pluginutils': 3.1.0(rollup@2.79.1) - rollup: 2.79.1 - dev: false - - /@rollup/plugin-node-resolve@11.2.1(rollup@2.79.1): - resolution: {integrity: sha512-yc2n43jcqVyGE2sqV5/YCmocy9ArjVAP/BeXyTtADTBBX6V0e5UMqwO8CdQ0kzjb6zu5P1qMzsScCMRvE9OlVg==} - engines: {node: '>= 10.0.0'} - peerDependencies: - rollup: ^1.20.0||^2.0.0 - dependencies: - '@rollup/pluginutils': 3.1.0(rollup@2.79.1) - '@types/resolve': 1.17.1 - builtin-modules: 3.3.0 - deepmerge: 4.3.1 - is-module: 1.0.0 - resolve: 1.22.2 - rollup: 2.79.1 - dev: false - - /@rollup/plugin-replace@2.4.2(rollup@2.79.1): - resolution: {integrity: sha512-IGcu+cydlUMZ5En85jxHH4qj2hta/11BHq95iHEyb2sbgiN0eCdzvUcHw5gt9pBL5lTi4JDYJ1acCoMGpTvEZg==} - peerDependencies: - rollup: ^1.20.0 || ^2.0.0 - dependencies: - '@rollup/pluginutils': 3.1.0(rollup@2.79.1) - magic-string: 0.25.9 - rollup: 2.79.1 - dev: false - /@rollup/plugin-typescript@11.1.6(rollup@4.13.0)(tslib@2.6.2)(typescript@5.4.2): resolution: {integrity: sha512-R92yOmIACgYdJ7dJ97p4K69I8gg6IEHt8M7dUBxN3W6nrO8uUxX5ixl0yU/N3aZTi8WhPuICvOHXQvF6FaykAA==} engines: {node: '>=14.0.0'} @@ -3063,18 +1039,6 @@ typescript: 5.4.2 dev: true - /@rollup/pluginutils@3.1.0(rollup@2.79.1): - resolution: {integrity: sha512-GksZ6pr6TpIjHm8h9lSQ8pi8BE9VeubNT0OMJ3B5uZJ8pz73NPiqOtCog/x2/QzM1ENChPKxMDhiQuRHsqc+lg==} - engines: {node: '>= 8.0.0'} - peerDependencies: - rollup: ^1.20.0||^2.0.0 - dependencies: - '@types/estree': 0.0.39 - estree-walker: 1.0.1 - picomatch: 2.3.1 - rollup: 2.79.1 - dev: false - /@rollup/pluginutils@5.1.0(rollup@4.13.0): resolution: {integrity: sha512-XTIWOPPcpvyKI6L1NHo0lFlCyznUEyPmPY1mc3KpPVDYulHSTvyeLNVW00QTLIAFNhR3kYnJTQHeGqU4M3n09g==} engines: {node: '>=14.0.0'} @@ -3194,152 +1158,14 @@ dev: true optional: true - /@rushstack/eslint-patch@1.3.2: - resolution: {integrity: sha512-V+MvGwaHH03hYhY+k6Ef/xKd6RYlc4q8WBx+2ANmipHJcKuktNcI/NgEsJgdSUF6Lw32njT6OnrRsKYCdgHjYw==} - dev: false - /@rushstack/eslint-patch@1.7.2: resolution: {integrity: sha512-RbhOOTCNoCrbfkRyoXODZp75MlpiHMgbE5MEBZAnnnLyQNgrigEj4p0lzsMDyc1zVsJDLrivB58tgg3emX0eEA==} dev: true - /@sinclair/typebox@0.24.51: - resolution: {integrity: sha512-1P1OROm/rdubP5aFDSZQILU0vrLCJ4fvHt6EoqHEM+2D/G5MK3bIaymUKLit8Js9gbns5UyJnkP/TZROLw4tUA==} - dev: false - /@sinclair/typebox@0.27.8: resolution: {integrity: sha512-+Fj43pSMwJs4KRrH/938Uf+uAELIgVBmQzg/q1YG10djyfA3TnrU8N8XzqCh/okZdszqBQTZf96idMfE5lnwTA==} dev: true - /@sinonjs/commons@1.8.6: - resolution: {integrity: sha512-Ky+XkAkqPZSm3NLBeUng77EBQl3cmeJhITaGHdYH8kjVB+aun3S4XBRti2zt17mtt0mIUDiNxYeoJm6drVvBJQ==} - dependencies: - type-detect: 4.0.8 - dev: false - - /@sinonjs/fake-timers@8.1.0: - resolution: {integrity: sha512-OAPJUAtgeINhh/TAlUID4QTs53Njm7xzddaVlEs/SXwgtiD1tW22zAB/W1wdqfrpmikgaWQ9Fw6Ws+hsiRm5Vg==} - dependencies: - '@sinonjs/commons': 1.8.6 - dev: false - - /@surma/rollup-plugin-off-main-thread@2.2.3: - resolution: {integrity: sha512-lR8q/9W7hZpMWweNiAKU7NQerBnzQQLvi8qnTDU/fxItPhtZVMbPV3lbCwjhIlNBe9Bbr5V+KHshvWmVSG9cxQ==} - dependencies: - ejs: 3.1.9 - json5: 2.2.3 - magic-string: 0.25.9 - string.prototype.matchall: 4.0.8 - dev: false - - /@svgr/babel-plugin-add-jsx-attribute@5.4.0: - resolution: {integrity: sha512-ZFf2gs/8/6B8PnSofI0inYXr2SDNTDScPXhN7k5EqD4aZ3gi6u+rbmZHVB8IM3wDyx8ntKACZbtXSm7oZGRqVg==} - engines: {node: '>=10'} - dev: false - - /@svgr/babel-plugin-remove-jsx-attribute@5.4.0: - resolution: {integrity: sha512-yaS4o2PgUtwLFGTKbsiAy6D0o3ugcUhWK0Z45umJ66EPWunAz9fuFw2gJuje6wqQvQWOTJvIahUwndOXb7QCPg==} - engines: {node: '>=10'} - dev: false - - /@svgr/babel-plugin-remove-jsx-empty-expression@5.0.1: - resolution: {integrity: sha512-LA72+88A11ND/yFIMzyuLRSMJ+tRKeYKeQ+mR3DcAZ5I4h5CPWN9AHyUzJbWSYp/u2u0xhmgOe0+E41+GjEueA==} - engines: {node: '>=10'} - dev: false - - /@svgr/babel-plugin-replace-jsx-attribute-value@5.0.1: - resolution: {integrity: sha512-PoiE6ZD2Eiy5mK+fjHqwGOS+IXX0wq/YDtNyIgOrc6ejFnxN4b13pRpiIPbtPwHEc+NT2KCjteAcq33/F1Y9KQ==} - engines: {node: '>=10'} - dev: false - - /@svgr/babel-plugin-svg-dynamic-title@5.4.0: - resolution: {integrity: sha512-zSOZH8PdZOpuG1ZVx/cLVePB2ibo3WPpqo7gFIjLV9a0QsuQAzJiwwqmuEdTaW2pegyBE17Uu15mOgOcgabQZg==} - engines: {node: '>=10'} - dev: false - - /@svgr/babel-plugin-svg-em-dimensions@5.4.0: - resolution: {integrity: sha512-cPzDbDA5oT/sPXDCUYoVXEmm3VIoAWAPT6mSPTJNbQaBNUuEKVKyGH93oDY4e42PYHRW67N5alJx/eEol20abw==} - engines: {node: '>=10'} - dev: false - - /@svgr/babel-plugin-transform-react-native-svg@5.4.0: - resolution: {integrity: sha512-3eYP/SaopZ41GHwXma7Rmxcv9uRslRDTY1estspeB1w1ueZWd/tPlMfEOoccYpEMZU3jD4OU7YitnXcF5hLW2Q==} - engines: {node: '>=10'} - dev: false - - /@svgr/babel-plugin-transform-svg-component@5.5.0: - resolution: {integrity: sha512-q4jSH1UUvbrsOtlo/tKcgSeiCHRSBdXoIoqX1pgcKK/aU3JD27wmMKwGtpB8qRYUYoyXvfGxUVKchLuR5pB3rQ==} - engines: {node: '>=10'} - dev: false - - /@svgr/babel-preset@5.5.0: - resolution: {integrity: sha512-4FiXBjvQ+z2j7yASeGPEi8VD/5rrGQk4Xrq3EdJmoZgz/tpqChpo5hgXDvmEauwtvOc52q8ghhZK4Oy7qph4ig==} - engines: {node: '>=10'} - dependencies: - '@svgr/babel-plugin-add-jsx-attribute': 5.4.0 - '@svgr/babel-plugin-remove-jsx-attribute': 5.4.0 - '@svgr/babel-plugin-remove-jsx-empty-expression': 5.0.1 - '@svgr/babel-plugin-replace-jsx-attribute-value': 5.0.1 - '@svgr/babel-plugin-svg-dynamic-title': 5.4.0 - '@svgr/babel-plugin-svg-em-dimensions': 5.4.0 - '@svgr/babel-plugin-transform-react-native-svg': 5.4.0 - '@svgr/babel-plugin-transform-svg-component': 5.5.0 - dev: false - - /@svgr/core@5.5.0: - resolution: {integrity: sha512-q52VOcsJPvV3jO1wkPtzTuKlvX7Y3xIcWRpCMtBF3MrteZJtBfQw/+u0B1BHy5ColpQc1/YVTrPEtSYIMNZlrQ==} - engines: {node: '>=10'} - dependencies: - '@svgr/plugin-jsx': 5.5.0 - camelcase: 6.3.0 - cosmiconfig: 7.1.0 - transitivePeerDependencies: - - supports-color - dev: false - - /@svgr/hast-util-to-babel-ast@5.5.0: - resolution: {integrity: sha512-cAaR/CAiZRB8GP32N+1jocovUtvlj0+e65TB50/6Lcime+EA49m/8l+P2ko+XPJ4dw3xaPS3jOL4F2X4KWxoeQ==} - engines: {node: '>=10'} - dependencies: - '@babel/types': 7.22.5 - dev: false - - /@svgr/plugin-jsx@5.5.0: - resolution: {integrity: sha512-V/wVh33j12hGh05IDg8GpIUXbjAPnTdPTKuP4VNLggnwaHMPNQNae2pRnyTAILWCQdz5GyMqtO488g7CKM8CBA==} - engines: {node: '>=10'} - dependencies: - '@babel/core': 7.22.9 - '@svgr/babel-preset': 5.5.0 - '@svgr/hast-util-to-babel-ast': 5.5.0 - svg-parser: 2.0.4 - transitivePeerDependencies: - - supports-color - dev: false - - /@svgr/plugin-svgo@5.5.0: - resolution: {integrity: sha512-r5swKk46GuQl4RrVejVwpeeJaydoxkdwkM1mBKOgJLBUJPGaLci6ylg/IjhrRsREKDkr4kbMWdgOtbXEh0fyLQ==} - engines: {node: '>=10'} - dependencies: - cosmiconfig: 7.1.0 - deepmerge: 4.3.1 - svgo: 1.3.2 - dev: false - - /@svgr/webpack@5.5.0: - resolution: {integrity: sha512-DOBOK255wfQxguUta2INKkzPj6AIS6iafZYiYmHn6W3pHlycSRRlvWKCfLDG10fXfLWqE3DJHgRUOyJYmARa7g==} - engines: {node: '>=10'} - dependencies: - '@babel/core': 7.22.9 - '@babel/plugin-transform-react-constant-elements': 7.22.5(@babel/core@7.22.9) - '@babel/preset-env': 7.22.9(@babel/core@7.22.9) - '@babel/preset-react': 7.22.5(@babel/core@7.22.9) - '@svgr/core': 5.5.0 - '@svgr/plugin-jsx': 5.5.0 - '@svgr/plugin-svgo': 5.5.0 - loader-utils: 2.0.4 - transitivePeerDependencies: - - supports-color - dev: false - /@swc/helpers@0.5.2: resolution: {integrity: sha512-E4KcWTpoLHqwPHLxidpOqQbcrZVgi0rsmmZXUle1jXmJfuIf/UWpczUJ7MZZ5tlxytgJXyp0w4PGkkeLiuIdZw==} dependencies: @@ -3358,62 +1184,17 @@ react: 18.2.0 dev: false - /@tootallnate/once@1.1.2: - resolution: {integrity: sha512-RbzJvlNzmRq5c3O09UipeuXno4tA1FE6ikOjxZK0tuxVv3412l64l5t1W5pj4+rJq9vpkm/kwiR07aZXnsKPxw==} - engines: {node: '>= 6'} - dev: false - - /@trysound/sax@0.2.0: - resolution: {integrity: sha512-L7z9BgrNEcYyUYtF+HaEfiS5ebkh9jXqbszz7pC0hRBPaatV0XjSD3+eHrpqFemQfgwiFF0QPIarnIihIDn7OA==} - engines: {node: '>=10.13.0'} - dev: false - /@types/accepts@1.3.5: resolution: {integrity: sha512-jOdnI/3qTpHABjM5cx1Hc0sKsPoYCp+DP/GJRGtDlPd7fiV9oXGGIcjW/ZOxLIvjGz8MA+uMZI9metHlgqbgwQ==} dependencies: '@types/node': 20.11.27 - /@types/babel__core@7.20.1: - resolution: {integrity: sha512-aACu/U/omhdk15O4Nfb+fHgH/z3QsfQzpnvRZhYhThms83ZnAOZz7zZAWO7mn2yyNQaA4xTO8GLK3uqFU4bYYw==} - dependencies: - '@babel/parser': 7.22.7 - '@babel/types': 7.22.5 - '@types/babel__generator': 7.6.4 - '@types/babel__template': 7.4.1 - '@types/babel__traverse': 7.20.1 - dev: false - - /@types/babel__generator@7.6.4: - resolution: {integrity: sha512-tFkciB9j2K755yrTALxD44McOrk+gfpIpvC3sxHjRawj6PfnQxrse4Clq5y/Rq+G3mrBurMax/lG8Qn2t9mSsg==} - dependencies: - '@babel/types': 7.22.5 - dev: false - - /@types/babel__template@7.4.1: - resolution: {integrity: sha512-azBFKemX6kMg5Io+/rdGT0dkGreboUVR0Cdm3fz9QJWpaQGJRQXl7C+6hOTCZcMll7KFyEQpgbYI2lHdsS4U7g==} - dependencies: - '@babel/parser': 7.22.7 - '@babel/types': 7.22.5 - dev: false - - /@types/babel__traverse@7.20.1: - resolution: {integrity: sha512-MitHFXnhtgwsGZWtT68URpOvLN4EREih1u3QtQiN4VdAxWKRVvGCSvw/Qth0M0Qq3pJpnGOu5JaM/ydK7OGbqg==} - dependencies: - '@babel/types': 7.22.5 - dev: false - /@types/body-parser@1.19.2: resolution: {integrity: sha512-ALYone6pm6QmwZoAgeyNksccT9Q4AWZQ6PvfwR37GT6r6FWUPguq6sUmNGSMV2Wr761oQoBxwGGa6DR5o1DC9g==} dependencies: '@types/connect': 3.4.35 '@types/node': 20.11.27 - /@types/bonjour@3.5.10: - resolution: {integrity: sha512-p7ienRMiS41Nu2/igbJxxLDWrSZ0WxM8UQgCeO9KhoVF7cOVFkrKsiDr1EsJIla8vV3oEEjGcz11jc5yimhzZw==} - dependencies: - '@types/node': 20.11.27 - dev: false - /@types/co-body@6.1.0: resolution: {integrity: sha512-3e0q2jyDAnx/DSZi0z2H0yoZ2wt5yRDZ+P7ymcMObvq0ufWRT4tsajyO+Q1VwVWiv9PRR4W3YEjEzBjeZlhF+w==} dependencies: @@ -3421,13 +1202,6 @@ '@types/qs': 6.9.12 dev: false - /@types/connect-history-api-fallback@1.5.0: - resolution: {integrity: sha512-4x5FkPpLipqwthjPsF7ZRbOv3uoLUFkTA9G9v583qi4pACvq0uTELrB8OLUzPWUI4IJIyvM85vzkV1nyiI2Lig==} - dependencies: - '@types/express-serve-static-core': 4.17.35 - '@types/node': 20.11.27 - dev: false - /@types/connect@3.4.35: resolution: {integrity: sha512-cdeYyv4KWoEgpBISTxWvqYsVy444DOqehiF3fM3ne10AmJ62RSyNkUnxMJXHQWRQQX2eR94m5y1IZyDwBjV9FQ==} dependencies: @@ -3453,30 +1227,13 @@ dependencies: '@types/trusted-types': 2.0.3 - /@types/eslint-scope@3.7.4: - resolution: {integrity: sha512-9K4zoImiZc3HlIp6AVUDE4CWYx22a+lhSZMYNpbjW04+YF0KWj4pJXnEMjdnFTiQibFFmElcsasJXDbdI/EPhA==} - dependencies: - '@types/eslint': 8.44.0 - '@types/estree': 1.0.5 - dev: false - - /@types/eslint@8.44.0: - resolution: {integrity: sha512-gsF+c/0XOguWgaOgvFs+xnnRqt9GwgTvIks36WpE6ueeI4KCEHHd8K/CKHqhOqrJKsYH8m27kRzQEvWXAwXUTw==} - dependencies: - '@types/estree': 1.0.5 - '@types/json-schema': 7.0.12 - dev: false - - /@types/estree@0.0.39: - resolution: {integrity: sha512-EYNwp3bU+98cpU4lAWYYL7Zz+2gryWH1qbdDTidVd6hkiR6weksdbMadyXKXNPEkQFhXM+hVO9ZygomHXp+AIw==} - dev: false - /@types/estree@1.0.1: resolution: {integrity: sha512-LG4opVs2ANWZ1TJoKc937iMmNstM/d0ae1vNbnBvBhqCSezgVUOzcLCqbI5elV8Vy6WKwKjaqR+zO9VKirBBCA==} dev: true /@types/estree@1.0.5: resolution: {integrity: sha512-/kYRxGDLWzHOB7q+wtSUQlFrtcdUccpfy+X+9iMBpHK8QLLhx2wIPYuS5DYtR9Wa/YlZAbIovy7qVdB1Aq6Lyw==} + dev: true /@types/express-serve-static-core@4.17.35: resolution: {integrity: sha512-wALWQwrgiB2AWTT91CB62b6Yt0sNHpznUXeZEcnPU3DRdlDIz74x8Qg1UUYKSVFi+va5vKOLYRBI1bRKiLLKIg==} @@ -3504,44 +1261,27 @@ resolution: {integrity: sha512-Nmh0K3iWQJzniTuPRcJn5hxXkfB1T1pgB89SBig5PlJQU5yocazeu4jATJlaA0GYFKWMqDdvYemoSnF2pXgLVA==} dev: false - /@types/graceful-fs@4.1.6: - resolution: {integrity: sha512-Sig0SNORX9fdW+bQuTEovKj3uHcUL6LQKbCrrqb1X7J6/ReAbhCXRAhc+SMejhLELFj2QcyuxmUooZ4bt5ReSw==} - dependencies: - '@types/node': 20.11.27 - dev: false - - /@types/history@4.7.11: - resolution: {integrity: sha512-qjDJRrmvBMiTx+jyLxvLfJU7UznFuokDv4f3WRuriHKERccVpFU+8XMQUAbDzoiJCsmexxRExQeMwwCdamSKDA==} - dev: true - - /@types/html-minifier-terser@6.1.0: - resolution: {integrity: sha512-oh/6byDPnL1zeNXFrDXFLyZjkr1MsBG667IM792caf1L2UPOOMf65NFzjUH/ltyfwjAGfs1rsX1eftK0jC/KIg==} - dev: false - /@types/http-assert@1.5.3: resolution: {integrity: sha512-FyAOrDuQmBi8/or3ns4rwPno7/9tJTijVW6aQQjK02+kOQ8zmoNg2XJtAuQhvQcy1ASJq38wirX5//9J1EqoUA==} /@types/http-errors@2.0.1: resolution: {integrity: sha512-/K3ds8TRAfBvi5vfjuz8y6+GiAYBZ0x4tXv1Av6CWBWn0IlADc+ZX9pMq7oU0fNQPnBwIZl3rmeLp6SBApbxSQ==} - /@types/http-proxy@1.17.11: - resolution: {integrity: sha512-HC8G7c1WmaF2ekqpnFq626xd3Zz0uvaqFmBJNRZCGEZCXkvSdJoNFn/8Ygbd9fKNQj8UzLdCETaI0UWPAjK7IA==} - dependencies: - '@types/node': 20.11.27 - dev: false - /@types/istanbul-lib-coverage@2.0.4: resolution: {integrity: sha512-z/QT1XN4K4KYuslS23k62yDIDLwLFkzxOuMplDtObz0+y7VqJCaO2o+SPwHCvLFZh7xazvvoor2tA/hPz9ee7g==} + dev: true /@types/istanbul-lib-report@3.0.0: resolution: {integrity: sha512-plGgXAPfVKFoYfa9NpYDAkseG+g6Jr294RqeqcqDixSbU34MZVJRi/P+7Y8GDpzkEwLaGZZOpKIEmeVZNtKsrg==} dependencies: '@types/istanbul-lib-coverage': 2.0.4 + dev: true /@types/istanbul-reports@3.0.1: resolution: {integrity: sha512-c3mAZEuK0lvBp8tmuL74XRKn1+y2dcwOUpH7x4WrF6gk1GIgiluDRgMYQtw2OFcBvAJWlt6ASU3tSqxp0Uu0Aw==} dependencies: '@types/istanbul-lib-report': 3.0.0 + dev: true /@types/jest@29.5.12: resolution: {integrity: sha512-eDC8bTvT/QhYdxJAulQikueigY5AsdBRH2yDKW3yveW7svY3+DzN84/2NUgkw10RTiJbWqZrTtoGVdYlvFJdLw==} @@ -3550,12 +1290,9 @@ pretty-format: 29.6.1 dev: true - /@types/json-schema@7.0.12: - resolution: {integrity: sha512-Hr5Jfhc9eYOQNPYO5WLDq/n4jqijdHNlDXjuAQkkt+mWdQR+XJToOHrsD4cPaMXpn6KO7y2+wM8AZEs8VpBLVA==} - dev: false - /@types/json5@0.0.29: resolution: {integrity: sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ==} + dev: true /@types/keygrip@1.0.2: resolution: {integrity: sha512-GJhpTepz2udxGexqos8wgaBx4I/zWIDPh/KOGEwAqtuGDkOUJu5eFvwmdBX4AmB8Odsr+9pHCQqiAqDL/yKMKw==} @@ -3598,21 +1335,9 @@ dependencies: undici-types: 5.26.5 - /@types/parse-json@4.0.0: - resolution: {integrity: sha512-//oorEZjL6sbPcKUaCdIGlIUeH26mgzimjBB77G6XRgnDl/L5wOnpyBGRe/Mmf5CVW3PwEBE1NjiMZ/ssFh4wA==} - dev: false - - /@types/prettier@2.7.3: - resolution: {integrity: sha512-+68kP9yzs4LMp7VNh8gdzMSPZFL44MLGqiHWvttYJe+6qnuVr4Ek9wSBQoveqY/r+LwjCcU29kNVkidwim+kYA==} - dev: false - /@types/prop-types@15.7.5: resolution: {integrity: sha512-JCB8C6SnDoQf0cNycqd/35A7MjcnK+ZTqE7judS6o7utxUCg6imJg3QK2qzHKszlTjcj2cn+NwMB2i96ubpj7w==} - /@types/q@1.5.5: - resolution: {integrity: sha512-L28j2FcJfSZOnL1WBjDYp2vUHCeIFlyYI/53EwD/rKUBQ7MtUUfbQWiyKJGpcnv4/WgrhWsFKrcPstcAt/J0tQ==} - dev: false - /@types/qs@6.9.12: resolution: {integrity: sha512-bZcOkJ6uWrL0Qb2NAWKa7TBU+mJHPzhx9jjLL1KHF+XpzEcR7EXHvjbHlGtR/IsP1vyPrehuS6XqkmaePy//mg==} @@ -3625,21 +1350,6 @@ '@types/react': 18.2.65 dev: true - /@types/react-router-dom@5.3.3: - resolution: {integrity: sha512-kpqnYK4wcdm5UaWI3fLcELopqLrHgLqNsdpHauzlQktfkHL3npOSwtj1Uz9oKBAzs7lFtVkV8j83voAz2D8fhw==} - dependencies: - '@types/history': 4.7.11 - '@types/react': 18.2.65 - '@types/react-router': 5.1.20 - dev: true - - /@types/react-router@5.1.20: - resolution: {integrity: sha512-jGjmu/ZqS7FjSH6owMcD5qpq19+1RS9DeVRqfl1FeBMxTDQAGwlMWOcs52NDoXaNKyG3d1cYQFMs9rCrb88o9Q==} - dependencies: - '@types/history': 4.7.11 - '@types/react': 18.2.65 - dev: true - /@types/react@18.2.65: resolution: {integrity: sha512-98TsY0aW4jqx/3RqsUXwMDZSWR1Z4CUlJNue8ueS2/wcxZOsz4xmW1X8ieaWVRHcmmQM3R8xVA4XWB3dJnWwDQ==} dependencies: @@ -3647,35 +1357,15 @@ '@types/scheduler': 0.16.3 csstype: 3.1.2 - /@types/resolve@1.17.1: - resolution: {integrity: sha512-yy7HuzQhj0dhGpD8RLXSZWEkLsV9ibvxvi6EiJ3bkqLAO1RGo0WbkWQiwpRlSFymTJRz0d3k5LM3kkx8ArDbLw==} - dependencies: - '@types/node': 20.11.27 - dev: false - - /@types/retry@0.12.0: - resolution: {integrity: sha512-wWKOClTTiizcZhXnPY4wikVAwmdYHp8q6DmC+EJUzAMsycb7HB32Kh9RN4+0gExjmPmZSAQjgURXIGATPegAvA==} - dev: false - /@types/scheduler@0.16.3: resolution: {integrity: sha512-5cJ8CB4yAx7BH1oMvdU0Jh9lrEXyPkar6F9G/ERswkCuvP4KQZfZkSjcMbAICCpQTN4OuZn8tz0HiKv9TGZgrQ==} - /@types/semver@7.5.0: - resolution: {integrity: sha512-G8hZ6XJiHnuhQKR7ZmysCeJWE08o8T0AXtk5darsCaTVsYZhhgUrq53jizaR2FvsoeCwJhlmwTjkXBY5Pn/ZHw==} - dev: false - /@types/send@0.17.1: resolution: {integrity: sha512-Cwo8LE/0rnvX7kIIa3QHCkcuF21c05Ayb0ZfxPiv0W8VRiZiNW/WuRupHKpqqGVGf7SUA44QSOUKaEd9lIrd/Q==} dependencies: '@types/mime': 1.3.2 '@types/node': 20.11.27 - /@types/serve-index@1.9.1: - resolution: {integrity: sha512-d/Hs3nWDxNL2xAczmOVZNj92YZCS6RGxfBPjKzuu/XirCgXdpKEb88dYNbrYGint6IVWLNP+yonwVAuRC0T2Dg==} - dependencies: - '@types/express': 4.17.17 - dev: false - /@types/serve-static@1.15.2: resolution: {integrity: sha512-J2LqtvFYCzaj8pVYKw8klQXrLLk7TBZmQ4ShlcdkELFKGwGMfevMLneMMRkMgZxotOD9wg497LpC7O8PcvAmfw==} dependencies: @@ -3687,18 +1377,9 @@ resolution: {integrity: sha512-pTvD/0CIeqe4x23+YJWlX2gArHa8G0J0Oh6GKaVXV7TAeickpkkZiNOgFcFcmLQ5lB/K0qBJL1FtRYltBfbGCQ==} dev: true - /@types/sockjs@0.3.33: - resolution: {integrity: sha512-f0KEEe05NvUnat+boPTZ0dgaLZ4SfSouXUgv5noUiefG2ajgKjmETo9ZJyuqsl7dfl2aHlLJUiki6B4ZYldiiw==} - dependencies: - '@types/node': 20.11.27 - dev: false - - /@types/sprintf-js@1.1.4: - resolution: {integrity: sha512-aWK1reDYWxcjgcIIPmQi3u+OQDuYa9b+lr6eIsGWrekJ9vr1NSjr4Eab8oQ1iKuH1ltFHpXGyerAv1a3FMKxzQ==} - dev: true - /@types/stack-utils@2.0.1: resolution: {integrity: sha512-Hl219/BT5fLAaz6NDkSuhzasy49dwQS/DSdu4MdggFB8zcXv7vflBI3xp7FEmkmdDkBUI2bPUNeMttp2knYdxw==} + dev: true /@types/triple-beam@1.3.2: resolution: {integrity: sha512-txGIh+0eDFzKGC25zORnswy+br1Ha7hj5cMVwKIU7+s0U2AxxJru/jZSMU6OC9MJWP6+pc/hc6ZjyZShpsyY2g==} @@ -3711,66 +1392,15 @@ resolution: {integrity: sha512-jg+97EGIcY9AGHJJRaaPVgetKDsrTgbRjQ5Msgjh/DQKEFl0DtyRr/VCOyD1T2R1MNeWPK/u7JoGhlDZnKBAfA==} dev: true - /@types/ws@8.5.5: - resolution: {integrity: sha512-lwhs8hktwxSjf9UaZ9tG5M03PGogvFaH8gUgLNbN9HKIg0dvv6q+gkSuJ8HN4/VbyxkuLzCjlN7GquQ0gUJfIg==} - dependencies: - '@types/node': 20.11.27 - dev: false - /@types/yargs-parser@21.0.0: resolution: {integrity: sha512-iO9ZQHkZxHn4mSakYV0vFHAVDyEOIJQrV2uZ06HxEPcx+mt8swXoZHIbaaJ2crJYFfErySgktuTZ3BeLz+XmFA==} - - /@types/yargs@16.0.5: - resolution: {integrity: sha512-AxO/ADJOBFJScHbWhq2xAhlWP24rY4aCEG/NFaMvbT3X2MgRsLjhjQwsn0Zi5zn0LG9jUhCCZMeX9Dkuw6k+vQ==} - dependencies: - '@types/yargs-parser': 21.0.0 - dev: false + dev: true /@types/yargs@17.0.24: resolution: {integrity: sha512-6i0aC7jV6QzQB8ne1joVZ0eSFIstHsCrobmOtghM11yGlH0j43FKL2UhWdELkyps0zuf7qVTUVCCR+tgSlyLLw==} dependencies: '@types/yargs-parser': 21.0.0 - - /@typescript-eslint/eslint-plugin@5.62.0(@typescript-eslint/parser@5.62.0)(eslint@8.57.0)(typescript@5.4.2): - resolution: {integrity: sha512-TiZzBSJja/LbhNPvk6yc0JrX9XqhQ0hdh6M2svYfsHGejaKFIAGd9MQ+ERIMzLGlN/kZoYIgdxFV0PuljTKXag==} - engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} - peerDependencies: - '@typescript-eslint/parser': ^5.0.0 - eslint: ^6.0.0 || ^7.0.0 || ^8.0.0 - typescript: '*' - peerDependenciesMeta: - typescript: - optional: true - dependencies: - '@eslint-community/regexpp': 4.6.2 - '@typescript-eslint/parser': 5.62.0(eslint@8.57.0)(typescript@5.4.2) - '@typescript-eslint/scope-manager': 5.62.0 - '@typescript-eslint/type-utils': 5.62.0(eslint@8.57.0)(typescript@5.4.2) - '@typescript-eslint/utils': 5.62.0(eslint@8.57.0)(typescript@5.4.2) - debug: 4.3.4(supports-color@5.5.0) - eslint: 8.57.0 - graphemer: 1.4.0 - ignore: 5.2.4 - natural-compare-lite: 1.4.0 - semver: 7.5.4 - tsutils: 3.21.0(typescript@5.4.2) - typescript: 5.4.2 - transitivePeerDependencies: - - supports-color - dev: false - - /@typescript-eslint/experimental-utils@5.62.0(eslint@8.57.0)(typescript@5.4.2): - resolution: {integrity: sha512-RTXpeB3eMkpoclG3ZHft6vG/Z30azNHuqY6wKPBHlVMZFuEvrtlEDe8gMqDb+SO+9hjC/pLekeSCryf9vMZlCw==} - engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} - peerDependencies: - eslint: ^6.0.0 || ^7.0.0 || ^8.0.0 - dependencies: - '@typescript-eslint/utils': 5.62.0(eslint@8.57.0)(typescript@5.4.2) - eslint: 8.57.0 - transitivePeerDependencies: - - supports-color - - typescript - dev: false + dev: true /@typescript-eslint/parser@5.62.0(eslint@8.57.0)(typescript@5.4.2): resolution: {integrity: sha512-VlJEV0fOQ7BExOsHYAGrgbEiZoi8D+Bl2+f6V2RrXerRSylnp+ZBHmPvaIa8cz0Ajx7WO7Z5RqfgYg7ED1nRhA==} @@ -3790,6 +1420,7 @@ typescript: 5.4.2 transitivePeerDependencies: - supports-color + dev: true /@typescript-eslint/scope-manager@5.62.0: resolution: {integrity: sha512-VXuvVvZeQCQb5Zgf4HAxc04q5j+WrNAtNh9OwCsCgpKqESMTu3tF/jhZ3xG6T4NZwWl65Bg8KuS2uEvhSfLl0w==} @@ -3797,30 +1428,12 @@ dependencies: '@typescript-eslint/types': 5.62.0 '@typescript-eslint/visitor-keys': 5.62.0 - - /@typescript-eslint/type-utils@5.62.0(eslint@8.57.0)(typescript@5.4.2): - resolution: {integrity: sha512-xsSQreu+VnfbqQpW5vnCJdq1Z3Q0U31qiWmRhr98ONQmcp/yhiPJFPq8MXiJVLiksmOKSjIldZzkebzHuCGzew==} - engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} - peerDependencies: - eslint: '*' - typescript: '*' - peerDependenciesMeta: - typescript: - optional: true - dependencies: - '@typescript-eslint/typescript-estree': 5.62.0(typescript@5.4.2) - '@typescript-eslint/utils': 5.62.0(eslint@8.57.0)(typescript@5.4.2) - debug: 4.3.4(supports-color@5.5.0) - eslint: 8.57.0 - tsutils: 3.21.0(typescript@5.4.2) - typescript: 5.4.2 - transitivePeerDependencies: - - supports-color - dev: false + dev: true /@typescript-eslint/types@5.62.0: resolution: {integrity: sha512-87NVngcbVXUahrRTqIK27gD2t5Cu1yuCXxbLcFtCzZGlfyVWWh8mLHkoxzjsB6DDNnvdL+fW8MiwPEJyGJQDgQ==} engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} + dev: true /@typescript-eslint/typescript-estree@5.62.0(typescript@5.4.2): resolution: {integrity: sha512-CmcQ6uY7b9y694lKdRB8FEel7JbU/40iSAPomu++SjLMntB+2Leay2LO6i8VnJk58MtE9/nQSFIH6jpyRWyYzA==} @@ -3841,26 +1454,7 @@ typescript: 5.4.2 transitivePeerDependencies: - supports-color - - /@typescript-eslint/utils@5.62.0(eslint@8.57.0)(typescript@5.4.2): - resolution: {integrity: sha512-n8oxjeb5aIbPFEtmQxQYOLI0i9n5ySBEY/ZEHHZqKQSFnxio1rv6dthascc9dLuwrL0RC5mPCxB7vnAVGAYWAQ==} - engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} - peerDependencies: - eslint: ^6.0.0 || ^7.0.0 || ^8.0.0 - dependencies: - '@eslint-community/eslint-utils': 4.4.0(eslint@8.57.0) - '@types/json-schema': 7.0.12 - '@types/semver': 7.5.0 - '@typescript-eslint/scope-manager': 5.62.0 - '@typescript-eslint/types': 5.62.0 - '@typescript-eslint/typescript-estree': 5.62.0(typescript@5.4.2) - eslint: 8.57.0 - eslint-scope: 5.1.1 - semver: 7.5.4 - transitivePeerDependencies: - - supports-color - - typescript - dev: false + dev: true /@typescript-eslint/visitor-keys@5.62.0: resolution: {integrity: sha512-07ny+LHRzQXepkGg6w0mFY41fVUNBrL2Roj/++7V1txKugfjm/Ci/qSND03r2RhlJhJYMcTn9AhhSSqQp0Ysyw==} @@ -3868,127 +1462,11 @@ dependencies: '@typescript-eslint/types': 5.62.0 eslint-visitor-keys: 3.4.3 + dev: true /@ungap/structured-clone@1.2.0: resolution: {integrity: sha512-zuVdFrMJiuCDQUMCzQaD6KL28MjnqqN8XnAqiEq9PNm/hCPTSGfrXCOfwj1ow4LFb/tNymJPwsNbVePc1xFqrQ==} - - /@webassemblyjs/ast@1.11.6: - resolution: {integrity: sha512-IN1xI7PwOvLPgjcf180gC1bqn3q/QaOCwYUahIOhbYUu8KA/3tw2RT/T0Gidi1l7Hhj5D/INhJxiICObqpMu4Q==} - dependencies: - '@webassemblyjs/helper-numbers': 1.11.6 - '@webassemblyjs/helper-wasm-bytecode': 1.11.6 - dev: false - - /@webassemblyjs/floating-point-hex-parser@1.11.6: - resolution: {integrity: sha512-ejAj9hfRJ2XMsNHk/v6Fu2dGS+i4UaXBXGemOfQ/JfQ6mdQg/WXtwleQRLLS4OvfDhv8rYnVwH27YJLMyYsxhw==} - dev: false - - /@webassemblyjs/helper-api-error@1.11.6: - resolution: {integrity: sha512-o0YkoP4pVu4rN8aTJgAyj9hC2Sv5UlkzCHhxqWj8butaLvnpdc2jOwh4ewE6CX0txSfLn/UYaV/pheS2Txg//Q==} - dev: false - - /@webassemblyjs/helper-buffer@1.11.6: - resolution: {integrity: sha512-z3nFzdcp1mb8nEOFFk8DrYLpHvhKC3grJD2ardfKOzmbmJvEf/tPIqCY+sNcwZIY8ZD7IkB2l7/pqhUhqm7hLA==} - dev: false - - /@webassemblyjs/helper-numbers@1.11.6: - resolution: {integrity: sha512-vUIhZ8LZoIWHBohiEObxVm6hwP034jwmc9kuq5GdHZH0wiLVLIPcMCdpJzG4C11cHoQ25TFIQj9kaVADVX7N3g==} - dependencies: - '@webassemblyjs/floating-point-hex-parser': 1.11.6 - '@webassemblyjs/helper-api-error': 1.11.6 - '@xtuc/long': 4.2.2 - dev: false - - /@webassemblyjs/helper-wasm-bytecode@1.11.6: - resolution: {integrity: sha512-sFFHKwcmBprO9e7Icf0+gddyWYDViL8bpPjJJl0WHxCdETktXdmtWLGVzoHbqUcY4Be1LkNfwTmXOJUFZYSJdA==} - dev: false - - /@webassemblyjs/helper-wasm-section@1.11.6: - resolution: {integrity: sha512-LPpZbSOwTpEC2cgn4hTydySy1Ke+XEu+ETXuoyvuyezHO3Kjdu90KK95Sh9xTbmjrCsUwvWwCOQQNta37VrS9g==} - dependencies: - '@webassemblyjs/ast': 1.11.6 - '@webassemblyjs/helper-buffer': 1.11.6 - '@webassemblyjs/helper-wasm-bytecode': 1.11.6 - '@webassemblyjs/wasm-gen': 1.11.6 - dev: false - - /@webassemblyjs/ieee754@1.11.6: - resolution: {integrity: sha512-LM4p2csPNvbij6U1f19v6WR56QZ8JcHg3QIJTlSwzFcmx6WSORicYj6I63f9yU1kEUtrpG+kjkiIAkevHpDXrg==} - dependencies: - '@xtuc/ieee754': 1.2.0 - dev: false - - /@webassemblyjs/leb128@1.11.6: - resolution: {integrity: sha512-m7a0FhE67DQXgouf1tbN5XQcdWoNgaAuoULHIfGFIEVKA6tu/edls6XnIlkmS6FrXAquJRPni3ZZKjw6FSPjPQ==} - dependencies: - '@xtuc/long': 4.2.2 - dev: false - - /@webassemblyjs/utf8@1.11.6: - resolution: {integrity: sha512-vtXf2wTQ3+up9Zsg8sa2yWiQpzSsMyXj0qViVP6xKGCUT8p8YJ6HqI7l5eCnWx1T/FYdsv07HQs2wTFbbof/RA==} - dev: false - - /@webassemblyjs/wasm-edit@1.11.6: - resolution: {integrity: sha512-Ybn2I6fnfIGuCR+Faaz7YcvtBKxvoLV3Lebn1tM4o/IAJzmi9AWYIPWpyBfU8cC+JxAO57bk4+zdsTjJR+VTOw==} - dependencies: - '@webassemblyjs/ast': 1.11.6 - '@webassemblyjs/helper-buffer': 1.11.6 - '@webassemblyjs/helper-wasm-bytecode': 1.11.6 - '@webassemblyjs/helper-wasm-section': 1.11.6 - '@webassemblyjs/wasm-gen': 1.11.6 - '@webassemblyjs/wasm-opt': 1.11.6 - '@webassemblyjs/wasm-parser': 1.11.6 - '@webassemblyjs/wast-printer': 1.11.6 - dev: false - - /@webassemblyjs/wasm-gen@1.11.6: - resolution: {integrity: sha512-3XOqkZP/y6B4F0PBAXvI1/bky7GryoogUtfwExeP/v7Nzwo1QLcq5oQmpKlftZLbT+ERUOAZVQjuNVak6UXjPA==} - dependencies: - '@webassemblyjs/ast': 1.11.6 - '@webassemblyjs/helper-wasm-bytecode': 1.11.6 - '@webassemblyjs/ieee754': 1.11.6 - '@webassemblyjs/leb128': 1.11.6 - '@webassemblyjs/utf8': 1.11.6 - dev: false - - /@webassemblyjs/wasm-opt@1.11.6: - resolution: {integrity: sha512-cOrKuLRE7PCe6AsOVl7WasYf3wbSo4CeOk6PkrjS7g57MFfVUF9u6ysQBBODX0LdgSvQqRiGz3CXvIDKcPNy4g==} - dependencies: - '@webassemblyjs/ast': 1.11.6 - '@webassemblyjs/helper-buffer': 1.11.6 - '@webassemblyjs/wasm-gen': 1.11.6 - '@webassemblyjs/wasm-parser': 1.11.6 - dev: false - - /@webassemblyjs/wasm-parser@1.11.6: - resolution: {integrity: sha512-6ZwPeGzMJM3Dqp3hCsLgESxBGtT/OeCvCZ4TA1JUPYgmhAx38tTPR9JaKy0S5H3evQpO/h2uWs2j6Yc/fjkpTQ==} - dependencies: - '@webassemblyjs/ast': 1.11.6 - '@webassemblyjs/helper-api-error': 1.11.6 - '@webassemblyjs/helper-wasm-bytecode': 1.11.6 - '@webassemblyjs/ieee754': 1.11.6 - '@webassemblyjs/leb128': 1.11.6 - '@webassemblyjs/utf8': 1.11.6 - dev: false - - /@webassemblyjs/wast-printer@1.11.6: - resolution: {integrity: sha512-JM7AhRcE+yW2GWYaKeHL5vt4xqee5N2WcezptmgyhNS+ScggqcT1OtXykhAb13Sn5Yas0j2uv9tHgrjwvzAP4A==} - dependencies: - '@webassemblyjs/ast': 1.11.6 - '@xtuc/long': 4.2.2 - dev: false - - /@xtuc/ieee754@1.2.0: - resolution: {integrity: sha512-DX8nKgqcGwsc0eJSqYt5lwP4DH5FlHnmuWWBRy7X0NcaGR0ZtuyeESgMwTYVEtxmsNGY+qit4QYT/MIYTOTPeA==} - dev: false - - /@xtuc/long@4.2.2: - resolution: {integrity: sha512-NuHqBY1PB/D8xU6s/thBgOAiAP7HOYDQ32+BFZILJ8ivkUkAHQnWfn6WhL79Owj1qmUnoN/YPhktdIoucipkAQ==} - dev: false - - /abab@2.0.6: - resolution: {integrity: sha512-j2afSsaIENvHZN2B8GOpF566vZ5WVk5opAiMTvWgaQT8DkbOqsTfvNAvHoRGU2zzP8cPoqys+xHTRDWW8L+/BA==} - dev: false + dev: true /abbrev@1.1.1: resolution: {integrity: sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==} @@ -4002,65 +1480,19 @@ negotiator: 0.6.3 dev: false - /acorn-globals@6.0.0: - resolution: {integrity: sha512-ZQl7LOWaF5ePqqcX4hLuv/bLXYQNfNWw2c0/yX/TsPRKamzHcTGQnlCjHT3TsmkOUVEPS3crCxiPfdzE/Trlhg==} - dependencies: - acorn: 7.4.1 - acorn-walk: 7.2.0 - dev: false - - /acorn-import-assertions@1.9.0(acorn@8.10.0): - resolution: {integrity: sha512-cmMwop9x+8KFhxvKrKfPYmN6/pKTYYHBqLa0DfvVZcKMJWNyWLnaqND7dx/qn66R7ewM1UX5XMaDVP5wlVTaVA==} - peerDependencies: - acorn: ^8 - dependencies: - acorn: 8.10.0 - dev: false - /acorn-jsx@5.3.2(acorn@8.10.0): resolution: {integrity: sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==} peerDependencies: acorn: ^6.0.0 || ^7.0.0 || ^8.0.0 dependencies: acorn: 8.10.0 - - /acorn-walk@7.2.0: - resolution: {integrity: sha512-OPdCF6GsMIP+Az+aWfAAOEt2/+iVDKE7oy6lJ098aoe59oAmK76qV6Gw60SbZ8jHuG2wH058GF4pLFbYamYrVA==} - engines: {node: '>=0.4.0'} - dev: false - - /acorn@7.4.1: - resolution: {integrity: sha512-nQyp0o1/mNdbTO1PO6kHkwSrmgZ0MT/jCCpNiwbUjGoRN4dlBhqJtoQuCnEOKzgTVwg0ZWiCoQy6SxMebQVh8A==} - engines: {node: '>=0.4.0'} - hasBin: true - dev: false + dev: true /acorn@8.10.0: resolution: {integrity: sha512-F0SAmZ8iUtS//m8DmCTA0jlh6TDKkHQyK6xc6V4KDTyZKA9dnvX9/3sRTVQrWm79glUAZbnmmNcdYwUIHWVybw==} engines: {node: '>=0.4.0'} hasBin: true - - /address@1.2.2: - resolution: {integrity: sha512-4B/qKCfeE/ODUaAUpSwfzazo5x29WD4r3vXiWsB7I2mSDAihwEqKO+g8GELZUQSSAo5e1XTYh3ZVfLyxBc12nA==} - engines: {node: '>= 10.0.0'} - dev: false - - /adjust-sourcemap-loader@4.0.0: - resolution: {integrity: sha512-OXwN5b9pCUXNQHJpwwD2qP40byEmSgzj8B4ydSN0uMNYWiFmJ6x6KwUllMmfk8Rwu/HJDFR7U8ubsWBoN0Xp0A==} - engines: {node: '>=8.9'} - dependencies: - loader-utils: 2.0.4 - regex-parser: 2.2.11 - dev: false - - /agent-base@6.0.2: - resolution: {integrity: sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ==} - engines: {node: '>= 6.0.0'} - dependencies: - debug: 4.3.4(supports-color@5.5.0) - transitivePeerDependencies: - - supports-color - dev: false + dev: true /agent-base@7.1.0: resolution: {integrity: sha512-o/zjMZRhJxny7OyEF+Op8X+efiELC7k7yOjMzgfzVqOzXqkBkWI79YoTdOtsuWd5BWhAGAuOY/Xa6xpiaWXiNg==} @@ -4071,34 +1503,6 @@ - supports-color dev: false - /ajv-formats@2.1.1(ajv@8.12.0): - resolution: {integrity: sha512-Wx0Kx52hxE7C18hkMEggYlEifqWZtYaRgouJor+WMdPnQyEK13vgEWyVNup7SoeeoLMsr4kf5h6dOW11I15MUA==} - peerDependencies: - ajv: ^8.0.0 - peerDependenciesMeta: - ajv: - optional: true - dependencies: - ajv: 8.12.0 - dev: false - - /ajv-keywords@3.5.2(ajv@6.12.6): - resolution: {integrity: sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==} - peerDependencies: - ajv: ^6.9.1 - dependencies: - ajv: 6.12.6 - dev: false - - /ajv-keywords@5.1.0(ajv@8.12.0): - resolution: {integrity: sha512-YCS/JNFAUyr5vAuhk1DWm1CBxRHW9LbJ2ozWeemrIqpbsqKjHVxYPyi5GC0rjZIT5JxJ3virVTS8wk4i/Z+krw==} - peerDependencies: - ajv: ^8.8.2 - dependencies: - ajv: 8.12.0 - fast-deep-equal: 3.1.3 - dev: false - /ajv@6.12.6: resolution: {integrity: sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==} dependencies: @@ -4106,62 +1510,42 @@ fast-json-stable-stringify: 2.1.0 json-schema-traverse: 0.4.1 uri-js: 4.4.1 - - /ajv@8.12.0: - resolution: {integrity: sha512-sRu1kpcO9yLtYxBKvqfTeh9KzZEwO3STyX1HT+4CaDzC6HpTGYhIhPIzj9XuKU7KYDwnaeh5hcOwjy1QuJzBPA==} - dependencies: - fast-deep-equal: 3.1.3 - json-schema-traverse: 1.0.0 - require-from-string: 2.0.2 - uri-js: 4.4.1 - dev: false - - /ansi-escapes@4.3.2: - resolution: {integrity: sha512-gKXj5ALrKWQLsYG9jlTRmR/xKluxHV+Z9QEwNIgCfM1/uwPMCuzVVnh5mwTd+OuBZcwSIMbqssNWRm1lE51QaQ==} - engines: {node: '>=8'} - dependencies: - type-fest: 0.21.3 - dev: false - - /ansi-html-community@0.0.8: - resolution: {integrity: sha512-1APHAyr3+PCamwNw3bXCPp4HFLONZt/yIH0sZp0/469KWNTEy+qN5jQ3GVX6DMZ1UXAi34yVwtTeaG/HpBuuzw==} - engines: {'0': node >= 0.8.0} - hasBin: true - dev: false + dev: true /ansi-regex@5.0.1: resolution: {integrity: sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==} engines: {node: '>=8'} + dev: true /ansi-regex@6.0.1: resolution: {integrity: sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA==} engines: {node: '>=12'} + dev: true /ansi-styles@3.2.1: resolution: {integrity: sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==} engines: {node: '>=4'} dependencies: color-convert: 1.9.3 + dev: true /ansi-styles@4.3.0: resolution: {integrity: sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==} engines: {node: '>=8'} dependencies: color-convert: 2.0.1 + dev: true /ansi-styles@5.2.0: resolution: {integrity: sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==} engines: {node: '>=10'} + dev: true /ansi-styles@6.2.1: resolution: {integrity: sha512-bN798gFfQX+viw3R7yrGWRqnrN2oRkEkUjjl4JNn4E8GxxbjtG3FbrEIIY3l8/hrwUwIeCZvi4QuOTP4MErVug==} engines: {node: '>=12'} dev: true - /any-promise@1.3.0: - resolution: {integrity: sha512-7UvmKalWRt1wgjL1RrGxoSJW/0QZFIegpeGvZG9kjp8vrRu55XTHbwnqq2GpXm9uLbcuhxm3IqX9OB4MZR1b2A==} - dev: false - /anymatch@3.1.3: resolution: {integrity: sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw==} engines: {node: '>= 8'} @@ -4169,29 +1553,22 @@ normalize-path: 3.0.0 picomatch: 2.3.1 - /arg@5.0.2: - resolution: {integrity: sha512-PYjyFOLKQ9y57JvQ6QLo8dAgNqswh8M1RMJYdQduT6xbWSgK36P/Z/v+p888pM69jMMfS8Xd8F6I1kQ/I9HUGg==} - dev: false - - /argparse@1.0.10: - resolution: {integrity: sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==} - dependencies: - sprintf-js: 1.0.3 - dev: false - /argparse@2.0.1: resolution: {integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==} + dev: true /aria-query@5.3.0: resolution: {integrity: sha512-b0P0sZPKtyu8HkeRAfCq0IfURZK+SuwMjY1UXGBU27wpAiTwQAIlq56IbIO+ytk/JjS1fMR14ee5WBBfKi5J6A==} dependencies: dequal: 2.0.3 + dev: true /array-buffer-byte-length@1.0.0: resolution: {integrity: sha512-LPuwb2P+NrQw3XhxGc36+XSvuBPopovXYTR9Ew++Du9Yb/bx5AzBfrIsBoj0EZUifjQU+sHL21sseZ3jerWO/A==} dependencies: call-bind: 1.0.2 is-array-buffer: 3.0.2 + dev: true /array-buffer-byte-length@1.0.1: resolution: {integrity: sha512-ahC5W1xgou+KTXix4sAO8Ki12Q+jf4i0+tmk3sC+zgcynshkHxzpXdImBehiUYKKKDwvfFiJl1tZt6ewscS1Mg==} @@ -4199,14 +1576,7 @@ dependencies: call-bind: 1.0.7 is-array-buffer: 3.0.4 - - /array-flatten@1.1.1: - resolution: {integrity: sha512-PCVAQswWemu6UdxsDFFX/+gVeYqKAod3D3UVm91jHwynguOwAvYPhx8nNlM++NqRcK6CxxpUafjmhIdKiHibqg==} - dev: false - - /array-flatten@2.1.2: - resolution: {integrity: sha512-hNfzcOV8W4NdualtqBFPyVO+54DSJuZGY9qT4pRroB6S9e3iiido2ISIC5h9R2sPJ8H3FHCIiEnsv1lPXO3KtQ==} - dev: false + dev: true /array-includes@3.1.6: resolution: {integrity: sha512-sgTbLvL6cNnw24FnbaDyjmvddQ2ML8arZsgaJhoABMoplz/4QRhtrYS+alr1BUM1Bwp6dhx8vVCBSLG+StwOFw==} @@ -4217,6 +1587,7 @@ es-abstract: 1.22.1 get-intrinsic: 1.2.1 is-string: 1.0.7 + dev: true /array-includes@3.1.7: resolution: {integrity: sha512-dlcsNBIiWhPkHdOEEKnehA+RNUWDc4UqFtnIXU4uuYDPtA4LDkr7qip2p0VvFAEXNDr0yWZ9PJyIRiGjRLQzwQ==} @@ -4227,10 +1598,12 @@ es-abstract: 1.22.1 get-intrinsic: 1.2.4 is-string: 1.0.7 + dev: true /array-union@2.1.0: resolution: {integrity: sha512-HGyxoOTYUyCM6stUe6EJgnd4EoewAI7zMdfqO+kGjnlZmBDz/cR5pf8r/cR4Wq60sL/p0IkcjUEEPwS3GFrIyw==} engines: {node: '>=8'} + dev: true /array.prototype.filter@1.0.3: resolution: {integrity: sha512-VizNcj/RGJiUyQBgzwxzE5oHdeuXY5hSbbmKMlphj1cy1Vl7Pn2asCGbSrru6hSQjmCzqTBPVWAF/whmEOVHbw==} @@ -4241,6 +1614,7 @@ es-abstract: 1.22.5 es-array-method-boxes-properly: 1.0.0 is-string: 1.0.7 + dev: true /array.prototype.findlast@1.2.4: resolution: {integrity: sha512-BMtLxpV+8BD+6ZPFIWmnUBpQoy+A+ujcg4rhp2iwCRJYA7PEh2MS4NL3lz8EiDlLrJPp2hg9qWihr5pd//jcGw==} @@ -4262,6 +1636,7 @@ es-abstract: 1.22.5 es-errors: 1.3.0 es-shim-unscopables: 1.0.2 + dev: true /array.prototype.flat@1.3.1: resolution: {integrity: sha512-roTU0KWIOmJ4DRLmwKd19Otg0/mT3qPNt0Qb3GWW8iObuZXxrjB/pzn0R3hqpRSWg4HCwqx+0vwOnWnvlOyeIA==} @@ -4271,6 +1646,7 @@ define-properties: 1.2.0 es-abstract: 1.22.1 es-shim-unscopables: 1.0.0 + dev: true /array.prototype.flat@1.3.2: resolution: {integrity: sha512-djYB+Zx2vLewY8RWlNCUdHjDXs2XOgm602S9E7P/UpHgfeHL00cRiIF+IN/G/aUJ7kGPb6yO/ErDI5V2s8iycA==} @@ -4280,6 +1656,7 @@ define-properties: 1.2.0 es-abstract: 1.22.1 es-shim-unscopables: 1.0.0 + dev: true /array.prototype.flatmap@1.3.1: resolution: {integrity: sha512-8UGn9O1FDVvMNB0UlLv4voxRMze7+FpHyF5mSMRjWHUMlpoDViniy05870VlxhfgTnLbpuwTzvD76MTtWxB/mQ==} @@ -4289,6 +1666,7 @@ define-properties: 1.2.0 es-abstract: 1.22.1 es-shim-unscopables: 1.0.0 + dev: true /array.prototype.flatmap@1.3.2: resolution: {integrity: sha512-Ewyx0c9PmpcsByhSW4r+9zDU7sGjFc86qf/kKtuSCRdhfbk0SNLLkaT5qvcHnRGgc5NP/ly/y+qkXkqONX54CQ==} @@ -4298,17 +1676,7 @@ define-properties: 1.2.0 es-abstract: 1.22.1 es-shim-unscopables: 1.0.0 - - /array.prototype.reduce@1.0.5: - resolution: {integrity: sha512-kDdugMl7id9COE8R7MHF5jWk7Dqt/fs4Pv+JXoICnYwqpjjjbUurz6w5fT5IG6brLdJhv6/VoHB0H7oyIBXd+Q==} - engines: {node: '>= 0.4'} - dependencies: - call-bind: 1.0.2 - define-properties: 1.2.0 - es-abstract: 1.22.1 - es-array-method-boxes-properly: 1.0.0 - is-string: 1.0.7 - dev: false + dev: true /array.prototype.toreversed@1.1.2: resolution: {integrity: sha512-wwDCoT4Ck4Cz7sLtgUmzR5UV3YF5mFHUlbChCzZBQZ+0m2cl/DH3tKgvphv1nKgFsJ48oCSg6p91q2Vm0I/ZMA==} @@ -4319,16 +1687,6 @@ es-shim-unscopables: 1.0.0 dev: true - /array.prototype.tosorted@1.1.1: - resolution: {integrity: sha512-pZYPXPRl2PqWcsUs6LOMn+1f1532nEoPTYowBtqLwAW+W8vSVhkIGnmOX1t/UQjD6YGI0vcD2B1U7ZFGQH9jnQ==} - dependencies: - call-bind: 1.0.2 - define-properties: 1.2.0 - es-abstract: 1.22.1 - es-shim-unscopables: 1.0.0 - get-intrinsic: 1.2.1 - dev: false - /array.prototype.tosorted@1.1.3: resolution: {integrity: sha512-/DdH4TiTmOKzyQbp/eadcCVexiCb36xJg7HshYOYJnNZFDj33GEv0P7GxsynpShhq4OLYJzbGcBDkLsDt7MnNg==} dependencies: @@ -4349,6 +1707,7 @@ get-intrinsic: 1.2.1 is-array-buffer: 3.0.2 is-shared-array-buffer: 1.0.2 + dev: true /arraybuffer.prototype.slice@1.0.3: resolution: {integrity: sha512-bMxMKAjg13EBSVscxTaYA4mRc5t1UAXa2kXiGTNfZ079HIWXEkKmkgFrh/nJqamaLSrXO5H4WFFkPEaLJWbs3A==} @@ -4362,6 +1721,7 @@ get-intrinsic: 1.2.4 is-array-buffer: 3.0.4 is-shared-array-buffer: 1.0.3 + dev: true /asap@2.0.6: resolution: {integrity: sha512-BSHWgDSAiKs50o2Re8ppvp3seVHXSRM44cdSsT9FfNEUUZLOGWVCsiWaRPWM1Znn+mqZ1OfVZ3z3DWEzSp7hRA==} @@ -4369,6 +1729,7 @@ /ast-types-flow@0.0.7: resolution: {integrity: sha512-eBvWn1lvIApYMhzQMsu9ciLfkBY499mFZlNqG+/9WR7PVlroQw0vG30cOQQbaKz3sCEc44TAOu2ykzqXSNnwag==} + dev: true /async@3.2.4: resolution: {integrity: sha512-iAB+JbDEGXhyIUavoDl9WP/Jj106Kz9DEn1DPgYw5ruDn0e3Wgi3sKFm55sASdGBNOQB8F59d9qQ7deqrHA8wQ==} @@ -4384,40 +1745,22 @@ resolution: {integrity: sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==} dev: false - /at-least-node@1.0.0: - resolution: {integrity: sha512-+q/t7Ekv1EDY2l6Gda6LLiX14rU9TV20Wa3ofeQmwPFZbOMo9DXrLbOjFaaclkXKWidIaopwAObQDqwWtGUjqg==} - engines: {node: '>= 4.0.0'} - dev: false - - /autoprefixer@10.4.14(postcss@8.4.26): - resolution: {integrity: sha512-FQzyfOsTlwVzjHxKEqRIAdJx9niO6VCBCoEwax/VLSoQF29ggECcPuBqUMZ+u8jCZOPSy8b8/8KnuFbp0SaFZQ==} - engines: {node: ^10 || ^12 || >=14} - hasBin: true - peerDependencies: - postcss: ^8.1.0 - dependencies: - browserslist: 4.21.9 - caniuse-lite: 1.0.30001516 - fraction.js: 4.2.0 - normalize-range: 0.1.2 - picocolors: 1.0.0 - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - /available-typed-arrays@1.0.5: resolution: {integrity: sha512-DMD0KiN46eipeziST1LPP/STfDU0sufISXmjSgvVsoU2tqxctQeASejWcfNtxYKqETM1UxQ8sp2OrSBWpHY6sw==} engines: {node: '>= 0.4'} + dev: true /available-typed-arrays@1.0.7: resolution: {integrity: sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==} engines: {node: '>= 0.4'} dependencies: possible-typed-array-names: 1.0.0 + dev: true /axe-core@4.7.2: resolution: {integrity: sha512-zIURGIS1E1Q4pcrMjp+nnEh+16G56eG/MUllJH8yEvw7asDo7Ac9uhC9KIH5jzpITueEZolfYglnCGIuSBz39g==} engines: {node: '>=4'} + dev: true /axios@1.6.7: resolution: {integrity: sha512-/hDJGff6/c7u0hDkvkGxR/oy6CbCs8ziCsC7SqmhjfozqiJGc8Z11wrv9z9lYfY4K8l+H9TpjcMDX0xOZmx+RA==} @@ -4433,238 +1776,16 @@ resolution: {integrity: sha512-jsyHu61e6N4Vbz/v18DHwWYKK0bSWLqn47eeDSKPB7m8tqMHF9YJ+mhIk2lVteyZrY8tnSj/jHOv4YiTCuCJgg==} dependencies: dequal: 2.0.3 - - /babel-jest@27.5.1(@babel/core@7.22.9): - resolution: {integrity: sha512-cdQ5dXjGRd0IBRATiQ4mZGlGlRE8kJpjPOixdNRdT+m3UcNqmYWN6rK6nvtXYfY3D76cb8s/O1Ss8ea24PIwcg==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - peerDependencies: - '@babel/core': ^7.8.0 - dependencies: - '@babel/core': 7.22.9 - '@jest/transform': 27.5.1 - '@jest/types': 27.5.1 - '@types/babel__core': 7.20.1 - babel-plugin-istanbul: 6.1.1 - babel-preset-jest: 27.5.1(@babel/core@7.22.9) - chalk: 4.1.2 - graceful-fs: 4.2.11 - slash: 3.0.0 - transitivePeerDependencies: - - supports-color - dev: false - - /babel-loader@8.3.0(@babel/core@7.22.9)(webpack@5.88.1): - resolution: {integrity: sha512-H8SvsMF+m9t15HNLMipppzkC+Y2Yq+v3SonZyU70RBL/h1gxPkH08Ot8pEE9Z4Kd+czyWJClmFS8qzIP9OZ04Q==} - engines: {node: '>= 8.9'} - peerDependencies: - '@babel/core': ^7.0.0 - webpack: '>=2' - dependencies: - '@babel/core': 7.22.9 - find-cache-dir: 3.3.2 - loader-utils: 2.0.4 - make-dir: 3.1.0 - schema-utils: 2.7.1 - webpack: 5.88.1 - dev: false - - /babel-plugin-istanbul@6.1.1: - resolution: {integrity: sha512-Y1IQok9821cC9onCx5otgFfRm7Lm+I+wwxOx738M/WLPZ9Q42m4IG5W0FNX8WLL2gYMZo3JkuXIH2DOpWM+qwA==} - engines: {node: '>=8'} - dependencies: - '@babel/helper-plugin-utils': 7.22.5 - '@istanbuljs/load-nyc-config': 1.1.0 - '@istanbuljs/schema': 0.1.3 - istanbul-lib-instrument: 5.2.1 - test-exclude: 6.0.0 - transitivePeerDependencies: - - supports-color - dev: false - - /babel-plugin-jest-hoist@27.5.1: - resolution: {integrity: sha512-50wCwD5EMNW4aRpOwtqzyZHIewTYNxLA4nhB+09d8BIssfNfzBRhkBIHiaPv1Si226TQSvp8gxAJm2iY2qs2hQ==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@babel/template': 7.22.5 - '@babel/types': 7.22.5 - '@types/babel__core': 7.20.1 - '@types/babel__traverse': 7.20.1 - dev: false - - /babel-plugin-macros@3.1.0: - resolution: {integrity: sha512-Cg7TFGpIr01vOQNODXOOaGz2NpCU5gl8x1qJFbb6hbZxR7XrcE2vtbAsTAbJ7/xwJtUuJEw8K8Zr/AE0LHlesg==} - engines: {node: '>=10', npm: '>=6'} - dependencies: - '@babel/runtime': 7.23.9 - cosmiconfig: 7.1.0 - resolve: 1.22.2 - dev: false - - /babel-plugin-named-asset-import@0.3.8(@babel/core@7.22.9): - resolution: {integrity: sha512-WXiAc++qo7XcJ1ZnTYGtLxmBCVbddAml3CEXgWaBzNzLNoxtQ8AiGEFDMOhot9XjTCQbvP5E77Fj9Gk924f00Q==} - peerDependencies: - '@babel/core': ^7.1.0 - dependencies: - '@babel/core': 7.22.9 - dev: false - - /babel-plugin-polyfill-corejs2@0.4.4(@babel/core@7.22.9): - resolution: {integrity: sha512-9WeK9snM1BfxB38goUEv2FLnA6ja07UMfazFHzCXUb3NyDZAwfXvQiURQ6guTTMeHcOsdknULm1PDhs4uWtKyA==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/compat-data': 7.22.9 - '@babel/core': 7.22.9 - '@babel/helper-define-polyfill-provider': 0.4.1(@babel/core@7.22.9) - '@nicolo-ribaudo/semver-v6': 6.3.3 - transitivePeerDependencies: - - supports-color - dev: false - - /babel-plugin-polyfill-corejs3@0.8.2(@babel/core@7.22.9): - resolution: {integrity: sha512-Cid+Jv1BrY9ReW9lIfNlNpsI53N+FN7gE+f73zLAUbr9C52W4gKLWSByx47pfDJsEysojKArqOtOKZSVIIUTuQ==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-define-polyfill-provider': 0.4.1(@babel/core@7.22.9) - core-js-compat: 3.31.1 - transitivePeerDependencies: - - supports-color - dev: false - - /babel-plugin-polyfill-regenerator@0.5.1(@babel/core@7.22.9): - resolution: {integrity: sha512-L8OyySuI6OSQ5hFy9O+7zFjyr4WhAfRjLIOkhQGYl+emwJkd/S4XXT1JpfrgR1jrQ1NcGiOh+yAdGlF8pnC3Jw==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.22.9 - '@babel/helper-define-polyfill-provider': 0.4.1(@babel/core@7.22.9) - transitivePeerDependencies: - - supports-color - dev: false - - /babel-plugin-transform-react-remove-prop-types@0.4.24: - resolution: {integrity: sha512-eqj0hVcJUR57/Ug2zE1Yswsw4LhuqqHhD+8v120T1cl3kjg76QwtyBrdIk4WVwK+lAhBJVYCd/v+4nc4y+8JsA==} - dev: false - - /babel-preset-current-node-syntax@1.0.1(@babel/core@7.22.9): - resolution: {integrity: sha512-M7LQ0bxarkxQoN+vz5aJPsLBn77n8QgTFmo8WK0/44auK2xlCXrYcUxHFxgU7qW5Yzw/CjmLRK2uJzaCd7LvqQ==} - peerDependencies: - '@babel/core': ^7.0.0 - dependencies: - '@babel/core': 7.22.9 - '@babel/plugin-syntax-async-generators': 7.8.4(@babel/core@7.22.9) - '@babel/plugin-syntax-bigint': 7.8.3(@babel/core@7.22.9) - '@babel/plugin-syntax-class-properties': 7.12.13(@babel/core@7.22.9) - '@babel/plugin-syntax-import-meta': 7.10.4(@babel/core@7.22.9) - '@babel/plugin-syntax-json-strings': 7.8.3(@babel/core@7.22.9) - '@babel/plugin-syntax-logical-assignment-operators': 7.10.4(@babel/core@7.22.9) - '@babel/plugin-syntax-nullish-coalescing-operator': 7.8.3(@babel/core@7.22.9) - '@babel/plugin-syntax-numeric-separator': 7.10.4(@babel/core@7.22.9) - '@babel/plugin-syntax-object-rest-spread': 7.8.3(@babel/core@7.22.9) - '@babel/plugin-syntax-optional-catch-binding': 7.8.3(@babel/core@7.22.9) - '@babel/plugin-syntax-optional-chaining': 7.8.3(@babel/core@7.22.9) - '@babel/plugin-syntax-top-level-await': 7.14.5(@babel/core@7.22.9) - dev: false - - /babel-preset-jest@27.5.1(@babel/core@7.22.9): - resolution: {integrity: sha512-Nptf2FzlPCWYuJg41HBqXVT8ym6bXOevuCTbhxlUpjwtysGaIWFvDEjp4y+G7fl13FgOdjs7P/DmErqH7da0Ag==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - peerDependencies: - '@babel/core': ^7.0.0 - dependencies: - '@babel/core': 7.22.9 - babel-plugin-jest-hoist: 27.5.1 - babel-preset-current-node-syntax: 1.0.1(@babel/core@7.22.9) - dev: false - - /babel-preset-react-app@10.0.1: - resolution: {integrity: sha512-b0D9IZ1WhhCWkrTXyFuIIgqGzSkRIH5D5AmB0bXbzYAB1OBAwHcUeyWW2LorutLWF5btNo/N7r/cIdmvvKJlYg==} - dependencies: - '@babel/core': 7.22.9 - '@babel/plugin-proposal-class-properties': 7.18.6(@babel/core@7.22.9) - '@babel/plugin-proposal-decorators': 7.22.7(@babel/core@7.22.9) - '@babel/plugin-proposal-nullish-coalescing-operator': 7.18.6(@babel/core@7.22.9) - '@babel/plugin-proposal-numeric-separator': 7.18.6(@babel/core@7.22.9) - '@babel/plugin-proposal-optional-chaining': 7.21.0(@babel/core@7.22.9) - '@babel/plugin-proposal-private-methods': 7.18.6(@babel/core@7.22.9) - '@babel/plugin-proposal-private-property-in-object': 7.21.11(@babel/core@7.22.9) - '@babel/plugin-transform-flow-strip-types': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-react-display-name': 7.22.5(@babel/core@7.22.9) - '@babel/plugin-transform-runtime': 7.22.9(@babel/core@7.22.9) - '@babel/preset-env': 7.22.9(@babel/core@7.22.9) - '@babel/preset-react': 7.22.5(@babel/core@7.22.9) - '@babel/preset-typescript': 7.22.5(@babel/core@7.22.9) - '@babel/runtime': 7.23.9 - babel-plugin-macros: 3.1.0 - babel-plugin-transform-react-remove-prop-types: 0.4.24 - transitivePeerDependencies: - - supports-color - dev: false + dev: true /balanced-match@1.0.2: resolution: {integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==} - - /batch@0.6.1: - resolution: {integrity: sha512-x+VAiMRL6UPkx+kudNvxTl6hB2XNNCG2r+7wixVfIYwu/2HKRXimwQyaumLjMveWvT2Hkd/cAJw+QBMfJ/EKVw==} - dev: false - - /bfj@7.0.2: - resolution: {integrity: sha512-+e/UqUzwmzJamNF50tBV6tZPTORow7gQ96iFow+8b562OdMpEK0BcJEq2OSPEDmAbSMBQ7PKZ87ubFkgxpYWgw==} - engines: {node: '>= 8.0.0'} - dependencies: - bluebird: 3.7.2 - check-types: 11.2.2 - hoopy: 0.1.4 - tryer: 1.0.1 - dev: false - - /big.js@5.2.2: - resolution: {integrity: sha512-vyL2OymJxmarO8gxMr0mhChsO9QGwhynfuu4+MHTAW6czfq9humCB7rKpUjDd9YUiDPU4mzpyupFSvOClAwbmQ==} - dev: false + dev: true /binary-extensions@2.2.0: resolution: {integrity: sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA==} engines: {node: '>=8'} - /bluebird@3.7.2: - resolution: {integrity: sha512-XpNj6GDQzdfW+r2Wnn7xiSAd7TM3jzkxGXBGTtWKuSXv1xUV+azxAm8jdWZN06QTQk+2N2XB9jRDkvbmQmcRtg==} - dev: false - - /body-parser@1.20.1: - resolution: {integrity: sha512-jWi7abTbYwajOytWCQc37VulmWiRae5RyTpaCyDcS5/lMdtwSz5lOpDE67srw/HYe35f1z3fDQw+3txg7gNtWw==} - engines: {node: '>= 0.8', npm: 1.2.8000 || >= 1.4.16} - dependencies: - bytes: 3.1.2 - content-type: 1.0.5 - debug: 2.6.9 - depd: 2.0.0 - destroy: 1.2.0 - http-errors: 2.0.0 - iconv-lite: 0.4.24 - on-finished: 2.4.1 - qs: 6.11.0 - raw-body: 2.5.1 - type-is: 1.6.18 - unpipe: 1.0.0 - transitivePeerDependencies: - - supports-color - dev: false - - /bonjour-service@1.1.1: - resolution: {integrity: sha512-Z/5lQRMOG9k7W+FkeGTNjh7htqn/2LMnfOvBZ8pynNZCM9MwkQkI3zeI4oz09uWdcgmgHugVvBqxGg4VQJ5PCg==} - dependencies: - array-flatten: 2.1.2 - dns-equal: 1.0.0 - fast-deep-equal: 3.1.3 - multicast-dns: 7.2.5 - dev: false - - /boolbase@1.0.0: - resolution: {integrity: sha512-JZOSA7Mo9sNGB8+UjSgzdLtokWAky1zbztM3WRLCbZ70/3cTANmQmOdR7y2g+J0e2WXywy1yS468tY+IruqEww==} - dev: false - /bootstrap@5.3.3(@popperjs/core@2.11.8): resolution: {integrity: sha512-8HLCdWgyoMguSO9o+aH+iuZ+aht+mzW0u3HIMzVu7Srrpv7EBBxTnrFlSCskwdY1+EOFQSm7uMJhNQHkdPcmjg==} peerDependencies: @@ -4678,11 +1799,13 @@ dependencies: balanced-match: 1.0.2 concat-map: 0.0.1 + dev: true /brace-expansion@2.0.1: resolution: {integrity: sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==} dependencies: balanced-match: 1.0.2 + dev: true /braces@3.0.2: resolution: {integrity: sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==} @@ -4690,46 +1813,12 @@ dependencies: fill-range: 7.0.1 - /browser-process-hrtime@1.0.0: - resolution: {integrity: sha512-9o5UecI3GhkpM6DrXr69PblIuWxPKk9Y0jHBRhdocZ2y7YECBFCsHm79Pr3OyR2AvjhDkabFJaDJMYRazHgsow==} - dev: false - - /browserslist@4.21.9: - resolution: {integrity: sha512-M0MFoZzbUrRU4KNfCrDLnvyE7gub+peetoTid3TBIqtunaDJyXlwhakT+/VkvSXcfIzFfK/nkCs4nmyTmxdNSg==} - engines: {node: ^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7} - hasBin: true - dependencies: - caniuse-lite: 1.0.30001516 - electron-to-chromium: 1.4.461 - node-releases: 2.0.13 - update-browserslist-db: 1.0.11(browserslist@4.21.9) - - /bser@2.1.1: - resolution: {integrity: sha512-gQxTNE/GAfIIrmHLUE3oJyp5FO6HRBfhjnw4/wMmA63ZGDJnWBmgY/lyQBpnDUkGmAhbSe39tx2d/iTOAfglwQ==} - dependencies: - node-int64: 0.4.0 - dev: false - - /buffer-from@1.1.2: - resolution: {integrity: sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==} - dev: false - - /builtin-modules@3.3.0: - resolution: {integrity: sha512-zhaCDicdLuWN5UbN5IMnFqNMhNfo919sH85y2/ea+5Yg9TsTkeZxpL+JLbp6cgYFS4sRLp3YV4S6yDuqVWHYOw==} - engines: {node: '>=6'} - dev: false - /busboy@1.6.0: resolution: {integrity: sha512-8SFQbg/0hQ9xy3UNTB0YEnsNBbWfhf7RtnzpL7TkBiTBRfrQ9Fxcnz7VJsleJpyp6rVLvXiuORqjlHi5q+PYuA==} engines: {node: '>=10.16.0'} dependencies: streamsearch: 1.1.0 - /bytes@3.0.0: - resolution: {integrity: sha512-pMhOfFDPiv9t5jjIXkHosWmkSyQbvsgEVNkz0ERHbuLh2T/7j4Mqqpz523Fe8MVY89KC6Sh/QfS2sM+SjgFDcw==} - engines: {node: '>= 0.8'} - dev: false - /bytes@3.1.2: resolution: {integrity: sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==} engines: {node: '>= 0.8'} @@ -4748,6 +1837,7 @@ dependencies: function-bind: 1.1.1 get-intrinsic: 1.2.1 + dev: true /call-bind@1.0.7: resolution: {integrity: sha512-GHTSNSYICQ7scH7sZ+M2rFopRoLh8t2bLSW6BbgrtLsahOIB5iyAVJf9GjWK3cYTDaMj4XdBpM1cA6pIS0Kv2w==} @@ -4762,49 +1852,11 @@ /callsites@3.1.0: resolution: {integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==} engines: {node: '>=6'} - - /camel-case@4.1.2: - resolution: {integrity: sha512-gxGWBrTT1JuMx6R+o5PTXMmUnhnVzLQ9SNutD4YqKtI6ap897t3tKECYla6gCWEkplXnlNybEkZg9GEGxKFCgw==} - dependencies: - pascal-case: 3.1.2 - tslib: 2.6.2 - dev: false - - /camelcase-css@2.0.1: - resolution: {integrity: sha512-QOSvevhslijgYwRx6Rv7zKdMF8lbRmx+uQGx2+vDc+KI/eBnsy9kit5aj23AgGu3pa4t9AgwbnXWqS+iOY+2aA==} - engines: {node: '>= 6'} - dev: false - - /camelcase@5.3.1: - resolution: {integrity: sha512-L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg==} - engines: {node: '>=6'} - dev: false - - /camelcase@6.3.0: - resolution: {integrity: sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA==} - engines: {node: '>=10'} - dev: false - - /caniuse-api@3.0.0: - resolution: {integrity: sha512-bsTwuIg/BZZK/vreVTYYbSWoe2F+71P7K5QGEX+pT250DZbfU1MQ5prOKpPR+LL6uWKK3KMwMCAS74QB3Um1uw==} - dependencies: - browserslist: 4.21.9 - caniuse-lite: 1.0.30001597 - lodash.memoize: 4.1.2 - lodash.uniq: 4.5.0 - dev: false - - /caniuse-lite@1.0.30001516: - resolution: {integrity: sha512-Wmec9pCBY8CWbmI4HsjBeQLqDTqV91nFVR83DnZpYyRnPI1wePDsTg0bGLPC5VU/3OIZV1fmxEea1b+tFKe86g==} + dev: true /caniuse-lite@1.0.30001597: resolution: {integrity: sha512-7LjJvmQU6Sj7bL0j5b5WY/3n7utXUJvAe1lxhsHDbLmwX9mdL86Yjtr+5SRCyf8qME4M7pU2hswj0FpyBVCv9w==} - /case-sensitive-paths-webpack-plugin@2.4.0: - resolution: {integrity: sha512-roIFONhcxog0JSSWbvVAh3OocukmSgpqOH6YpMkCvav/ySIV3JKg4Dc8vYtQjYi/UxpNE36r/9v+VqTQqgkYmw==} - engines: {node: '>=4'} - dev: false - /chalk@2.4.2: resolution: {integrity: sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==} engines: {node: '>=4'} @@ -4812,6 +1864,7 @@ ansi-styles: 3.2.1 escape-string-regexp: 1.0.5 supports-color: 5.5.0 + dev: true /chalk@4.1.2: resolution: {integrity: sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==} @@ -4819,16 +1872,7 @@ dependencies: ansi-styles: 4.3.0 supports-color: 7.2.0 - - /char-regex@1.0.2: - resolution: {integrity: sha512-kWWXztvZ5SBQV+eRgKFeh8q5sLuZY2+8WUIzlxWVTg+oGwY14qylx1KbKzHd8P6ZYkAg0xyIDU9JMHhyJMZ1jw==} - engines: {node: '>=10'} - dev: false - - /char-regex@2.0.1: - resolution: {integrity: sha512-oSvEeo6ZUD7NepqAat3RqoucZ5SeqLJgOvVIwkafu6IP3V0pO38s/ypdVUmDDK6qIIHNlYHJAKX9E7R7HoKElw==} - engines: {node: '>=12.20'} - dev: false + dev: true /chart.js@4.4.2: resolution: {integrity: sha512-6GD7iKwFpP5kbSD4MeRRRlTnQvxfQREy36uEtm1hzHzcOqwWx0YEHuspuoNlslu+nciLIB7fjjsHkUv/FzFcOg==} @@ -4837,10 +1881,6 @@ '@kurkle/color': 0.3.2 dev: false - /check-types@11.2.2: - resolution: {integrity: sha512-HBiYvXvn9Z70Z88XKjz3AEKd4HJhBXsa3j7xFnITAzoS8+q6eIGi8qDB8FKPBAjtuxjI/zFpwuiCb8oDtKOYrA==} - dev: false - /chokidar@3.5.3: resolution: {integrity: sha512-Dr3sfKRP6oTcjf2JmUmFJfeVMvXBdegxB0iVQ5eb2V10uFJUCAS8OByZdVAyVb8xXNz3GjjTgj9kLWsZTqE6kw==} engines: {node: '>= 8.10.0'} @@ -4855,41 +1895,18 @@ optionalDependencies: fsevents: 2.3.3 - /chrome-trace-event@1.0.3: - resolution: {integrity: sha512-p3KULyQg4S7NIHixdwbGX+nFHkoBiA4YQmyWtjb8XngSKV124nJmRysgAeujbUVb15vh+RvFUfCPqU7rXk+hZg==} - engines: {node: '>=6.0'} - dev: false - /ci-info@3.8.0: resolution: {integrity: sha512-eXTggHWSooYhq49F2opQhuHWgzucfF2YgODK4e1566GQs5BIfP30B0oenwBJHfWxAs2fyPB1s7Mg949zLf61Yw==} engines: {node: '>=8'} - - /cjs-module-lexer@1.2.3: - resolution: {integrity: sha512-0TNiGstbQmCFwt4akjjBg5pLRTSyj/PkWQ1ZoO2zntmg9yLqSRxwEa4iCfQLGjqhiqBfOJa7W/E8wfGrTDmlZQ==} - dev: false + dev: true /classnames@2.3.2: resolution: {integrity: sha512-CSbhY4cFEJRe6/GQzIk5qXZ4Jeg5pcsP7b5peFSDpffpe1cqjASH/n9UTjBwOp6XpMSTwQ8Za2K5V02ueA7Tmw==} dev: false - /clean-css@5.3.2: - resolution: {integrity: sha512-JVJbM+f3d3Q704rF4bqQ5UUyTtuJ0JRKNbTKVEeujCCBoMdkEi+V+e8oktO9qGQNSvHrFTM6JZRXrUvGR1czww==} - engines: {node: '>= 10.0'} - dependencies: - source-map: 0.6.1 - dev: false - /client-only@0.0.1: resolution: {integrity: sha512-IV3Ou0jSMzZrd3pZ48nLkT9DA7Ag1pnPzaiQhpW7c3RbcqqzvzzVu+L8gfqMp/8IM2MQtSiqaCxrrcfu8I8rMA==} - /cliui@7.0.4: - resolution: {integrity: sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ==} - dependencies: - string-width: 4.2.3 - strip-ansi: 6.0.1 - wrap-ansi: 7.0.0 - dev: false - /cliui@8.0.1: resolution: {integrity: sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==} engines: {node: '>=12'} @@ -4923,19 +1940,6 @@ engines: {iojs: '>= 1.0.0', node: '>= 0.12.0'} dev: false - /coa@2.0.2: - resolution: {integrity: sha512-q5/jG+YQnSy4nRTV4F7lPepBJZ8qBNJJDBuJdoejDyLXgmL7IEo+Le2JDZudFTFt7mrCqIRaSjws4ygRCTCAXA==} - engines: {node: '>= 4.0'} - dependencies: - '@types/q': 1.5.5 - chalk: 2.4.2 - q: 1.5.1 - dev: false - - /collect-v8-coverage@1.0.2: - resolution: {integrity: sha512-lHl4d5/ONEbLlJvaJNtsF/Lz+WvB07u2ycqTYbdrq7UypDXailES4valYb2eWiJFxZlVmpGekfqoxQhzyFdT4Q==} - dev: false - /color-convert@1.9.3: resolution: {integrity: sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==} dependencies: @@ -4975,14 +1979,6 @@ color-string: 1.9.1 dev: false - /colord@2.9.3: - resolution: {integrity: sha512-jeC1axXpnb0/2nn/Y1LPuLdgXBLH7aDcHu4KEKfqw3CUhX7ZpfBSlPKyqXE6btIgEzfWtrX3/tyBCaCvXvMkOw==} - dev: false - - /colorette@2.0.20: - resolution: {integrity: sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==} - dev: false - /colorspace@1.1.4: resolution: {integrity: sha512-BgvKJiuVu1igBUF2kEjRCZXol6wiiGbY5ipL/oVPwm0BL9sIpMIzM8IK7vwuxIIzOXMV3Ey5w+vxhm0rR/TN8w==} dependencies: @@ -4997,62 +1993,9 @@ delayed-stream: 1.0.0 dev: false - /commander@2.20.3: - resolution: {integrity: sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==} - dev: false - - /commander@4.1.1: - resolution: {integrity: sha512-NOKm8xhkzAjzFx8B2v5OAHT+u5pRQc2UCa2Vq9jYL/31o2wi9mxBA7LIFs3sV5VSC49z6pEhfbMULvShKj26WA==} - engines: {node: '>= 6'} - dev: false - - /commander@7.2.0: - resolution: {integrity: sha512-QrWXB+ZQSVPmIWIhtEO9H+gwHaMGYiF5ChvoJ+K9ZGHG/sVsa6yiesAD1GC/x46sET00Xlwo1u49RVVVzvcSkw==} - engines: {node: '>= 10'} - dev: false - - /commander@8.3.0: - resolution: {integrity: sha512-OkTL9umf+He2DZkUq8f8J9of7yL6RJKI24dVITBmNfZBmri9zYZQrKkuXiKhyfPSu8tUhnVBB1iKXevvnlR4Ww==} - engines: {node: '>= 12'} - dev: false - - /common-path-prefix@3.0.0: - resolution: {integrity: sha512-QE33hToZseCH3jS0qN96O/bSh3kaw/h+Tq7ngyY9eWDUnTlTNUyqfqvCXioLe5Na5jFsL78ra/wuBU4iuEgd4w==} - dev: false - - /common-tags@1.8.2: - resolution: {integrity: sha512-gk/Z852D2Wtb//0I+kRFNKKE9dIIVirjoqPoA1wJU+XePVXZfGeBpk45+A1rKO4Q43prqWBNY/MiIeRLbPWUaA==} - engines: {node: '>=4.0.0'} - dev: false - - /commondir@1.0.1: - resolution: {integrity: sha512-W9pAhw0ja1Edb5GVdIF1mjZw/ASI0AlShXM83UUGe2DVr5TdAPEA1OA8m/g8zWp9x6On7gqufY+FatDbC3MDQg==} - dev: false - - /compressible@2.0.18: - resolution: {integrity: sha512-AF3r7P5dWxL8MxyITRMlORQNaOA2IkAFaTr4k7BUumjPtRpGDTZpl0Pb1XCO6JeDCBdp126Cgs9sMxqSjgYyRg==} - engines: {node: '>= 0.6'} - dependencies: - mime-db: 1.52.0 - dev: false - - /compression@1.7.4: - resolution: {integrity: sha512-jaSIDzP9pZVS4ZfQ+TzvtiWhdpFhE2RDHz8QJkpX9SIpLq88VueF5jJw6t+6CUQcAoA6t+x89MLrWAqpfDE8iQ==} - engines: {node: '>= 0.8.0'} - dependencies: - accepts: 1.3.8 - bytes: 3.0.0 - compressible: 2.0.18 - debug: 2.6.9 - on-headers: 1.0.2 - safe-buffer: 5.1.2 - vary: 1.1.2 - transitivePeerDependencies: - - supports-color - dev: false - /concat-map@0.0.1: resolution: {integrity: sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==} + dev: true /concurrently@8.2.2: resolution: {integrity: sha512-1dP4gpXFhei8IOtlXRE/T/4H88ElHgTiUzh71YUmtjTEHMSRS2Z/fgOxHSxxusGHogsRfxNq1vyAwxSC+EVyDg==} @@ -5070,15 +2013,6 @@ yargs: 17.7.2 dev: true - /confusing-browser-globals@1.0.11: - resolution: {integrity: sha512-JsPKdmh8ZkmnHxDk55FZ1TqVLvEQTvoByJZRN9jzI0UjxK/QgAmsphz7PGtqgPieQZ/CQcHWXCR7ATDNhGe+YA==} - dev: false - - /connect-history-api-fallback@2.0.0: - resolution: {integrity: sha512-U73+6lQFmfiNPrYbXqr6kZ1i1wiRqXnp2nhMsINseWXO8lDau0LGEffJ8kQi4EjLZympVgRdvqjAgiZ1tgzDDA==} - engines: {node: '>=0.8'} - dev: false - /content-disposition@0.5.4: resolution: {integrity: sha512-FveZTNuGw04cxlAiWbzi6zTAL/lhehaWbTtgluJh4/E95DqMwTmha3KZN1aAWA8cFIhHzMZUvLevkw5Rqk+tSQ==} engines: {node: '>= 0.6'} @@ -5091,18 +2025,6 @@ engines: {node: '>= 0.6'} dev: false - /convert-source-map@1.9.0: - resolution: {integrity: sha512-ASFBup0Mz1uyiIjANan1jzLQami9z1PoYSZCiiYW2FczPbenXc45FZdBZLzOT+r6+iciuEModtmCti+hjaAk0A==} - - /cookie-signature@1.0.6: - resolution: {integrity: sha512-QADzlaHc8icV8I7vbaJXJwod9HWYp8uCqf1xa4OfNu1T7JVxQIrUgOWtHdNDtPiywmFbiS12VjotIXLrKM3orQ==} - dev: false - - /cookie@0.5.0: - resolution: {integrity: sha512-YZ3GUyn/o8gfKJlnlX7g7xq4gyO6OSuhGPKaaGssGB2qgDUS0gPgtTvoyZLTt9Ab6dC4hfc9dV5arkvc/OCmrw==} - engines: {node: '>= 0.6'} - dev: false - /cookies@0.9.0: resolution: {integrity: sha512-mtyMqy14RsH7+IRJglGcKtRLOq0SRt0DdXVrLgc+v1e/o0TNJUpdElhgr3AAi638LO0xZwEPcRRkJ3afxvGhUw==} engines: {node: '>= 0.8'} @@ -5111,48 +2033,6 @@ keygrip: 1.1.0 dev: false - /core-js-compat@3.31.1: - resolution: {integrity: sha512-wIDWd2s5/5aJSdpOJHfSibxNODxoGoWOBHt8JSPB41NOE94M7kuTPZCYLOlTtuoXTsBPKobpJ6T+y0SSy5L9SA==} - dependencies: - browserslist: 4.21.9 - dev: false - - /core-js-pure@3.31.1: - resolution: {integrity: sha512-w+C62kvWti0EPs4KPMCMVv9DriHSXfQOCQ94bGGBiEW5rrbtt/Rz8n5Krhfw9cpFyzXBjf3DB3QnPdEzGDY4Fw==} - requiresBuild: true - dev: false - - /core-js@3.31.1: - resolution: {integrity: sha512-2sKLtfq1eFST7l7v62zaqXacPc7uG8ZAya8ogijLhTtaKNcpzpB4TMoTw2Si+8GYKRwFPMMtUT0263QFWFfqyQ==} - requiresBuild: true - dev: false - - /core-util-is@1.0.3: - resolution: {integrity: sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==} - dev: false - - /cosmiconfig@6.0.0: - resolution: {integrity: sha512-xb3ZL6+L8b9JLLCx3ZdoZy4+2ECphCMo2PwqgP1tlfVq6M6YReyzBJtvWWtbDSpNr9hn96pkCiZqUcFEc+54Qg==} - engines: {node: '>=8'} - dependencies: - '@types/parse-json': 4.0.0 - import-fresh: 3.3.0 - parse-json: 5.2.0 - path-type: 4.0.0 - yaml: 1.10.2 - dev: false - - /cosmiconfig@7.1.0: - resolution: {integrity: sha512-AdmX6xUzdNASswsFtmwSt7Vj8po9IuqXm0UXz7QKPuEUmPB4XyjGfaAr2PSuELMwkRMVH1EpIkX5bTZGRB3eCA==} - engines: {node: '>=10'} - dependencies: - '@types/parse-json': 4.0.0 - import-fresh: 3.3.0 - parse-json: 5.2.0 - path-type: 4.0.0 - yaml: 1.10.2 - dev: false - /cross-spawn@7.0.3: resolution: {integrity: sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w==} engines: {node: '>= 8'} @@ -5160,242 +2040,12 @@ path-key: 3.1.1 shebang-command: 2.0.0 which: 2.0.2 + dev: true /crypto-js@4.2.0: resolution: {integrity: sha512-KALDyEYgpY+Rlob/iriUtjV6d5Eq+Y191A5g4UqLAi8CyGP9N1+FdVbkc1SxKc2r4YAYqG8JzO2KGL+AizD70Q==} dev: false - /crypto-random-string@2.0.0: - resolution: {integrity: sha512-v1plID3y9r/lPhviJ1wrXpLeyUIGAZ2SHNYTEapm7/8A9nLPoyvVp3RK/EPFqn5kEznyWgYZNsRtYYIWbuG8KA==} - engines: {node: '>=8'} - dev: false - - /css-blank-pseudo@3.0.3(postcss@8.4.26): - resolution: {integrity: sha512-VS90XWtsHGqoM0t4KpH053c4ehxZ2E6HtGI7x68YFV0pTo/QmkV/YFA+NnlvK8guxZVNWGQhVNJGC39Q8XF4OQ==} - engines: {node: ^12 || ^14 || >=16} - hasBin: true - peerDependencies: - postcss: ^8.4 - dependencies: - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /css-declaration-sorter@6.4.1(postcss@8.4.26): - resolution: {integrity: sha512-rtdthzxKuyq6IzqX6jEcIzQF/YqccluefyCYheovBOLhFT/drQA9zj/UbRAa9J7C0o6EG6u3E6g+vKkay7/k3g==} - engines: {node: ^10 || ^12 || >=14} - peerDependencies: - postcss: ^8.0.9 - dependencies: - postcss: 8.4.26 - dev: false - - /css-has-pseudo@3.0.4(postcss@8.4.26): - resolution: {integrity: sha512-Vse0xpR1K9MNlp2j5w1pgWIJtm1a8qS0JwS9goFYcImjlHEmywP9VUF05aGBXzGpDJF86QXk4L0ypBmwPhGArw==} - engines: {node: ^12 || ^14 || >=16} - hasBin: true - peerDependencies: - postcss: ^8.4 - dependencies: - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /css-loader@6.8.1(webpack@5.88.1): - resolution: {integrity: sha512-xDAXtEVGlD0gJ07iclwWVkLoZOpEvAWaSyf6W18S2pOC//K8+qUDIx8IIT3D+HjnmkJPQeesOPv5aiUaJsCM2g==} - engines: {node: '>= 12.13.0'} - peerDependencies: - webpack: ^5.0.0 - dependencies: - icss-utils: 5.1.0(postcss@8.4.26) - postcss: 8.4.26 - postcss-modules-extract-imports: 3.0.0(postcss@8.4.26) - postcss-modules-local-by-default: 4.0.3(postcss@8.4.26) - postcss-modules-scope: 3.0.0(postcss@8.4.26) - postcss-modules-values: 4.0.0(postcss@8.4.26) - postcss-value-parser: 4.2.0 - semver: 7.5.4 - webpack: 5.88.1 - dev: false - - /css-minimizer-webpack-plugin@3.4.1(webpack@5.88.1): - resolution: {integrity: sha512-1u6D71zeIfgngN2XNRJefc/hY7Ybsxd74Jm4qngIXyUEk7fss3VUzuHxLAq/R8NAba4QU9OUSaMZlbpRc7bM4Q==} - engines: {node: '>= 12.13.0'} - peerDependencies: - '@parcel/css': '*' - clean-css: '*' - csso: '*' - esbuild: '*' - webpack: ^5.0.0 - peerDependenciesMeta: - '@parcel/css': - optional: true - clean-css: - optional: true - csso: - optional: true - esbuild: - optional: true - dependencies: - cssnano: 5.1.15(postcss@8.4.26) - jest-worker: 27.5.1 - postcss: 8.4.26 - schema-utils: 4.2.0 - serialize-javascript: 6.0.1 - source-map: 0.6.1 - webpack: 5.88.1 - dev: false - - /css-prefers-color-scheme@6.0.3(postcss@8.4.26): - resolution: {integrity: sha512-4BqMbZksRkJQx2zAjrokiGMd07RqOa2IxIrrN10lyBe9xhn9DEvjUK79J6jkeiv9D9hQFXKb6g1jwU62jziJZA==} - engines: {node: ^12 || ^14 || >=16} - hasBin: true - peerDependencies: - postcss: ^8.4 - dependencies: - postcss: 8.4.26 - dev: false - - /css-select-base-adapter@0.1.1: - resolution: {integrity: sha512-jQVeeRG70QI08vSTwf1jHxp74JoZsr2XSgETae8/xC8ovSnL2WF87GTLO86Sbwdt2lK4Umg4HnnwMO4YF3Ce7w==} - dev: false - - /css-select@2.1.0: - resolution: {integrity: sha512-Dqk7LQKpwLoH3VovzZnkzegqNSuAziQyNZUcrdDM401iY+R5NkGBXGmtO05/yaXQziALuPogeG0b7UAgjnTJTQ==} - dependencies: - boolbase: 1.0.0 - css-what: 3.4.2 - domutils: 1.7.0 - nth-check: 1.0.2 - dev: false - - /css-select@4.3.0: - resolution: {integrity: sha512-wPpOYtnsVontu2mODhA19JrqWxNsfdatRKd64kmpRbQgh1KtItko5sTnEpPdpSaJszTOhEMlF/RPz28qj4HqhQ==} - dependencies: - boolbase: 1.0.0 - css-what: 6.1.0 - domhandler: 4.3.1 - domutils: 2.8.0 - nth-check: 2.1.1 - dev: false - - /css-tree@1.0.0-alpha.37: - resolution: {integrity: sha512-DMxWJg0rnz7UgxKT0Q1HU/L9BeJI0M6ksor0OgqOnF+aRCDWg/N2641HmVyU9KVIu0OVVWOb2IpC9A+BJRnejg==} - engines: {node: '>=8.0.0'} - dependencies: - mdn-data: 2.0.4 - source-map: 0.6.1 - dev: false - - /css-tree@1.1.3: - resolution: {integrity: sha512-tRpdppF7TRazZrjJ6v3stzv93qxRcSsFmW6cX0Zm2NVKpxE1WV1HblnghVv9TreireHkqI/VDEsfolRF1p6y7Q==} - engines: {node: '>=8.0.0'} - dependencies: - mdn-data: 2.0.14 - source-map: 0.6.1 - dev: false - - /css-what@3.4.2: - resolution: {integrity: sha512-ACUm3L0/jiZTqfzRM3Hi9Q8eZqd6IK37mMWPLz9PJxkLWllYeRf+EHUSHYEtFop2Eqytaq1FizFVh7XfBnXCDQ==} - engines: {node: '>= 6'} - dev: false - - /css-what@6.1.0: - resolution: {integrity: sha512-HTUrgRJ7r4dsZKU6GjmpfRK1O76h97Z8MfS1G0FozR+oF2kG6Vfe8JE6zwrkbxigziPHinCJ+gCPjA9EaBDtRw==} - engines: {node: '>= 6'} - dev: false - - /cssdb@7.6.0: - resolution: {integrity: sha512-Nna7rph8V0jC6+JBY4Vk4ndErUmfJfV6NJCaZdurL0omggabiy+QB2HCQtu5c/ACLZ0I7REv7A4QyPIoYzZx0w==} - dev: false - - /cssesc@3.0.0: - resolution: {integrity: sha512-/Tb/JcjK111nNScGob5MNtsntNM1aCNUDipB/TkwZFhyDrrE47SOx/18wF2bbjgc3ZzCSKW1T5nt5EbFoAz/Vg==} - engines: {node: '>=4'} - hasBin: true - dev: false - - /cssnano-preset-default@5.2.14(postcss@8.4.26): - resolution: {integrity: sha512-t0SFesj/ZV2OTylqQVOrFgEh5uanxbO6ZAdeCrNsUQ6fVuXwYTxJPNAGvGTxHbD68ldIJNec7PyYZDBrfDQ+6A==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - css-declaration-sorter: 6.4.1(postcss@8.4.26) - cssnano-utils: 3.1.0(postcss@8.4.26) - postcss: 8.4.26 - postcss-calc: 8.2.4(postcss@8.4.26) - postcss-colormin: 5.3.1(postcss@8.4.26) - postcss-convert-values: 5.1.3(postcss@8.4.26) - postcss-discard-comments: 5.1.2(postcss@8.4.26) - postcss-discard-duplicates: 5.1.0(postcss@8.4.26) - postcss-discard-empty: 5.1.1(postcss@8.4.26) - postcss-discard-overridden: 5.1.0(postcss@8.4.26) - postcss-merge-longhand: 5.1.7(postcss@8.4.26) - postcss-merge-rules: 5.1.4(postcss@8.4.26) - postcss-minify-font-values: 5.1.0(postcss@8.4.26) - postcss-minify-gradients: 5.1.1(postcss@8.4.26) - postcss-minify-params: 5.1.4(postcss@8.4.26) - postcss-minify-selectors: 5.2.1(postcss@8.4.26) - postcss-normalize-charset: 5.1.0(postcss@8.4.26) - postcss-normalize-display-values: 5.1.0(postcss@8.4.26) - postcss-normalize-positions: 5.1.1(postcss@8.4.26) - postcss-normalize-repeat-style: 5.1.1(postcss@8.4.26) - postcss-normalize-string: 5.1.0(postcss@8.4.26) - postcss-normalize-timing-functions: 5.1.0(postcss@8.4.26) - postcss-normalize-unicode: 5.1.1(postcss@8.4.26) - postcss-normalize-url: 5.1.0(postcss@8.4.26) - postcss-normalize-whitespace: 5.1.1(postcss@8.4.26) - postcss-ordered-values: 5.1.3(postcss@8.4.26) - postcss-reduce-initial: 5.1.2(postcss@8.4.26) - postcss-reduce-transforms: 5.1.0(postcss@8.4.26) - postcss-svgo: 5.1.0(postcss@8.4.26) - postcss-unique-selectors: 5.1.1(postcss@8.4.26) - dev: false - - /cssnano-utils@3.1.0(postcss@8.4.26): - resolution: {integrity: sha512-JQNR19/YZhz4psLX/rQ9M83e3z2Wf/HdJbryzte4a3NSuafyp9w/I4U+hx5C2S9g41qlstH7DEWnZaaj83OuEA==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - dev: false - - /cssnano@5.1.15(postcss@8.4.26): - resolution: {integrity: sha512-j+BKgDcLDQA+eDifLx0EO4XSA56b7uut3BQFH+wbSaSTuGLuiyTa/wbRYthUXX8LC9mLg+WWKe8h+qJuwTAbHw==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - cssnano-preset-default: 5.2.14(postcss@8.4.26) - lilconfig: 2.1.0 - postcss: 8.4.26 - yaml: 1.10.2 - dev: false - - /csso@4.2.0: - resolution: {integrity: sha512-wvlcdIbf6pwKEk7vHj8/Bkc0B4ylXZruLvOgs9doS5eOsOpuodOV2zJChSpkp+pRpYQLQMeF04nr3Z68Sta9jA==} - engines: {node: '>=8.0.0'} - dependencies: - css-tree: 1.1.3 - dev: false - - /cssom@0.3.8: - resolution: {integrity: sha512-b0tGHbfegbhPJpxpiBPU2sCkigAqtM9O121le6bbOlgyV+NyGyCmVfJ6QW9eRjz8CpNfWEOYBIMIGRYkLwsIYg==} - dev: false - - /cssom@0.4.4: - resolution: {integrity: sha512-p3pvU7r1MyyqbTk+WbNJIgJjG2VmTIaB10rI93LzVPrmDJKkzKYMtxxyAvQXR/NS6otuzveI7+7BBq3SjBS2mw==} - dev: false - - /cssstyle@2.3.0: - resolution: {integrity: sha512-AZL67abkUzIuvcHqk7c09cezpGNcxUxU4Ioi/05xHk4DQeTkWmGYftIE6ctU6AEt+Gn4n1lDStOtj7FKycP71A==} - engines: {node: '>=8'} - dependencies: - cssom: 0.3.8 - dev: false - /cssstyle@4.0.1: resolution: {integrity: sha512-8ZYiJ3A/3OkDd093CBT/0UKDWry7ak4BdPTFP2+QEP7cmhouyq/Up709ASSj2cK02BbZiMgk7kYjZNS4QP5qrQ==} engines: {node: '>=18'} @@ -5408,15 +2058,7 @@ /damerau-levenshtein@1.0.8: resolution: {integrity: sha512-sdQSFB7+llfUcQHUQO3+B8ERRj0Oa4w9POWMI/puGtuf7gFywGmkaLCElnudfTiKZV+NvHqL0ifzdrI8Ro7ESA==} - - /data-urls@2.0.0: - resolution: {integrity: sha512-X5eWTSXO/BJmpdIKCRuKUgSCgAN0OwliVK3yPKbwIWU1Tdw5BRajxlzMidvh+gwko9AfQ9zIj52pzF91Q3YAvQ==} - engines: {node: '>=10'} - dependencies: - abab: 2.0.6 - whatwg-mimetype: 2.3.0 - whatwg-url: 8.7.0 - dev: false + dev: true /data-urls@5.0.0: resolution: {integrity: sha512-ZYP5VBHshaDAiVZxjbRVcFJpc+4xGgT0bK3vzy1HLN8jTO975HEbuYzZJcHoQEY5K1a0z8YayJkyVETa08eNTg==} @@ -5436,17 +2078,6 @@ /dayjs@1.11.10: resolution: {integrity: sha512-vjAczensTgRcqDERK0SR2XMwsF/tSvnvlv6VcF2GIhg6Sx4yOIt/irsr1RDJsKiIyBzJDpCoXiWWq28MqH2cnQ==} - /debug@2.6.9: - resolution: {integrity: sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==} - peerDependencies: - supports-color: '*' - peerDependenciesMeta: - supports-color: - optional: true - dependencies: - ms: 2.0.0 - dev: false - /debug@3.2.7: resolution: {integrity: sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==} peerDependencies: @@ -5456,6 +2087,7 @@ optional: true dependencies: ms: 2.1.3 + dev: true /debug@4.3.4(supports-color@5.5.0): resolution: {integrity: sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ==} @@ -5473,28 +2105,13 @@ resolution: {integrity: sha512-VBBaLc1MgL5XpzgIP7ny5Z6Nx3UrRkIViUkPUdtl9aya5amy3De1gsUUSB1g3+3sExYNjCAsAznmukyxCb1GRA==} dev: false - /dedent@0.7.0: - resolution: {integrity: sha512-Q6fKUPqnAHAyhiUgFU7BUzLiv0kd8saH9al7tnu5Q/okj6dnupxyTgFIBjVzJATdfIAm9NAsvXNzjaKa+bxVyA==} - dev: false - /deep-equal@1.0.1: resolution: {integrity: sha512-bHtC0iYvWhyaTzvV3CZgPeZQqCOBGyGsVV7v4eevpdkLHfiSrXUdBG+qAuSz4RI70sszvjQ1QSZ98An1yNwpSw==} dev: false /deep-is@0.1.4: resolution: {integrity: sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==} - - /deepmerge@4.3.1: - resolution: {integrity: sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==} - engines: {node: '>=0.10.0'} - dev: false - - /default-gateway@6.0.3: - resolution: {integrity: sha512-fwSOJsbbNzZ/CUFpqFBqYfYNLj1NbMPm8MMCIzHjC83iSJRBEGmDUxU+WP661BaBQImeC2yHwXtz+P/O9o+XEg==} - engines: {node: '>= 10'} - dependencies: - execa: 5.1.1 - dev: false + dev: true /define-data-property@1.1.4: resolution: {integrity: sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==} @@ -5504,17 +2121,13 @@ es-errors: 1.3.0 gopd: 1.0.1 - /define-lazy-prop@2.0.0: - resolution: {integrity: sha512-Ds09qNh8yw3khSjiJjiUInaGX9xlqZDY7JVryGxdxV7NPeuqQfplOpQ66yJFZut3jLa5zOwkXw1g9EI2uKh4Og==} - engines: {node: '>=8'} - dev: false - /define-properties@1.2.0: resolution: {integrity: sha512-xvqAVKGfT1+UAvPwKTVw/njhdQ8ZhXK4lI0bCIuCMrp2up9nPnaDftrLtmpTazqd1o+UY4zgzU+avtMbDP+ldA==} engines: {node: '>= 0.4'} dependencies: has-property-descriptors: 1.0.0 object-keys: 1.1.1 + dev: true /define-properties@1.2.1: resolution: {integrity: sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==} @@ -5523,6 +2136,7 @@ define-data-property: 1.1.4 has-property-descriptors: 1.0.2 object-keys: 1.1.1 + dev: true /delayed-stream@1.0.0: resolution: {integrity: sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==} @@ -5551,6 +2165,7 @@ /dequal@2.0.3: resolution: {integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==} engines: {node: '>=6'} + dev: true /destroy@1.2.0: resolution: {integrity: sha512-2sJGJTaXIIaR1w4iJSNoN0hnMY7Gpc/n8D4qSCJw8QqFWXf7cuAgnEHxBpweaVcPevC2l3KpjYCx3NypQQgaJg==} @@ -5562,26 +2177,6 @@ engines: {node: '>=8'} dev: false - /detect-newline@3.1.0: - resolution: {integrity: sha512-TLz+x/vEXm/Y7P7wn1EJFNLxYpUD4TgMosxY6fAVJUnJMbupHBOncxyWUG9OpTaH9EBD7uFI5LfEgmMOc54DsA==} - engines: {node: '>=8'} - dev: false - - /detect-node@2.1.0: - resolution: {integrity: sha512-T0NIuQpnTvFDATNuHN5roPwSBG83rFsuO+MXXH9/3N1eFbn4wcPjttvjMLEPWJ0RGUYgQE7cGgS3tNxbqCGM7g==} - dev: false - - /detect-port-alt@1.1.6: - resolution: {integrity: sha512-5tQykt+LqfJFBEYaDITx7S7cR7mJ/zQmLXZ2qt5w04ainYZw6tBf9dBunMjVeVOdYVRUzUOE4HkY5J7+uttb5Q==} - engines: {node: '>= 4.2.1'} - hasBin: true - dependencies: - address: 1.2.2 - debug: 2.6.9 - transitivePeerDependencies: - - supports-color - dev: false - /dezalgo@1.0.4: resolution: {integrity: sha512-rXSP0bf+5n0Qonsb+SVVfNfIsimO4HEtmnIpPHY8Q1UCzKlQrDMfdobr8nJOOsRgWCyMRqeSBQzmWUMq7zvVig==} dependencies: @@ -5589,15 +2184,6 @@ wrappy: 1.0.2 dev: false - /didyoumean@1.2.2: - resolution: {integrity: sha512-gxtyfqMg7GKyhQmb056K7M3xszy/myH8w+B4RT+QXBQsvAOdc3XymqDDPHx1BgPgsdAA5SIifona89YtRATDzw==} - dev: false - - /diff-sequences@27.5.1: - resolution: {integrity: sha512-k1gCAXAsNgLwEL+Y8Wvl+M6oEFj5bgazfZULpS5CneoPPXRaCCW7dm+q21Ky2VEE5X+VeRDBVg1Pcvvsr4TtNQ==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dev: false - /diff-sequences@29.4.3: resolution: {integrity: sha512-ofrBgwpPhCD85kMKtE9RYFFq6OC1A89oW2vvgWZNCwxrUpRUILopY7lsYyMDSjc8g6U6aiO0Qubg6r4Wgt5ZnA==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} @@ -5608,39 +2194,21 @@ engines: {node: '>=8'} dependencies: path-type: 4.0.0 - - /dlv@1.1.3: - resolution: {integrity: sha512-+HlytyjlPKnIG8XuRG8WvmBP8xs8P71y+SKKS6ZXWoEgLuePxtDoUEiH7WkdePWrQ5JBpE6aoVqfZfJUQkjXwA==} - dev: false - - /dns-equal@1.0.0: - resolution: {integrity: sha512-z+paD6YUQsk+AbGCEM4PrOXSss5gd66QfcVBFTKR/HpFL9jCqikS94HYwKww6fQyO7IxrIIyUu+g0Ka9tUS2Cg==} - dev: false - - /dns-packet@5.6.0: - resolution: {integrity: sha512-rza3UH1LwdHh9qyPXp8lkwpjSNk/AMD3dPytUoRoqnypDUhY0xvbdmVhWOfxO68frEfV9BU8V12Ez7ZsHGZpCQ==} - engines: {node: '>=6'} - dependencies: - '@leichtgewicht/ip-codec': 2.0.4 - dev: false + dev: true /doctrine@2.1.0: resolution: {integrity: sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==} engines: {node: '>=0.10.0'} dependencies: esutils: 2.0.3 + dev: true /doctrine@3.0.0: resolution: {integrity: sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w==} engines: {node: '>=6.0.0'} dependencies: esutils: 2.0.3 - - /dom-converter@0.2.0: - resolution: {integrity: sha512-gd3ypIPfOMr9h5jIKq8E3sHOTCjeirnl0WK5ZdS1AW0Odt0b1PaWaHdJ4Qk4klv+YB9aJBS7mESXjFoDQPu6DA==} - dependencies: - utila: 0.4.0 - dev: false + dev: true /dom-helpers@5.2.1: resolution: {integrity: sha512-nRCa7CK3VTrM2NmGkIy4cbK7IZlgBE/PYMn55rrXefr5xXDP0LdtfPnblFDoVdcAfslJ7or6iqAUnx0CCGIWQA==} @@ -5649,21 +2217,6 @@ csstype: 3.1.2 dev: false - /dom-serializer@0.2.2: - resolution: {integrity: sha512-2/xPb3ORsQ42nHYiSunXkDjPLBaEj/xTwUO4B7XCZQTRk7EBtTOPaygh10YAAh2OI1Qrp6NWfpAhzswj0ydt9g==} - dependencies: - domelementtype: 2.3.0 - entities: 2.2.0 - dev: false - - /dom-serializer@1.4.1: - resolution: {integrity: sha512-VHwB3KfrcOOkelEG2ZOfxqLZdfkil8PtJi4P8N2MMXucZq2yLp75ClViUlOVwyoHEDjYU433Aq+5zWP61+RGag==} - dependencies: - domelementtype: 2.3.0 - domhandler: 4.3.1 - entities: 2.2.0 - dev: false - /dom-serializer@2.0.0: resolution: {integrity: sha512-wIkAryiqt/nV5EQKqQpo3SToSOV9J0DnbJqwK7Wv/Trc92zIAYZ4FlMu+JPFW1DfGFt81ZTCGgDEabffXeLyJg==} dependencies: @@ -5672,28 +2225,10 @@ entities: 4.5.0 dev: false - /domelementtype@1.3.1: - resolution: {integrity: sha512-BSKB+TSpMpFI/HOxCNr1O8aMOTZ8hT3pM3GQ0w/mWRmkhEDSFJkkyzz4XQsBV44BChwGkrDfMyjVD0eA2aFV3w==} - dev: false - /domelementtype@2.3.0: resolution: {integrity: sha512-OLETBj6w0OsagBwdXnPdN0cnMfF9opN69co+7ZrbfPGrdpPVNBUj02spi6B1N7wChLQiPn4CSH/zJvXw56gmHw==} dev: false - /domexception@2.0.1: - resolution: {integrity: sha512-yxJ2mFy/sibVQlu5qHjOkf9J3K6zgmCxgJ94u2EdvDOV09H+32LtRswEcUsmUWN72pVLOEnTSRaIVVzVQgS0dg==} - engines: {node: '>=8'} - dependencies: - webidl-conversions: 5.0.0 - dev: false - - /domhandler@4.3.1: - resolution: {integrity: sha512-GrwoxYN+uWlzO8uhUXRl0P+kHE4GtVPfYzVLcUxPL7KNdHKj66vvlhiweIHqYYXWlw+T8iLMp42Lm67ghw4WMQ==} - engines: {node: '>= 4'} - dependencies: - domelementtype: 2.3.0 - dev: false - /domhandler@5.0.3: resolution: {integrity: sha512-cgwlv/1iFQiFnU96XXgROh8xTeetsnJiDsTc7TYCLFd9+/WNkIqPTxiM/8pSd8VIrhXGTf1Ny1q1hquVqDJB5w==} engines: {node: '>= 4'} @@ -5705,21 +2240,6 @@ resolution: {integrity: sha512-uyb4NDIvQ3hRn6NiC+SIFaP4mJ/MdXlvtunaqK9Bn6dD3RuB/1S/gasEjDHD8eiaqdSael2vBv+hOs7Y+jhYOQ==} dev: false - /domutils@1.7.0: - resolution: {integrity: sha512-Lgd2XcJ/NjEw+7tFvfKxOzCYKZsdct5lczQ2ZaQY8Djz7pfAD3Gbp8ySJWtreII/vDlMVmxwa6pHmdxIYgttDg==} - dependencies: - dom-serializer: 0.2.2 - domelementtype: 1.3.1 - dev: false - - /domutils@2.8.0: - resolution: {integrity: sha512-w96Cjofp72M5IIhpjgobBimYEfoPjx1Vx0BSX9P30WBdZW2WIKU0T1Bd0kz2eNZ9ikjKgHbEyKx8BB6H1L3h3A==} - dependencies: - dom-serializer: 1.4.1 - domelementtype: 2.3.0 - domhandler: 4.3.1 - dev: false - /domutils@3.1.0: resolution: {integrity: sha512-H78uMmQtI2AhgDJjWeQmHwJJ2bLPD3GMmO7Zja/ZZh84wkm+4ut+IUnUdRa8uCGX88DiVx1j6FRe1XfxEgjEZA==} dependencies: @@ -5728,26 +2248,6 @@ domhandler: 5.0.3 dev: false - /dot-case@3.0.4: - resolution: {integrity: sha512-Kv5nKlh6yRrdrGvxeJ2e5y2eRUpkUosIW4A2AS38zwSz27zu7ufDwQPi5Jhs3XAlGNetl3bmnGhQsMtkKJnj3w==} - dependencies: - no-case: 3.0.4 - tslib: 2.6.2 - dev: false - - /dotenv-expand@5.1.0: - resolution: {integrity: sha512-YXQl1DSa4/PQyRfgrv6aoNjhasp/p4qs9FjJ4q4cQk+8m4r6k4ZSiEyytKG8f8W9gi8WsQtIObNmKd+tMzNTmA==} - dev: false - - /dotenv@10.0.0: - resolution: {integrity: sha512-rlBi9d8jpv9Sf1klPjNfFAuWDjKLwTIJJ/VxtoTwIR6hnZxcEOQCZg2oIL3MWBYw5GpUDKOEnND7LXTbIpQ03Q==} - engines: {node: '>=10'} - dev: false - - /duplexer@0.1.2: - resolution: {integrity: sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg==} - dev: false - /eastasianwidth@0.2.0: resolution: {integrity: sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==} dev: true @@ -5756,37 +2256,13 @@ resolution: {integrity: sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==} dev: false - /ejs@3.1.9: - resolution: {integrity: sha512-rC+QVNMJWv+MtPgkt0y+0rVEIdbtxVADApW9JXrUVlzHetgcyczP/E7DJmWJ4fJCZF2cPcBk0laWO9ZHMG3DmQ==} - engines: {node: '>=0.10.0'} - hasBin: true - dependencies: - jake: 10.8.7 - dev: false - - /electron-to-chromium@1.4.461: - resolution: {integrity: sha512-1JkvV2sgEGTDXjdsaQCeSwYYuhLRphRpc+g6EHTFELJXEiznLt3/0pZ9JuAOQ5p2rI3YxKTbivtvajirIfhrEQ==} - - /emittery@0.10.2: - resolution: {integrity: sha512-aITqOwnLanpHLNXZJENbOgjUBeHocD+xsSJmNrjovKBW5HbSpW3d1pEls7GFQPUWXiwG9+0P4GtHfEqC/4M0Iw==} - engines: {node: '>=12'} - dev: false - - /emittery@0.8.1: - resolution: {integrity: sha512-uDfvUjVrfGJJhymx/kz6prltenw1u7WrCg1oa94zYY8xxVpLLUu045LAT0dhDZdXG58/EpPL/5kA180fQ/qudg==} - engines: {node: '>=10'} - dev: false - /emoji-regex@8.0.0: resolution: {integrity: sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==} + dev: true /emoji-regex@9.2.2: resolution: {integrity: sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==} - - /emojis-list@3.0.0: - resolution: {integrity: sha512-/kyM18EfinwXZbno9FyUGeFh87KC8HRQBQGildHZbEuRyWFOmv1U10o9BBp8XVZDVNNuQKyIGIu5ZYAAXJ0V2Q==} - engines: {node: '>= 4'} - dev: false + dev: true /enabled@2.0.0: resolution: {integrity: sha512-AKrN98kuwOzMIdAizXGI86UFBoo26CL21UM763y1h/GMSJ4/OHU9k2YlsmBpyScFo/wbLzWQJBMCW4+IO3/+OQ==} @@ -5803,28 +2279,13 @@ dependencies: graceful-fs: 4.2.11 tapable: 2.2.1 - - /entities@2.2.0: - resolution: {integrity: sha512-p92if5Nz619I0w+akJrLZH0MX0Pb5DX39XOwQTtXSdQQOaYH03S1uIQp4mhOZtAXrxq4ViO67YTiLBo2638o9A==} - dev: false + dev: true /entities@4.5.0: resolution: {integrity: sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==} engines: {node: '>=0.12'} dev: false - /error-ex@1.3.2: - resolution: {integrity: sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==} - dependencies: - is-arrayish: 0.2.1 - dev: false - - /error-stack-parser@2.1.4: - resolution: {integrity: sha512-Sk5V6wVazPhq5MhpO+AUxJn5x7XSXGl1R93Vn7i+zS15KDVxQijejNCrz8340/2bgLBjR9GtEG8ZVKONDjcqGQ==} - dependencies: - stackframe: 1.3.4 - dev: false - /es-abstract@1.22.1: resolution: {integrity: sha512-ioRRcXMO6OFyRpyzV3kE1IIBd4WG5/kltnzdxSCqoP8CMGs/Li+M1uF5o7lOkZVFjDs+NLesthnF66Pg/0q0Lw==} engines: {node: '>= 0.4'} @@ -5868,6 +2329,7 @@ typed-array-length: 1.0.4 unbox-primitive: 1.0.2 which-typed-array: 1.1.10 + dev: true /es-abstract@1.22.5: resolution: {integrity: sha512-oW69R+4q2wG+Hc3KZePPZxOiisRIqfKBVo/HLx94QcJeWGU/8sZhCvc829rd1kS366vlJbzBfXf9yWwf0+Ko7w==} @@ -5914,9 +2376,11 @@ typed-array-length: 1.0.5 unbox-primitive: 1.0.2 which-typed-array: 1.1.15 + dev: true /es-array-method-boxes-properly@1.0.0: resolution: {integrity: sha512-wd6JXUmyHmt8T5a2xreUwKcGPq6f1f+WwIJkijUqiGcJz1qqnZgP6XIK+QyIWU5lT7imeNxUll48bziG+TSYcA==} + dev: true /es-define-property@1.0.0: resolution: {integrity: sha512-jxayLKShrEqqzJ0eumQbVhTYQM27CfT1T35+gCgDFoL82JLsXqTJ76zv6A0YLOgEnLUMvLzsDsGIrl8NFpT2gQ==} @@ -5949,10 +2413,6 @@ safe-array-concat: 1.1.2 dev: true - /es-module-lexer@1.3.0: - resolution: {integrity: sha512-vZK7T0N2CBmBOixhmjdqx2gWVbFZ4DXZ/NyRMZVlJXPa7CyFS+/a4QQsDGDQy9ZfEzxFuNEsMLeQJnKP2p5/JA==} - dev: false - /es-set-tostringtag@2.0.1: resolution: {integrity: sha512-g3OMbtlwY3QewlqAiMLI47KywjWZoEytKr8pf6iTC8uJq5bIAH52Z9pnQ8pVL6whrCto53JZDuUIsifGeLorTg==} engines: {node: '>= 0.4'} @@ -5960,6 +2420,7 @@ get-intrinsic: 1.2.1 has: 1.0.3 has-tostringtag: 1.0.0 + dev: true /es-set-tostringtag@2.0.3: resolution: {integrity: sha512-3T8uNMC3OQTHkFUsFq8r/BwAXLHvU/9O9mE0fBc/MY5iq/8H7ncvO947LmYA6ldWw9Uh8Yhf25zu6n7nML5QWQ==} @@ -5968,16 +2429,19 @@ get-intrinsic: 1.2.4 has-tostringtag: 1.0.2 hasown: 2.0.1 + dev: true /es-shim-unscopables@1.0.0: resolution: {integrity: sha512-Jm6GPcCdC30eMLbZ2x8z2WuRwAws3zTBBKuusffYVUrNj/GVSUAZ+xKMaUpfNDR5IbyNA5LJbaecoUVbmUcB1w==} dependencies: has: 1.0.3 + dev: true /es-shim-unscopables@1.0.2: resolution: {integrity: sha512-J3yBRXCzDu4ULnQwxyToo/OjdMx6akgVC7K6few0a7F/0wLtmKKN7I73AH5T2836UuXRqN7Qg+IIUw/+YJksRw==} dependencies: hasown: 2.0.1 + dev: true /es-to-primitive@1.2.1: resolution: {integrity: sha512-QCOllgZJtaUo9miYBcLChTUaHNjJF3PYs1VidD7AwiEj1kYxKeQTctLAezAOH5ZKRH0g2IgPn6KwB4IT8iRpvA==} @@ -5986,6 +2450,7 @@ is-callable: 1.2.7 is-date-object: 1.0.5 is-symbol: 1.0.4 + dev: true /esbuild@0.20.1: resolution: {integrity: sha512-OJwEgrpWm/PCMsLVWXKqvcjme3bHNpOgN7Tb6cQnR5n0TPbQx1/Xrn7rqM+wn17bYeT6MGB5sn1Bh5YiGi70nA==} @@ -6021,6 +2486,7 @@ /escalade@3.1.1: resolution: {integrity: sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==} engines: {node: '>=6'} + dev: true /escape-html@1.0.3: resolution: {integrity: sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==} @@ -6029,26 +2495,17 @@ /escape-string-regexp@1.0.5: resolution: {integrity: sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==} engines: {node: '>=0.8.0'} + dev: true /escape-string-regexp@2.0.0: resolution: {integrity: sha512-UpzcLCXolUWcNu5HtVMHYdXJjArjsF9C0aNnquZYY4uW/Vu0miy5YoWvbV345HauVvcAUnpRuhMMcqTcGOY2+w==} engines: {node: '>=8'} + dev: true /escape-string-regexp@4.0.0: resolution: {integrity: sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==} engines: {node: '>=10'} - - /escodegen@2.1.0: - resolution: {integrity: sha512-2NlIDTwUWJN0mRPQOdtQBzbUHvdGY2P1VXSyU83Q3xKxM7WHX2Ql8dKq782Q9TgQUNOLEzEYu9bzLNj1q88I5w==} - engines: {node: '>=6.0'} - hasBin: true - dependencies: - esprima: 4.0.1 - estraverse: 5.3.0 - esutils: 2.0.3 - optionalDependencies: - source-map: 0.6.1 - dev: false + dev: true /eslint-config-next@14.1.3(eslint@8.57.0)(typescript@5.4.2): resolution: {integrity: sha512-sUCpWlGuHpEhI0pIT0UtdSLJk5Z8E2DYinPTwsBiWaSYQomchdl0i60pjynY48+oXvtyWMQ7oE+G3m49yrfacg==} @@ -6075,51 +2532,6 @@ - supports-color dev: true - /eslint-config-react-app@7.0.1(@babel/plugin-syntax-flow@7.23.3)(@babel/plugin-transform-react-jsx@7.23.4)(eslint@8.57.0)(jest@27.5.1)(typescript@5.4.2): - resolution: {integrity: sha512-K6rNzvkIeHaTd8m/QEh1Zko0KI7BACWkkneSs6s9cKZC/J27X3eZR6Upt1jkmZ/4FK+XUOPPxMEN7+lbUXfSlA==} - engines: {node: '>=14.0.0'} - peerDependencies: - eslint: ^8.0.0 - typescript: '*' - peerDependenciesMeta: - typescript: - optional: true - dependencies: - '@babel/core': 7.22.9 - '@babel/eslint-parser': 7.22.9(@babel/core@7.22.9)(eslint@8.57.0) - '@rushstack/eslint-patch': 1.3.2 - '@typescript-eslint/eslint-plugin': 5.62.0(@typescript-eslint/parser@5.62.0)(eslint@8.57.0)(typescript@5.4.2) - '@typescript-eslint/parser': 5.62.0(eslint@8.57.0)(typescript@5.4.2) - babel-preset-react-app: 10.0.1 - confusing-browser-globals: 1.0.11 - eslint: 8.57.0 - eslint-plugin-flowtype: 8.0.3(@babel/plugin-syntax-flow@7.23.3)(@babel/plugin-transform-react-jsx@7.23.4)(eslint@8.57.0) - eslint-plugin-import: 2.27.5(@typescript-eslint/parser@5.62.0)(eslint@8.57.0) - eslint-plugin-jest: 25.7.0(@typescript-eslint/eslint-plugin@5.62.0)(eslint@8.57.0)(jest@27.5.1)(typescript@5.4.2) - eslint-plugin-jsx-a11y: 6.7.1(eslint@8.57.0) - eslint-plugin-react: 7.32.2(eslint@8.57.0) - eslint-plugin-react-hooks: 4.6.0(eslint@8.57.0) - eslint-plugin-testing-library: 5.11.0(eslint@8.57.0)(typescript@5.4.2) - typescript: 5.4.2 - transitivePeerDependencies: - - '@babel/plugin-syntax-flow' - - '@babel/plugin-transform-react-jsx' - - eslint-import-resolver-typescript - - eslint-import-resolver-webpack - - jest - - supports-color - dev: false - - /eslint-import-resolver-node@0.3.7: - resolution: {integrity: sha512-gozW2blMLJCeFpBwugLTGyvVjNoeo1knonXAcatC6bjPBZitotxdWf7Gimr25N4c0AAOo4eOUfaG82IJPDpqCA==} - dependencies: - debug: 3.2.7 - is-core-module: 2.12.1 - resolve: 1.22.2 - transitivePeerDependencies: - - supports-color - dev: false - /eslint-import-resolver-node@0.3.9: resolution: {integrity: sha512-WFj2isz22JahUv+B788TlO3N6zL3nNJGU8CcZbPZvVEkBPaJdCV4vy5wyghty5ROFbCRnm132v8BScu5/1BQ8g==} dependencies: @@ -6128,29 +2540,7 @@ resolve: 1.22.8 transitivePeerDependencies: - supports-color - - /eslint-import-resolver-typescript@3.6.1(@typescript-eslint/parser@5.62.0)(eslint-import-resolver-node@0.3.7)(eslint-plugin-import@2.29.1)(eslint@8.57.0): - resolution: {integrity: sha512-xgdptdoi5W3niYeuQxKmzVDTATvLYqhpwmykwsh7f6HIOStGWEIL9iqZgQDF9u9OEzrRwR8no5q2VT+bjAujTg==} - engines: {node: ^14.18.0 || >=16.0.0} - peerDependencies: - eslint: '*' - eslint-plugin-import: '*' - dependencies: - debug: 4.3.4(supports-color@5.5.0) - enhanced-resolve: 5.15.0 - eslint: 8.57.0 - eslint-module-utils: 2.8.0(@typescript-eslint/parser@5.62.0)(eslint-import-resolver-node@0.3.7)(eslint-import-resolver-typescript@3.6.1)(eslint@8.57.0) - eslint-plugin-import: 2.29.1(eslint@8.57.0) - fast-glob: 3.3.2 - get-tsconfig: 4.7.3 - is-core-module: 2.12.1 - is-glob: 4.0.3 - transitivePeerDependencies: - - '@typescript-eslint/parser' - - eslint-import-resolver-node - - eslint-import-resolver-webpack - - supports-color - dev: false + dev: true /eslint-import-resolver-typescript@3.6.1(@typescript-eslint/parser@5.62.0)(eslint-import-resolver-node@0.3.9)(eslint-plugin-import@2.29.1)(eslint@8.57.0): resolution: {integrity: sha512-xgdptdoi5W3niYeuQxKmzVDTATvLYqhpwmykwsh7f6HIOStGWEIL9iqZgQDF9u9OEzrRwR8no5q2VT+bjAujTg==} @@ -6173,36 +2563,7 @@ - eslint-import-resolver-node - eslint-import-resolver-webpack - supports-color - - /eslint-module-utils@2.8.0(@typescript-eslint/parser@5.62.0)(eslint-import-resolver-node@0.3.7)(eslint-import-resolver-typescript@3.6.1)(eslint@8.57.0): - resolution: {integrity: sha512-aWajIYfsqCKRDgUfjEXNN/JlrzauMuSEy5sbd7WXbtW3EH6A6MpwEh42c7qD+MqQo9QMJ6fWLAeIJynx0g6OAw==} - engines: {node: '>=4'} - peerDependencies: - '@typescript-eslint/parser': '*' - eslint: '*' - eslint-import-resolver-node: '*' - eslint-import-resolver-typescript: '*' - eslint-import-resolver-webpack: '*' - peerDependenciesMeta: - '@typescript-eslint/parser': - optional: true - eslint: - optional: true - eslint-import-resolver-node: - optional: true - eslint-import-resolver-typescript: - optional: true - eslint-import-resolver-webpack: - optional: true - dependencies: - '@typescript-eslint/parser': 5.62.0(eslint@8.57.0)(typescript@5.4.2) - debug: 3.2.7 - eslint: 8.57.0 - eslint-import-resolver-node: 0.3.7 - eslint-import-resolver-typescript: 3.6.1(@typescript-eslint/parser@5.62.0)(eslint-import-resolver-node@0.3.7)(eslint-plugin-import@2.29.1)(eslint@8.57.0) - transitivePeerDependencies: - - supports-color - dev: false + dev: true /eslint-module-utils@2.8.0(@typescript-eslint/parser@5.62.0)(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.6.1)(eslint@8.57.0): resolution: {integrity: sha512-aWajIYfsqCKRDgUfjEXNN/JlrzauMuSEy5sbd7WXbtW3EH6A6MpwEh42c7qD+MqQo9QMJ6fWLAeIJynx0g6OAw==} @@ -6232,54 +2593,7 @@ eslint-import-resolver-typescript: 3.6.1(@typescript-eslint/parser@5.62.0)(eslint-import-resolver-node@0.3.9)(eslint-plugin-import@2.29.1)(eslint@8.57.0) transitivePeerDependencies: - supports-color - - /eslint-plugin-flowtype@8.0.3(@babel/plugin-syntax-flow@7.23.3)(@babel/plugin-transform-react-jsx@7.23.4)(eslint@8.57.0): - resolution: {integrity: sha512-dX8l6qUL6O+fYPtpNRideCFSpmWOUVx5QcaGLVqe/vlDiBSe4vYljDWDETwnyFzpl7By/WVIu6rcrniCgH9BqQ==} - engines: {node: '>=12.0.0'} - peerDependencies: - '@babel/plugin-syntax-flow': ^7.14.5 - '@babel/plugin-transform-react-jsx': ^7.14.9 - eslint: ^8.1.0 - dependencies: - '@babel/plugin-syntax-flow': 7.23.3(@babel/core@7.22.9) - '@babel/plugin-transform-react-jsx': 7.23.4(@babel/core@7.22.9) - eslint: 8.57.0 - lodash: 4.17.21 - string-natural-compare: 3.0.1 - dev: false - - /eslint-plugin-import@2.27.5(@typescript-eslint/parser@5.62.0)(eslint@8.57.0): - resolution: {integrity: sha512-LmEt3GVofgiGuiE+ORpnvP+kAm3h6MLZJ4Q5HCyHADofsb4VzXFsRiWj3c0OFiV+3DWFh0qg3v9gcPlfc3zRow==} - engines: {node: '>=4'} - peerDependencies: - '@typescript-eslint/parser': '*' - eslint: ^2 || ^3 || ^4 || ^5 || ^6 || ^7.2.0 || ^8 - peerDependenciesMeta: - '@typescript-eslint/parser': - optional: true - dependencies: - '@typescript-eslint/parser': 5.62.0(eslint@8.57.0)(typescript@5.4.2) - array-includes: 3.1.6 - array.prototype.flat: 1.3.1 - array.prototype.flatmap: 1.3.1 - debug: 3.2.7 - doctrine: 2.1.0 - eslint: 8.57.0 - eslint-import-resolver-node: 0.3.7 - eslint-module-utils: 2.8.0(@typescript-eslint/parser@5.62.0)(eslint-import-resolver-node@0.3.7)(eslint-import-resolver-typescript@3.6.1)(eslint@8.57.0) - has: 1.0.3 - is-core-module: 2.12.1 - is-glob: 4.0.3 - minimatch: 3.1.2 - object.values: 1.1.6 - resolve: 1.22.2 - semver: 6.3.1 - tsconfig-paths: 3.14.2 - transitivePeerDependencies: - - eslint-import-resolver-typescript - - eslint-import-resolver-webpack - - supports-color - dev: false + dev: true /eslint-plugin-import@2.29.1(@typescript-eslint/parser@5.62.0)(eslint-import-resolver-typescript@3.6.1)(eslint@8.57.0): resolution: {integrity: sha512-BbPC0cuExzhiMo4Ff1BTVwHpjjv28C5R+btTOGaCRC7UEz801up0JadwkeSk5Ued6TG34uaczuVuH6qyy5YUxw==} @@ -6314,62 +2628,7 @@ - eslint-import-resolver-typescript - eslint-import-resolver-webpack - supports-color - - /eslint-plugin-import@2.29.1(eslint@8.57.0): - resolution: {integrity: sha512-BbPC0cuExzhiMo4Ff1BTVwHpjjv28C5R+btTOGaCRC7UEz801up0JadwkeSk5Ued6TG34uaczuVuH6qyy5YUxw==} - engines: {node: '>=4'} - peerDependencies: - '@typescript-eslint/parser': '*' - eslint: ^2 || ^3 || ^4 || ^5 || ^6 || ^7.2.0 || ^8 - peerDependenciesMeta: - '@typescript-eslint/parser': - optional: true - dependencies: - array-includes: 3.1.7 - array.prototype.findlastindex: 1.2.4 - array.prototype.flat: 1.3.2 - array.prototype.flatmap: 1.3.2 - debug: 3.2.7 - doctrine: 2.1.0 - eslint: 8.57.0 - eslint-import-resolver-node: 0.3.9 - eslint-module-utils: 2.8.0(@typescript-eslint/parser@5.62.0)(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@3.6.1)(eslint@8.57.0) - hasown: 2.0.1 - is-core-module: 2.13.1 - is-glob: 4.0.3 - minimatch: 3.1.2 - object.fromentries: 2.0.7 - object.groupby: 1.0.2 - object.values: 1.1.7 - semver: 6.3.1 - tsconfig-paths: 3.15.0 - transitivePeerDependencies: - - eslint-import-resolver-typescript - - eslint-import-resolver-webpack - - supports-color - dev: false - - /eslint-plugin-jest@25.7.0(@typescript-eslint/eslint-plugin@5.62.0)(eslint@8.57.0)(jest@27.5.1)(typescript@5.4.2): - resolution: {integrity: sha512-PWLUEXeeF7C9QGKqvdSbzLOiLTx+bno7/HC9eefePfEb257QFHg7ye3dh80AZVkaa/RQsBB1Q/ORQvg2X7F0NQ==} - engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} - peerDependencies: - '@typescript-eslint/eslint-plugin': ^4.0.0 || ^5.0.0 - eslint: ^6.0.0 || ^7.0.0 || ^8.0.0 - jest: '*' - peerDependenciesMeta: - '@typescript-eslint/eslint-plugin': - optional: true - jest: - optional: true - dependencies: - '@typescript-eslint/eslint-plugin': 5.62.0(@typescript-eslint/parser@5.62.0)(eslint@8.57.0)(typescript@5.4.2) - '@typescript-eslint/experimental-utils': 5.62.0(eslint@8.57.0)(typescript@5.4.2) - eslint: 8.57.0 - jest: 27.5.1 - transitivePeerDependencies: - - supports-color - - typescript - dev: false + dev: true /eslint-plugin-jsx-a11y@6.7.1(eslint@8.57.0): resolution: {integrity: sha512-63Bog4iIethyo8smBklORknVjB0T2dwB8Mr/hIC+fBS0uyHdYYpzM/Ed+YC8VxTjlXHEWFOdmgwcDn1U2L9VCA==} @@ -6394,6 +2653,7 @@ object.entries: 1.1.6 object.fromentries: 2.0.6 semver: 6.3.1 + dev: true /eslint-plugin-react-hooks@4.6.0(eslint@8.57.0): resolution: {integrity: sha512-oFc7Itz9Qxh2x4gNHStv3BqJq54ExXmfC+a1NjAta66IAN87Wu0R/QArgIS9qKzX3dXKPI9H5crl9QchNMY9+g==} @@ -6402,30 +2662,7 @@ eslint: ^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0 || ^8.0.0-0 dependencies: eslint: 8.57.0 - - /eslint-plugin-react@7.32.2(eslint@8.57.0): - resolution: {integrity: sha512-t2fBMa+XzonrrNkyVirzKlvn5RXzzPwRHtMvLAtVZrt8oxgnTQaYbU6SXTOO1mwQgp1y5+toMSKInnzGr0Knqg==} - engines: {node: '>=4'} - peerDependencies: - eslint: ^3 || ^4 || ^5 || ^6 || ^7 || ^8 - dependencies: - array-includes: 3.1.6 - array.prototype.flatmap: 1.3.1 - array.prototype.tosorted: 1.1.1 - doctrine: 2.1.0 - eslint: 8.57.0 - estraverse: 5.3.0 - jsx-ast-utils: 3.3.4 - minimatch: 3.1.2 - object.entries: 1.1.6 - object.fromentries: 2.0.6 - object.hasown: 1.1.2 - object.values: 1.1.6 - prop-types: 15.8.1 - resolve: 2.0.0-next.4 - semver: 6.3.1 - string.prototype.matchall: 4.0.8 - dev: false + dev: true /eslint-plugin-react@7.34.0(eslint@8.57.0): resolution: {integrity: sha512-MeVXdReleBTdkz/bvcQMSnCXGi+c9kvy51IpinjnJgutl3YTHWsDdke7Z1ufZpGfDG8xduBDKyjtB9JH1eBKIQ==} @@ -6454,58 +2691,18 @@ string.prototype.matchall: 4.0.10 dev: true - /eslint-plugin-testing-library@5.11.0(eslint@8.57.0)(typescript@5.4.2): - resolution: {integrity: sha512-ELY7Gefo+61OfXKlQeXNIDVVLPcvKTeiQOoMZG9TeuWa7Ln4dUNRv8JdRWBQI9Mbb427XGlVB1aa1QPZxBJM8Q==} - engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0, npm: '>=6'} - peerDependencies: - eslint: ^7.5.0 || ^8.0.0 - dependencies: - '@typescript-eslint/utils': 5.62.0(eslint@8.57.0)(typescript@5.4.2) - eslint: 8.57.0 - transitivePeerDependencies: - - supports-color - - typescript - dev: false - - /eslint-scope@5.1.1: - resolution: {integrity: sha512-2NxwbF/hZ0KpepYN0cNbo+FN6XoK7GaHlQhgx/hIZl6Va0bF45RQOOwhLIy8lQDbuCiadSLCBnH2CFYquit5bw==} - engines: {node: '>=8.0.0'} - dependencies: - esrecurse: 4.3.0 - estraverse: 4.3.0 - dev: false - /eslint-scope@7.2.2: resolution: {integrity: sha512-dOt21O7lTMhDM+X9mB4GX+DZrZtCUJPL/wlcTqxyrx5IvO0IYtILdtrQGQp+8n5S0gwSVmOf9NQrjMOgfQZlIg==} engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} dependencies: esrecurse: 4.3.0 estraverse: 5.3.0 - - /eslint-visitor-keys@2.1.0: - resolution: {integrity: sha512-0rSmRBzXgDzIsD6mGdJgevzgezI534Cer5L/vyMX0kHzT/jiB43jRhd9YUlMGYLQy2zprNmoT8qasCGtY+QaKw==} - engines: {node: '>=10'} - dev: false + dev: true /eslint-visitor-keys@3.4.3: resolution: {integrity: sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==} engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} - - /eslint-webpack-plugin@3.2.0(eslint@8.57.0)(webpack@5.88.1): - resolution: {integrity: sha512-avrKcGncpPbPSUHX6B3stNGzkKFto3eL+DKM4+VyMrVnhPc3vRczVlCq3uhuFOdRvDHTVXuzwk1ZKUrqDQHQ9w==} - engines: {node: '>= 12.13.0'} - peerDependencies: - eslint: ^7.0.0 || ^8.0.0 - webpack: ^5.0.0 - dependencies: - '@types/eslint': 8.44.0 - eslint: 8.57.0 - jest-worker: 28.1.3 - micromatch: 4.0.5 - normalize-path: 3.0.0 - schema-utils: 4.2.0 - webpack: 5.88.1 - dev: false + dev: true /eslint@8.57.0: resolution: {integrity: sha512-dZ6+mexnaTIbSBZWgou51U6OmzIhYM2VcNdtiTtI7qPNZm35Akpr0f6vtw3w1Kmn5PYo+tZVfh13WrhpS6oLqQ==} @@ -6552,6 +2749,7 @@ text-table: 0.2.0 transitivePeerDependencies: - supports-color + dev: true /espree@9.6.1: resolution: {integrity: sha512-oruZaFkjorTpF32kDSI5/75ViwGeZginGGy2NoOSg3Q9bnwlnmDm4HLnkl0RE3n+njDXR037aY1+x58Z/zFdwQ==} @@ -6560,37 +2758,26 @@ acorn: 8.10.0 acorn-jsx: 5.3.2(acorn@8.10.0) eslint-visitor-keys: 3.4.3 - - /esprima@4.0.1: - resolution: {integrity: sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==} - engines: {node: '>=4'} - hasBin: true - dev: false + dev: true /esquery@1.5.0: resolution: {integrity: sha512-YQLXUplAwJgCydQ78IMJywZCceoqk1oH01OERdSAJc/7U2AylwjhSCLDEtqwg811idIS/9fIU5GjG73IgjKMVg==} engines: {node: '>=0.10'} dependencies: estraverse: 5.3.0 + dev: true /esrecurse@4.3.0: resolution: {integrity: sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==} engines: {node: '>=4.0'} dependencies: estraverse: 5.3.0 - - /estraverse@4.3.0: - resolution: {integrity: sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw==} - engines: {node: '>=4.0'} - dev: false + dev: true /estraverse@5.3.0: resolution: {integrity: sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==} engines: {node: '>=4.0'} - - /estree-walker@1.0.1: - resolution: {integrity: sha512-1fMXF3YP4pZZVozF8j/ZLfvnR8NSIljt56UhbZ5PeeDmmGHpgpdwQt7ITlGvYaQukCvuBRMLEiKiYC+oeIg4cg==} - dev: false + dev: true /estree-walker@2.0.2: resolution: {integrity: sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w==} @@ -6599,50 +2786,7 @@ /esutils@2.0.3: resolution: {integrity: sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==} engines: {node: '>=0.10.0'} - - /etag@1.8.1: - resolution: {integrity: sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==} - engines: {node: '>= 0.6'} - dev: false - - /eventemitter3@4.0.7: - resolution: {integrity: sha512-8guHBZCwKnFhYdHr2ysuRWErTwhoN2X8XELRlrRwpmfeY2jjuUN4taQMsULKUVo1K4DvZl+0pgfyoysHxvmvEw==} - dev: false - - /events@3.3.0: - resolution: {integrity: sha512-mQw+2fkQbALzQ7V0MY0IqdnXNOeTtP4r0lN9z7AAawCXgqea7bDii20AYrIBrFd/Hx0M2Ocz6S111CaFkUcb0Q==} - engines: {node: '>=0.8.x'} - dev: false - - /execa@5.1.1: - resolution: {integrity: sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg==} - engines: {node: '>=10'} - dependencies: - cross-spawn: 7.0.3 - get-stream: 6.0.1 - human-signals: 2.1.0 - is-stream: 2.0.1 - merge-stream: 2.0.0 - npm-run-path: 4.0.1 - onetime: 5.1.2 - signal-exit: 3.0.7 - strip-final-newline: 2.0.0 - dev: false - - /exit@0.1.2: - resolution: {integrity: sha512-Zk/eNKV2zbjpKzrsQ+n1G6poVbErQxJ0LBOJXaKZ1EViLzH+hrLu9cdXI4zw9dBQJslwBEpbQ2P1oS7nDxs6jQ==} - engines: {node: '>= 0.8.0'} - dev: false - - /expect@27.5.1: - resolution: {integrity: sha512-E1q5hSUG2AmYQwQJ041nvgpkODHQvB+RKlB4IYdru6uJsyFTRyZAP463M+1lINorwbqAmUggi6+WwkD8lCS/Dw==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/types': 27.5.1 - jest-get-type: 27.5.1 - jest-matcher-utils: 27.5.1 - jest-message-util: 27.5.1 - dev: false + dev: true /expect@29.6.1: resolution: {integrity: sha512-XEdDLonERCU1n9uR56/Stx9OqojaLAQtZf9PrCHH9Hl8YXiEIka3H4NXJ3NOIBmQJTg7+j7buh34PMHfJujc8g==} @@ -6656,47 +2800,9 @@ jest-util: 29.6.1 dev: true - /express@4.18.2: - resolution: {integrity: sha512-5/PsL6iGPdfQ/lKM1UuielYgv3BUoJfz1aUwU9vHZ+J7gyvwdQXFEBIEIaxeGf0GIcreATNyBExtalisDbuMqQ==} - engines: {node: '>= 0.10.0'} - dependencies: - accepts: 1.3.8 - array-flatten: 1.1.1 - body-parser: 1.20.1 - content-disposition: 0.5.4 - content-type: 1.0.5 - cookie: 0.5.0 - cookie-signature: 1.0.6 - debug: 2.6.9 - depd: 2.0.0 - encodeurl: 1.0.2 - escape-html: 1.0.3 - etag: 1.8.1 - finalhandler: 1.2.0 - fresh: 0.5.2 - http-errors: 2.0.0 - merge-descriptors: 1.0.1 - methods: 1.1.2 - on-finished: 2.4.1 - parseurl: 1.3.3 - path-to-regexp: 0.1.7 - proxy-addr: 2.0.7 - qs: 6.11.0 - range-parser: 1.2.1 - safe-buffer: 5.2.1 - send: 0.18.0 - serve-static: 1.15.0 - setprototypeof: 1.2.0 - statuses: 2.0.1 - type-is: 1.6.18 - utils-merge: 1.0.1 - vary: 1.1.2 - transitivePeerDependencies: - - supports-color - dev: false - /fast-deep-equal@3.1.3: resolution: {integrity: sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==} + dev: true /fast-glob@3.3.0: resolution: {integrity: sha512-ChDuvbOypPuNjO8yIDf36x7BlZX1smcUMTTcyoIjycexOxd6DFsKsg21qVBzEmr3G7fUKIRy2/psii+CIUt7FA==} @@ -6707,6 +2813,7 @@ glob-parent: 5.1.2 merge2: 1.4.1 micromatch: 4.0.5 + dev: true /fast-glob@3.3.2: resolution: {integrity: sha512-oX2ruAFQwf/Orj8m737Y5adxDQO0LAB7/S5MnxCdTNDd4p6BsyIVsv9JQsATbTSq8KHRpLwIHbVlUNatxd+1Ow==} @@ -6717,30 +2824,21 @@ glob-parent: 5.1.2 merge2: 1.4.1 micromatch: 4.0.5 + dev: true /fast-json-stable-stringify@2.1.0: resolution: {integrity: sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==} + dev: true /fast-levenshtein@2.0.6: resolution: {integrity: sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==} + dev: true /fastq@1.15.0: resolution: {integrity: sha512-wBrocU2LCXXa+lWBt8RoIRD89Fi8OdABODa/kEnyeyjS5aZO5/GNvI5sEINADqP/h8M29UHTHUb53sUu5Ihqdw==} dependencies: reusify: 1.0.4 - - /faye-websocket@0.11.4: - resolution: {integrity: sha512-CzbClwlXAuiRQAlUyfqPgvPoNKTckTPGfwZV4ZdAhVcP2lh9KUxJg2b5GkE7XbjKQ3YJnQ9z6D9ntLAlB+tP8g==} - engines: {node: '>=0.8.0'} - dependencies: - websocket-driver: 0.7.4 - dev: false - - /fb-watchman@2.0.2: - resolution: {integrity: sha512-p5161BqbuCaSnB8jIbzQHOlpgsPmK5rJVDfDKO91Axs5NC1uu3HRQm6wt9cd9/+GtQQIO53JdGXXoyDpTAsgYA==} - dependencies: - bser: 2.1.1 - dev: false + dev: true /fecha@4.2.3: resolution: {integrity: sha512-OP2IUU6HeYKJi3i0z4A19kHMQoLVs4Hc+DPqqxI2h/DPZHTm/vjsfC6P0b4jCMy14XizLBqvndQ+UilD7707Jw==} @@ -6751,17 +2849,7 @@ engines: {node: ^10.12.0 || >=12.0.0} dependencies: flat-cache: 3.0.4 - - /file-loader@6.2.0(webpack@5.88.1): - resolution: {integrity: sha512-qo3glqyTa61Ytg4u73GultjHGjdRyig3tG6lPtyX/jOEJvHif9uB0/OCI2Kif6ctF3caQTW2G5gym21oAsI4pw==} - engines: {node: '>= 10.13.0'} - peerDependencies: - webpack: ^4.0.0 || ^5.0.0 - dependencies: - loader-utils: 2.0.4 - schema-utils: 3.3.0 - webpack: 5.88.1 - dev: false + dev: true /file-stream-rotator@0.6.1: resolution: {integrity: sha512-u+dBid4PvZw17PmDeRcNOtCP9CCK/9lRN2w+r1xIS7yOL9JFrIBKTvrYsxT4P0pGtThYTn++QS5ChHaUov3+zQ==} @@ -6769,68 +2857,19 @@ moment: 2.29.4 dev: false - /filelist@1.0.4: - resolution: {integrity: sha512-w1cEuf3S+DrLCQL7ET6kz+gmlJdbq9J7yXCSjK/OZCPA+qEN1WyF4ZAf0YYJa4/shHJra2t/d/r8SV4Ji+x+8Q==} - dependencies: - minimatch: 5.1.6 - dev: false - - /filesize@8.0.7: - resolution: {integrity: sha512-pjmC+bkIF8XI7fWaH8KxHcZL3DPybs1roSKP4rKDvy20tAWwIObE4+JIseG2byfGKhud5ZnM4YSGKBz7Sh0ndQ==} - engines: {node: '>= 0.4.0'} - dev: false - /fill-range@7.0.1: resolution: {integrity: sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==} engines: {node: '>=8'} dependencies: to-regex-range: 5.0.1 - /finalhandler@1.2.0: - resolution: {integrity: sha512-5uXcUVftlQMFnWC9qu/svkWv3GTd2PfUhK/3PLkYNAe7FbqJMt3515HaxE6eRL74GdsriiwujiawdaB1BpEISg==} - engines: {node: '>= 0.8'} - dependencies: - debug: 2.6.9 - encodeurl: 1.0.2 - escape-html: 1.0.3 - on-finished: 2.4.1 - parseurl: 1.3.3 - statuses: 2.0.1 - unpipe: 1.0.0 - transitivePeerDependencies: - - supports-color - dev: false - - /find-cache-dir@3.3.2: - resolution: {integrity: sha512-wXZV5emFEjrridIgED11OoUKLxiYjAcqot/NJdAkOhlJ+vGzwhOAfcG5OX1jP+S0PcjEn8bdMJv+g2jwQ3Onig==} - engines: {node: '>=8'} - dependencies: - commondir: 1.0.1 - make-dir: 3.1.0 - pkg-dir: 4.2.0 - dev: false - - /find-up@3.0.0: - resolution: {integrity: sha512-1yD6RmLI1XBfxugvORwlck6f75tYL+iR0jqwsOrOxMZyGYqUuDhJ0l4AXdO1iX/FTs9cBAMEk1gWSEx1kSbylg==} - engines: {node: '>=6'} - dependencies: - locate-path: 3.0.0 - dev: false - - /find-up@4.1.0: - resolution: {integrity: sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==} - engines: {node: '>=8'} - dependencies: - locate-path: 5.0.0 - path-exists: 4.0.0 - dev: false - /find-up@5.0.0: resolution: {integrity: sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==} engines: {node: '>=10'} dependencies: locate-path: 6.0.0 path-exists: 4.0.0 + dev: true /flat-cache@3.0.4: resolution: {integrity: sha512-dm9s5Pw7Jc0GvMYbshN6zchCA9RgQlzzEZX3vylR9IqFfS8XciblUXOKfW6SiuJ0e13eDYZoZV5wdrev7P3Nwg==} @@ -6838,9 +2877,11 @@ dependencies: flatted: 3.2.7 rimraf: 3.0.2 + dev: true /flatted@3.2.7: resolution: {integrity: sha512-5nqDSxl8nn5BSNxyR3n4I6eDmbolI6WT+QqR547RwxQapgjQBmtktdP+HTBb/a/zLsbzERTONyUB5pefh5TtjQ==} + dev: true /fn.name@1.1.0: resolution: {integrity: sha512-GRnmB5gPyJpAhTQdSZTSp9uaPSvl09KoYcMQtsB9rQoOmzs9dH6ffeccH+Z+cv6P68Hu5bC6JjRh4Ah/mHSNRw==} @@ -6860,6 +2901,7 @@ resolution: {integrity: sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==} dependencies: is-callable: 1.2.7 + dev: true /foreground-child@3.1.1: resolution: {integrity: sha512-TMKDUnIte6bfb5nWv7V/caI169OHgvwjb7V4WkeUvbQQdjr5rWKqHFiKWb/fcOwB+CzBT+qbWjvj+DVwRskpIg==} @@ -6869,47 +2911,6 @@ signal-exit: 4.1.0 dev: true - /fork-ts-checker-webpack-plugin@6.5.3(eslint@8.57.0)(typescript@5.4.2)(webpack@5.88.1): - resolution: {integrity: sha512-SbH/l9ikmMWycd5puHJKTkZJKddF4iRLyW3DeZ08HTI7NGyLS38MXd/KGgeWumQO7YNQbW2u/NtPT2YowbPaGQ==} - engines: {node: '>=10', yarn: '>=1.0.0'} - peerDependencies: - eslint: '>= 6' - typescript: '>= 2.7' - vue-template-compiler: '*' - webpack: '>= 4' - peerDependenciesMeta: - eslint: - optional: true - vue-template-compiler: - optional: true - dependencies: - '@babel/code-frame': 7.22.5 - '@types/json-schema': 7.0.12 - chalk: 4.1.2 - chokidar: 3.5.3 - cosmiconfig: 6.0.0 - deepmerge: 4.3.1 - eslint: 8.57.0 - fs-extra: 9.1.0 - glob: 7.2.3 - memfs: 3.5.3 - minimatch: 3.1.2 - schema-utils: 2.7.0 - semver: 7.5.4 - tapable: 1.1.3 - typescript: 5.4.2 - webpack: 5.88.1 - dev: false - - /form-data@3.0.1: - resolution: {integrity: sha512-RHkBKtLWUVwd7SqRIvCZMEvAMoGUp0XU+seQiZejj0COz3RI3hWP4sCv3gZWWLjJTd7rGwcsF5eKZGii0r/hbg==} - engines: {node: '>= 6'} - dependencies: - asynckit: 0.4.0 - combined-stream: 1.0.8 - mime-types: 2.1.35 - dev: false - /form-data@4.0.0: resolution: {integrity: sha512-ETEklSGi5t0QMZuiXoA/Q6vcnxcLQP5vdugSpuAyi6SVGi2clPPp+xgEhuMaHC+zGgn31Kd235W35f7Hykkaww==} engines: {node: '>= 6'} @@ -6927,45 +2928,14 @@ once: 1.4.0 dev: false - /forwarded@0.2.0: - resolution: {integrity: sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==} - engines: {node: '>= 0.6'} - dev: false - - /fraction.js@4.2.0: - resolution: {integrity: sha512-MhLuK+2gUcnZe8ZHlaaINnQLl0xRIGRfcGk2yl8xoQAfHrSsL3rYu6FCmBdkdbhc9EPlwyGHewaRsvwRMJtAlA==} - dev: false - /fresh@0.5.2: resolution: {integrity: sha512-zJ2mQYM18rEFOudeV4GShTGIQ7RbzA7ozbU9I/XBpm7kqgMywgmylMwXHxZJmkVoYkna9d2pVXVXPdYTP9ej8Q==} engines: {node: '>= 0.6'} dev: false - /fs-extra@10.1.0: - resolution: {integrity: sha512-oRXApq54ETRj4eMiFzGnHWGy+zo5raudjuxN0b8H7s/RU2oW0Wvsx9O0ACRN/kRq9E8Vu/ReskGB5o3ji+FzHQ==} - engines: {node: '>=12'} - dependencies: - graceful-fs: 4.2.11 - jsonfile: 6.1.0 - universalify: 2.0.0 - dev: false - - /fs-extra@9.1.0: - resolution: {integrity: sha512-hcg3ZmepS30/7BSFqRvoo3DOMQu7IjqxO5nCDt+zM9XWjb33Wg7ziNT+Qvqbuc3+gWpzO02JubVyk2G4Zvo1OQ==} - engines: {node: '>=10'} - dependencies: - at-least-node: 1.0.0 - graceful-fs: 4.2.11 - jsonfile: 6.1.0 - universalify: 2.0.0 - dev: false - - /fs-monkey@1.0.4: - resolution: {integrity: sha512-INM/fWAxMICjttnD0DX1rBvinKskj5G1w+oy/pnm9u/tSlnBrzFonJMcalKJ30P8RRsPzKcCG7Q8l0jx5Fh9YQ==} - dev: false - /fs.realpath@1.0.0: resolution: {integrity: sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==} + dev: true /fsevents@2.3.3: resolution: {integrity: sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==} @@ -6976,6 +2946,7 @@ /function-bind@1.1.1: resolution: {integrity: sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==} + dev: true /function-bind@1.1.2: resolution: {integrity: sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==} @@ -6988,6 +2959,7 @@ define-properties: 1.2.0 es-abstract: 1.22.1 functions-have-names: 1.2.3 + dev: true /function.prototype.name@1.1.6: resolution: {integrity: sha512-Z5kx79swU5P27WEayXM1tBi5Ze/lbIyiNgU3qyXUOf9b2rgXYyF9Dy9Cx+IQv/Lc8WCG6L82zwUPpSS9hGehIg==} @@ -6997,17 +2969,16 @@ define-properties: 1.2.1 es-abstract: 1.22.5 functions-have-names: 1.2.3 + dev: true /functions-have-names@1.2.3: resolution: {integrity: sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==} - - /gensync@1.0.0-beta.2: - resolution: {integrity: sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg==} - engines: {node: '>=6.9.0'} + dev: true /get-caller-file@2.0.5: resolution: {integrity: sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg==} engines: {node: 6.* || 8.* || >= 10.*} + dev: true /get-intrinsic@1.2.1: resolution: {integrity: sha512-2DcsyfABl+gVHEfCOaTrWgyt+tb6MSEGmKq+kI5HwLbIYgjgmMcV8KQ41uaKz1xxUcn9tJtgFbQUEVcEbd0FYw==} @@ -7016,6 +2987,7 @@ has: 1.0.3 has-proto: 1.0.1 has-symbols: 1.0.3 + dev: true /get-intrinsic@1.2.4: resolution: {integrity: sha512-5uYhsJH8VJBTv7oslg4BznJYhDoRI6waYCxMmCdnTrcCrHA/fCFKoTFz2JKKE0HdDFUF7/oQuhzumXJK7paBRQ==} @@ -7027,26 +2999,13 @@ has-symbols: 1.0.3 hasown: 2.0.1 - /get-own-enumerable-property-symbols@3.0.2: - resolution: {integrity: sha512-I0UBV/XOz1XkIJHEUDMZAbzCThU/H8DxmSfmdGcKPnVhu2VfFqr34jr9777IyaTYvxjedWhqVIilEDsCdP5G6g==} - dev: false - - /get-package-type@0.1.0: - resolution: {integrity: sha512-pjzuKtY64GYfWizNAJ0fr9VqttZkNiK2iS430LtIHzjBEr6bX8Am2zm4sW4Ro5wjWW5cAlRL1qAMTcXbjNAO2Q==} - engines: {node: '>=8.0.0'} - dev: false - - /get-stream@6.0.1: - resolution: {integrity: sha512-ts6Wi+2j3jQjqi70w5AlN8DFnkSwC+MqmxEzdEALB2qXZYV3X/b1CTfgPLGJNMeAWxdPfU8FO1ms3NUfaHCPYg==} - engines: {node: '>=10'} - dev: false - /get-symbol-description@1.0.0: resolution: {integrity: sha512-2EmdH1YvIQiZpltCNgkuiUnyukzxM/R6NDJX31Ke3BG1Nq5b0S2PhX59UKi9vZpPDQVdqn+1IcaAwnzTT5vCjw==} engines: {node: '>= 0.4'} dependencies: call-bind: 1.0.2 get-intrinsic: 1.2.1 + dev: true /get-symbol-description@1.0.2: resolution: {integrity: sha512-g0QYk1dZBxGwk+Ngc+ltRH2IBp2f7zBkBMBJZCDerh6EhlhSR6+9irMCuT/09zD6qkarHUSn529sK/yL4S27mg==} @@ -7055,11 +3014,13 @@ call-bind: 1.0.7 es-errors: 1.3.0 get-intrinsic: 1.2.4 + dev: true /get-tsconfig@4.7.3: resolution: {integrity: sha512-ZvkrzoUA0PQZM6fy6+/Hce561s+faD1rsNwhnO5FelNjyy7EMGJ3Rz1AQ8GYDWjhRs/7dBLOEJvhK8MiEJOAFg==} dependencies: resolve-pkg-maps: 1.0.0 + dev: true /glob-parent@5.1.2: resolution: {integrity: sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==} @@ -7072,10 +3033,7 @@ engines: {node: '>=10.13.0'} dependencies: is-glob: 4.0.3 - - /glob-to-regexp@0.4.1: - resolution: {integrity: sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw==} - dev: false + dev: true /glob@10.3.10: resolution: {integrity: sha512-fa46+tv1Ak0UPK1TOy/pZrIybNNt4HCv7SDzwyfiOZkvZLEbjsZkJBPtDHVshZjbecAoAGSC20MjLDG/qr679g==} @@ -7089,17 +3047,6 @@ path-scurry: 1.10.1 dev: true - /glob@7.1.6: - resolution: {integrity: sha512-LwaxwyZ72Lk7vZINtNNrywX0ZuLyStrdDtabefZKAY5ZGJhVtgdznluResxNmPitE0SAO+O26sWTHeKSI2wMBA==} - dependencies: - fs.realpath: 1.0.0 - inflight: 1.0.6 - inherits: 2.0.4 - minimatch: 3.1.2 - once: 1.4.0 - path-is-absolute: 1.0.1 - dev: false - /glob@7.2.3: resolution: {integrity: sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==} dependencies: @@ -7109,38 +3056,21 @@ minimatch: 3.1.2 once: 1.4.0 path-is-absolute: 1.0.1 - - /global-modules@2.0.0: - resolution: {integrity: sha512-NGbfmJBp9x8IxyJSd1P+otYK8vonoJactOogrVfFRIAEY1ukil8RSKDz2Yo7wh1oihl51l/r6W4epkeKJHqL8A==} - engines: {node: '>=6'} - dependencies: - global-prefix: 3.0.0 - dev: false - - /global-prefix@3.0.0: - resolution: {integrity: sha512-awConJSVCHVGND6x3tmMaKcQvwXLhjdkmomy2W+Goaui8YPgYgXJZewhg3fWC+DlfqqQuWg8AwqjGTD2nAPVWg==} - engines: {node: '>=6'} - dependencies: - ini: 1.3.8 - kind-of: 6.0.3 - which: 1.3.1 - dev: false - - /globals@11.12.0: - resolution: {integrity: sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==} - engines: {node: '>=4'} + dev: true /globals@13.20.0: resolution: {integrity: sha512-Qg5QtVkCy/kv3FUSlu4ukeZDVf9ee0iXLAUYX13gbR17bnejFTzr4iS9bY7kwCf1NztRNm1t91fjOiyx4CSwPQ==} engines: {node: '>=8'} dependencies: type-fest: 0.20.2 + dev: true /globalthis@1.0.3: resolution: {integrity: sha512-sFdI5LyBiNTHjRd7cGPWapiHWMOXKyuBNX/cWJ3NfzrZQVa8GI/8cofCl74AOVqq9W5kNmguTIzJ/1s2gyI9wA==} engines: {node: '>= 0.4'} dependencies: define-properties: 1.2.0 + dev: true /globby@11.1.0: resolution: {integrity: sha512-jhIXaOzy1sb8IyocaruWSn1TjmnBVs8Ayhcy83rmxNJ8q2uWKCAj3CnJY+KpGSXCueAPc0i05kVvVKtP1t9S3g==} @@ -7152,6 +3082,7 @@ ignore: 5.2.4 merge2: 1.4.1 slash: 3.0.0 + dev: true /google-protobuf@3.21.2: resolution: {integrity: sha512-3MSOYFO5U9mPGikIYCzK0SaThypfGgS6bHqrUGXG3DPHCrb+txNqeEcns1W0lkGfk0rCyNXm7xB9rMxnCiZOoA==} @@ -7167,24 +3098,11 @@ /graphemer@1.4.0: resolution: {integrity: sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==} - - /gzip-size@6.0.0: - resolution: {integrity: sha512-ax7ZYomf6jqPTQ4+XCpUGyXKHk5WweS+e05MBO4/y3WJ5RkmPXNKvX+bx1behVILVwr6JSQvZAku021CHPXG3Q==} - engines: {node: '>=10'} - dependencies: - duplexer: 0.1.2 - dev: false - - /handle-thing@2.0.1: - resolution: {integrity: sha512-9Qn4yBxelxoh2Ow62nP+Ka/kMnOXRi8BXnRaUwezLNhqelnN49xKz4F/dPP8OYLxLxq6JDtZb2i9XznUQbNPTg==} - dev: false - - /harmony-reflect@1.6.2: - resolution: {integrity: sha512-HIp/n38R9kQjDEziXyDTuW3vvoxxyxjxFzXLrBr18uB47GnSt+G9D29fqrpM5ZkspMcPICud3XsBJQ4Y2URg8g==} - dev: false + dev: true /has-bigints@1.0.2: resolution: {integrity: sha512-tSvCKtBr9lkF0Ex0aQiP9N+OpV4zi2r/Nee5VkRDbaqv35RLYMzbwQfFSZZH0kR+Rd6302UJZ2p/bJCEoR3VoQ==} + dev: true /has-flag@3.0.0: resolution: {integrity: sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw==} @@ -7193,11 +3111,13 @@ /has-flag@4.0.0: resolution: {integrity: sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==} engines: {node: '>=8'} + dev: true /has-property-descriptors@1.0.0: resolution: {integrity: sha512-62DVLZGoiEBDHQyqG4w9xCuZ7eJEwNmJRWw2VY84Oedb7WFcA27fiEVe8oUQx9hAUJ4ekurquucTGwsyO1XGdQ==} dependencies: get-intrinsic: 1.2.1 + dev: true /has-property-descriptors@1.0.2: resolution: {integrity: sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==} @@ -7211,6 +3131,7 @@ /has-proto@1.0.3: resolution: {integrity: sha512-SJ1amZAJUiZS+PhsVLf5tGydlaVB8EdFpaSO4gmiUKUOxk8qzn5AIy4ZeJUmh22znIdk/uMAUT2pl3FxzVUH+Q==} engines: {node: '>= 0.4'} + dev: true /has-symbols@1.0.3: resolution: {integrity: sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A==} @@ -7227,12 +3148,14 @@ engines: {node: '>= 0.4'} dependencies: has-symbols: 1.0.3 + dev: true /has@1.0.3: resolution: {integrity: sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==} engines: {node: '>= 0.4.0'} dependencies: function-bind: 1.1.1 + dev: true /hasown@2.0.1: resolution: {integrity: sha512-1/th4MHjnwncwXsIW6QMzlvYL9kG5e/CpVvLRZe4XPa8TOUNbCELqmvhDmnkNsAjwaG4+I8gJJL0JBvTTLO9qA==} @@ -7240,11 +3163,6 @@ dependencies: function-bind: 1.1.2 - /he@1.2.0: - resolution: {integrity: sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw==} - hasBin: true - dev: false - /helmet@6.2.0: resolution: {integrity: sha512-DWlwuXLLqbrIOltR6tFQXShj/+7Cyp0gLi6uAb8qMdFh/YBBFbKSgQ6nbXmScYd8emMctuthmgIa7tUfo9Rtyg==} engines: {node: '>=14.0.0'} @@ -7255,27 +3173,6 @@ engines: {node: '>=8'} dev: false - /hoopy@0.1.4: - resolution: {integrity: sha512-HRcs+2mr52W0K+x8RzcLzuPPmVIKMSv97RGHy0Ea9y/mpcaK+xTrjICA04KAHi4GRzxliNqNJEFYWHghy3rSfQ==} - engines: {node: '>= 6.0.0'} - dev: false - - /hpack.js@2.1.6: - resolution: {integrity: sha512-zJxVehUdMGIKsRaNt7apO2Gqp0BdqW5yaiGHXXmbpvxgBYVZnAql+BJb4RO5ad2MgpbZKn5G6nMnegrH1FcNYQ==} - dependencies: - inherits: 2.0.4 - obuf: 1.1.2 - readable-stream: 2.3.8 - wbuf: 1.7.3 - dev: false - - /html-encoding-sniffer@2.0.1: - resolution: {integrity: sha512-D5JbOMBIR/TVZkubHT+OyT2705QvogUW4IBn6nHd756OwieSF9aDYFj4dv6HHEVGYbHaLETa3WggZYWWMyy3ZQ==} - engines: {node: '>=10'} - dependencies: - whatwg-encoding: 1.0.5 - dev: false - /html-encoding-sniffer@4.0.0: resolution: {integrity: sha512-Y22oTqIU4uuPgEemfz7NDJz6OeKf12Lsu+QC+s3BVpda64lTiMYCyGwg5ki4vFxkMwQdeZDl2adZoqUgdFuTgQ==} engines: {node: '>=18'} @@ -7283,51 +3180,6 @@ whatwg-encoding: 3.1.1 dev: false - /html-entities@2.4.0: - resolution: {integrity: sha512-igBTJcNNNhvZFRtm8uA6xMY6xYleeDwn3PeBCkDz7tHttv4F2hsDI2aPgNERWzvRcNYHNT3ymRaQzllmXj4YsQ==} - dev: false - - /html-escaper@2.0.2: - resolution: {integrity: sha512-H2iMtd0I4Mt5eYiapRdIDjp+XzelXQ0tFE4JS7YFwFevXXMmOp9myNrUvCg0D6ws8iqkRPBfKHgbwig1SmlLfg==} - dev: false - - /html-minifier-terser@6.1.0: - resolution: {integrity: sha512-YXxSlJBZTP7RS3tWnQw74ooKa6L9b9i9QYXY21eUEvhZ3u9XLfv6OnFsQq6RxkhHygsaUMvYsZRV5rU/OVNZxw==} - engines: {node: '>=12'} - hasBin: true - dependencies: - camel-case: 4.1.2 - clean-css: 5.3.2 - commander: 8.3.0 - he: 1.2.0 - param-case: 3.0.4 - relateurl: 0.2.7 - terser: 5.19.0 - dev: false - - /html-webpack-plugin@5.5.3(webpack@5.88.1): - resolution: {integrity: sha512-6YrDKTuqaP/TquFH7h4srYWsZx+x6k6+FbsTm0ziCwGHDP78Unr1r9F/H4+sGmMbX08GQcJ+K64x55b+7VM/jg==} - engines: {node: '>=10.13.0'} - peerDependencies: - webpack: ^5.20.0 - dependencies: - '@types/html-minifier-terser': 6.1.0 - html-minifier-terser: 6.1.0 - lodash: 4.17.21 - pretty-error: 4.0.0 - tapable: 2.2.1 - webpack: 5.88.1 - dev: false - - /htmlparser2@6.1.0: - resolution: {integrity: sha512-gyyPk6rgonLFEDGoeRgQNaEUvdJ4ktTmmUh/h2t7s+M8oPpIPxgNACWa+6ESR57kXstwqPiCut0V8NRpcwgU7A==} - dependencies: - domelementtype: 2.3.0 - domhandler: 4.3.1 - domutils: 2.8.0 - entities: 2.2.0 - dev: false - /htmlparser2@9.1.0: resolution: {integrity: sha512-5zfg6mHUoaer/97TxnGpxmbR7zJtPwIYFMZ/H5ucTlPZhKvtum05yiPK3Mgai3a0DyVxv7qYqoweaEd2nrYQzQ==} dependencies: @@ -7345,20 +3197,6 @@ http-errors: 1.8.1 dev: false - /http-deceiver@1.2.7: - resolution: {integrity: sha512-LmpOGxTfbpgtGVxJrj5k7asXHCgNZp5nLfp+hWc8QQRqtb7fUy6kRY3BO1h9ddF6yIPYUARgxGOwB42DnxIaNw==} - dev: false - - /http-errors@1.6.3: - resolution: {integrity: sha512-lks+lVC8dgGyh97jxvxeYTWQFvh4uw4yC12gVl63Cg30sjPX4wuGcdkICVXDAESr6OJGjqGA8Iz5mkeN6zlD7A==} - engines: {node: '>= 0.6'} - dependencies: - depd: 1.1.2 - inherits: 2.0.3 - setprototypeof: 1.1.0 - statuses: 1.5.0 - dev: false - /http-errors@1.8.1: resolution: {integrity: sha512-Kpk9Sm7NmI+RHhnj6OIWDI1d6fIoFAtFt9RLaTMRlg/8w49juAStsrBgp0Dp4OdxdVbRIeKhtCUvoi/RuAhO4g==} engines: {node: '>= 0.6'} @@ -7381,21 +3219,6 @@ toidentifier: 1.0.1 dev: false - /http-parser-js@0.5.8: - resolution: {integrity: sha512-SGeBX54F94Wgu5RH3X5jsDtf4eHyRogWX1XGT3b4HuW3tQPM4AaBzoUji/4AAJNXCEOWZ5O0DgZmJw1947gD5Q==} - dev: false - - /http-proxy-agent@4.0.1: - resolution: {integrity: sha512-k0zdNgqWTGA6aeIRVpvfVob4fL52dTfaehylg0Y4UvSySvOq/Y+BOyPrgpUrA7HylqvU8vIZGsRuXmspskV0Tg==} - engines: {node: '>= 6'} - dependencies: - '@tootallnate/once': 1.1.2 - agent-base: 6.0.2 - debug: 4.3.4(supports-color@5.5.0) - transitivePeerDependencies: - - supports-color - dev: false - /http-proxy-agent@7.0.2: resolution: {integrity: sha512-T1gkAiYYDWYx3V5Bmyu7HcfcvL7mUrTWiM6yOfa3PIphViJ/gFPbvidQ+veqSOHci/PxBcDabeUNCzpOODJZig==} engines: {node: '>= 14'} @@ -7406,46 +3229,6 @@ - supports-color dev: false - /http-proxy-middleware@2.0.6(@types/express@4.17.17): - resolution: {integrity: sha512-ya/UeJ6HVBYxrgYotAZo1KvPWlgB48kUJLDePFeneHsVujFaW5WNj2NgWCAE//B1Dl02BIfYlpNgBy8Kf8Rjmw==} - engines: {node: '>=12.0.0'} - peerDependencies: - '@types/express': ^4.17.13 - peerDependenciesMeta: - '@types/express': - optional: true - dependencies: - '@types/express': 4.17.17 - '@types/http-proxy': 1.17.11 - http-proxy: 1.18.1 - is-glob: 4.0.3 - is-plain-obj: 3.0.0 - micromatch: 4.0.5 - transitivePeerDependencies: - - debug - dev: false - - /http-proxy@1.18.1: - resolution: {integrity: sha512-7mz/721AbnJwIVbnaSv1Cz3Am0ZLT/UBwkC92VlxhXv/k/BBQfM2fXElQNC27BVGr0uwUpplYPQM9LnaBMR5NQ==} - engines: {node: '>=8.0.0'} - dependencies: - eventemitter3: 4.0.7 - follow-redirects: 1.15.4 - requires-port: 1.0.0 - transitivePeerDependencies: - - debug - dev: false - - /https-proxy-agent@5.0.1: - resolution: {integrity: sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA==} - engines: {node: '>= 6'} - dependencies: - agent-base: 6.0.2 - debug: 4.3.4(supports-color@5.5.0) - transitivePeerDependencies: - - supports-color - dev: false - /https-proxy-agent@7.0.4: resolution: {integrity: sha512-wlwpilI7YdjSkWaQ/7omYBMTliDcmCN8OLihO6I9B86g06lMyAoqgoDpV0XqoaPOKj+0DIdAvnsWfyAAhmimcg==} engines: {node: '>= 14'} @@ -7456,11 +3239,6 @@ - supports-color dev: false - /human-signals@2.1.0: - resolution: {integrity: sha512-B4FFZ6q/T2jhhksgkbEW3HBvWIfDW85snkQgawt07S7J5QXTk6BkNV+0yAeZrM5QpMAdYlocGoljn0sJ/WQkFw==} - engines: {node: '>=10.17.0'} - dev: false - /iconv-lite@0.4.24: resolution: {integrity: sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==} engines: {node: '>=0.10.0'} @@ -7475,26 +3253,6 @@ safer-buffer: 2.1.2 dev: false - /icss-utils@5.1.0(postcss@8.4.26): - resolution: {integrity: sha512-soFhflCVWLfRNOPU3iv5Z9VUdT44xFRbzjLsEzSr5AQmgqPMTHdU3PMT1Cf1ssx8fLNJDA1juftYl+PUcv3MqA==} - engines: {node: ^10 || ^12 || >= 14} - peerDependencies: - postcss: ^8.1.0 - dependencies: - postcss: 8.4.26 - dev: false - - /idb@7.1.1: - resolution: {integrity: sha512-gchesWBzyvGHRO9W8tzUWFDycow5gwjvFKfyV9FF32Y7F50yZMp7mP+T2mJIWFx49zicqyC4uefHM17o6xKIVQ==} - dev: false - - /identity-obj-proxy@3.0.0: - resolution: {integrity: sha512-00n6YnVHKrinT9t0d9+5yZC6UBNJANpYEQvL2LlX6Ab9lnmxzIRcEmTPuyGScvl1+jKuCICX1Z0Ab1pPKKdikA==} - engines: {node: '>=4'} - dependencies: - harmony-reflect: 1.6.2 - dev: false - /ignore-by-default@1.0.1: resolution: {integrity: sha512-Ius2VYcGNk7T90CppJqcIkS5ooHUZyIQK+ClZfMfMNFEF9VSE73Fq+906u/CWu92x4gzZMWOwfFYckPObzdEbA==} dev: true @@ -7502,10 +3260,7 @@ /ignore@5.2.4: resolution: {integrity: sha512-MAb38BcSbH0eHNBxn7ql2NH/kX33OkB3lZ1BNdh7ENeRChHTYsTvWrMubiIAMNS2llXEEgZ1MUOBtXChP3kaFQ==} engines: {node: '>= 4'} - - /immer@9.0.21: - resolution: {integrity: sha512-bc4NBHqOqSfRW7POMkHd51LvClaeMXpm8dx0e8oE2GORbq5aRK7Bxl4FyzVLdGtLmvLKL7BTDBG5ACQm4HWjTA==} - dev: false + dev: true /immutable@4.3.1: resolution: {integrity: sha512-lj9cnmB/kVS0QHsJnYKD1uo3o39nrbKxszjnqS9Fr6NB7bZzW45U6WSGBPKXDL/CvDKqDNPA4r3DoDQ8GTxo2A==} @@ -7516,19 +3271,12 @@ dependencies: parent-module: 1.0.1 resolve-from: 4.0.0 - - /import-local@3.1.0: - resolution: {integrity: sha512-ASB07uLtnDs1o6EHjKpX34BKYDSqnFerfTOJL2HvMqF70LnxpjkzDB8J44oT9pu4AMPkQwf8jl6szgvNd2tRIg==} - engines: {node: '>=8'} - hasBin: true - dependencies: - pkg-dir: 4.2.0 - resolve-cwd: 3.0.0 - dev: false + dev: true /imurmurhash@0.1.4: resolution: {integrity: sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==} engines: {node: '>=0.8.19'} + dev: true /inflation@2.0.0: resolution: {integrity: sha512-m3xv4hJYR2oXw4o4Y5l6P5P16WYmazYof+el6Al3f+YlggGj6qT9kImBAnzDelRALnP5d3h4jGBPKzYCizjZZw==} @@ -7540,18 +3288,11 @@ dependencies: once: 1.4.0 wrappy: 1.0.2 - - /inherits@2.0.3: - resolution: {integrity: sha512-x00IRNXNy63jwGkJmzPigoySHbaqpNuzKbBOmzK+g2OdZpQ9w+sxCN+VSB3ja7IAge2OP2qpfxTjeNcyjmW1uw==} - dev: false + dev: true /inherits@2.0.4: resolution: {integrity: sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==} - /ini@1.3.8: - resolution: {integrity: sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==} - dev: false - /internal-slot@1.0.5: resolution: {integrity: sha512-Y+R5hJrzs52QCG2laLn4udYVnxsfny9CpOhNhUvk/SSSVyF6T27FzRbF0sroPidSu3X8oEAkOn2K804mjpt6UQ==} engines: {node: '>= 0.4'} @@ -7559,6 +3300,7 @@ get-intrinsic: 1.2.1 has: 1.0.3 side-channel: 1.0.4 + dev: true /internal-slot@1.0.7: resolution: {integrity: sha512-NGnrKwXzSms2qUUih/ILZ5JBqNTSa1+ZmP6flaIp6KmSElgE9qdndzS3cqjrDovwFdmwsGsLdeFgB6suw+1e9g==} @@ -7567,6 +3309,7 @@ es-errors: 1.3.0 hasown: 2.0.1 side-channel: 1.0.6 + dev: true /intl-messageformat@9.13.0: resolution: {integrity: sha512-7sGC7QnSQGa5LZP7bXLDhVDtQOeKGeBFGHF2Y8LVBwYZoQZCgWeKoPGTa5GMG8g/TzDgeXuYJQis7Ggiw2xTOw==} @@ -7576,22 +3319,13 @@ '@formatjs/icu-messageformat-parser': 2.1.0 tslib: 2.6.2 - /ipaddr.js@1.9.1: - resolution: {integrity: sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==} - engines: {node: '>= 0.10'} - dev: false - - /ipaddr.js@2.1.0: - resolution: {integrity: sha512-LlbxQ7xKzfBusov6UMi4MFpEg0m+mAm9xyNGEduwXMEDuf4WfzB/RZwMVYEd7IKGvh4IUkEXYxtAVu9T3OelJQ==} - engines: {node: '>= 10'} - dev: false - /is-array-buffer@3.0.2: resolution: {integrity: sha512-y+FyyR/w8vfIRq4eQcM1EYgSTnmHXPqaF+IgzgraytCFq5Xh8lllDVmAZolPJiZttZLeFSINPYMaEJ7/vWUa1w==} dependencies: call-bind: 1.0.2 get-intrinsic: 1.2.1 is-typed-array: 1.1.10 + dev: true /is-array-buffer@3.0.4: resolution: {integrity: sha512-wcjaerHw0ydZwfhiKbXJWLDY8A7yV7KhjQOpb83hGgGfId/aQa4TOvwyzn2PuswW2gPCYEL/nEAiSVpdOj1lXw==} @@ -7599,10 +3333,7 @@ dependencies: call-bind: 1.0.7 get-intrinsic: 1.2.4 - - /is-arrayish@0.2.1: - resolution: {integrity: sha512-zz06S8t0ozoDXMG+ube26zeCTNXcKIPJZJi8hBrF4idCLms4CG9QtK7qBl1boi5ODzFpjswb5JPmHCbMpjaYzg==} - dev: false + dev: true /is-arrayish@0.3.2: resolution: {integrity: sha512-eVRqCvVlZbuw3GrM63ovNSNAeA1K16kaR/LRY/92w0zxQ5/1YzwblUX652i4Xs9RwAGjW9d9y6X88t8OaAJfWQ==} @@ -7619,6 +3350,7 @@ resolution: {integrity: sha512-zB9CruMamjym81i2JZ3UMn54PKGsQzsJeo6xvN3HJJ4CAsQNB6iRutp2To77OfCNuoxspsIhzaPoO1zyCEhFOg==} dependencies: has-bigints: 1.0.2 + dev: true /is-binary-path@2.1.0: resolution: {integrity: sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==} @@ -7632,32 +3364,31 @@ dependencies: call-bind: 1.0.2 has-tostringtag: 1.0.0 + dev: true /is-callable@1.2.7: resolution: {integrity: sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==} engines: {node: '>= 0.4'} + dev: true /is-core-module@2.12.1: resolution: {integrity: sha512-Q4ZuBAe2FUsKtyQJoQHlvP8OvBERxO3jEmy1I7hcRXcJBGGHFh/aJBswbXuS9sgrDH2QUO8ilkwNPHvHMd8clg==} dependencies: has: 1.0.3 + dev: true /is-core-module@2.13.1: resolution: {integrity: sha512-hHrIjvZsftOsvKSn2TRYl63zvxsgE0K+0mYMoH6gD4omR5IWB2KynivBQczo3+wF1cCkjzvptnI9Q0sPU66ilw==} dependencies: hasown: 2.0.1 + dev: true /is-date-object@1.0.5: resolution: {integrity: sha512-9YQaSxsAiSwcvS33MBk3wTCVnWK+HhF8VZR2jRxehM16QcVOdHqPn4VPHmRK4lSr38n9JriurInLcP90xsYNfQ==} engines: {node: '>= 0.4'} dependencies: has-tostringtag: 1.0.0 - - /is-docker@2.2.1: - resolution: {integrity: sha512-F+i2BKsFrH66iaUFc0woD8sLy8getkwTwtOBjvs56Cx4CgJDeKQeqfz8wAYiSb8JOprWhHH5p77PbmYCvvUuXQ==} - engines: {node: '>=8'} - hasBin: true - dev: false + dev: true /is-extglob@2.1.1: resolution: {integrity: sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==} @@ -7672,11 +3403,7 @@ /is-fullwidth-code-point@3.0.0: resolution: {integrity: sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==} engines: {node: '>=8'} - - /is-generator-fn@2.1.0: - resolution: {integrity: sha512-cTIB4yPYL/Grw0EaSzASzg6bBy9gqCofvWN8okThAYIxKJZC+udlRAmGbM0XLeniEJSs8uEgHPGuHSe1XsOLSQ==} - engines: {node: '>=6'} - dev: false + dev: true /is-generator-function@1.0.10: resolution: {integrity: sha512-jsEjy9l3yiXEQ+PsXdmBwEPcOxaXWLspKdplFUVI9vq1iZgIekeC0L167qeu86czQaxed3q/Uzuw0swL0irL8A==} @@ -7695,41 +3422,31 @@ engines: {node: '>= 0.4'} dev: true - /is-module@1.0.0: - resolution: {integrity: sha512-51ypPSPCoTEIN9dy5Oy+h4pShgJmPCygKfyRCISBI+JoWT/2oJvK8QPxmwv7b/p239jXrm9M1mlQbyKJ5A152g==} - dev: false - /is-negative-zero@2.0.2: resolution: {integrity: sha512-dqJvarLawXsFbNDeJW7zAz8ItJ9cd28YufuuFzh0G8pNHjJMnY08Dv7sYX2uF5UpQOwieAeOExEYAWWfu7ZZUA==} engines: {node: '>= 0.4'} + dev: true /is-negative-zero@2.0.3: resolution: {integrity: sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw==} engines: {node: '>= 0.4'} + dev: true /is-number-object@1.0.7: resolution: {integrity: sha512-k1U0IRzLMo7ZlYIfzRu23Oh6MiIFasgpb9X76eqfFZAqwH44UI4KTBvBYIZ1dSL9ZzChTB9ShHfLkR4pdW5krQ==} engines: {node: '>= 0.4'} dependencies: has-tostringtag: 1.0.0 + dev: true /is-number@7.0.0: resolution: {integrity: sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==} engines: {node: '>=0.12.0'} - /is-obj@1.0.1: - resolution: {integrity: sha512-l4RyHgRqGN4Y3+9JHVrNqO+tN0rV5My76uW5/nuO4K1b6vw5G8d/cmFjP9tRfEsdhZNt0IFdZuK/c2Vr4Nb+Qg==} - engines: {node: '>=0.10.0'} - dev: false - /is-path-inside@3.0.3: resolution: {integrity: sha512-Fd4gABb+ycGAmKou8eMftCupSir5lRxqf4aD/vd0cD2qc4HL07OjCeuHMr8Ro4CoMaeCKDB0/ECBOVWjTwUvPQ==} engines: {node: '>=8'} - - /is-plain-obj@3.0.0: - resolution: {integrity: sha512-gwsOE28k+23GP1B6vFl1oVh/WOzmawBrKwo5Ev6wMKzPkaXaCDIQKzLnvsA42DRlbVTWorkgTKIviAKCWkfUwA==} - engines: {node: '>=10'} - dev: false + dev: true /is-potential-custom-element-name@1.0.1: resolution: {integrity: sha512-bCYeRA2rVibKZd+s2625gGnGF/t7DSqDs4dP7CrLA1m7jKWz6pps0LpYLJN8Q64HtmPKJ1hrN3nzPNKFEKOUiQ==} @@ -7741,16 +3458,7 @@ dependencies: call-bind: 1.0.2 has-tostringtag: 1.0.0 - - /is-regexp@1.0.0: - resolution: {integrity: sha512-7zjFAPO4/gwyQAAgRRmqeEeyIICSdmCqa3tsVHMdBzaXXRiqopZL4Cyghg/XulGWrtABTpbnYYzzIRffLkP4oA==} - engines: {node: '>=0.10.0'} - dev: false - - /is-root@2.1.0: - resolution: {integrity: sha512-AGOriNp96vNBd3HtU+RzFEc75FfR5ymiYv8E553I71SCeXBiMsVDUtdio1OEFvrPyLIQ9tVR5RxXIFe5PUFjMg==} - engines: {node: '>=6'} - dev: false + dev: true /is-set@2.0.3: resolution: {integrity: sha512-iPAjerrse27/ygGLxw+EBR9agv9Y6uLeYVJMu+QNCoouJ1/1ri0mGrcWpfCqFZuzzx3WjtwxG098X+n4OuRkPg==} @@ -7761,12 +3469,14 @@ resolution: {integrity: sha512-sqN2UDu1/0y6uvXyStCOzyhAjCSlHceFoMKJW8W9EU9cvic/QdsZ0kEU93HEy3IUEFZIiH/3w+AH/UQbPHNdhA==} dependencies: call-bind: 1.0.2 + dev: true /is-shared-array-buffer@1.0.3: resolution: {integrity: sha512-nA2hv5XIhLR3uVzDDfCIknerhx8XUKnstuOERPNNIinXG7v9u+ohXF67vxm4TPTEPU6lm61ZkwP3c9PCB97rhg==} engines: {node: '>= 0.4'} dependencies: call-bind: 1.0.7 + dev: true /is-stream@2.0.1: resolution: {integrity: sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==} @@ -7778,12 +3488,14 @@ engines: {node: '>= 0.4'} dependencies: has-tostringtag: 1.0.0 + dev: true /is-symbol@1.0.4: resolution: {integrity: sha512-C/CPBqKWnvdcxqIARxyOh4v1UUEOCHpgDa0WYgpKDFMszcrPcffg5uhwSgPCLD2WWxmq6isisz87tzT01tuGhg==} engines: {node: '>= 0.4'} dependencies: has-symbols: 1.0.3 + dev: true /is-typed-array@1.1.10: resolution: {integrity: sha512-PJqgEHiWZvMpaFZ3uTc8kHPM4+4ADTlDniuQL7cU/UDA0Ql7F70yGfHph3cLNe+c9toaigv+DFzTJKhc2CtO6A==} @@ -7794,16 +3506,14 @@ for-each: 0.3.3 gopd: 1.0.1 has-tostringtag: 1.0.0 + dev: true /is-typed-array@1.1.13: resolution: {integrity: sha512-uZ25/bUAlUY5fR4OKT4rZQEBrzQWYV9ZJYGGsUmEJ6thodVJ1HX64ePQ6Z0qPWP+m+Uq6e9UugrE38jeYsDSMw==} engines: {node: '>= 0.4'} dependencies: which-typed-array: 1.1.15 - - /is-typedarray@1.0.0: - resolution: {integrity: sha512-cyA56iCMHAh5CdzjJIa4aohJyeO1YbwLi3Jc35MmRU6poroFjIGZzUzupGiRPOjgHg9TLu43xbpwXk523fMxKA==} - dev: false + dev: true /is-weakmap@2.0.2: resolution: {integrity: sha512-K5pXYOm9wqY1RgjpL3YTkF39tni1XajUIkawTLUo9EZEVUFga5gSQJF8nNS7ZwJQ02y+1YCNYcMh+HIf1ZqE+w==} @@ -7814,6 +3524,7 @@ resolution: {integrity: sha512-qctsuLZmIQ0+vSSMfoVvyFe2+GSEvnmZ2ezTup1SBse9+twCCeial6EEi3Nc2KFcf6+qz2FBPnjXsk8xhKSaPQ==} dependencies: call-bind: 1.0.2 + dev: true /is-weakset@2.0.3: resolution: {integrity: sha512-LvIm3/KWzS9oRFHugab7d+M/GcBXuXX5xZkzPmN+NxihdQlZUQ4dWuSV1xR/sq6upL1TJEDrfBgRepHFdBtSNQ==} @@ -7823,22 +3534,13 @@ get-intrinsic: 1.2.4 dev: true - /is-wsl@2.2.0: - resolution: {integrity: sha512-fKzAra0rGJUUBwGBgNkHZuToZcn+TtXHpeCgmkMJMMYx1sQDYaCSyjJBSCa2nH1DGm7s3n1oBnohoVTBaN7Lww==} - engines: {node: '>=8'} - dependencies: - is-docker: 2.2.1 - dev: false - - /isarray@1.0.0: - resolution: {integrity: sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==} - dev: false - /isarray@2.0.5: resolution: {integrity: sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==} + dev: true /isexe@2.0.0: resolution: {integrity: sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==} + dev: true /isomorphic-dompurify@2.4.0: resolution: {integrity: sha512-OW3VSGrjppnbshcHz7RNKnoYlCJkyBBJzEE5yxrTSA+kOl9JPTIrXsnIgOuH4wdLqqRujx22bz/IXebGWPLMAg==} @@ -7854,52 +3556,6 @@ - utf-8-validate dev: false - /istanbul-lib-coverage@3.2.0: - resolution: {integrity: sha512-eOeJ5BHCmHYvQK7xt9GkdHuzuCGS1Y6g9Gvnx3Ym33fz/HpLRYxiS0wHNr+m/MBC8B647Xt608vCDEvhl9c6Mw==} - engines: {node: '>=8'} - dev: false - - /istanbul-lib-instrument@5.2.1: - resolution: {integrity: sha512-pzqtp31nLv/XFOzXGuvhCb8qhjmTVo5vjVk19XE4CRlSWz0KoeJ3bw9XsA7nOp9YBf4qHjwBxkDzKcME/J29Yg==} - engines: {node: '>=8'} - dependencies: - '@babel/core': 7.22.9 - '@babel/parser': 7.22.7 - '@istanbuljs/schema': 0.1.3 - istanbul-lib-coverage: 3.2.0 - semver: 6.3.1 - transitivePeerDependencies: - - supports-color - dev: false - - /istanbul-lib-report@3.0.0: - resolution: {integrity: sha512-wcdi+uAKzfiGT2abPpKZ0hSU1rGQjUQnLvtY5MpQ7QCTahD3VODhcu4wcfY1YtkGaDD5yuydOLINXsfbus9ROw==} - engines: {node: '>=8'} - dependencies: - istanbul-lib-coverage: 3.2.0 - make-dir: 3.1.0 - supports-color: 7.2.0 - dev: false - - /istanbul-lib-source-maps@4.0.1: - resolution: {integrity: sha512-n3s8EwkdFIJCG3BPKBYvskgXGoy88ARzvegkitk60NxRdwltLOTaH7CUiMRXvwYorl0Q712iEjcWB+fK/MrWVw==} - engines: {node: '>=10'} - dependencies: - debug: 4.3.4(supports-color@5.5.0) - istanbul-lib-coverage: 3.2.0 - source-map: 0.6.1 - transitivePeerDependencies: - - supports-color - dev: false - - /istanbul-reports@3.1.5: - resolution: {integrity: sha512-nUsEMa9pBt/NOHqbcbeJEgqIlY/K7rVWUX6Lql2orY5e9roQOthbR3vtY4zzf2orPELg80fnxxk9zUyPlgwD1w==} - engines: {node: '>=8'} - dependencies: - html-escaper: 2.0.2 - istanbul-lib-report: 3.0.0 - dev: false - /iterator.prototype@1.1.2: resolution: {integrity: sha512-DR33HMMr8EzwuRL8Y9D3u2BMj8+RqSE850jfGu59kS7tbmPLzGkZmVSfyCFSDxuZiEY6Rzt3T2NA/qU+NwVj1w==} dependencies: @@ -7919,133 +3575,6 @@ '@pkgjs/parseargs': 0.11.0 dev: true - /jake@10.8.7: - resolution: {integrity: sha512-ZDi3aP+fG/LchyBzUM804VjddnwfSfsdeYkwt8NcbKRvo4rFkjhs456iLFn3k2ZUWvNe4i48WACDbza8fhq2+w==} - engines: {node: '>=10'} - hasBin: true - dependencies: - async: 3.2.4 - chalk: 4.1.2 - filelist: 1.0.4 - minimatch: 3.1.2 - dev: false - - /jest-changed-files@27.5.1: - resolution: {integrity: sha512-buBLMiByfWGCoMsLLzGUUSpAmIAGnbR2KJoMN10ziLhOLvP4e0SlypHnAel8iqQXTrcbmfEY9sSqae5sgUsTvw==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/types': 27.5.1 - execa: 5.1.1 - throat: 6.0.2 - dev: false - - /jest-circus@27.5.1: - resolution: {integrity: sha512-D95R7x5UtlMA5iBYsOHFFbMD/GVA4R/Kdq15f7xYWUfWHBto9NYRsOvnSauTgdF+ogCpJ4tyKOXhUifxS65gdw==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/environment': 27.5.1 - '@jest/test-result': 27.5.1 - '@jest/types': 27.5.1 - '@types/node': 20.11.27 - chalk: 4.1.2 - co: 4.6.0 - dedent: 0.7.0 - expect: 27.5.1 - is-generator-fn: 2.1.0 - jest-each: 27.5.1 - jest-matcher-utils: 27.5.1 - jest-message-util: 27.5.1 - jest-runtime: 27.5.1 - jest-snapshot: 27.5.1 - jest-util: 27.5.1 - pretty-format: 27.5.1 - slash: 3.0.0 - stack-utils: 2.0.6 - throat: 6.0.2 - transitivePeerDependencies: - - supports-color - dev: false - - /jest-cli@27.5.1: - resolution: {integrity: sha512-Hc6HOOwYq4/74/c62dEE3r5elx8wjYqxY0r0G/nFrLDPMFRu6RA/u8qINOIkvhxG7mMQ5EJsOGfRpI8L6eFUVw==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - hasBin: true - peerDependencies: - node-notifier: ^8.0.1 || ^9.0.0 || ^10.0.0 - peerDependenciesMeta: - node-notifier: - optional: true - dependencies: - '@jest/core': 27.5.1 - '@jest/test-result': 27.5.1 - '@jest/types': 27.5.1 - chalk: 4.1.2 - exit: 0.1.2 - graceful-fs: 4.2.11 - import-local: 3.1.0 - jest-config: 27.5.1 - jest-util: 27.5.1 - jest-validate: 27.5.1 - prompts: 2.4.2 - yargs: 16.2.0 - transitivePeerDependencies: - - bufferutil - - canvas - - supports-color - - ts-node - - utf-8-validate - dev: false - - /jest-config@27.5.1: - resolution: {integrity: sha512-5sAsjm6tGdsVbW9ahcChPAFCk4IlkQUknH5AvKjuLTSlcO/wCZKyFdn7Rg0EkC+OGgWODEy2hDpWB1PgzH0JNA==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - peerDependencies: - ts-node: '>=9.0.0' - peerDependenciesMeta: - ts-node: - optional: true - dependencies: - '@babel/core': 7.22.9 - '@jest/test-sequencer': 27.5.1 - '@jest/types': 27.5.1 - babel-jest: 27.5.1(@babel/core@7.22.9) - chalk: 4.1.2 - ci-info: 3.8.0 - deepmerge: 4.3.1 - glob: 7.2.3 - graceful-fs: 4.2.11 - jest-circus: 27.5.1 - jest-environment-jsdom: 27.5.1 - jest-environment-node: 27.5.1 - jest-get-type: 27.5.1 - jest-jasmine2: 27.5.1 - jest-regex-util: 27.5.1 - jest-resolve: 27.5.1 - jest-runner: 27.5.1 - jest-util: 27.5.1 - jest-validate: 27.5.1 - micromatch: 4.0.5 - parse-json: 5.2.0 - pretty-format: 27.5.1 - slash: 3.0.0 - strip-json-comments: 3.1.1 - transitivePeerDependencies: - - bufferutil - - canvas - - supports-color - - utf-8-validate - dev: false - - /jest-diff@27.5.1: - resolution: {integrity: sha512-m0NvkX55LDt9T4mctTEgnZk3fmEg3NRYutvMPWM/0iPnkFj2wIeF45O1718cMSOFO1vINkqmxqD8vE37uTEbqw==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - chalk: 4.1.2 - diff-sequences: 27.5.1 - jest-get-type: 27.5.1 - pretty-format: 27.5.1 - dev: false - /jest-diff@29.6.1: resolution: {integrity: sha512-FsNCvinvl8oVxpNLttNQX7FAq7vR+gMDGj90tiP7siWw1UdakWUGqrylpsYrpvj908IYckm5Y0Q7azNAozU1Kg==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} @@ -8056,127 +3585,11 @@ pretty-format: 29.6.1 dev: true - /jest-docblock@27.5.1: - resolution: {integrity: sha512-rl7hlABeTsRYxKiUfpHrQrG4e2obOiTQWfMEH3PxPjOtdsfLQO4ReWSZaQ7DETm4xu07rl4q/h4zcKXyU0/OzQ==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - detect-newline: 3.1.0 - dev: false - - /jest-each@27.5.1: - resolution: {integrity: sha512-1Ff6p+FbhT/bXQnEouYy00bkNSY7OUpfIcmdl8vZ31A1UUaurOLPA8a8BbJOF2RDUElwJhmeaV7LnagI+5UwNQ==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/types': 27.5.1 - chalk: 4.1.2 - jest-get-type: 27.5.1 - jest-util: 27.5.1 - pretty-format: 27.5.1 - dev: false - - /jest-environment-jsdom@27.5.1: - resolution: {integrity: sha512-TFBvkTC1Hnnnrka/fUb56atfDtJ9VMZ94JkjTbggl1PEpwrYtUBKMezB3inLmWqQsXYLcMwNoDQwoBTAvFfsfw==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/environment': 27.5.1 - '@jest/fake-timers': 27.5.1 - '@jest/types': 27.5.1 - '@types/node': 20.11.27 - jest-mock: 27.5.1 - jest-util: 27.5.1 - jsdom: 16.7.0 - transitivePeerDependencies: - - bufferutil - - canvas - - supports-color - - utf-8-validate - dev: false - - /jest-environment-node@27.5.1: - resolution: {integrity: sha512-Jt4ZUnxdOsTGwSRAfKEnE6BcwsSPNOijjwifq5sDFSA2kesnXTvNqKHYgM0hDq3549Uf/KzdXNYn4wMZJPlFLw==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/environment': 27.5.1 - '@jest/fake-timers': 27.5.1 - '@jest/types': 27.5.1 - '@types/node': 20.11.27 - jest-mock: 27.5.1 - jest-util: 27.5.1 - dev: false - - /jest-get-type@27.5.1: - resolution: {integrity: sha512-2KY95ksYSaK7DMBWQn6dQz3kqAf3BB64y2udeG+hv4KfSOb9qwcYQstTJc1KCbsix+wLZWZYN8t7nwX3GOBLRw==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dev: false - /jest-get-type@29.4.3: resolution: {integrity: sha512-J5Xez4nRRMjk8emnTpWrlkyb9pfRQQanDrvWHhsR1+VUfbwxi30eVcZFlcdGInRibU4G5LwHXpI7IRHU0CY+gg==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} dev: true - /jest-haste-map@27.5.1: - resolution: {integrity: sha512-7GgkZ4Fw4NFbMSDSpZwXeBiIbx+t/46nJ2QitkOjvwPYyZmqttu2TDSimMHP1EkPOi4xUZAN1doE5Vd25H4Jng==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/types': 27.5.1 - '@types/graceful-fs': 4.1.6 - '@types/node': 20.11.27 - anymatch: 3.1.3 - fb-watchman: 2.0.2 - graceful-fs: 4.2.11 - jest-regex-util: 27.5.1 - jest-serializer: 27.5.1 - jest-util: 27.5.1 - jest-worker: 27.5.1 - micromatch: 4.0.5 - walker: 1.0.8 - optionalDependencies: - fsevents: 2.3.3 - dev: false - - /jest-jasmine2@27.5.1: - resolution: {integrity: sha512-jtq7VVyG8SqAorDpApwiJJImd0V2wv1xzdheGHRGyuT7gZm6gG47QEskOlzsN1PG/6WNaCo5pmwMHDf3AkG2pQ==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/environment': 27.5.1 - '@jest/source-map': 27.5.1 - '@jest/test-result': 27.5.1 - '@jest/types': 27.5.1 - '@types/node': 20.11.27 - chalk: 4.1.2 - co: 4.6.0 - expect: 27.5.1 - is-generator-fn: 2.1.0 - jest-each: 27.5.1 - jest-matcher-utils: 27.5.1 - jest-message-util: 27.5.1 - jest-runtime: 27.5.1 - jest-snapshot: 27.5.1 - jest-util: 27.5.1 - pretty-format: 27.5.1 - throat: 6.0.2 - transitivePeerDependencies: - - supports-color - dev: false - - /jest-leak-detector@27.5.1: - resolution: {integrity: sha512-POXfWAMvfU6WMUXftV4HolnJfnPOGEu10fscNCA76KBpRRhcMN2c8d3iT2pxQS3HLbA+5X4sOUPzYO2NUyIlHQ==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - jest-get-type: 27.5.1 - pretty-format: 27.5.1 - dev: false - - /jest-matcher-utils@27.5.1: - resolution: {integrity: sha512-z2uTx/T6LBaCoNWNFWwChLBKYxTMcGBRjAt+2SbP929/Fflb9aa5LGma654Rz8z9HLxsrUaYzxE9T/EFIL/PAw==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - chalk: 4.1.2 - jest-diff: 27.5.1 - jest-get-type: 27.5.1 - pretty-format: 27.5.1 - dev: false - /jest-matcher-utils@29.6.1: resolution: {integrity: sha512-SLaztw9d2mfQQKHmJXKM0HCbl2PPVld/t9Xa6P9sgiExijviSp7TnZZpw2Fpt+OI3nwUO/slJbOfzfUMKKC5QA==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} @@ -8187,36 +3600,6 @@ pretty-format: 29.6.1 dev: true - /jest-message-util@27.5.1: - resolution: {integrity: sha512-rMyFe1+jnyAAf+NHwTclDz0eAaLkVDdKVHHBFWsBWHnnh5YeJMNWWsv7AbFYXfK3oTqvL7VTWkhNLu1jX24D+g==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@babel/code-frame': 7.22.5 - '@jest/types': 27.5.1 - '@types/stack-utils': 2.0.1 - chalk: 4.1.2 - graceful-fs: 4.2.11 - micromatch: 4.0.5 - pretty-format: 27.5.1 - slash: 3.0.0 - stack-utils: 2.0.6 - dev: false - - /jest-message-util@28.1.3: - resolution: {integrity: sha512-PFdn9Iewbt575zKPf1286Ht9EPoJmYT7P0kY+RibeYZ2XtOr53pDLEFoTWXbd1h4JiGiWpTBC84fc8xMXQMb7g==} - engines: {node: ^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0} - dependencies: - '@babel/code-frame': 7.22.5 - '@jest/types': 28.1.3 - '@types/stack-utils': 2.0.1 - chalk: 4.1.2 - graceful-fs: 4.2.11 - micromatch: 4.0.5 - pretty-format: 28.1.3 - slash: 3.0.0 - stack-utils: 2.0.6 - dev: false - /jest-message-util@29.6.1: resolution: {integrity: sha512-KoAW2zAmNSd3Gk88uJ56qXUWbFk787QKmjjJVOjtGFmmGSZgDBrlIL4AfQw1xyMYPNVD7dNInfIbur9B2rd/wQ==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} @@ -8232,187 +3615,6 @@ stack-utils: 2.0.6 dev: true - /jest-mock@27.5.1: - resolution: {integrity: sha512-K4jKbY1d4ENhbrG2zuPWaQBvDly+iZ2yAW+T1fATN78hc0sInwn7wZB8XtlNnvHug5RMwV897Xm4LqmPM4e2Og==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/types': 27.5.1 - '@types/node': 20.11.27 - dev: false - - /jest-pnp-resolver@1.2.3(jest-resolve@27.5.1): - resolution: {integrity: sha512-+3NpwQEnRoIBtx4fyhblQDPgJI0H1IEIkX7ShLUjPGA7TtUTvI1oiKi3SR4oBR0hQhQR80l4WAe5RrXBwWMA8w==} - engines: {node: '>=6'} - peerDependencies: - jest-resolve: '*' - peerDependenciesMeta: - jest-resolve: - optional: true - dependencies: - jest-resolve: 27.5.1 - dev: false - - /jest-regex-util@27.5.1: - resolution: {integrity: sha512-4bfKq2zie+x16okqDXjXn9ql2B0dScQu+vcwe4TvFVhkVyuWLqpZrZtXxLLWoXYgn0E87I6r6GRYHF7wFZBUvg==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dev: false - - /jest-regex-util@28.0.2: - resolution: {integrity: sha512-4s0IgyNIy0y9FK+cjoVYoxamT7Zeo7MhzqRGx7YDYmaQn1wucY9rotiGkBzzcMXTtjrCAP/f7f+E0F7+fxPNdw==} - engines: {node: ^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0} - dev: false - - /jest-resolve-dependencies@27.5.1: - resolution: {integrity: sha512-QQOOdY4PE39iawDn5rzbIePNigfe5B9Z91GDD1ae/xNDlu9kaat8QQ5EKnNmVWPV54hUdxCVwwj6YMgR2O7IOg==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/types': 27.5.1 - jest-regex-util: 27.5.1 - jest-snapshot: 27.5.1 - transitivePeerDependencies: - - supports-color - dev: false - - /jest-resolve@27.5.1: - resolution: {integrity: sha512-FFDy8/9E6CV83IMbDpcjOhumAQPDyETnU2KZ1O98DwTnz8AOBsW/Xv3GySr1mOZdItLR+zDZ7I/UdTFbgSOVCw==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/types': 27.5.1 - chalk: 4.1.2 - graceful-fs: 4.2.11 - jest-haste-map: 27.5.1 - jest-pnp-resolver: 1.2.3(jest-resolve@27.5.1) - jest-util: 27.5.1 - jest-validate: 27.5.1 - resolve: 1.22.2 - resolve.exports: 1.1.1 - slash: 3.0.0 - dev: false - - /jest-runner@27.5.1: - resolution: {integrity: sha512-g4NPsM4mFCOwFKXO4p/H/kWGdJp9V8kURY2lX8Me2drgXqG7rrZAx5kv+5H7wtt/cdFIjhqYx1HrlqWHaOvDaQ==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/console': 27.5.1 - '@jest/environment': 27.5.1 - '@jest/test-result': 27.5.1 - '@jest/transform': 27.5.1 - '@jest/types': 27.5.1 - '@types/node': 20.11.27 - chalk: 4.1.2 - emittery: 0.8.1 - graceful-fs: 4.2.11 - jest-docblock: 27.5.1 - jest-environment-jsdom: 27.5.1 - jest-environment-node: 27.5.1 - jest-haste-map: 27.5.1 - jest-leak-detector: 27.5.1 - jest-message-util: 27.5.1 - jest-resolve: 27.5.1 - jest-runtime: 27.5.1 - jest-util: 27.5.1 - jest-worker: 27.5.1 - source-map-support: 0.5.21 - throat: 6.0.2 - transitivePeerDependencies: - - bufferutil - - canvas - - supports-color - - utf-8-validate - dev: false - - /jest-runtime@27.5.1: - resolution: {integrity: sha512-o7gxw3Gf+H2IGt8fv0RiyE1+r83FJBRruoA+FXrlHw6xEyBsU8ugA6IPfTdVyA0w8HClpbK+DGJxH59UrNMx8A==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/environment': 27.5.1 - '@jest/fake-timers': 27.5.1 - '@jest/globals': 27.5.1 - '@jest/source-map': 27.5.1 - '@jest/test-result': 27.5.1 - '@jest/transform': 27.5.1 - '@jest/types': 27.5.1 - chalk: 4.1.2 - cjs-module-lexer: 1.2.3 - collect-v8-coverage: 1.0.2 - execa: 5.1.1 - glob: 7.2.3 - graceful-fs: 4.2.11 - jest-haste-map: 27.5.1 - jest-message-util: 27.5.1 - jest-mock: 27.5.1 - jest-regex-util: 27.5.1 - jest-resolve: 27.5.1 - jest-snapshot: 27.5.1 - jest-util: 27.5.1 - slash: 3.0.0 - strip-bom: 4.0.0 - transitivePeerDependencies: - - supports-color - dev: false - - /jest-serializer@27.5.1: - resolution: {integrity: sha512-jZCyo6iIxO1aqUxpuBlwTDMkzOAJS4a3eYz3YzgxxVQFwLeSA7Jfq5cbqCY+JLvTDrWirgusI/0KwxKMgrdf7w==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@types/node': 20.11.27 - graceful-fs: 4.2.11 - dev: false - - /jest-snapshot@27.5.1: - resolution: {integrity: sha512-yYykXI5a0I31xX67mgeLw1DZ0bJB+gpq5IpSuCAoyDi0+BhgU/RIrL+RTzDmkNTchvDFWKP8lp+w/42Z3us5sA==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@babel/core': 7.22.9 - '@babel/generator': 7.22.9 - '@babel/plugin-syntax-typescript': 7.22.5(@babel/core@7.22.9) - '@babel/traverse': 7.22.8 - '@babel/types': 7.22.5 - '@jest/transform': 27.5.1 - '@jest/types': 27.5.1 - '@types/babel__traverse': 7.20.1 - '@types/prettier': 2.7.3 - babel-preset-current-node-syntax: 1.0.1(@babel/core@7.22.9) - chalk: 4.1.2 - expect: 27.5.1 - graceful-fs: 4.2.11 - jest-diff: 27.5.1 - jest-get-type: 27.5.1 - jest-haste-map: 27.5.1 - jest-matcher-utils: 27.5.1 - jest-message-util: 27.5.1 - jest-util: 27.5.1 - natural-compare: 1.4.0 - pretty-format: 27.5.1 - semver: 7.5.4 - transitivePeerDependencies: - - supports-color - dev: false - - /jest-util@27.5.1: - resolution: {integrity: sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/types': 27.5.1 - '@types/node': 20.11.27 - chalk: 4.1.2 - ci-info: 3.8.0 - graceful-fs: 4.2.11 - picomatch: 2.3.1 - dev: false - - /jest-util@28.1.3: - resolution: {integrity: sha512-XdqfpHwpcSRko/C35uLYFM2emRAltIIKZiJ9eAmhjsj0CqZMa0p1ib0R5fWIqGhn1a103DebTbpqIaP1qCQ6tQ==} - engines: {node: ^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0} - dependencies: - '@jest/types': 28.1.3 - '@types/node': 20.11.27 - chalk: 4.1.2 - ci-info: 3.8.0 - graceful-fs: 4.2.11 - picomatch: 2.3.1 - dev: false - /jest-util@29.6.1: resolution: {integrity: sha512-NRFCcjc+/uO3ijUVyNOQJluf8PtGCe/W6cix36+M3cTFgiYqFOOW5MgN4JOOcvbUhcKTYVd1CvHz/LWi8d16Mg==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} @@ -8425,172 +3627,15 @@ picomatch: 2.3.1 dev: true - /jest-validate@27.5.1: - resolution: {integrity: sha512-thkNli0LYTmOI1tDB3FI1S1RTp/Bqyd9pTarJwL87OIBFuqEb5Apv5EaApEudYg4g86e3CT6kM0RowkhtEnCBQ==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/types': 27.5.1 - camelcase: 6.3.0 - chalk: 4.1.2 - jest-get-type: 27.5.1 - leven: 3.1.0 - pretty-format: 27.5.1 - dev: false - - /jest-watch-typeahead@1.1.0(jest@27.5.1): - resolution: {integrity: sha512-Va5nLSJTN7YFtC2jd+7wsoe1pNe5K4ShLux/E5iHEwlB9AxaxmggY7to9KUqKojhaJw3aXqt5WAb4jGPOolpEw==} - engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} - peerDependencies: - jest: ^27.0.0 || ^28.0.0 - dependencies: - ansi-escapes: 4.3.2 - chalk: 4.1.2 - jest: 27.5.1 - jest-regex-util: 28.0.2 - jest-watcher: 28.1.3 - slash: 4.0.0 - string-length: 5.0.1 - strip-ansi: 7.1.0 - dev: false - - /jest-watcher@27.5.1: - resolution: {integrity: sha512-z676SuD6Z8o8qbmEGhoEUFOM1+jfEiL3DXHK/xgEiG2EyNYfFG60jluWcupY6dATjfEsKQuibReS1djInQnoVw==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - '@jest/test-result': 27.5.1 - '@jest/types': 27.5.1 - '@types/node': 20.11.27 - ansi-escapes: 4.3.2 - chalk: 4.1.2 - jest-util: 27.5.1 - string-length: 4.0.2 - dev: false - - /jest-watcher@28.1.3: - resolution: {integrity: sha512-t4qcqj9hze+jviFPUN3YAtAEeFnr/azITXQEMARf5cMwKY2SMBRnCQTXLixTl20OR6mLh9KLMrgVJgJISym+1g==} - engines: {node: ^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0} - dependencies: - '@jest/test-result': 28.1.3 - '@jest/types': 28.1.3 - '@types/node': 20.11.27 - ansi-escapes: 4.3.2 - chalk: 4.1.2 - emittery: 0.10.2 - jest-util: 28.1.3 - string-length: 4.0.2 - dev: false - - /jest-worker@26.6.2: - resolution: {integrity: sha512-KWYVV1c4i+jbMpaBC+U++4Va0cp8OisU185o73T1vo99hqi7w8tSJfUXYswwqqrjzwxa6KpRK54WhPvwf5w6PQ==} - engines: {node: '>= 10.13.0'} - dependencies: - '@types/node': 20.11.27 - merge-stream: 2.0.0 - supports-color: 7.2.0 - dev: false - - /jest-worker@27.5.1: - resolution: {integrity: sha512-7vuh85V5cdDofPyxn58nrPjBktZo0u9x1g8WtjQol+jZDaE+fhN+cIvTj11GndBnMnyfrUOG1sZQxCdjKh+DKg==} - engines: {node: '>= 10.13.0'} - dependencies: - '@types/node': 20.11.27 - merge-stream: 2.0.0 - supports-color: 8.1.1 - dev: false - - /jest-worker@28.1.3: - resolution: {integrity: sha512-CqRA220YV/6jCo8VWvAt1KKx6eek1VIHMPeLEbpcfSfkEeWyBNppynM/o6q+Wmw+sOhos2ml34wZbSX3G13//g==} - engines: {node: ^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0} - dependencies: - '@types/node': 20.11.27 - merge-stream: 2.0.0 - supports-color: 8.1.1 - dev: false - - /jest@27.5.1: - resolution: {integrity: sha512-Yn0mADZB89zTtjkPJEXwrac3LHudkQMR+Paqa8uxJHCBr9agxztUifWCyiYrjhMPBoUVBjyny0I7XH6ozDr7QQ==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - hasBin: true - peerDependencies: - node-notifier: ^8.0.1 || ^9.0.0 || ^10.0.0 - peerDependenciesMeta: - node-notifier: - optional: true - dependencies: - '@jest/core': 27.5.1 - import-local: 3.1.0 - jest-cli: 27.5.1 - transitivePeerDependencies: - - bufferutil - - canvas - - supports-color - - ts-node - - utf-8-validate - dev: false - - /jiti@1.19.1: - resolution: {integrity: sha512-oVhqoRDaBXf7sjkll95LHVS6Myyyb1zaunVwk4Z0+WPSW4gjS0pl01zYKHScTuyEhQsFxV5L4DR5r+YqSyqyyg==} - hasBin: true - dev: false - /js-tokens@4.0.0: resolution: {integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==} - /js-yaml@3.14.1: - resolution: {integrity: sha512-okMH7OXXJ7YrN9Ok3/SXrnu4iX9yOk+25nqX4imS2npuvTYDmo/QEZoqwZkYaIDk3jVvBOTOIEgEhaLOynBS9g==} - hasBin: true - dependencies: - argparse: 1.0.10 - esprima: 4.0.1 - dev: false - /js-yaml@4.1.0: resolution: {integrity: sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==} hasBin: true dependencies: argparse: 2.0.1 - - /jsdom@16.7.0: - resolution: {integrity: sha512-u9Smc2G1USStM+s/x1ru5Sxrl6mPYCbByG1U/hUmqaVsm4tbNyS7CicOSRyuGQYZhTu0h84qkZZQ/I+dzizSVw==} - engines: {node: '>=10'} - peerDependencies: - canvas: ^2.5.0 - peerDependenciesMeta: - canvas: - optional: true - dependencies: - abab: 2.0.6 - acorn: 8.10.0 - acorn-globals: 6.0.0 - cssom: 0.4.4 - cssstyle: 2.3.0 - data-urls: 2.0.0 - decimal.js: 10.4.3 - domexception: 2.0.1 - escodegen: 2.1.0 - form-data: 3.0.1 - html-encoding-sniffer: 2.0.1 - http-proxy-agent: 4.0.1 - https-proxy-agent: 5.0.1 - is-potential-custom-element-name: 1.0.1 - nwsapi: 2.2.7 - parse5: 6.0.1 - saxes: 5.0.1 - symbol-tree: 3.2.4 - tough-cookie: 4.1.3 - w3c-hr-time: 1.0.2 - w3c-xmlserializer: 2.0.0 - webidl-conversions: 6.1.0 - whatwg-encoding: 1.0.5 - whatwg-mimetype: 2.3.0 - whatwg-url: 8.7.0 - ws: 7.5.9 - xml-name-validator: 3.0.0 - transitivePeerDependencies: - - bufferutil - - supports-color - - utf-8-validate - dev: false + dev: true /jsdom@24.0.0: resolution: {integrity: sha512-UDS2NayCvmXSXVP6mpTj+73JnNQadZlr9N68189xib2tx5Mls7swlTNao26IoHv46BZJFvXygyRtyXd1feAk1A==} @@ -8628,57 +3673,20 @@ - utf-8-validate dev: false - /jsesc@0.5.0: - resolution: {integrity: sha512-uZz5UnB7u4T9LvwmFqXii7pZSouaRPorGs5who1Ip7VO0wxanFvBL7GkM6dTHlgX+jhBApRetaWpnDabOeTcnA==} - hasBin: true - dev: false - - /jsesc@2.5.2: - resolution: {integrity: sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA==} - engines: {node: '>=4'} - hasBin: true - - /json-parse-even-better-errors@2.3.1: - resolution: {integrity: sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==} - dev: false - /json-schema-traverse@0.4.1: resolution: {integrity: sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==} - - /json-schema-traverse@1.0.0: - resolution: {integrity: sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==} - dev: false - - /json-schema@0.4.0: - resolution: {integrity: sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA==} - dev: false + dev: true /json-stable-stringify-without-jsonify@1.0.1: resolution: {integrity: sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==} + dev: true /json5@1.0.2: resolution: {integrity: sha512-g1MWMLBiz8FKi1e4w0UyVL3w+iJceWAFBAaBnnGKOpNa5f8TLktkbre1+s6oICydWAm+HRUGTmI+//xv2hvXYA==} hasBin: true dependencies: minimist: 1.2.8 - - /json5@2.2.3: - resolution: {integrity: sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==} - engines: {node: '>=6'} - hasBin: true - - /jsonfile@6.1.0: - resolution: {integrity: sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ==} - dependencies: - universalify: 2.0.0 - optionalDependencies: - graceful-fs: 4.2.11 - dev: false - - /jsonpointer@5.0.1: - resolution: {integrity: sha512-p/nXbhSEcu3pZRdkW1OfJhpsVtW1gd4Wa1fnQc9YLiTfAjn0312eMKimbdIQzuZl9aa9xUGaRlP9T/CJE/ditQ==} - engines: {node: '>=0.10.0'} - dev: false + dev: true /jsx-ast-utils@3.3.4: resolution: {integrity: sha512-fX2TVdCViod6HwKEtSWGHs57oFhVfCMwieb9PuRDgjDPh5XeqJiHFFFJCHxU5cnTc3Bu/GRL+kPiFmw8XWOfKw==} @@ -8688,6 +3696,7 @@ array.prototype.flat: 1.3.1 object.assign: 4.1.4 object.values: 1.1.6 + dev: true /keygrip@1.1.0: resolution: {integrity: sha512-iYSchDJ+liQ8iwbSI2QqsQOvqv58eJCEanyJPJi+Khyu8smkcKSFUCbPwzFcL7YVtZ6eONjqRX/38caJ7QjRAQ==} @@ -8696,21 +3705,6 @@ tsscmp: 1.0.6 dev: false - /kind-of@6.0.3: - resolution: {integrity: sha512-dcS1ul+9tmeD95T+x28/ehLgd9mENa3LsvDTtzm3vyBEO7RPptvAD+t44WVXaUjTBRcrpFeFlC8WCruUR456hw==} - engines: {node: '>=0.10.0'} - dev: false - - /kleur@3.0.3: - resolution: {integrity: sha512-eTIzlVOSUR+JxdDFepEYcBMtZ9Qqdef+rnzWdRZuMbOywu5tO2w2N7rqjoANZ5k9vywhL6Br1VRjUIgTQx4E8w==} - engines: {node: '>=6'} - dev: false - - /klona@2.0.6: - resolution: {integrity: sha512-dhG34DXATL5hSxJbIexCft8FChFXtmskoZYnoPWjXQuebWYCNkVeV3KkGegCK9CP1oswI/vQibS2GY7Em/sJJA==} - engines: {node: '>= 8'} - dev: false - /koa-body@6.0.1: resolution: {integrity: sha512-M8ZvMD8r+kPHy28aWP9VxL7kY8oPWA+C7ZgCljrCMeaU7uX6wsIQgDHskyrAr9sw+jqnIXyv4Mlxri5R4InIJg==} dependencies: @@ -8791,23 +3785,13 @@ /language-subtag-registry@0.3.22: resolution: {integrity: sha512-tN0MCzyWnoz/4nHS6uxdlFWoUZT7ABptwKPQ52Ea7URk6vll88bWBVhodtnlfEuCcKWNGoc+uGbw1cwa9IKh/w==} + dev: true /language-tags@1.0.5: resolution: {integrity: sha512-qJhlO9cGXi6hBGKoxEG/sKZDAHD5Hnu9Hs4WbOY3pCWXDhw0N8x1NenNzm2EnNLkLkk7J2SdxAkDSbb6ftT+UQ==} dependencies: language-subtag-registry: 0.3.22 - - /launch-editor@2.6.0: - resolution: {integrity: sha512-JpDCcQnyAAzZZaZ7vEiSqL690w7dAEyLao+KC96zBplnYbJS7TYNjvM3M7y3dGz+v7aIsJk3hllWuc0kWAjyRQ==} - dependencies: - picocolors: 1.0.0 - shell-quote: 1.8.1 - dev: false - - /leven@3.1.0: - resolution: {integrity: sha512-qsda+H8jTaUaN/x5vzW2rzc+8Rw4TAQ/4KjB46IwK5VH+IlVeeeje/EoZRpiXvIqjFgK84QffqPztGI3VBLG1A==} - engines: {node: '>=6'} - dev: false + dev: true /levn@0.4.1: resolution: {integrity: sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==} @@ -8815,77 +3799,22 @@ dependencies: prelude-ls: 1.2.1 type-check: 0.4.0 - - /lilconfig@2.1.0: - resolution: {integrity: sha512-utWOt/GHzuUxnLKxB6dk81RoOeoNeHgbrXiuGk4yyF5qlRz+iIVWu56E2fqGHFrXz0QNUhLB/8nKqvRH66JKGQ==} - engines: {node: '>=10'} - dev: false - - /lines-and-columns@1.2.4: - resolution: {integrity: sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg==} - dev: false - - /loader-runner@4.3.0: - resolution: {integrity: sha512-3R/1M+yS3j5ou80Me59j7F9IMs4PXs3VqRrm0TU3AbKPxlmpoY1TNscJV/oGJXo8qCatFGTfDbY6W6ipGOYXfg==} - engines: {node: '>=6.11.5'} - dev: false - - /loader-utils@2.0.4: - resolution: {integrity: sha512-xXqpXoINfFhgua9xiqD8fPFHgkoq1mmmpE92WlDbm9rNRd/EbRb+Gqf908T2DMfuHjjJlksiK2RbHVOdD/MqSw==} - engines: {node: '>=8.9.0'} - dependencies: - big.js: 5.2.2 - emojis-list: 3.0.0 - json5: 2.2.3 - dev: false - - /loader-utils@3.2.1: - resolution: {integrity: sha512-ZvFw1KWS3GVyYBYb7qkmRM/WwL2TQQBxgCK62rlvm4WpVQ23Nb4tYjApUlfjrEGvOs7KHEsmyUn75OHZrJMWPw==} - engines: {node: '>= 12.13.0'} - dev: false - - /locate-path@3.0.0: - resolution: {integrity: sha512-7AO748wWnIhNqAuaty2ZWHkQHRSNfPVIsPIfwEOWO22AmaoVrWavlOcMR5nzTLNYvp36X220/maaRsrec1G65A==} - engines: {node: '>=6'} - dependencies: - p-locate: 3.0.0 - path-exists: 3.0.0 - dev: false - - /locate-path@5.0.0: - resolution: {integrity: sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==} - engines: {node: '>=8'} - dependencies: - p-locate: 4.1.0 - dev: false + dev: true /locate-path@6.0.0: resolution: {integrity: sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==} engines: {node: '>=10'} dependencies: p-locate: 5.0.0 - - /lodash.debounce@4.0.8: - resolution: {integrity: sha512-FT1yDzDYEoYWhnSGnpE/4Kj1fLZkDFyqRb7fNt6FdYOSxlUWAtp42Eh6Wb0rGIv/m9Bgo7x4GhQbm5Ys4SG5ow==} - dev: false - - /lodash.memoize@4.1.2: - resolution: {integrity: sha512-t7j+NzmgnQzTAYXcsHYLgimltOV1MXHtlOWf6GjL9Kj8GK5FInw5JotxvbOs+IvV1/Dzo04/fCGfLVs7aXb4Ag==} - dev: false + dev: true /lodash.merge@4.6.2: resolution: {integrity: sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==} - - /lodash.sortby@4.7.0: - resolution: {integrity: sha512-HDWXG8isMntAyRF5vZ7xKuEvOhT4AhlRt/3czTSjvGUxjYCBVRQY48ViDHyfYz9VIoBkW4TMGQNapx+l3RUwdA==} - dev: false - - /lodash.uniq@4.5.0: - resolution: {integrity: sha512-xfBaXQd9ryd9dlSDvnvI0lvxfLJlYAZzXomUYzLKtUeOQvOP5piqAWuGtrhWeqaXK9hhoM/iyJc5AV+XfsX3HQ==} - dev: false + dev: true /lodash@4.17.21: resolution: {integrity: sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==} + dev: true /logform@2.5.1: resolution: {integrity: sha512-9FyqAm9o9NKKfiAKfZoYo9bGXXuwMkxQiQttkT4YjjVtQVIQtK6LmVtlxmCaFswo6N4AfEkHqZTV0taDtPotNg==} @@ -8904,46 +3833,16 @@ dependencies: js-tokens: 4.0.0 - /lower-case@2.0.2: - resolution: {integrity: sha512-7fm3l3NAF9WfN6W3JOmf5drwpVqX78JtoGJ3A6W0a6ZnldM41w2fV5D490psKFTpMds8TJse/eHLFFsNHHjHgg==} - dependencies: - tslib: 2.6.2 - dev: false - /lru-cache@10.0.1: resolution: {integrity: sha512-IJ4uwUTi2qCccrioU6g9g/5rvvVl13bsdczUUcqbciD9iLr095yj8DQKdObriEvuNSx325N1rV1O0sJFszx75g==} engines: {node: 14 || >=16.14} - /lru-cache@5.1.1: - resolution: {integrity: sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w==} - dependencies: - yallist: 3.1.1 - /lru-cache@6.0.0: resolution: {integrity: sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==} engines: {node: '>=10'} dependencies: yallist: 4.0.0 - /magic-string@0.25.9: - resolution: {integrity: sha512-RmF0AsMzgt25qzqqLc1+MbHmhdx0ojF2Fvs4XnOqz2ZOBXzzkEwc/dJQZCYHAn7v1jbVOjAZfK8msRn4BxO4VQ==} - dependencies: - sourcemap-codec: 1.4.8 - dev: false - - /make-dir@3.1.0: - resolution: {integrity: sha512-g3FeP20LNwhALb/6Cz6Dd4F2ngze0jz7tbzrD2wAV+o9FeNHe4rL+yK2md0J/fiSf1sa1ADhXqi5+oVwOM/eGw==} - engines: {node: '>=8'} - dependencies: - semver: 6.3.1 - dev: false - - /makeerror@1.0.12: - resolution: {integrity: sha512-JmqCvUhmt43madlpFzG4BQzG2Z3m6tvQDNKdClZnO3VbIudJYmxsT0FNJMeiB2+JTSlTQTSbU8QdesVmwJcmLg==} - dependencies: - tmpl: 1.0.5 - dev: false - /mariadb@3.2.3: resolution: {integrity: sha512-Hyc1ehdUJwzvvzcLU2juZS528wJ6oE8pUlpgY0BAOdpKWcdN1motuugi5lC3jkpCkFpyNknHG7Yg66KASl3aPg==} engines: {node: '>= 12'} @@ -8955,37 +3854,15 @@ lru-cache: 10.0.1 dev: false - /mdn-data@2.0.14: - resolution: {integrity: sha512-dn6wd0uw5GsdswPFfsgMp5NSB0/aDe6fK94YJV/AJDYXL6HVLWBsxeq7js7Ad+mU2K9LAlwpk6kN2D5mwCPVow==} - dev: false - - /mdn-data@2.0.4: - resolution: {integrity: sha512-iV3XNKw06j5Q7mi6h+9vbx23Tv7JkjEVgKHW4pimwyDGWm0OIQntJJ+u1C6mg6mK1EaTv42XQ7w76yuzH7M2cA==} - dev: false - /media-typer@0.3.0: resolution: {integrity: sha512-dq+qelQ9akHpcOl/gUVRTxVIOkAJ1wR3QAvb4RsVjS8oVoFjDGTc679wJYmUmknUF5HwMLOgb5O+a3KxfWapPQ==} engines: {node: '>= 0.6'} dev: false - /memfs@3.5.3: - resolution: {integrity: sha512-UERzLsxzllchadvbPs5aolHh65ISpKpM+ccLbOJ8/vvpBKmAWf+la7dXFy7Mr0ySHbdHrFv5kGFCUHHe6GFEmw==} - engines: {node: '>= 4.0.0'} - dependencies: - fs-monkey: 1.0.4 - dev: false - - /merge-descriptors@1.0.1: - resolution: {integrity: sha512-cCi6g3/Zr1iqQi6ySbseM1Xvooa98N0w31jzUYrXPX2xqObmFGHJ0tQ5u74H3mVh7wLouTseZyYIq39g8cNp1w==} - dev: false - - /merge-stream@2.0.0: - resolution: {integrity: sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==} - dev: false - /merge2@1.4.1: resolution: {integrity: sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==} engines: {node: '>= 8'} + dev: true /methods@1.1.2: resolution: {integrity: sha512-iclAHeNqNm68zFtnZ0e+1L2yUIdvzNoauKU4WBA3VvH/vPFieF7qfRlwUZU+DA9P9bPXIS90ulxoUoCH23sV2w==} @@ -8998,6 +3875,7 @@ dependencies: braces: 3.0.2 picomatch: 2.3.1 + dev: true /mime-db@1.52.0: resolution: {integrity: sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==} @@ -9011,42 +3889,11 @@ mime-db: 1.52.0 dev: false - /mime@1.6.0: - resolution: {integrity: sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==} - engines: {node: '>=4'} - hasBin: true - dev: false - - /mimic-fn@2.1.0: - resolution: {integrity: sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg==} - engines: {node: '>=6'} - dev: false - - /mini-css-extract-plugin@2.7.6(webpack@5.88.1): - resolution: {integrity: sha512-Qk7HcgaPkGG6eD77mLvZS1nmxlao3j+9PkrT9Uc7HAE1id3F41+DdBRYRYkbyfNRGzm8/YWtzhw7nVPmwhqTQw==} - engines: {node: '>= 12.13.0'} - peerDependencies: - webpack: ^5.0.0 - dependencies: - schema-utils: 4.2.0 - webpack: 5.88.1 - dev: false - - /minimalistic-assert@1.0.1: - resolution: {integrity: sha512-UtJcAD4yEaGtjPezWuO9wC4nwUnVH/8/Im3yEHQP4b67cXlD/Qr9hdITCU1xDbSEXg2XKNaP8jsReV7vQd00/A==} - dev: false - /minimatch@3.1.2: resolution: {integrity: sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==} dependencies: brace-expansion: 1.1.11 - - /minimatch@5.1.6: - resolution: {integrity: sha512-lKwV/1brpG6mBUFHtb7NUmtABCb2WZZmm2wNiOA5hAb8VdCS4B3dtMWyvcoViccwAW/COERjXLt0zP1zXUN26g==} - engines: {node: '>=10'} - dependencies: - brace-expansion: 2.0.1 - dev: false + dev: true /minimatch@9.0.3: resolution: {integrity: sha512-RHiac9mvaRw0x3AYRgDC1CxAP7HTcNrrECeA8YYJeWnpo+2Q5CegtZjaotWTWxDG3UeGA1coE05iH1mPjT/2mg==} @@ -9057,19 +3904,13 @@ /minimist@1.2.8: resolution: {integrity: sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==} + dev: true /minipass@7.0.4: resolution: {integrity: sha512-jYofLM5Dam9279rdkWzqHozUo4ybjdZmCsDHePy5V/PbBcVMiSZR97gmAy45aqi8CK1lG2ECd356FU86avfwUQ==} engines: {node: '>=16 || 14 >=14.17'} dev: true - /mkdirp@0.5.6: - resolution: {integrity: sha512-FP+p8RB8OWpF3YZBCrP5gtADmtXApB5AMLn+vdyA+PyxCjrCs00mjyUozssO33cwDeT3wNGdLxJ5M//YqtHAJw==} - hasBin: true - dependencies: - minimist: 1.2.8 - dev: false - /mobx-react-lite@4.0.6(mobx@6.12.0)(react-dom@18.2.0)(react@18.2.0): resolution: {integrity: sha512-0rOE0KDMwV9CzsstYC86ZxxrUpKLGBN0/T3WpKZibLnJcukdb9HVL8VKHoDxaBPbInLZ5azPKUod4mXTsi+u+A==} peerDependencies: @@ -9097,52 +3938,25 @@ resolution: {integrity: sha512-5LC9SOxjSc2HF6vO2CyuTDNivEdoz2IvyJJGj6X8DJ0eFyfszE0QiEd+iXmBvUP3WHxSjFH/vIsA0EN00cgr8w==} dev: false - /ms@2.0.0: - resolution: {integrity: sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==} - dev: false - /ms@2.1.2: resolution: {integrity: sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==} /ms@2.1.3: resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==} - /multicast-dns@7.2.5: - resolution: {integrity: sha512-2eznPJP8z2BFLX50tf0LuODrpINqP1RVIm/CObbTcBRITQgmC/TjcREF1NeTBzIcR5XO/ukWo+YHOjBbFwIupg==} - hasBin: true - dependencies: - dns-packet: 5.6.0 - thunky: 1.1.0 - dev: false - - /mz@2.7.0: - resolution: {integrity: sha512-z81GNO7nnYMEhrGh9LeymoE4+Yr0Wn5McHIZMK5cfQCl+NDX08sCZgUc9/6MHni9IWuFLm1Z3HTCXu2z9fN62Q==} - dependencies: - any-promise: 1.3.0 - object-assign: 4.1.1 - thenify-all: 1.6.0 - dev: false - /nanoid@3.3.6: resolution: {integrity: sha512-BGcqMMJuToF7i1rt+2PWSNVnWIkGCU78jBG3RxO/bZlnZPK2Cmi2QaffxGO/2RvWi9sL+FAiRiXMgsyxQ1DIDA==} engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1} hasBin: true - /natural-compare-lite@1.4.0: - resolution: {integrity: sha512-Tj+HTDSJJKaZnfiuw+iaF9skdPpTo2GtEly5JHnWV/hfv2Qj/9RKsGISQtLh2ox3l5EAGw487hnBee0sIJ6v2g==} - dev: false - /natural-compare@1.4.0: resolution: {integrity: sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==} + dev: true /negotiator@0.6.3: resolution: {integrity: sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg==} engines: {node: '>= 0.6'} - /neo-async@2.6.2: - resolution: {integrity: sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==} - dev: false - /next-intl@3.9.5(next@14.1.3)(react@18.2.0): resolution: {integrity: sha512-tsp4N433WgTAbbyZdMlcsLGHFM88wv2a7ZpF/od8X9+qAlO1TrajZrNrGBpIg6nA9EGZyMbQPzZD7XZrqYIv7g==} peerDependencies: @@ -9151,11 +3965,11 @@ dependencies: '@formatjs/intl-localematcher': 0.2.32 negotiator: 0.6.3 - next: 14.1.3(@babel/core@7.22.9)(react-dom@18.2.0)(react@18.2.0)(sass@1.72.0) + next: 14.1.3(react-dom@18.2.0)(react@18.2.0)(sass@1.72.0) react: 18.2.0 use-intl: 3.9.5(react@18.2.0) - /next@14.1.3(@babel/core@7.22.9)(react-dom@18.2.0)(react@18.2.0)(sass@1.72.0): + /next@14.1.3(react-dom@18.2.0)(react@18.2.0)(sass@1.72.0): resolution: {integrity: sha512-oexgMV2MapI0UIWiXKkixF8J8ORxpy64OuJ/J9oVUmIthXOUCcuVEZX+dtpgq7wIfIqtBwQsKEDXejcjTsan9g==} engines: {node: '>=18.17.0'} hasBin: true @@ -9179,7 +3993,7 @@ react: 18.2.0 react-dom: 18.2.0(react@18.2.0) sass: 1.72.0 - styled-jsx: 5.1.1(@babel/core@7.22.9)(react@18.2.0) + styled-jsx: 5.1.1(react@18.2.0) optionalDependencies: '@next/swc-darwin-arm64': 14.1.3 '@next/swc-darwin-x64': 14.1.3 @@ -9194,25 +4008,6 @@ - '@babel/core' - babel-plugin-macros - /no-case@3.0.4: - resolution: {integrity: sha512-fgAN3jGAh+RoxUGZHTSOLJIqUc2wmoBwGR4tbpNAKmmovFoWq0OdRkb0VkldReO2a2iBT/OEulG9XSUc10r3zg==} - dependencies: - lower-case: 2.0.2 - tslib: 2.6.2 - dev: false - - /node-forge@1.3.1: - resolution: {integrity: sha512-dPEtOeMvF9VMcYV/1Wb8CPoVAXtp6MKMlcbAt4ddqmGqUJ6fQZFXkNZNkNlfevtNkGtaSoXf/vNNNSvgrdXwtA==} - engines: {node: '>= 6.13.0'} - dev: false - - /node-int64@0.4.0: - resolution: {integrity: sha512-O5lz91xSOeoXP6DulyHfllpq+Eg00MWitZIbtPfoSEvqIHdl5gfcY6hYzDWnj0qD5tz52PI08u9qUvSVeUBeHw==} - dev: false - - /node-releases@2.0.13: - resolution: {integrity: sha512-uYr7J37ae/ORWdZeQ1xxMJe3NtdmqMC/JZK+geofDrkLUApKRHPd18/TxtBOJ4A0/+uUIliorNrfYV6s1b02eQ==} - /nodemon@3.1.0: resolution: {integrity: sha512-xqlktYlDMCepBJd43ZQhjWwMw2obW/JRvkrLxq5RCNcuDDX1DbcPT+qT1IlIIdf+DhnWs90JpTMe+Y5KxOchvA==} engines: {node: '>=10'} @@ -9241,35 +4036,6 @@ resolution: {integrity: sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==} engines: {node: '>=0.10.0'} - /normalize-range@0.1.2: - resolution: {integrity: sha512-bdok/XvKII3nUpklnV6P2hxtMNrCboOjAcyBuQnWEhO665FwrSNRxU+AqpsyvO6LgGYPspN+lu5CLtw4jPRKNA==} - engines: {node: '>=0.10.0'} - dev: false - - /normalize-url@6.1.0: - resolution: {integrity: sha512-DlL+XwOy3NxAQ8xuC0okPgK46iuVNAK01YN7RueYBqqFeGsBjV9XmCAzAdgt+667bCl5kPh9EqKKDwnaPG1I7A==} - engines: {node: '>=10'} - dev: false - - /npm-run-path@4.0.1: - resolution: {integrity: sha512-S48WzZW777zhNIrn7gxOlISNAqi9ZC/uQFnRdbeIHhZhCA6UqpkOT8T1G7BvfdgP4Er8gF4sUbaS0i7QvIfCWw==} - engines: {node: '>=8'} - dependencies: - path-key: 3.1.1 - dev: false - - /nth-check@1.0.2: - resolution: {integrity: sha512-WeBOdju8SnzPN5vTUJYxYUxLeXpCaVP5i5e0LF8fg7WORF2Wd7wFX/pk0tYZk7s8T+J7VLy0Da6J1+wCT0AtHg==} - dependencies: - boolbase: 1.0.0 - dev: false - - /nth-check@2.1.1: - resolution: {integrity: sha512-lqjrjmaOoAnWfMmBPL+XNnynZh2+swxiX3WUE0s4yEHI6m+AwrK2UZOimIRl3X/4QctVqS8AiZjFqyOGrMXb/w==} - dependencies: - boolbase: 1.0.0 - dev: false - /nwsapi@2.2.7: resolution: {integrity: sha512-ub5E4+FBPKwAZx0UwIQOjYWGHTEq5sPqHQNRN8Z9e4A7u3Tj1weLJsL59yH9vmvqEtBHaOmT6cYQKIZOxp35FQ==} dev: false @@ -9285,6 +4051,7 @@ /object-inspect@1.12.3: resolution: {integrity: sha512-geUvdk7c+eizMNUDkRpW1wJwgfOiOeHbxBR/hLXK1aT6zmVSO0jsQcs7fj6MGw89jC/cjGfLcNOrtMYtGqm81g==} + dev: true /object-inspect@1.13.1: resolution: {integrity: sha512-5qoj1RUiKOMsCCNLV1CBiPYE10sziTsnmNxkAI/rZhiD63CF7IqdFGC/XzjWjpSgLf0LxXX3bDFIh0E18f6UhQ==} @@ -9292,6 +4059,7 @@ /object-keys@1.1.1: resolution: {integrity: sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==} engines: {node: '>= 0.4'} + dev: true /object.assign@4.1.4: resolution: {integrity: sha512-1mxKf0e58bvyjSCtKYY4sRe9itRk3PJpquJOjeIkz885CczcI4IvJJDLPS72oowuSh+pBxUFROpX+TU++hxhZQ==} @@ -9301,6 +4069,7 @@ define-properties: 1.2.0 has-symbols: 1.0.3 object-keys: 1.1.1 + dev: true /object.assign@4.1.5: resolution: {integrity: sha512-byy+U7gp+FVwmyzKPYhW2h5l3crpmGsxl7X2s8y43IgxvG4g3QZ6CffDtsNQy1WsmZpQbO+ybo0AlW7TY6DcBQ==} @@ -9310,6 +4079,7 @@ define-properties: 1.2.1 has-symbols: 1.0.3 object-keys: 1.1.1 + dev: true /object.entries@1.1.6: resolution: {integrity: sha512-leTPzo4Zvg3pmbQ3rDK69Rl8GQvIqMWubrkxONG9/ojtFE2rD9fjMKfSI5BxW3osRH1m6VdzmqK8oAY9aT4x5w==} @@ -9318,6 +4088,7 @@ call-bind: 1.0.2 define-properties: 1.2.0 es-abstract: 1.22.1 + dev: true /object.entries@1.1.7: resolution: {integrity: sha512-jCBs/0plmPsOnrKAfFQXRG2NFjlhZgjjcBLSmTnEhU8U6vVTsVe8ANeQJCHTl3gSsI4J+0emOoCgoKlmQPMgmA==} @@ -9335,6 +4106,7 @@ call-bind: 1.0.2 define-properties: 1.2.0 es-abstract: 1.22.1 + dev: true /object.fromentries@2.0.7: resolution: {integrity: sha512-UPbPHML6sL8PI/mOqPwsH4G6iyXcCGzLin8KvEPenOZN5lpCNBZZQ+V62vdjB1mQHrmqGQt5/OJzemUA+KJmEA==} @@ -9343,17 +4115,7 @@ call-bind: 1.0.7 define-properties: 1.2.0 es-abstract: 1.22.1 - - /object.getownpropertydescriptors@2.1.6: - resolution: {integrity: sha512-lq+61g26E/BgHv0ZTFgRvi7NMEPuAxLkFU7rukXjc/AlwH4Am5xXVnIXy3un1bg/JPbXHrixRkK1itUzzPiIjQ==} - engines: {node: '>= 0.8'} - dependencies: - array.prototype.reduce: 1.0.5 - call-bind: 1.0.2 - define-properties: 1.2.0 - es-abstract: 1.22.1 - safe-array-concat: 1.0.0 - dev: false + dev: true /object.groupby@1.0.2: resolution: {integrity: sha512-bzBq58S+x+uo0VjurFT0UktpKHOZmv4/xePiOA1nbB9pMqpGK7rUPNgf+1YC+7mE+0HzhTMqNUuCqvKhj6FnBw==} @@ -9363,13 +4125,7 @@ define-properties: 1.2.1 es-abstract: 1.22.5 es-errors: 1.3.0 - - /object.hasown@1.1.2: - resolution: {integrity: sha512-B5UIT3J1W+WuWIU55h0mjlwaqxiE5vYENJXIXZ4VFe05pNYrkKuK0U/6aFcb0pKywYJh7IhfoqUfKVmrJJHZHw==} - dependencies: - define-properties: 1.2.0 - es-abstract: 1.22.1 - dev: false + dev: true /object.hasown@1.1.3: resolution: {integrity: sha512-fFI4VcYpRHvSLXxP7yiZOMAd331cPfd2p7PFDVbgUsYOfCT3tICVqXWngbjr4m49OvsBwUBQ6O2uQoJvy3RexA==} @@ -9385,6 +4141,7 @@ call-bind: 1.0.2 define-properties: 1.2.0 es-abstract: 1.22.1 + dev: true /object.values@1.1.7: resolution: {integrity: sha512-aU6xnDFYT3x17e/f0IiiwlGPTy2jzMySGfUB4fq6z7CV8l85CWHDk5ErhyhpfDHhrOMwGFhSQkhMGHaIotA6Ng==} @@ -9393,10 +4150,7 @@ call-bind: 1.0.7 define-properties: 1.2.0 es-abstract: 1.22.1 - - /obuf@1.1.2: - resolution: {integrity: sha512-PX1wu0AmAdPqOL1mWhqmlOd8kOIZQwGZw6rh7uby9fTc5lhaOWFLX3I6R1hrF9k3zUY40e6igsLGkDXK92LJNg==} - dev: false + dev: true /on-finished@2.4.1: resolution: {integrity: sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==} @@ -9405,11 +4159,6 @@ ee-first: 1.1.1 dev: false - /on-headers@1.0.2: - resolution: {integrity: sha512-pZAE+FJLoyITytdqK0U5s+FIpjN0JP3OzFi/u8Rx+EV5/W+JTWGXG8xFzevE7AjBfDqHv/8vL8qQsIhHnqRkrA==} - engines: {node: '>= 0.8'} - dev: false - /once@1.4.0: resolution: {integrity: sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==} dependencies: @@ -9421,26 +4170,10 @@ fn.name: 1.1.0 dev: false - /onetime@5.1.2: - resolution: {integrity: sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg==} - engines: {node: '>=6'} - dependencies: - mimic-fn: 2.1.0 - dev: false - /only@0.0.2: resolution: {integrity: sha512-Fvw+Jemq5fjjyWz6CpKx6w9s7xxqo3+JCyM0WXWeCSOboZ8ABkyvP8ID4CZuChA/wxSx+XSJmdOm8rGVyJ1hdQ==} dev: false - /open@8.4.2: - resolution: {integrity: sha512-7x81NCL719oNbsq/3mh+hVrAWmFuEYUqrq/Iw3kUzH8ReypT9QQ0BLoJS7/G9k6N81XjW4qHWtjWwe/9eLy1EQ==} - engines: {node: '>=12'} - dependencies: - define-lazy-prop: 2.0.0 - is-docker: 2.2.1 - is-wsl: 2.2.0 - dev: false - /optionator@0.9.3: resolution: {integrity: sha512-JjCoypp+jKn1ttEFExxhetCKeJt9zhAgAve5FXHixTvFDW/5aEktX9bufBKLRRMdU7bNtpLfcGu94B3cdEJgjg==} engines: {node: '>= 0.8.0'} @@ -9451,79 +4184,28 @@ levn: 0.4.1 prelude-ls: 1.2.1 type-check: 0.4.0 - - /p-limit@2.3.0: - resolution: {integrity: sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==} - engines: {node: '>=6'} - dependencies: - p-try: 2.2.0 - dev: false + dev: true /p-limit@3.1.0: resolution: {integrity: sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==} engines: {node: '>=10'} dependencies: yocto-queue: 0.1.0 - - /p-locate@3.0.0: - resolution: {integrity: sha512-x+12w/To+4GFfgJhBEpiDcLozRJGegY+Ei7/z0tSLkMmxGZNybVMSfWj9aJn8Z5Fc7dBUNJOOVgPv2H7IwulSQ==} - engines: {node: '>=6'} - dependencies: - p-limit: 2.3.0 - dev: false - - /p-locate@4.1.0: - resolution: {integrity: sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==} - engines: {node: '>=8'} - dependencies: - p-limit: 2.3.0 - dev: false + dev: true /p-locate@5.0.0: resolution: {integrity: sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==} engines: {node: '>=10'} dependencies: p-limit: 3.1.0 - - /p-retry@4.6.2: - resolution: {integrity: sha512-312Id396EbJdvRONlngUx0NydfrIQ5lsYu0znKVUzVvArzEIt08V1qhtyESbGVd1FGX7UKtiFp5uwKZdM8wIuQ==} - engines: {node: '>=8'} - dependencies: - '@types/retry': 0.12.0 - retry: 0.13.1 - dev: false - - /p-try@2.2.0: - resolution: {integrity: sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ==} - engines: {node: '>=6'} - dev: false - - /param-case@3.0.4: - resolution: {integrity: sha512-RXlj7zCYokReqWpOPH9oYivUzLYZ5vAPIfEmCTNViosC78F8F0H9y7T7gG2M39ymgutxF5gcFEsyZQSph9Bp3A==} - dependencies: - dot-case: 3.0.4 - tslib: 2.6.2 - dev: false + dev: true /parent-module@1.0.1: resolution: {integrity: sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==} engines: {node: '>=6'} dependencies: callsites: 3.1.0 - - /parse-json@5.2.0: - resolution: {integrity: sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg==} - engines: {node: '>=8'} - dependencies: - '@babel/code-frame': 7.22.5 - error-ex: 1.3.2 - json-parse-even-better-errors: 2.3.1 - lines-and-columns: 1.2.4 - dev: false - - /parse5@6.0.1: - resolution: {integrity: sha512-Ofn/CTFzRGTTxwpNEs9PP93gXShHcTq255nzRYSKe8AkVpZY7e1fpmTfOyoIvjP5HG7Z2ZM7VS9PPhQGW2pOpw==} - dev: false + dev: true /parse5@7.1.2: resolution: {integrity: sha512-Czj1WaSVpaoj0wbhMzLmWD69anp2WH7FXMB9n1Sy8/ZFF9jolSQVMu1Ij5WIyGmcBmhk7EOndpO4mIpihVqAXw==} @@ -9536,32 +4218,24 @@ engines: {node: '>= 0.8'} dev: false - /pascal-case@3.1.2: - resolution: {integrity: sha512-uWlGT3YSnK9x3BQJaOdcZwrnV6hPpd8jFH1/ucpiLRPh/2zCVJKS19E4GvYHvaCcACn3foXZ0cLB9Wrx1KGe5g==} - dependencies: - no-case: 3.0.4 - tslib: 2.6.2 - dev: false - - /path-exists@3.0.0: - resolution: {integrity: sha512-bpC7GYwiDYQ4wYLe+FA8lhRjhQCMcQGuSgGGqDkg/QerRWw9CmGRT0iSOVRSZJ29NMLZgIzqaljJ63oaL4NIJQ==} - engines: {node: '>=4'} - dev: false - /path-exists@4.0.0: resolution: {integrity: sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==} engines: {node: '>=8'} + dev: true /path-is-absolute@1.0.1: resolution: {integrity: sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==} engines: {node: '>=0.10.0'} + dev: true /path-key@3.1.1: resolution: {integrity: sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==} engines: {node: '>=8'} + dev: true /path-parse@1.0.7: resolution: {integrity: sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==} + dev: true /path-scurry@1.10.1: resolution: {integrity: sha512-MkhCqzzBEpPvxxQ71Md0b1Kk51W01lrYvlMzSUaIzNsODdd7mqhiimSZlr+VegAz5Z6Vzt9Xg2ttE//XBhH3EQ==} @@ -9571,10 +4245,6 @@ minipass: 7.0.4 dev: true - /path-to-regexp@0.1.7: - resolution: {integrity: sha512-5DFkuoqlv1uYQKxy8omFBeJPQcdoE07Kv2sferDCrAq1ohOU+MSDswDIbnx3YAM60qIOnYa53wBhXW0EbMonrQ==} - dev: false - /path-to-regexp@6.2.1: resolution: {integrity: sha512-JLyh7xT1kizaEvcaXOQwOc2/Yhw6KZOvPf1S8401UyLk86CU79LN3vl7ztXGm/pZ+YjoyAJ4rxmHwbkBXJX+yw==} dev: false @@ -9582,14 +4252,7 @@ /path-type@4.0.0: resolution: {integrity: sha512-gDKb8aZMDeD/tZWs9P6+q0J9Mwkdl6xMV8TjnGP3qJVJ06bdMgkbBlLU8IdfOsIsFz2BW1rNVT3XuNEl8zPAvw==} engines: {node: '>=8'} - - /performance-now@2.1.0: - resolution: {integrity: sha512-7EAHlyLHI56VEIdK57uwHdHKIaAGbnXPiw0yWbarQZOKaKpvUIgW0jWRVLiatnM+XXlSwsanIBH/hzGMJulMow==} - dev: false - - /picocolors@0.2.1: - resolution: {integrity: sha512-cMlDqaLEqfSaW8Z7N5Jw+lyIW869EzT73/F5lhtY9cLGoVxSXznfgfXMO0Z5K0o0Q2TkTXq+0KFsdnSe3jDViA==} - dev: false + dev: true /picocolors@1.0.0: resolution: {integrity: sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ==} @@ -9598,810 +4261,10 @@ resolution: {integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==} engines: {node: '>=8.6'} - /pify@2.3.0: - resolution: {integrity: sha512-udgsAY+fTnvv7kI7aaxbqwWNb0AHiB0qBO89PZKPkoTmGOgdbrHDKD+0B2X4uTfJ/FT1R09r9gTsjUjNJotuog==} - engines: {node: '>=0.10.0'} - dev: false - - /pirates@4.0.6: - resolution: {integrity: sha512-saLsH7WeYYPiD25LDuLRRY/i+6HaPYr6G1OUlN39otzkSTxKnubR9RTxS3/Kk50s1g2JTgFwWQDQyplC5/SHZg==} - engines: {node: '>= 6'} - dev: false - - /pkg-dir@4.2.0: - resolution: {integrity: sha512-HRDzbaKjC+AOWVXxAU/x54COGeIv9eb+6CkDSQoNTt4XyWoIJvuPsXizxu/Fr23EiekbtZwmh1IcIG/l/a10GQ==} - engines: {node: '>=8'} - dependencies: - find-up: 4.1.0 - dev: false - - /pkg-up@3.1.0: - resolution: {integrity: sha512-nDywThFk1i4BQK4twPQ6TA4RT8bDY96yeuCVBWL3ePARCiEKDRSrNGbFIgUJpLp+XeIR65v8ra7WuJOFUBtkMA==} - engines: {node: '>=8'} - dependencies: - find-up: 3.0.0 - dev: false - /possible-typed-array-names@1.0.0: resolution: {integrity: sha512-d7Uw+eZoloe0EHDIYoe+bQ5WXnGMOpmiZFTuMWCwpjzzkL2nTjcKiAk4hh8TjnGye2TwWOk3UXucZ+3rbmBa8Q==} engines: {node: '>= 0.4'} - - /postcss-attribute-case-insensitive@5.0.2(postcss@8.4.26): - resolution: {integrity: sha512-XIidXV8fDr0kKt28vqki84fRK8VW8eTuIa4PChv2MqKuT6C9UjmSKzen6KaWhWEoYvwxFCa7n/tC1SZ3tyq4SQ==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /postcss-browser-comments@4.0.0(browserslist@4.21.9)(postcss@8.4.26): - resolution: {integrity: sha512-X9X9/WN3KIvY9+hNERUqX9gncsgBA25XaeR+jshHz2j8+sYyHktHw1JdKuMjeLpGktXidqDhA7b/qm1mrBDmgg==} - engines: {node: '>=8'} - peerDependencies: - browserslist: '>=4' - postcss: '>=8' - dependencies: - browserslist: 4.21.9 - postcss: 8.4.26 - dev: false - - /postcss-calc@8.2.4(postcss@8.4.26): - resolution: {integrity: sha512-SmWMSJmB8MRnnULldx0lQIyhSNvuDl9HfrZkaqqE/WHAhToYsAvDq+yAsA/kIyINDszOp3Rh0GFoNuH5Ypsm3Q==} - peerDependencies: - postcss: ^8.2.2 - dependencies: - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-clamp@4.1.0(postcss@8.4.26): - resolution: {integrity: sha512-ry4b1Llo/9zz+PKC+030KUnPITTJAHeOwjfAyyB60eT0AorGLdzp52s31OsPRHRf8NchkgFoG2y6fCfn1IV1Ow==} - engines: {node: '>=7.6.0'} - peerDependencies: - postcss: ^8.4.6 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-color-functional-notation@4.2.4(postcss@8.4.26): - resolution: {integrity: sha512-2yrTAUZUab9s6CpxkxC4rVgFEVaR6/2Pipvi6qcgvnYiVqZcbDHEoBDhrXzyb7Efh2CCfHQNtcqWcIruDTIUeg==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-color-hex-alpha@8.0.4(postcss@8.4.26): - resolution: {integrity: sha512-nLo2DCRC9eE4w2JmuKgVA3fGL3d01kGq752pVALF68qpGLmx2Qrk91QTKkdUqqp45T1K1XV8IhQpcu1hoAQflQ==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.4 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-color-rebeccapurple@7.1.1(postcss@8.4.26): - resolution: {integrity: sha512-pGxkuVEInwLHgkNxUc4sdg4g3py7zUeCQ9sMfwyHAT+Ezk8a4OaaVZ8lIY5+oNqA/BXXgLyXv0+5wHP68R79hg==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-colormin@5.3.1(postcss@8.4.26): - resolution: {integrity: sha512-UsWQG0AqTFQmpBegeLLc1+c3jIqBNB0zlDGRWR+dQ3pRKJL1oeMzyqmH3o2PIfn9MBdNrVPWhDbT769LxCTLJQ==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - browserslist: 4.21.9 - caniuse-api: 3.0.0 - colord: 2.9.3 - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-convert-values@5.1.3(postcss@8.4.26): - resolution: {integrity: sha512-82pC1xkJZtcJEfiLw6UXnXVXScgtBrjlO5CBmuDQc+dlb88ZYheFsjTn40+zBVi3DkfF7iezO0nJUPLcJK3pvA==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - browserslist: 4.21.9 - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-custom-media@8.0.2(postcss@8.4.26): - resolution: {integrity: sha512-7yi25vDAoHAkbhAzX9dHx2yc6ntS4jQvejrNcC+csQJAXjj15e7VcWfMgLqBNAbOvqi5uIa9huOVwdHbf+sKqg==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.3 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-custom-properties@12.1.11(postcss@8.4.26): - resolution: {integrity: sha512-0IDJYhgU8xDv1KY6+VgUwuQkVtmYzRwu+dMjnmdMafXYv86SWqfxkc7qdDvWS38vsjaEtv8e0vGOUQrAiMBLpQ==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-custom-selectors@6.0.3(postcss@8.4.26): - resolution: {integrity: sha512-fgVkmyiWDwmD3JbpCmB45SvvlCD6z9CG6Ie6Iere22W5aHea6oWa7EM2bpnv2Fj3I94L3VbtvX9KqwSi5aFzSg==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.3 - dependencies: - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /postcss-dir-pseudo-class@6.0.5(postcss@8.4.26): - resolution: {integrity: sha512-eqn4m70P031PF7ZQIvSgy9RSJ5uI2171O/OO/zcRNYpJbvaeKFUlar1aJ7rmgiQtbm0FSPsRewjpdS0Oew7MPA==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /postcss-discard-comments@5.1.2(postcss@8.4.26): - resolution: {integrity: sha512-+L8208OVbHVF2UQf1iDmRcbdjJkuBF6IS29yBDSiWUIzpYaAhtNl6JYnYm12FnkeCwQqF5LeklOu6rAqgfBZqQ==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - dev: false - - /postcss-discard-duplicates@5.1.0(postcss@8.4.26): - resolution: {integrity: sha512-zmX3IoSI2aoenxHV6C7plngHWWhUOV3sP1T8y2ifzxzbtnuhk1EdPwm0S1bIUNaJ2eNbWeGLEwzw8huPD67aQw==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - dev: false - - /postcss-discard-empty@5.1.1(postcss@8.4.26): - resolution: {integrity: sha512-zPz4WljiSuLWsI0ir4Mcnr4qQQ5e1Ukc3i7UfE2XcrwKK2LIPIqE5jxMRxO6GbI3cv//ztXDsXwEWT3BHOGh3A==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - dev: false - - /postcss-discard-overridden@5.1.0(postcss@8.4.26): - resolution: {integrity: sha512-21nOL7RqWR1kasIVdKs8HNqQJhFxLsyRfAnUDm4Fe4t4mCWL9OJiHvlHPjcd8zc5Myu89b/7wZDnOSjFgeWRtw==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - dev: false - - /postcss-double-position-gradients@3.1.2(postcss@8.4.26): - resolution: {integrity: sha512-GX+FuE/uBR6eskOK+4vkXgT6pDkexLokPaz/AbJna9s5Kzp/yl488pKPjhy0obB475ovfT1Wv8ho7U/cHNaRgQ==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - '@csstools/postcss-progressive-custom-properties': 1.3.0(postcss@8.4.26) - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-env-function@4.0.6(postcss@8.4.26): - resolution: {integrity: sha512-kpA6FsLra+NqcFnL81TnsU+Z7orGtDTxcOhl6pwXeEq1yFPpRMkCDpHhrz8CFQDr/Wfm0jLiNQ1OsGGPjlqPwA==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.4 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-flexbugs-fixes@5.0.2(postcss@8.4.26): - resolution: {integrity: sha512-18f9voByak7bTktR2QgDveglpn9DTbBWPUzSOe9g0N4WR/2eSt6Vrcbf0hmspvMI6YWGywz6B9f7jzpFNJJgnQ==} - peerDependencies: - postcss: ^8.1.4 - dependencies: - postcss: 8.4.26 - dev: false - - /postcss-focus-visible@6.0.4(postcss@8.4.26): - resolution: {integrity: sha512-QcKuUU/dgNsstIK6HELFRT5Y3lbrMLEOwG+A4s5cA+fx3A3y/JTq3X9LaOj3OC3ALH0XqyrgQIgey/MIZ8Wczw==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.4 - dependencies: - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /postcss-focus-within@5.0.4(postcss@8.4.26): - resolution: {integrity: sha512-vvjDN++C0mu8jz4af5d52CB184ogg/sSxAFS+oUJQq2SuCe7T5U2iIsVJtsCp2d6R4j0jr5+q3rPkBVZkXD9fQ==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.4 - dependencies: - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /postcss-font-variant@5.0.0(postcss@8.4.26): - resolution: {integrity: sha512-1fmkBaCALD72CK2a9i468mA/+tr9/1cBxRRMXOUaZqO43oWPR5imcyPjXwuv7PXbCid4ndlP5zWhidQVVa3hmA==} - peerDependencies: - postcss: ^8.1.0 - dependencies: - postcss: 8.4.26 - dev: false - - /postcss-gap-properties@3.0.5(postcss@8.4.26): - resolution: {integrity: sha512-IuE6gKSdoUNcvkGIqdtjtcMtZIFyXZhmFd5RUlg97iVEvp1BZKV5ngsAjCjrVy+14uhGBQl9tzmi1Qwq4kqVOg==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - dev: false - - /postcss-image-set-function@4.0.7(postcss@8.4.26): - resolution: {integrity: sha512-9T2r9rsvYzm5ndsBE8WgtrMlIT7VbtTfE7b3BQnudUqnBcBo7L758oc+o+pdj/dUV0l5wjwSdjeOH2DZtfv8qw==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-import@15.1.0(postcss@8.4.26): - resolution: {integrity: sha512-hpr+J05B2FVYUAXHeK1YyI267J/dDDhMU6B6civm8hSY1jYJnBXxzKDKDswzJmtLHryrjhnDjqqp/49t8FALew==} - engines: {node: '>=14.0.0'} - peerDependencies: - postcss: ^8.0.0 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - read-cache: 1.0.0 - resolve: 1.22.2 - dev: false - - /postcss-initial@4.0.1(postcss@8.4.26): - resolution: {integrity: sha512-0ueD7rPqX8Pn1xJIjay0AZeIuDoF+V+VvMt/uOnn+4ezUKhZM/NokDeP6DwMNyIoYByuN/94IQnt5FEkaN59xQ==} - peerDependencies: - postcss: ^8.0.0 - dependencies: - postcss: 8.4.26 - dev: false - - /postcss-js@4.0.1(postcss@8.4.26): - resolution: {integrity: sha512-dDLF8pEO191hJMtlHFPRa8xsizHaM82MLfNkUHdUtVEV3tgTp5oj+8qbEqYM57SLfc74KSbw//4SeJma2LRVIw==} - engines: {node: ^12 || ^14 || >= 16} - peerDependencies: - postcss: ^8.4.21 - dependencies: - camelcase-css: 2.0.1 - postcss: 8.4.26 - dev: false - - /postcss-lab-function@4.2.1(postcss@8.4.26): - resolution: {integrity: sha512-xuXll4isR03CrQsmxyz92LJB2xX9n+pZJ5jE9JgcnmsCammLyKdlzrBin+25dy6wIjfhJpKBAN80gsTlCgRk2w==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - '@csstools/postcss-progressive-custom-properties': 1.3.0(postcss@8.4.26) - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-load-config@4.0.1(postcss@8.4.26): - resolution: {integrity: sha512-vEJIc8RdiBRu3oRAI0ymerOn+7rPuMvRXslTvZUKZonDHFIczxztIyJ1urxM1x9JXEikvpWWTUUqal5j/8QgvA==} - engines: {node: '>= 14'} - peerDependencies: - postcss: '>=8.0.9' - ts-node: '>=9.0.0' - peerDependenciesMeta: - postcss: - optional: true - ts-node: - optional: true - dependencies: - lilconfig: 2.1.0 - postcss: 8.4.26 - yaml: 2.3.1 - dev: false - - /postcss-loader@6.2.1(postcss@8.4.26)(webpack@5.88.1): - resolution: {integrity: sha512-WbbYpmAaKcux/P66bZ40bpWsBucjx/TTgVVzRZ9yUO8yQfVBlameJ0ZGVaPfH64hNSBh63a+ICP5nqOpBA0w+Q==} - engines: {node: '>= 12.13.0'} - peerDependencies: - postcss: ^7.0.0 || ^8.0.1 - webpack: ^5.0.0 - dependencies: - cosmiconfig: 7.1.0 - klona: 2.0.6 - postcss: 8.4.26 - semver: 7.5.4 - webpack: 5.88.1 - dev: false - - /postcss-logical@5.0.4(postcss@8.4.26): - resolution: {integrity: sha512-RHXxplCeLh9VjinvMrZONq7im4wjWGlRJAqmAVLXyZaXwfDWP73/oq4NdIp+OZwhQUMj0zjqDfM5Fj7qby+B4g==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.4 - dependencies: - postcss: 8.4.26 - dev: false - - /postcss-media-minmax@5.0.0(postcss@8.4.26): - resolution: {integrity: sha512-yDUvFf9QdFZTuCUg0g0uNSHVlJ5X1lSzDZjPSFaiCWvjgsvu8vEVxtahPrLMinIDEEGnx6cBe6iqdx5YWz08wQ==} - engines: {node: '>=10.0.0'} - peerDependencies: - postcss: ^8.1.0 - dependencies: - postcss: 8.4.26 - dev: false - - /postcss-merge-longhand@5.1.7(postcss@8.4.26): - resolution: {integrity: sha512-YCI9gZB+PLNskrK0BB3/2OzPnGhPkBEwmwhfYk1ilBHYVAZB7/tkTHFBAnCrvBBOmeYyMYw3DMjT55SyxMBzjQ==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - stylehacks: 5.1.1(postcss@8.4.26) - dev: false - - /postcss-merge-rules@5.1.4(postcss@8.4.26): - resolution: {integrity: sha512-0R2IuYpgU93y9lhVbO/OylTtKMVcHb67zjWIfCiKR9rWL3GUk1677LAqD/BcHizukdZEjT8Ru3oHRoAYoJy44g==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - browserslist: 4.21.9 - caniuse-api: 3.0.0 - cssnano-utils: 3.1.0(postcss@8.4.26) - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /postcss-minify-font-values@5.1.0(postcss@8.4.26): - resolution: {integrity: sha512-el3mYTgx13ZAPPirSVsHqFzl+BBBDrXvbySvPGFnQcTI4iNslrPaFq4muTkLZmKlGk4gyFAYUBMH30+HurREyA==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-minify-gradients@5.1.1(postcss@8.4.26): - resolution: {integrity: sha512-VGvXMTpCEo4qHTNSa9A0a3D+dxGFZCYwR6Jokk+/3oB6flu2/PnPXAh2x7x52EkY5xlIHLm+Le8tJxe/7TNhzw==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - colord: 2.9.3 - cssnano-utils: 3.1.0(postcss@8.4.26) - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-minify-params@5.1.4(postcss@8.4.26): - resolution: {integrity: sha512-+mePA3MgdmVmv6g+30rn57USjOGSAyuxUmkfiWpzalZ8aiBkdPYjXWtHuwJGm1v5Ojy0Z0LaSYhHaLJQB0P8Jw==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - browserslist: 4.21.9 - cssnano-utils: 3.1.0(postcss@8.4.26) - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-minify-selectors@5.2.1(postcss@8.4.26): - resolution: {integrity: sha512-nPJu7OjZJTsVUmPdm2TcaiohIwxP+v8ha9NehQ2ye9szv4orirRU3SDdtUmKH+10nzn0bAyOXZ0UEr7OpvLehg==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /postcss-modules-extract-imports@3.0.0(postcss@8.4.26): - resolution: {integrity: sha512-bdHleFnP3kZ4NYDhuGlVK+CMrQ/pqUm8bx/oGL93K6gVwiclvX5x0n76fYMKuIGKzlABOy13zsvqjb0f92TEXw==} - engines: {node: ^10 || ^12 || >= 14} - peerDependencies: - postcss: ^8.1.0 - dependencies: - postcss: 8.4.26 - dev: false - - /postcss-modules-local-by-default@4.0.3(postcss@8.4.26): - resolution: {integrity: sha512-2/u2zraspoACtrbFRnTijMiQtb4GW4BvatjaG/bCjYQo8kLTdevCUlwuBHx2sCnSyrI3x3qj4ZK1j5LQBgzmwA==} - engines: {node: ^10 || ^12 || >= 14} - peerDependencies: - postcss: ^8.1.0 - dependencies: - icss-utils: 5.1.0(postcss@8.4.26) - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-modules-scope@3.0.0(postcss@8.4.26): - resolution: {integrity: sha512-hncihwFA2yPath8oZ15PZqvWGkWf+XUfQgUGamS4LqoP1anQLOsOJw0vr7J7IwLpoY9fatA2qiGUGmuZL0Iqlg==} - engines: {node: ^10 || ^12 || >= 14} - peerDependencies: - postcss: ^8.1.0 - dependencies: - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /postcss-modules-values@4.0.0(postcss@8.4.26): - resolution: {integrity: sha512-RDxHkAiEGI78gS2ofyvCsu7iycRv7oqw5xMWn9iMoR0N/7mf9D50ecQqUo5BZ9Zh2vH4bCUR/ktCqbB9m8vJjQ==} - engines: {node: ^10 || ^12 || >= 14} - peerDependencies: - postcss: ^8.1.0 - dependencies: - icss-utils: 5.1.0(postcss@8.4.26) - postcss: 8.4.26 - dev: false - - /postcss-nested@6.0.1(postcss@8.4.26): - resolution: {integrity: sha512-mEp4xPMi5bSWiMbsgoPfcP74lsWLHkQbZc3sY+jWYd65CUwXrUaTp0fmNpa01ZcETKlIgUdFN/MpS2xZtqL9dQ==} - engines: {node: '>=12.0'} - peerDependencies: - postcss: ^8.2.14 - dependencies: - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /postcss-nesting@10.2.0(postcss@8.4.26): - resolution: {integrity: sha512-EwMkYchxiDiKUhlJGzWsD9b2zvq/r2SSubcRrgP+jujMXFzqvANLt16lJANC+5uZ6hjI7lpRmI6O8JIl+8l1KA==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - '@csstools/selector-specificity': 2.2.0(postcss-selector-parser@6.0.13) - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /postcss-normalize-charset@5.1.0(postcss@8.4.26): - resolution: {integrity: sha512-mSgUJ+pd/ldRGVx26p2wz9dNZ7ji6Pn8VWBajMXFf8jk7vUoSrZ2lt/wZR7DtlZYKesmZI680qjr2CeFF2fbUg==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - dev: false - - /postcss-normalize-display-values@5.1.0(postcss@8.4.26): - resolution: {integrity: sha512-WP4KIM4o2dazQXWmFaqMmcvsKmhdINFblgSeRgn8BJ6vxaMyaJkwAzpPpuvSIoG/rmX3M+IrRZEz2H0glrQNEA==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-normalize-positions@5.1.1(postcss@8.4.26): - resolution: {integrity: sha512-6UpCb0G4eofTCQLFVuI3EVNZzBNPiIKcA1AKVka+31fTVySphr3VUgAIULBhxZkKgwLImhzMR2Bw1ORK+37INg==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-normalize-repeat-style@5.1.1(postcss@8.4.26): - resolution: {integrity: sha512-mFpLspGWkQtBcWIRFLmewo8aC3ImN2i/J3v8YCFUwDnPu3Xz4rLohDO26lGjwNsQxB3YF0KKRwspGzE2JEuS0g==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-normalize-string@5.1.0(postcss@8.4.26): - resolution: {integrity: sha512-oYiIJOf4T9T1N4i+abeIc7Vgm/xPCGih4bZz5Nm0/ARVJ7K6xrDlLwvwqOydvyL3RHNf8qZk6vo3aatiw/go3w==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-normalize-timing-functions@5.1.0(postcss@8.4.26): - resolution: {integrity: sha512-DOEkzJ4SAXv5xkHl0Wa9cZLF3WCBhF3o1SKVxKQAa+0pYKlueTpCgvkFAHfk+Y64ezX9+nITGrDZeVGgITJXjg==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-normalize-unicode@5.1.1(postcss@8.4.26): - resolution: {integrity: sha512-qnCL5jzkNUmKVhZoENp1mJiGNPcsJCs1aaRmURmeJGES23Z/ajaln+EPTD+rBeNkSryI+2WTdW+lwcVdOikrpA==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - browserslist: 4.21.9 - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-normalize-url@5.1.0(postcss@8.4.26): - resolution: {integrity: sha512-5upGeDO+PVthOxSmds43ZeMeZfKH+/DKgGRD7TElkkyS46JXAUhMzIKiCa7BabPeIy3AQcTkXwVVN7DbqsiCew==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - normalize-url: 6.1.0 - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-normalize-whitespace@5.1.1(postcss@8.4.26): - resolution: {integrity: sha512-83ZJ4t3NUDETIHTa3uEg6asWjSBYL5EdkVB0sDncx9ERzOKBVJIUeDO9RyA9Zwtig8El1d79HBp0JEi8wvGQnA==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-normalize@10.0.1(browserslist@4.21.9)(postcss@8.4.26): - resolution: {integrity: sha512-+5w18/rDev5mqERcG3W5GZNMJa1eoYYNGo8gB7tEwaos0ajk3ZXAI4mHGcNT47NE+ZnZD1pEpUOFLvltIwmeJA==} - engines: {node: '>= 12'} - peerDependencies: - browserslist: '>= 4' - postcss: '>= 8' - dependencies: - '@csstools/normalize.css': 12.0.0 - browserslist: 4.21.9 - postcss: 8.4.26 - postcss-browser-comments: 4.0.0(browserslist@4.21.9)(postcss@8.4.26) - sanitize.css: 13.0.0 - dev: false - - /postcss-opacity-percentage@1.1.3(postcss@8.4.26): - resolution: {integrity: sha512-An6Ba4pHBiDtyVpSLymUUERMo2cU7s+Obz6BTrS+gxkbnSBNKSuD0AVUc+CpBMrpVPKKfoVz0WQCX+Tnst0i4A==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - dev: false - - /postcss-ordered-values@5.1.3(postcss@8.4.26): - resolution: {integrity: sha512-9UO79VUhPwEkzbb3RNpqqghc6lcYej1aveQteWY+4POIwlqkYE21HKWaLDF6lWNuqCobEAyTovVhtI32Rbv2RQ==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - cssnano-utils: 3.1.0(postcss@8.4.26) - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-overflow-shorthand@3.0.4(postcss@8.4.26): - resolution: {integrity: sha512-otYl/ylHK8Y9bcBnPLo3foYFLL6a6Ak+3EQBPOTR7luMYCOsiVTUk1iLvNf6tVPNGXcoL9Hoz37kpfriRIFb4A==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-page-break@3.0.4(postcss@8.4.26): - resolution: {integrity: sha512-1JGu8oCjVXLa9q9rFTo4MbeeA5FMe00/9C7lN4va606Rdb+HkxXtXsmEDrIraQ11fGz/WvKWa8gMuCKkrXpTsQ==} - peerDependencies: - postcss: ^8 - dependencies: - postcss: 8.4.26 - dev: false - - /postcss-place@7.0.5(postcss@8.4.26): - resolution: {integrity: sha512-wR8igaZROA6Z4pv0d+bvVrvGY4GVHihBCBQieXFY3kuSuMyOmEnnfFzHl/tQuqHZkfkIVBEbDvYcFfHmpSet9g==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-preset-env@7.8.3(postcss@8.4.26): - resolution: {integrity: sha512-T1LgRm5uEVFSEF83vHZJV2z19lHg4yJuZ6gXZZkqVsqv63nlr6zabMH3l4Pc01FQCyfWVrh2GaUeCVy9Po+Aag==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - '@csstools/postcss-cascade-layers': 1.1.1(postcss@8.4.26) - '@csstools/postcss-color-function': 1.1.1(postcss@8.4.26) - '@csstools/postcss-font-format-keywords': 1.0.1(postcss@8.4.26) - '@csstools/postcss-hwb-function': 1.0.2(postcss@8.4.26) - '@csstools/postcss-ic-unit': 1.0.1(postcss@8.4.26) - '@csstools/postcss-is-pseudo-class': 2.0.7(postcss@8.4.26) - '@csstools/postcss-nested-calc': 1.0.0(postcss@8.4.26) - '@csstools/postcss-normalize-display-values': 1.0.1(postcss@8.4.26) - '@csstools/postcss-oklab-function': 1.1.1(postcss@8.4.26) - '@csstools/postcss-progressive-custom-properties': 1.3.0(postcss@8.4.26) - '@csstools/postcss-stepped-value-functions': 1.0.1(postcss@8.4.26) - '@csstools/postcss-text-decoration-shorthand': 1.0.0(postcss@8.4.26) - '@csstools/postcss-trigonometric-functions': 1.0.2(postcss@8.4.26) - '@csstools/postcss-unset-value': 1.0.2(postcss@8.4.26) - autoprefixer: 10.4.14(postcss@8.4.26) - browserslist: 4.21.9 - css-blank-pseudo: 3.0.3(postcss@8.4.26) - css-has-pseudo: 3.0.4(postcss@8.4.26) - css-prefers-color-scheme: 6.0.3(postcss@8.4.26) - cssdb: 7.6.0 - postcss: 8.4.26 - postcss-attribute-case-insensitive: 5.0.2(postcss@8.4.26) - postcss-clamp: 4.1.0(postcss@8.4.26) - postcss-color-functional-notation: 4.2.4(postcss@8.4.26) - postcss-color-hex-alpha: 8.0.4(postcss@8.4.26) - postcss-color-rebeccapurple: 7.1.1(postcss@8.4.26) - postcss-custom-media: 8.0.2(postcss@8.4.26) - postcss-custom-properties: 12.1.11(postcss@8.4.26) - postcss-custom-selectors: 6.0.3(postcss@8.4.26) - postcss-dir-pseudo-class: 6.0.5(postcss@8.4.26) - postcss-double-position-gradients: 3.1.2(postcss@8.4.26) - postcss-env-function: 4.0.6(postcss@8.4.26) - postcss-focus-visible: 6.0.4(postcss@8.4.26) - postcss-focus-within: 5.0.4(postcss@8.4.26) - postcss-font-variant: 5.0.0(postcss@8.4.26) - postcss-gap-properties: 3.0.5(postcss@8.4.26) - postcss-image-set-function: 4.0.7(postcss@8.4.26) - postcss-initial: 4.0.1(postcss@8.4.26) - postcss-lab-function: 4.2.1(postcss@8.4.26) - postcss-logical: 5.0.4(postcss@8.4.26) - postcss-media-minmax: 5.0.0(postcss@8.4.26) - postcss-nesting: 10.2.0(postcss@8.4.26) - postcss-opacity-percentage: 1.1.3(postcss@8.4.26) - postcss-overflow-shorthand: 3.0.4(postcss@8.4.26) - postcss-page-break: 3.0.4(postcss@8.4.26) - postcss-place: 7.0.5(postcss@8.4.26) - postcss-pseudo-class-any-link: 7.1.6(postcss@8.4.26) - postcss-replace-overflow-wrap: 4.0.0(postcss@8.4.26) - postcss-selector-not: 6.0.1(postcss@8.4.26) - postcss-value-parser: 4.2.0 - dev: false - - /postcss-pseudo-class-any-link@7.1.6(postcss@8.4.26): - resolution: {integrity: sha512-9sCtZkO6f/5ML9WcTLcIyV1yz9D1rf0tWc+ulKcvV30s0iZKS/ONyETvoWsr6vnrmW+X+KmuK3gV/w5EWnT37w==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /postcss-reduce-initial@5.1.2(postcss@8.4.26): - resolution: {integrity: sha512-dE/y2XRaqAi6OvjzD22pjTUQ8eOfc6m/natGHgKFBK9DxFmIm69YmaRVQrGgFlEfc1HePIurY0TmDeROK05rIg==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - browserslist: 4.21.9 - caniuse-api: 3.0.0 - postcss: 8.4.26 - dev: false - - /postcss-reduce-transforms@5.1.0(postcss@8.4.26): - resolution: {integrity: sha512-2fbdbmgir5AvpW9RLtdONx1QoYG2/EtqpNQbFASDlixBbAYuTcJ0dECwlqNqH7VbaUnEnh8SrxOe2sRIn24XyQ==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - dev: false - - /postcss-replace-overflow-wrap@4.0.0(postcss@8.4.26): - resolution: {integrity: sha512-KmF7SBPphT4gPPcKZc7aDkweHiKEEO8cla/GjcBK+ckKxiZslIu3C4GCRW3DNfL0o7yW7kMQu9xlZ1kXRXLXtw==} - peerDependencies: - postcss: ^8.0.3 - dependencies: - postcss: 8.4.26 - dev: false - - /postcss-selector-not@6.0.1(postcss@8.4.26): - resolution: {integrity: sha512-1i9affjAe9xu/y9uqWH+tD4r6/hDaXJruk8xn2x1vzxC2U3J3LKO3zJW4CyxlNhA56pADJ/djpEwpH1RClI2rQ==} - engines: {node: ^12 || ^14 || >=16} - peerDependencies: - postcss: ^8.2 - dependencies: - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /postcss-selector-parser@6.0.13: - resolution: {integrity: sha512-EaV1Gl4mUEV4ddhDnv/xtj7sxwrwxdetHdWUGnT4VJQf+4d05v6lHYZr8N573k5Z0BViss7BDhfWtKS3+sfAqQ==} - engines: {node: '>=4'} - dependencies: - cssesc: 3.0.0 - util-deprecate: 1.0.2 - dev: false - - /postcss-svgo@5.1.0(postcss@8.4.26): - resolution: {integrity: sha512-D75KsH1zm5ZrHyxPakAxJWtkyXew5qwS70v56exwvw542d9CRtTo78K0WeFxZB4G7JXKKMbEZtZayTGdIky/eA==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - postcss-value-parser: 4.2.0 - svgo: 2.8.0 - dev: false - - /postcss-unique-selectors@5.1.1(postcss@8.4.26): - resolution: {integrity: sha512-5JiODlELrz8L2HwxfPnhOWZYWDxVHWL83ufOv84NrcgipI7TaeRsatAhK4Tr2/ZiYldpK/wBvw5BD3qfaK96GA==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /postcss-value-parser@4.2.0: - resolution: {integrity: sha512-1NNCs6uurfkVbeXG4S8JFT9t19m45ICnif8zWLd5oPSZ50QnwMfK+H3jv408d4jw/7Bttv5axS5IiHoLaVNHeQ==} - dev: false - - /postcss@7.0.39: - resolution: {integrity: sha512-yioayjNbHn6z1/Bywyb2Y4s3yvDAeXGOyxqD+LnVOinq6Mdmd++SW2wUNVzavyyHxd6+DxzWGIuosg6P1Rj8uA==} - engines: {node: '>=6.0.0'} - dependencies: - picocolors: 0.2.1 - source-map: 0.6.1 - dev: false - - /postcss@8.4.26: - resolution: {integrity: sha512-jrXHFF8iTloAenySjM/ob3gSj7pCu0Ji49hnjqzsgSRa50hkWCKD0HQ+gMNJkW38jBI68MpAAg7ZWwHwX8NMMw==} - engines: {node: ^10 || ^12 || >=14} - dependencies: - nanoid: 3.3.6 - picocolors: 1.0.0 - source-map-js: 1.0.2 - dev: false + dev: true /postcss@8.4.31: resolution: {integrity: sha512-PS08Iboia9mts/2ygV3eLpY5ghnUcfLV/EXTOW1E2qYxJKGGBUtNjN76FYHnMs36RmARn41bC0AZmn+rR0OVpQ==} @@ -10414,6 +4277,7 @@ /prelude-ls@1.2.1: resolution: {integrity: sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==} engines: {node: '>= 0.8.0'} + dev: true /prettier@3.2.5: resolution: {integrity: sha512-3/GWa9aOC0YeD7LUfvOG2NiDyhOWRvt1k+rcKhOuYnMY24iiCphgneUfJDyFXd6rZCAnuLBv6UeAULtrhT/F4A==} @@ -10421,37 +4285,6 @@ hasBin: true dev: true - /pretty-bytes@5.6.0: - resolution: {integrity: sha512-FFw039TmrBqFK8ma/7OL3sDz/VytdtJr044/QUJtH0wK9lb9jLq9tJyIxUwtQJHwar2BqtiA4iCWSwo9JLkzFg==} - engines: {node: '>=6'} - dev: false - - /pretty-error@4.0.0: - resolution: {integrity: sha512-AoJ5YMAcXKYxKhuJGdcvse+Voc6v1RgnsR3nWcYU7q4t6z0Q6T86sv5Zq8VIRbOWWFpvdGE83LtdSMNd+6Y0xw==} - dependencies: - lodash: 4.17.21 - renderkid: 3.0.0 - dev: false - - /pretty-format@27.5.1: - resolution: {integrity: sha512-Qb1gy5OrP5+zDf2Bvnzdl3jsTf1qXVMazbvCoKhtKqVs4/YK4ozX4gKQJJVyNe+cajNPn0KoC0MC3FUmaHWEmQ==} - engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0} - dependencies: - ansi-regex: 5.0.1 - ansi-styles: 5.2.0 - react-is: 17.0.2 - dev: false - - /pretty-format@28.1.3: - resolution: {integrity: sha512-8gFb/To0OmxHR9+ZTb14Df2vNxdGCX8g1xWGUTqUw5TiZvcQf5sHKObd5UcPyLLyowNwDAMTF3XWOG1B6mxl1Q==} - engines: {node: ^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0} - dependencies: - '@jest/schemas': 28.1.3 - ansi-regex: 5.0.1 - ansi-styles: 5.2.0 - react-is: 18.2.0 - dev: false - /pretty-format@29.6.1: resolution: {integrity: sha512-7jRj+yXO0W7e4/tSJKoR7HRIHLPPjtNaUGG2xxKQnGvPNRkgWcQ0AZX6P4KBRJN4FcTBWb3sa7DVUJmocYuoog==} engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0} @@ -10461,24 +4294,6 @@ react-is: 18.2.0 dev: true - /process-nextick-args@2.0.1: - resolution: {integrity: sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==} - dev: false - - /promise@8.3.0: - resolution: {integrity: sha512-rZPNPKTOYVNEEKFaq1HqTgOwZD+4/YHS5ukLzQCypkj+OkYx7iv0mA91lJlpPPZ8vMau3IIGj5Qlwrx+8iiSmg==} - dependencies: - asap: 2.0.6 - dev: false - - /prompts@2.4.2: - resolution: {integrity: sha512-NxNv/kLguCA7p3jE8oL2aEBsrJWgAakBpgmgK6lpPWV+WuOmY6r2/zbAVnP+T8bQlA0nzHXSJSJW0Hq7ylaD2Q==} - engines: {node: '>= 6'} - dependencies: - kleur: 3.0.3 - sisteransi: 1.0.5 - dev: false - /prop-types@15.8.1: resolution: {integrity: sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==} dependencies: @@ -10486,14 +4301,6 @@ object-assign: 4.1.1 react-is: 16.13.1 - /proxy-addr@2.0.7: - resolution: {integrity: sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==} - engines: {node: '>= 0.10'} - dependencies: - forwarded: 0.2.0 - ipaddr.js: 1.9.1 - dev: false - /proxy-from-env@1.1.0: resolution: {integrity: sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==} dev: false @@ -10515,18 +4322,6 @@ resolution: {integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==} engines: {node: '>=6'} - /q@1.5.1: - resolution: {integrity: sha512-kV/CThkXo6xyFEZUugw/+pIOywXcDbFYgSct5cT3gqlbkBE1SJdwy6UQoZvodiWF/ckQLZyDE/Bu1M6gVu5lVw==} - engines: {node: '>=0.6.0', teleport: '>=0.2.0'} - dev: false - - /qs@6.11.0: - resolution: {integrity: sha512-MvjoMCJwEarSbUYk5O+nmoSzSutSsTwF85zcHPQ9OrlFoZOYIjaqBAJIqIXjptyD5vThxGq52Xu/MaJzRkIk4Q==} - engines: {node: '>=0.6'} - dependencies: - side-channel: 1.0.4 - dev: false - /qs@6.12.0: resolution: {integrity: sha512-trVZiI6RMOkO476zLGaBIzszOdFPnCCXHPG9kn0yuS1uz6xdVxPfZdB3vUig9pxPFDM9BRAgz/YUIVQ1/vuiUg==} engines: {node: '>=0.6'} @@ -10539,33 +4334,7 @@ /queue-microtask@1.2.3: resolution: {integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==} - - /raf@3.4.1: - resolution: {integrity: sha512-Sq4CW4QhwOHE8ucn6J34MqtZCeWFP2aQSmrlroYgqAV1PjStIhJXxYuTgUIfkEk7zTLjmIjLmU5q+fbD1NnOJA==} - dependencies: - performance-now: 2.1.0 - dev: false - - /randombytes@2.1.0: - resolution: {integrity: sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==} - dependencies: - safe-buffer: 5.2.1 - dev: false - - /range-parser@1.2.1: - resolution: {integrity: sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==} - engines: {node: '>= 0.6'} - dev: false - - /raw-body@2.5.1: - resolution: {integrity: sha512-qqJBtEyVgS0ZmPGdCFPWJ3FreoqvG4MVQln/kCgF7Olq95IbOp0/BWyMwbdtn4VTvkM8Y7khCQ2Xgk/tcrCXig==} - engines: {node: '>= 0.8'} - dependencies: - bytes: 3.1.2 - http-errors: 2.0.0 - iconv-lite: 0.4.24 - unpipe: 1.0.0 - dev: false + dev: true /raw-body@2.5.2: resolution: {integrity: sha512-8zGqypfENjCIqGhgXToC8aB2r7YrBX+AQAfIPs/Mlk+BtPTztOvTS01NRW/3Eh60J+a48lt8qsCzirQ6loCVfA==} @@ -10577,18 +4346,6 @@ unpipe: 1.0.0 dev: false - /react-app-polyfill@3.0.0: - resolution: {integrity: sha512-sZ41cxiU5llIB003yxxQBYrARBqe0repqPTTYBTmMqTz9szeBbE37BehCE891NZsmdZqqP+xWKdT3eo3vOzN8w==} - engines: {node: '>=14'} - dependencies: - core-js: 3.31.1 - object-assign: 4.1.1 - promise: 8.3.0 - raf: 3.4.1 - regenerator-runtime: 0.13.11 - whatwg-fetch: 3.6.2 - dev: false - /react-content-loader@7.0.0(react@18.2.0): resolution: {integrity: sha512-xaBwpO7eiJyEc4ndym+g6wcruV9W2y3DKqbw4U48QFBsv0IeAVZO+aCUb8GptlDLWM8n5zi2HcFSGlj5r+53Tg==} engines: {node: '>=10'} @@ -10609,48 +4366,6 @@ react-dom: 18.2.0(react@18.2.0) dev: false - /react-dev-utils@12.0.1(eslint@8.57.0)(typescript@5.4.2)(webpack@5.88.1): - resolution: {integrity: sha512-84Ivxmr17KjUupyqzFode6xKhjwuEJDROWKJy/BthkL7Wn6NJ8h4WE6k/exAv6ImS+0oZLRRW5j/aINMHyeGeQ==} - engines: {node: '>=14'} - peerDependencies: - typescript: '>=2.7' - webpack: '>=4' - peerDependenciesMeta: - typescript: - optional: true - dependencies: - '@babel/code-frame': 7.22.5 - address: 1.2.2 - browserslist: 4.21.9 - chalk: 4.1.2 - cross-spawn: 7.0.3 - detect-port-alt: 1.1.6 - escape-string-regexp: 4.0.0 - filesize: 8.0.7 - find-up: 5.0.0 - fork-ts-checker-webpack-plugin: 6.5.3(eslint@8.57.0)(typescript@5.4.2)(webpack@5.88.1) - global-modules: 2.0.0 - globby: 11.1.0 - gzip-size: 6.0.0 - immer: 9.0.21 - is-root: 2.1.0 - loader-utils: 3.2.1 - open: 8.4.2 - pkg-up: 3.1.0 - prompts: 2.4.2 - react-error-overlay: 6.0.11 - recursive-readdir: 2.2.3 - shell-quote: 1.8.1 - strip-ansi: 6.0.1 - text-table: 0.2.0 - typescript: 5.4.2 - webpack: 5.88.1 - transitivePeerDependencies: - - eslint - - supports-color - - vue-template-compiler - dev: false - /react-dom@18.2.0(react@18.2.0): resolution: {integrity: sha512-6IMTriUmvsjHUjNtEDudZfuDQUoWXVxKHhlEGSk81n4YFS+r/Kl99wXiwlVXtPBtJenozv2P+hxDsw9eA7Xo6g==} peerDependencies: @@ -10660,10 +4375,6 @@ react: 18.2.0 scheduler: 0.23.0 - /react-error-overlay@6.0.11: - resolution: {integrity: sha512-/6UZ2qgEyH2aqzYZgQPxEnz33NJ2gNsnHA2o5+o4wW9bLM/JYQitNP9xPhsXwC08hMMovfGe/8retsdDsczPRg==} - dev: false - /react-fast-compare@3.2.2: resolution: {integrity: sha512-nsO+KSNgo1SbJqJEYRE9ERzo7YtYbou/OqjSQKxV7jcKox7+usiUVZOAC+XnDOABXggQTno0Y1CpVnuWEc1boQ==} dev: false @@ -10680,12 +4391,9 @@ /react-is@16.13.1: resolution: {integrity: sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==} - /react-is@17.0.2: - resolution: {integrity: sha512-w2GsyukL62IJnlaff/nRegPQR94C/XXamvMWmSHRJ4y7Ts/4ocGRmTHvOs8PSE6pB3dWOrD/nueuU5sduBsQ4w==} - dev: false - /react-is@18.2.0: resolution: {integrity: sha512-xWGDIW6x921xtzPkhiULtthJHoJvBbF3q26fzloPCK0hsvxtPVelvftw3zjbHWSkR2km9Z+4uxbDDK/6Zw9B8w==} + dev: true /react-popper@2.3.0(@popperjs/core@2.11.8)(react-dom@18.2.0)(react@18.2.0): resolution: {integrity: sha512-e1hj8lL3uM+sgSR4Lxzn5h1GxBlpa4CQz0XLF8kx4MDrDRWY0Ena4c97PUeSX9i5W3UAfDP0z0FXCTQkoXUl3Q==} @@ -10701,108 +4409,6 @@ warning: 4.0.3 dev: false - /react-refresh@0.11.0: - resolution: {integrity: sha512-F27qZr8uUqwhWZboondsPx8tnC3Ct3SxZA3V5WyEvujRyyNv0VYPhoBg1gZ8/MV5tubQp76Trw8lTv9hzRBa+A==} - engines: {node: '>=0.10.0'} - dev: false - - /react-scripts@5.0.1(@babel/plugin-syntax-flow@7.23.3)(@babel/plugin-transform-react-jsx@7.23.4)(eslint@8.57.0)(react@18.2.0)(sass@1.72.0)(typescript@5.4.2): - resolution: {integrity: sha512-8VAmEm/ZAwQzJ+GOMLbBsTdDKOpuZh7RPs0UymvBR2vRk4iZWCskjbFnxqjrzoIvlNNRZ3QJFx6/qDSi6zSnaQ==} - engines: {node: '>=14.0.0'} - hasBin: true - peerDependencies: - eslint: '*' - react: '>= 16' - typescript: ^3.2.1 || ^4 - peerDependenciesMeta: - typescript: - optional: true - dependencies: - '@babel/core': 7.22.9 - '@pmmmwh/react-refresh-webpack-plugin': 0.5.10(react-refresh@0.11.0)(webpack-dev-server@4.15.1)(webpack@5.88.1) - '@svgr/webpack': 5.5.0 - babel-jest: 27.5.1(@babel/core@7.22.9) - babel-loader: 8.3.0(@babel/core@7.22.9)(webpack@5.88.1) - babel-plugin-named-asset-import: 0.3.8(@babel/core@7.22.9) - babel-preset-react-app: 10.0.1 - bfj: 7.0.2 - browserslist: 4.21.9 - camelcase: 6.3.0 - case-sensitive-paths-webpack-plugin: 2.4.0 - css-loader: 6.8.1(webpack@5.88.1) - css-minimizer-webpack-plugin: 3.4.1(webpack@5.88.1) - dotenv: 10.0.0 - dotenv-expand: 5.1.0 - eslint: 8.57.0 - eslint-config-react-app: 7.0.1(@babel/plugin-syntax-flow@7.23.3)(@babel/plugin-transform-react-jsx@7.23.4)(eslint@8.57.0)(jest@27.5.1)(typescript@5.4.2) - eslint-webpack-plugin: 3.2.0(eslint@8.57.0)(webpack@5.88.1) - file-loader: 6.2.0(webpack@5.88.1) - fs-extra: 10.1.0 - html-webpack-plugin: 5.5.3(webpack@5.88.1) - identity-obj-proxy: 3.0.0 - jest: 27.5.1 - jest-resolve: 27.5.1 - jest-watch-typeahead: 1.1.0(jest@27.5.1) - mini-css-extract-plugin: 2.7.6(webpack@5.88.1) - postcss: 8.4.26 - postcss-flexbugs-fixes: 5.0.2(postcss@8.4.26) - postcss-loader: 6.2.1(postcss@8.4.26)(webpack@5.88.1) - postcss-normalize: 10.0.1(browserslist@4.21.9)(postcss@8.4.26) - postcss-preset-env: 7.8.3(postcss@8.4.26) - prompts: 2.4.2 - react: 18.2.0 - react-app-polyfill: 3.0.0 - react-dev-utils: 12.0.1(eslint@8.57.0)(typescript@5.4.2)(webpack@5.88.1) - react-refresh: 0.11.0 - resolve: 1.22.2 - resolve-url-loader: 4.0.0 - sass-loader: 12.6.0(sass@1.72.0)(webpack@5.88.1) - semver: 7.5.4 - source-map-loader: 3.0.2(webpack@5.88.1) - style-loader: 3.3.3(webpack@5.88.1) - tailwindcss: 3.3.3 - terser-webpack-plugin: 5.3.9(webpack@5.88.1) - typescript: 5.4.2 - webpack: 5.88.1 - webpack-dev-server: 4.15.1(webpack@5.88.1) - webpack-manifest-plugin: 4.1.1(webpack@5.88.1) - workbox-webpack-plugin: 6.6.0(webpack@5.88.1) - optionalDependencies: - fsevents: 2.3.3 - transitivePeerDependencies: - - '@babel/plugin-syntax-flow' - - '@babel/plugin-transform-react-jsx' - - '@parcel/css' - - '@swc/core' - - '@types/babel__core' - - '@types/webpack' - - bufferutil - - canvas - - clean-css - - csso - - debug - - esbuild - - eslint-import-resolver-typescript - - eslint-import-resolver-webpack - - fibers - - node-notifier - - node-sass - - rework - - rework-visit - - sass - - sass-embedded - - sockjs-client - - supports-color - - ts-node - - type-fest - - uglify-js - - utf-8-validate - - vue-template-compiler - - webpack-cli - - webpack-hot-middleware - - webpack-plugin-serve - dev: false - /react-spinners@0.13.8(react-dom@18.2.0)(react@18.2.0): resolution: {integrity: sha512-3e+k56lUkPj0vb5NDXPVFAOkPC//XyhKPJjvcGjyMNPWsBKpplfeyialP74G7H7+It7KzhtET+MvGqbKgAqpZA==} peerDependencies: @@ -10819,7 +4425,7 @@ peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 dependencies: - '@babel/runtime': 7.22.6 + '@babel/runtime': 7.23.9 react: 18.2.0 use-composed-ref: 1.3.0(react@18.2.0) use-latest: 1.2.1(@types/react@18.2.65)(react@18.2.0) @@ -10874,24 +4480,6 @@ react-transition-group: 4.4.5(react-dom@18.2.0)(react@18.2.0) dev: false - /read-cache@1.0.0: - resolution: {integrity: sha512-Owdv/Ft7IjOgm/i0xvNDZ1LrRANRfew4b2prF3OWMQLxLfu3bS8FVhCsrSCMK4lR56Y9ya+AThoTpDCTxCmpRA==} - dependencies: - pify: 2.3.0 - dev: false - - /readable-stream@2.3.8: - resolution: {integrity: sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA==} - dependencies: - core-util-is: 1.0.3 - inherits: 2.0.4 - isarray: 1.0.0 - process-nextick-args: 2.0.1 - safe-buffer: 5.1.2 - string_decoder: 1.1.1 - util-deprecate: 1.0.2 - dev: false - /readable-stream@3.6.2: resolution: {integrity: sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==} engines: {node: '>= 6'} @@ -10907,13 +4495,6 @@ dependencies: picomatch: 2.3.1 - /recursive-readdir@2.2.3: - resolution: {integrity: sha512-8HrF5ZsXk5FAH9dgsx3BlUer73nIhuj+9OrQwEbLTPOBzGkL1lsFCR01am+v+0m2Cmbs1nP12hLDl5FA7EszKA==} - engines: {node: '>=6.0.0'} - dependencies: - minimatch: 3.1.2 - dev: false - /reflect.getprototypeof@1.0.5: resolution: {integrity: sha512-62wgfC8dJWrmxv44CA36pLDnP6KKl3Vhxb7PL+8+qrrFMMoJij4vgiMP8zV4O8+CBMXY1mHxI5fITGHXFHVmQQ==} engines: {node: '>= 0.4'} @@ -10927,34 +4508,9 @@ which-builtin-type: 1.1.3 dev: true - /regenerate-unicode-properties@10.1.0: - resolution: {integrity: sha512-d1VudCLoIGitcU/hEg2QqvyGZQmdC0Lf8BqdOMXGFSvJP4bNV1+XqbPQeHHLD51Jh4QJJ225dlIFvY4Ly6MXmQ==} - engines: {node: '>=4'} - dependencies: - regenerate: 1.4.2 - dev: false - - /regenerate@1.4.2: - resolution: {integrity: sha512-zrceR/XhGYU/d/opr2EKO7aRHUeiBI8qjtfHqADTwZd6Szfy16la6kqD0MIUs5z5hx6AaKa+PixpPrR289+I0A==} - dev: false - - /regenerator-runtime@0.13.11: - resolution: {integrity: sha512-kY1AZVr2Ra+t+piVaJ4gxaFaReZVH40AKNo7UCX6W+dEwBo/2oZJzqfuN1qLq1oL45o56cPaTXELwrTh8Fpggg==} - dev: false - /regenerator-runtime@0.14.0: resolution: {integrity: sha512-srw17NI0TUWHuGa5CFGGmhfNIeja30WMBfbslPNhf6JrqQlLN5gcrvig1oqPxiVaXb0oW0XRKtH6Nngs5lKCIA==} - /regenerator-transform@0.15.1: - resolution: {integrity: sha512-knzmNAcuyxV+gQCufkYcvOqX/qIIfHLv0u5x79kRxuGojfYVky1f15TzZEu2Avte8QGepvUNTnLskf8E6X6Vyg==} - dependencies: - '@babel/runtime': 7.23.9 - dev: false - - /regex-parser@2.2.11: - resolution: {integrity: sha512-jbD/FT0+9MBU2XAZluI7w2OBs1RBi6p9M83nkoZayQXXU9e8Robt69FcZc7wU4eJD/YFTjn1JdCk3rbMJajz8Q==} - dev: false - /regexp.prototype.flags@1.5.0: resolution: {integrity: sha512-0SutC3pNudRKgquxGoRGIz946MZVHqbNfPjBdxeOhBrdgDKlRoXmYLQN9xRbrR09ZXWeGAdPuif7egofn6v5LA==} engines: {node: '>= 0.4'} @@ -10962,6 +4518,7 @@ call-bind: 1.0.2 define-properties: 1.2.0 functions-have-names: 1.2.3 + dev: true /regexp.prototype.flags@1.5.2: resolution: {integrity: sha512-NcDiDkTLuPR+++OCKB0nWafEmhg/Da8aUPLPMQbK+bxKKCm1/S5he+AqYa4PlMCVBalb4/yxIRub6qkEx5yJbw==} @@ -10971,96 +4528,25 @@ define-properties: 1.2.1 es-errors: 1.3.0 set-function-name: 2.0.2 - - /regexpu-core@5.3.2: - resolution: {integrity: sha512-RAM5FlZz+Lhmo7db9L298p2vHP5ZywrVXmVXpmAD9GuL5MPH6t9ROw1iA/wfHkQ76Qe7AaPF0nGuim96/IrQMQ==} - engines: {node: '>=4'} - dependencies: - '@babel/regjsgen': 0.8.0 - regenerate: 1.4.2 - regenerate-unicode-properties: 10.1.0 - regjsparser: 0.9.1 - unicode-match-property-ecmascript: 2.0.0 - unicode-match-property-value-ecmascript: 2.1.0 - dev: false - - /regjsparser@0.9.1: - resolution: {integrity: sha512-dQUtn90WanSNl+7mQKcXAgZxvUe7Z0SqXlgzv0za4LwiUhyzBC58yQO3liFoUgu8GiJVInAhJjkj1N0EtQ5nkQ==} - hasBin: true - dependencies: - jsesc: 0.5.0 - dev: false - - /relateurl@0.2.7: - resolution: {integrity: sha512-G08Dxvm4iDN3MLM0EsP62EDV9IuhXPR6blNz6Utcp7zyV3tr4HVNINt6MpaRWbxoOHT3Q7YN2P+jaHX8vUbgog==} - engines: {node: '>= 0.10'} - dev: false - - /renderkid@3.0.0: - resolution: {integrity: sha512-q/7VIQA8lmM1hF+jn+sFSPWGlMkSAeNYcPLmDQx2zzuiDfaLrOmumR8iaUKlenFgh0XRPIUeSPlH3A+AW3Z5pg==} - dependencies: - css-select: 4.3.0 - dom-converter: 0.2.0 - htmlparser2: 6.1.0 - lodash: 4.17.21 - strip-ansi: 6.0.1 - dev: false + dev: true /require-directory@2.1.1: resolution: {integrity: sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q==} engines: {node: '>=0.10.0'} - - /require-from-string@2.0.2: - resolution: {integrity: sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==} - engines: {node: '>=0.10.0'} - dev: false + dev: true /requires-port@1.0.0: resolution: {integrity: sha512-KigOCHcocU3XODJxsu8i/j8T9tzT4adHiecwORRQ0ZZFcp7ahwXuRU1m+yuO90C5ZUyGeGfocHDI14M3L3yDAQ==} dev: false - /resolve-cwd@3.0.0: - resolution: {integrity: sha512-OrZaX2Mb+rJCpH/6CpSqt9xFVpN++x01XnN2ie9g6P5/3xelLAkXWVADpdz1IHD/KFfEXyE6V0U01OQ3UO2rEg==} - engines: {node: '>=8'} - dependencies: - resolve-from: 5.0.0 - dev: false - /resolve-from@4.0.0: resolution: {integrity: sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==} engines: {node: '>=4'} - - /resolve-from@5.0.0: - resolution: {integrity: sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==} - engines: {node: '>=8'} - dev: false + dev: true /resolve-pkg-maps@1.0.0: resolution: {integrity: sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw==} - - /resolve-url-loader@4.0.0: - resolution: {integrity: sha512-05VEMczVREcbtT7Bz+C+96eUO5HDNvdthIiMB34t7FcF8ehcu4wC0sSgPUubs3XW2Q3CNLJk/BJrCU9wVRymiA==} - engines: {node: '>=8.9'} - peerDependencies: - rework: 1.0.1 - rework-visit: 1.0.0 - peerDependenciesMeta: - rework: - optional: true - rework-visit: - optional: true - dependencies: - adjust-sourcemap-loader: 4.0.0 - convert-source-map: 1.9.0 - loader-utils: 2.0.4 - postcss: 7.0.39 - source-map: 0.6.1 - dev: false - - /resolve.exports@1.1.1: - resolution: {integrity: sha512-/NtpHNDN7jWhAaQ9BvBUYZ6YTXsRBgfqWFWP7BZBaoMJO/I3G5OFzvTuWNlZC3aPjins1F+TNrLKsGbH4rfsRQ==} - engines: {node: '>=10'} - dev: false + dev: true /resolve@1.22.2: resolution: {integrity: sha512-Sb+mjNHOULsBv818T40qSPeRiuWLyaGMa5ewydRLFimneixmVy2zdivRl+AF6jaYPC8ERxGDmFSiqui6SfPd+g==} @@ -11069,6 +4555,7 @@ is-core-module: 2.12.1 path-parse: 1.0.7 supports-preserve-symlinks-flag: 1.0.0 + dev: true /resolve@1.22.8: resolution: {integrity: sha512-oKWePCxqpd6FlLvGV1VU0x7bkPmmCNolxzjMf4NczoDnQcIWrAF+cPtZn5i6n+RfD2d9i0tzpKnG6Yk168yIyw==} @@ -11077,15 +4564,7 @@ is-core-module: 2.13.1 path-parse: 1.0.7 supports-preserve-symlinks-flag: 1.0.0 - - /resolve@2.0.0-next.4: - resolution: {integrity: sha512-iMDbmAWtfU+MHpxt/I5iWI7cY6YVEZUQ3MBgPQ++XD1PELuJHIl82xBmObyP2KyQmkNB2dsqF7seoQQiAn5yDQ==} - hasBin: true - dependencies: - is-core-module: 2.12.1 - path-parse: 1.0.7 - supports-preserve-symlinks-flag: 1.0.0 - dev: false + dev: true /resolve@2.0.0-next.5: resolution: {integrity: sha512-U7WjGVG9sH8tvjW5SmGbQuui75FiyjAX72HX15DwBBwF9dNiQZRQAg9nnPhYy+TUnE0+VcrttuvNI8oSxZcocA==} @@ -11096,41 +4575,17 @@ supports-preserve-symlinks-flag: 1.0.0 dev: true - /retry@0.13.1: - resolution: {integrity: sha512-XQBQ3I8W1Cge0Seh+6gjj03LbmRFWuoszgK9ooCpwYIrhhoO80pfq4cUkU5DkknwfOfFteRwlZ56PYOGYyFWdg==} - engines: {node: '>= 4'} - dev: false - /reusify@1.0.4: resolution: {integrity: sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==} engines: {iojs: '>=1.0.0', node: '>=0.10.0'} + dev: true /rimraf@3.0.2: resolution: {integrity: sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==} hasBin: true dependencies: glob: 7.2.3 - - /rollup-plugin-terser@7.0.2(rollup@2.79.1): - resolution: {integrity: sha512-w3iIaU4OxcF52UUXiZNsNeuXIMDvFrr+ZXK6bFZ0Q60qyVfq4uLptoS4bbq3paG3x216eQllFZX7zt6TIImguQ==} - deprecated: This package has been deprecated and is no longer maintained. Please use @rollup/plugin-terser - peerDependencies: - rollup: ^2.0.0 - dependencies: - '@babel/code-frame': 7.22.5 - jest-worker: 26.6.2 - rollup: 2.79.1 - serialize-javascript: 4.0.0 - terser: 5.19.0 - dev: false - - /rollup@2.79.1: - resolution: {integrity: sha512-uKxbd0IhMZOhjAiD5oAFp7BqvkA4Dv47qpOCtaNvng4HBwdbWtdOh8f5nZNuk2rp51PMGk3bzfWu5oayNEuYnw==} - engines: {node: '>=10.0.0'} - hasBin: true - optionalDependencies: - fsevents: 2.3.3 - dev: false + dev: true /rollup@4.13.0: resolution: {integrity: sha512-3YegKemjoQnYKmsBlOHfMLVPPA5xLkQ8MHLLSw/fBrFaVkEayL51DilPpNNLq1exr98F2B1TzrV0FUlN3gWRPg==} @@ -11163,6 +4618,7 @@ resolution: {integrity: sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==} dependencies: queue-microtask: 1.2.3 + dev: true /rxjs@7.8.1: resolution: {integrity: sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==} @@ -11178,6 +4634,7 @@ get-intrinsic: 1.2.1 has-symbols: 1.0.3 isarray: 2.0.5 + dev: true /safe-array-concat@1.1.2: resolution: {integrity: sha512-vj6RsCsWBCf19jIeHEfkRMw8DPiBb+DMXklQ/1SGDHOMlHdPUkZXFQ2YdplS23zESTijAcurb1aSgJA3AgMu1Q==} @@ -11187,10 +4644,7 @@ get-intrinsic: 1.2.4 has-symbols: 1.0.3 isarray: 2.0.5 - - /safe-buffer@5.1.2: - resolution: {integrity: sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==} - dev: false + dev: true /safe-buffer@5.2.1: resolution: {integrity: sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==} @@ -11202,6 +4656,7 @@ call-bind: 1.0.2 get-intrinsic: 1.2.1 is-regex: 1.1.4 + dev: true /safe-regex-test@1.0.3: resolution: {integrity: sha512-CdASjNJPvRa7roO6Ra/gLYBTzYzzPyyBXxIMdGW3USQLyjWEls2RgW5UBTXaQVp+OrpeCK3bLem8smtmheoRuw==} @@ -11210,6 +4665,7 @@ call-bind: 1.0.7 es-errors: 1.3.0 is-regex: 1.1.4 + dev: true /safe-stable-stringify@2.4.3: resolution: {integrity: sha512-e2bDA2WJT0wxseVd4lsDP4+3ONX6HpMXQa1ZhFQ7SU+GjvORCmShbCMltrtIDfkYhVHrOcPtj+KhmDBdPdZD1g==} @@ -11220,35 +4676,6 @@ resolution: {integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==} dev: false - /sanitize.css@13.0.0: - resolution: {integrity: sha512-ZRwKbh/eQ6w9vmTjkuG0Ioi3HBwPFce0O+v//ve+aOq1oeCy7jMV2qzzAlpsNuqpqCBjjriM1lbtZbF/Q8jVyA==} - dev: false - - /sass-loader@12.6.0(sass@1.72.0)(webpack@5.88.1): - resolution: {integrity: sha512-oLTaH0YCtX4cfnJZxKSLAyglED0naiYfNG1iXfU5w1LNZ+ukoA5DtyDIN5zmKVZwYNJP4KRc5Y3hkWga+7tYfA==} - engines: {node: '>= 12.13.0'} - peerDependencies: - fibers: '>= 3.1.0' - node-sass: ^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0 - sass: ^1.3.0 - sass-embedded: '*' - webpack: ^5.0.0 - peerDependenciesMeta: - fibers: - optional: true - node-sass: - optional: true - sass: - optional: true - sass-embedded: - optional: true - dependencies: - klona: 2.0.6 - neo-async: 2.6.2 - sass: 1.72.0 - webpack: 5.88.1 - dev: false - /sass@1.72.0: resolution: {integrity: sha512-Gpczt3WA56Ly0Mn8Sl21Vj94s1axi9hDIzDFn9Ph9x3C3p4nNyvsqJoQyVXKou6cBlfFWEgRW4rT8Tb4i3XnVA==} engines: {node: '>=14.0.0'} @@ -11258,17 +4685,6 @@ immutable: 4.3.1 source-map-js: 1.0.2 - /sax@1.2.4: - resolution: {integrity: sha512-NqVDv9TpANUjFm0N8uM5GxL36UgKi9/atZw+x7YFnQ8ckwFGKrl4xX4yWtrey3UJm5nP1kUbnYgLopqWNSRhWw==} - dev: false - - /saxes@5.0.1: - resolution: {integrity: sha512-5LBh1Tls8c9xgGjw3QrMwETmTMVk0oFgvrFSvWx62llR2hcEInrKNZ2GZCCuuy2lvWrdl5jhbpeqc5hRYKFOcw==} - engines: {node: '>=10'} - dependencies: - xmlchars: 2.2.0 - dev: false - /saxes@6.0.0: resolution: {integrity: sha512-xAg7SOnEhrm5zI3puOOKyy1OMcMlIJZYNJY7xLBwSze0UjhPLnWfj2GF2EpT0jmzaJKIWKHLsaSSajf35bcYnA==} engines: {node: '>=v12.22.7'} @@ -11281,57 +4697,10 @@ dependencies: loose-envify: 1.4.0 - /schema-utils@2.7.0: - resolution: {integrity: sha512-0ilKFI6QQF5nxDZLFn2dMjvc4hjg/Wkg7rHd3jK6/A4a1Hl9VFdQWvgB1UMGoU94pad1P/8N7fMcEnLnSiju8A==} - engines: {node: '>= 8.9.0'} - dependencies: - '@types/json-schema': 7.0.12 - ajv: 6.12.6 - ajv-keywords: 3.5.2(ajv@6.12.6) - dev: false - - /schema-utils@2.7.1: - resolution: {integrity: sha512-SHiNtMOUGWBQJwzISiVYKu82GiV4QYGePp3odlY1tuKO7gPtphAT5R/py0fA6xtbgLL/RvtJZnU9b8s0F1q0Xg==} - engines: {node: '>= 8.9.0'} - dependencies: - '@types/json-schema': 7.0.12 - ajv: 6.12.6 - ajv-keywords: 3.5.2(ajv@6.12.6) - dev: false - - /schema-utils@3.3.0: - resolution: {integrity: sha512-pN/yOAvcC+5rQ5nERGuwrjLlYvLTbCibnZ1I7B1LaiAz9BRBlE9GMgE/eqV30P7aJQUf7Ddimy/RsbYO/GrVGg==} - engines: {node: '>= 10.13.0'} - dependencies: - '@types/json-schema': 7.0.12 - ajv: 6.12.6 - ajv-keywords: 3.5.2(ajv@6.12.6) - dev: false - - /schema-utils@4.2.0: - resolution: {integrity: sha512-L0jRsrPpjdckP3oPug3/VxNKt2trR8TcabrM6FOAAlvC/9Phcmm+cuAgTlxBqdBR1WJx7Naj9WHw+aOmheSVbw==} - engines: {node: '>= 12.13.0'} - dependencies: - '@types/json-schema': 7.0.12 - ajv: 8.12.0 - ajv-formats: 2.1.1(ajv@8.12.0) - ajv-keywords: 5.1.0(ajv@8.12.0) - dev: false - - /select-hose@2.0.0: - resolution: {integrity: sha512-mEugaLK+YfkijB4fx0e6kImuJdCIt2LxCRcbEYPqRGCs4F2ogyfZU5IAZRdjCP8JPq2AtdNoC/Dux63d9Kiryg==} - dev: false - - /selfsigned@2.1.1: - resolution: {integrity: sha512-GSL3aowiF7wa/WtSFwnUrludWFoNhftq8bUkH9pkzjpN2XSPOAYEgg6e0sS9s0rZwgJzJiQRPU18A6clnoW5wQ==} - engines: {node: '>=10'} - dependencies: - node-forge: 1.3.1 - dev: false - /semver@6.3.1: resolution: {integrity: sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==} hasBin: true + dev: true /semver@7.5.4: resolution: {integrity: sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA==} @@ -11340,66 +4709,6 @@ dependencies: lru-cache: 6.0.0 - /send@0.18.0: - resolution: {integrity: sha512-qqWzuOjSFOuqPjFe4NOsMLafToQQwBSOEpS+FwEt3A2V3vKubTquT3vmLTQpFgMXp8AlFWFuP1qKaJZOtPpVXg==} - engines: {node: '>= 0.8.0'} - dependencies: - debug: 2.6.9 - depd: 2.0.0 - destroy: 1.2.0 - encodeurl: 1.0.2 - escape-html: 1.0.3 - etag: 1.8.1 - fresh: 0.5.2 - http-errors: 2.0.0 - mime: 1.6.0 - ms: 2.1.3 - on-finished: 2.4.1 - range-parser: 1.2.1 - statuses: 2.0.1 - transitivePeerDependencies: - - supports-color - dev: false - - /serialize-javascript@4.0.0: - resolution: {integrity: sha512-GaNA54380uFefWghODBWEGisLZFj00nS5ACs6yHa9nLqlLpVLO8ChDGeKRjZnV4Nh4n0Qi7nhYZD/9fCPzEqkw==} - dependencies: - randombytes: 2.1.0 - dev: false - - /serialize-javascript@6.0.1: - resolution: {integrity: sha512-owoXEFjWRllis8/M1Q+Cw5k8ZH40e3zhp/ovX+Xr/vi1qj6QesbyXXViFbpNvWvPNAD62SutwEXavefrLJWj7w==} - dependencies: - randombytes: 2.1.0 - dev: false - - /serve-index@1.9.1: - resolution: {integrity: sha512-pXHfKNP4qujrtteMrSBb0rc8HJ9Ms/GrXwcUtUtD5s4ewDJI8bT3Cz2zTVRMKtri49pLx2e0Ya8ziP5Ya2pZZw==} - engines: {node: '>= 0.8.0'} - dependencies: - accepts: 1.3.8 - batch: 0.6.1 - debug: 2.6.9 - escape-html: 1.0.3 - http-errors: 1.6.3 - mime-types: 2.1.35 - parseurl: 1.3.3 - transitivePeerDependencies: - - supports-color - dev: false - - /serve-static@1.15.0: - resolution: {integrity: sha512-XGuRDNjXUijsUL0vl6nSD7cwURuzEgglbOaFuZM9g3kwDXOWVTck0jLzjPzGD+TazWbboZYu52/9/XPdUgne9g==} - engines: {node: '>= 0.8.0'} - dependencies: - encodeurl: 1.0.2 - escape-html: 1.0.3 - parseurl: 1.3.3 - send: 0.18.0 - transitivePeerDependencies: - - supports-color - dev: false - /set-function-length@1.2.1: resolution: {integrity: sha512-j4t6ccc+VsKwYHso+kElc5neZpjtq9EnRICFZtWyBsLojhmeF/ZBd/elqm22WJh/BziDe/SBiOeAt0m2mfLD0g==} engines: {node: '>= 0.4'} @@ -11419,10 +4728,7 @@ es-errors: 1.3.0 functions-have-names: 1.2.3 has-property-descriptors: 1.0.2 - - /setprototypeof@1.1.0: - resolution: {integrity: sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==} - dev: false + dev: true /setprototypeof@1.2.0: resolution: {integrity: sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==} @@ -11463,13 +4769,16 @@ engines: {node: '>=8'} dependencies: shebang-regex: 3.0.0 + dev: true /shebang-regex@3.0.0: resolution: {integrity: sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==} engines: {node: '>=8'} + dev: true /shell-quote@1.8.1: resolution: {integrity: sha512-6j1W9l1iAs/4xYBI1SYOVZyFcCis9b4KCLQ8fgAGG07QvzaRLVVRQvAy85yNmmZSjYjg4MWh4gNvlPujU/5LpA==} + dev: true /side-channel@1.0.4: resolution: {integrity: sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==} @@ -11477,6 +4786,7 @@ call-bind: 1.0.2 get-intrinsic: 1.2.1 object-inspect: 1.12.3 + dev: true /side-channel@1.0.6: resolution: {integrity: sha512-fDW/EZ6Q9RiO8eFG8Hj+7u/oW+XrPTIChwCOM2+th2A6OblDtYYIpve9m+KvI9Z4C9qSEXlaGR6bTEYHReuglA==} @@ -11487,10 +4797,6 @@ get-intrinsic: 1.2.4 object-inspect: 1.13.1 - /signal-exit@3.0.7: - resolution: {integrity: sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==} - dev: false - /signal-exit@4.1.0: resolution: {integrity: sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw==} engines: {node: '>=14'} @@ -11509,119 +4815,19 @@ semver: 7.5.4 dev: true - /sisteransi@1.0.5: - resolution: {integrity: sha512-bLGGlR1QxBcynn2d5YmDX4MGjlZvy2MRBDRNHLJ8VI6l6+9FUiyTFNJ0IveOSP0bcXgVDPRcfGqA0pjaqUpfVg==} - dev: false - /slash@3.0.0: resolution: {integrity: sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q==} engines: {node: '>=8'} - - /slash@4.0.0: - resolution: {integrity: sha512-3dOsAHXXUkQTpOYcoAxLIorMTp4gIQr5IW3iVb7A7lFIp0VHhnynm9izx6TssdrIcVIESAlVjtnO2K8bg+Coew==} - engines: {node: '>=12'} - dev: false - - /sockjs@0.3.24: - resolution: {integrity: sha512-GJgLTZ7vYb/JtPSSZ10hsOYIvEYsjbNU+zPdIHcUaWVNUEPivzxku31865sSSud0Da0W4lEeOPlmw93zLQchuQ==} - dependencies: - faye-websocket: 0.11.4 - uuid: 8.3.2 - websocket-driver: 0.7.4 - dev: false - - /source-list-map@2.0.1: - resolution: {integrity: sha512-qnQ7gVMxGNxsiL4lEuJwe/To8UnK7fAnmbGEEH8RpLouuKbeEm0lhbQVFIrNSuB+G7tVrAlVsZgETT5nljf+Iw==} - dev: false + dev: true /source-map-js@1.0.2: resolution: {integrity: sha512-R0XvVJ9WusLiqTCEiGCmICCMplcCkIwwR11mOSD9CR5u+IXYdiseeEuXCVAjS54zqwkLcPNnmU4OeJ6tUrWhDw==} engines: {node: '>=0.10.0'} - /source-map-loader@3.0.2(webpack@5.88.1): - resolution: {integrity: sha512-BokxPoLjyl3iOrgkWaakaxqnelAJSS+0V+De0kKIq6lyWrXuiPgYTGp6z3iHmqljKAaLXwZa+ctD8GccRJeVvg==} - engines: {node: '>= 12.13.0'} - peerDependencies: - webpack: ^5.0.0 - dependencies: - abab: 2.0.6 - iconv-lite: 0.6.3 - source-map-js: 1.0.2 - webpack: 5.88.1 - dev: false - - /source-map-support@0.5.21: - resolution: {integrity: sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w==} - dependencies: - buffer-from: 1.1.2 - source-map: 0.6.1 - dev: false - - /source-map@0.6.1: - resolution: {integrity: sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==} - engines: {node: '>=0.10.0'} - dev: false - - /source-map@0.7.4: - resolution: {integrity: sha512-l3BikUxvPOcn5E74dZiq5BGsTb5yEwhaTSzccU6t4sDOH8NWJCstKO5QT2CvtFoK6F0saL7p9xHAqHOlCPJygA==} - engines: {node: '>= 8'} - dev: false - - /source-map@0.8.0-beta.0: - resolution: {integrity: sha512-2ymg6oRBpebeZi9UUNsgQ89bhx01TcTkmNTGnNO88imTmbSgy4nfujrgVEFKWpMTEGA11EDkTt7mqObTPdigIA==} - engines: {node: '>= 8'} - dependencies: - whatwg-url: 7.1.0 - dev: false - - /sourcemap-codec@1.4.8: - resolution: {integrity: sha512-9NykojV5Uih4lgo5So5dtw+f0JgJX30KCNI8gwhz2J9A15wD0Ml6tjHKwf6fTSa6fAdVBdZeNOs9eJ71qCk8vA==} - deprecated: Please use @jridgewell/sourcemap-codec instead - dev: false - /spawn-command@0.0.2: resolution: {integrity: sha512-zC8zGoGkmc8J9ndvml8Xksr1Amk9qBujgbF0JAIWO7kXr43w0h/0GJNM/Vustixu+YE8N/MTrQ7N31FvHUACxQ==} dev: true - /spdy-transport@3.0.0: - resolution: {integrity: sha512-hsLVFE5SjA6TCisWeJXFKniGGOpBgMLmerfO2aCyCU5s7nJ/rpAepqmFifv/GCbSbueEeAJJnmSQ2rKC/g8Fcw==} - dependencies: - debug: 4.3.4(supports-color@5.5.0) - detect-node: 2.1.0 - hpack.js: 2.1.6 - obuf: 1.1.2 - readable-stream: 3.6.2 - wbuf: 1.7.3 - transitivePeerDependencies: - - supports-color - dev: false - - /spdy@4.0.2: - resolution: {integrity: sha512-r46gZQZQV+Kl9oItvl1JZZqJKGr+oEkB08A6BzkiR7593/7IbtuncXHd2YoYeTsG4157ZssMu9KYvUHLcjcDoA==} - engines: {node: '>=6.0.0'} - dependencies: - debug: 4.3.4(supports-color@5.5.0) - handle-thing: 2.0.1 - http-deceiver: 1.2.7 - select-hose: 2.0.0 - spdy-transport: 3.0.0 - transitivePeerDependencies: - - supports-color - dev: false - - /sprintf-js@1.0.3: - resolution: {integrity: sha512-D9cPgkvLlV3t3IzL0D0YLvGA9Ahk4PcvVwUbN0dSGr1aP0Nrt4AEnTUbuGvquEC0mA64Gqt1fzirlRs5ibXx8g==} - dev: false - - /sprintf-js@1.1.3: - resolution: {integrity: sha512-Oo+0REFV59/rz3gfJNKQiBlwfHaSESl1pcGyABQsnnIfWOFt6JNj5gCog2U6MLZ//IGYD+nA8nI+mTShREReaA==} - dev: false - - /stable@0.1.8: - resolution: {integrity: sha512-ji9qxRnOVfcuLDySj9qzhGSEFVobyt1kIOSkj1qZzYLzq7Tos/oUUWvotUPQLlrsidqsK6tBH89Bc9kL5zHA6w==} - deprecated: 'Modern JS already guarantees Array#sort() is a stable sort, so this library is deprecated. See the compatibility table on MDN: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/sort#browser_compatibility' - dev: false - /stack-trace@0.0.10: resolution: {integrity: sha512-KGzahc7puUKkzyMt+IqAep+TVNbKP+k2Lmwhub39m1AsTSkaDutx56aDCo+HLDzf/D26BIHTJWNiTG1KAJiQCg==} dev: false @@ -11631,10 +4837,7 @@ engines: {node: '>=10'} dependencies: escape-string-regexp: 2.0.0 - - /stackframe@1.3.4: - resolution: {integrity: sha512-oeVtt7eWQS+Na6F//S4kJ2K2VbRlS9D43mAlMyVpVWovy9o+jfgH8O9agzANzaiLjclA0oYzUXEM4PurhSUChw==} - dev: false + dev: true /statuses@1.5.0: resolution: {integrity: sha512-OpZ3zP+jT1PI7I8nemJX4AKmAX070ZkYPVWV/AaKTJl+tXCTGyVdC1a4SL8RUQYEwk/f34ZX8UTykN68FwrqAA==} @@ -11650,26 +4853,6 @@ resolution: {integrity: sha512-Mcc5wHehp9aXz1ax6bZUyY5afg9u2rv5cqQI3mRrYkGC8rW2hM02jWuwjtL++LS5qinSyhj2QfLyNsuc+VsExg==} engines: {node: '>=10.0.0'} - /string-length@4.0.2: - resolution: {integrity: sha512-+l6rNN5fYHNhZZy41RXsYptCjA2Igmq4EG7kZAYFQI1E1VTXarr6ZPXBg6eq7Y6eK4FEhY6AJlyuFIb/v/S0VQ==} - engines: {node: '>=10'} - dependencies: - char-regex: 1.0.2 - strip-ansi: 6.0.1 - dev: false - - /string-length@5.0.1: - resolution: {integrity: sha512-9Ep08KAMUn0OadnVaBuRdE2l615CQ508kr0XMadjClfYpdCyvrbFp6Taebo8yyxokQ4viUd/xPPUA4FGgUa0ow==} - engines: {node: '>=12.20'} - dependencies: - char-regex: 2.0.1 - strip-ansi: 7.1.0 - dev: false - - /string-natural-compare@3.0.1: - resolution: {integrity: sha512-n3sPwynL1nwKi3WJ6AIsClwBMa0zTi54fn2oLU6ndfTSIO05xaznjSf15PcBZU6FNWbmN5Q6cxT4V5hGvB4taw==} - dev: false - /string-width@4.2.3: resolution: {integrity: sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==} engines: {node: '>=8'} @@ -11677,6 +4860,7 @@ emoji-regex: 8.0.0 is-fullwidth-code-point: 3.0.0 strip-ansi: 6.0.1 + dev: true /string-width@5.1.2: resolution: {integrity: sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA==} @@ -11701,19 +4885,6 @@ side-channel: 1.0.6 dev: true - /string.prototype.matchall@4.0.8: - resolution: {integrity: sha512-6zOCOcJ+RJAQshcTvXPHoxoQGONa3e/Lqx90wUA+wEzX78sg5Bo+1tQo4N0pohS0erG9qtCqJDjNCQBjeWVxyg==} - dependencies: - call-bind: 1.0.2 - define-properties: 1.2.0 - es-abstract: 1.22.1 - get-intrinsic: 1.2.1 - has-symbols: 1.0.3 - internal-slot: 1.0.5 - regexp.prototype.flags: 1.5.0 - side-channel: 1.0.4 - dev: false - /string.prototype.trim@1.2.7: resolution: {integrity: sha512-p6TmeT1T3411M8Cgg9wBTMRtY2q9+PNy9EV1i2lIXUN/btt763oIfxwN3RR8VU6wHX8j/1CFy0L+YuThm6bgOg==} engines: {node: '>= 0.4'} @@ -11721,6 +4892,7 @@ call-bind: 1.0.2 define-properties: 1.2.0 es-abstract: 1.22.1 + dev: true /string.prototype.trim@1.2.8: resolution: {integrity: sha512-lfjY4HcixfQXOfaqCvcBuOIapyaroTXhbkfJN3gcB1OtyupngWK4sEET9Knd0cXd28kTUqu/kHoV4HKSJdnjiQ==} @@ -11729,6 +4901,7 @@ call-bind: 1.0.7 define-properties: 1.2.1 es-abstract: 1.22.5 + dev: true /string.prototype.trimend@1.0.6: resolution: {integrity: sha512-JySq+4mrPf9EsDBEDYMOb/lM7XQLulwg5R/m1r0PXEFqrV0qHvl58sdTilSXtKOflCsK2E8jxf+GKC0T07RWwQ==} @@ -11736,6 +4909,7 @@ call-bind: 1.0.2 define-properties: 1.2.0 es-abstract: 1.22.1 + dev: true /string.prototype.trimend@1.0.7: resolution: {integrity: sha512-Ni79DqeB72ZFq1uH/L6zJ+DKZTkOtPIHovb3YZHQViE+HDouuU4mBrLOLDn5Dde3RF8qw5qVETEjhu9locMLvA==} @@ -11743,6 +4917,7 @@ call-bind: 1.0.7 define-properties: 1.2.1 es-abstract: 1.22.5 + dev: true /string.prototype.trimstart@1.0.6: resolution: {integrity: sha512-omqjMDaY92pbn5HOX7f9IccLA+U1tA9GvtU4JrodiXFfYB7jPzzHpRzpglLAjtUV6bB557zwClJezTqnAiYnQA==} @@ -11750,6 +4925,7 @@ call-bind: 1.0.2 define-properties: 1.2.0 es-abstract: 1.22.1 + dev: true /string.prototype.trimstart@1.0.7: resolution: {integrity: sha512-NGhtDFu3jCEm7B4Fy0DpLewdJQOZcQ0rGbwQ/+stjnrp2i+rlKeCvos9hOIeCmqwratM47OBxY7uFZzjxHXmrg==} @@ -11757,12 +4933,7 @@ call-bind: 1.0.7 define-properties: 1.2.1 es-abstract: 1.22.5 - - /string_decoder@1.1.1: - resolution: {integrity: sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==} - dependencies: - safe-buffer: 5.1.2 - dev: false + dev: true /string_decoder@1.3.0: resolution: {integrity: sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==} @@ -11770,60 +4941,31 @@ safe-buffer: 5.2.1 dev: false - /stringify-object@3.3.0: - resolution: {integrity: sha512-rHqiFh1elqCQ9WPLIC8I0Q/g/wj5J1eMkyoiD6eoQApWHP0FtlK7rqnhmabL5VUY9JQCcqwwvlOaSuutekgyrw==} - engines: {node: '>=4'} - dependencies: - get-own-enumerable-property-symbols: 3.0.2 - is-obj: 1.0.1 - is-regexp: 1.0.0 - dev: false - /strip-ansi@6.0.1: resolution: {integrity: sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==} engines: {node: '>=8'} dependencies: ansi-regex: 5.0.1 + dev: true /strip-ansi@7.1.0: resolution: {integrity: sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==} engines: {node: '>=12'} dependencies: ansi-regex: 6.0.1 + dev: true /strip-bom@3.0.0: resolution: {integrity: sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA==} engines: {node: '>=4'} - - /strip-bom@4.0.0: - resolution: {integrity: sha512-3xurFv5tEgii33Zi8Jtp55wEIILR9eh34FAW00PZf+JnSsTmV/ioewSgQl97JHvgjoRGwPShsWm+IdrxB35d0w==} - engines: {node: '>=8'} - dev: false - - /strip-comments@2.0.1: - resolution: {integrity: sha512-ZprKx+bBLXv067WTCALv8SSz5l2+XhpYCsVtSqlMnkAXMWDq+/ekVbl1ghqP9rUHTzv6sm/DwCOiYutU/yp1fw==} - engines: {node: '>=10'} - dev: false - - /strip-final-newline@2.0.0: - resolution: {integrity: sha512-BrpvfNAE3dcvq7ll3xVumzjKjZQ5tI1sEUIKr3Uoks0XUl45St3FlatVqef9prk4jRDzhW6WZg+3bk93y6pLjA==} - engines: {node: '>=6'} - dev: false + dev: true /strip-json-comments@3.1.1: resolution: {integrity: sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==} engines: {node: '>=8'} + dev: true - /style-loader@3.3.3(webpack@5.88.1): - resolution: {integrity: sha512-53BiGLXAcll9maCYtZi2RCQZKa8NQQai5C4horqKyRmHj9H7QmcUyucrH+4KW/gBQbXM2AsB0axoEcFZPlfPcw==} - engines: {node: '>= 12.13.0'} - peerDependencies: - webpack: ^5.0.0 - dependencies: - webpack: 5.88.1 - dev: false - - /styled-jsx@5.1.1(@babel/core@7.22.9)(react@18.2.0): + /styled-jsx@5.1.1(react@18.2.0): resolution: {integrity: sha512-pW7uC1l4mBZ8ugbiZrcIsiIvVx1UmTfw7UkC3Um2tmfUq9Bhk8IiyEIPl6F8agHgjzku6j0xQEZbfA5uSgSaCw==} engines: {node: '>= 12.0.0'} peerDependencies: @@ -11836,35 +4978,9 @@ babel-plugin-macros: optional: true dependencies: - '@babel/core': 7.22.9 client-only: 0.0.1 react: 18.2.0 - /stylehacks@5.1.1(postcss@8.4.26): - resolution: {integrity: sha512-sBpcd5Hx7G6seo7b1LkpttvTz7ikD0LlH5RmdcBNb6fFR0Fl7LQwHDFr300q4cwUqi+IYrFGmsIHieMBfnN/Bw==} - engines: {node: ^10 || ^12 || >=14.0} - peerDependencies: - postcss: ^8.2.15 - dependencies: - browserslist: 4.21.9 - postcss: 8.4.26 - postcss-selector-parser: 6.0.13 - dev: false - - /sucrase@3.33.0: - resolution: {integrity: sha512-ARGC7vbufOHfpvyGcZZXFaXCMZ9A4fffOGC5ucOW7+WHDGlAe8LJdf3Jts1sWhDeiI1RSWrKy5Hodl+JWGdW2A==} - engines: {node: '>=8'} - hasBin: true - dependencies: - '@jridgewell/gen-mapping': 0.3.3 - commander: 4.1.1 - glob: 7.1.6 - lines-and-columns: 1.2.4 - mz: 2.7.0 - pirates: 4.0.6 - ts-interface-checker: 0.1.13 - dev: false - /supports-color@5.5.0: resolution: {integrity: sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==} engines: {node: '>=4'} @@ -11876,63 +4992,19 @@ engines: {node: '>=8'} dependencies: has-flag: 4.0.0 + dev: true /supports-color@8.1.1: resolution: {integrity: sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==} engines: {node: '>=10'} dependencies: has-flag: 4.0.0 - - /supports-hyperlinks@2.3.0: - resolution: {integrity: sha512-RpsAZlpWcDwOPQA22aCH4J0t7L8JmAvsCxfOSEwm7cQs3LshN36QaTkwd70DnBOXDWGssw2eUoc8CaRWT0XunA==} - engines: {node: '>=8'} - dependencies: - has-flag: 4.0.0 - supports-color: 7.2.0 - dev: false + dev: true /supports-preserve-symlinks-flag@1.0.0: resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==} engines: {node: '>= 0.4'} - - /svg-parser@2.0.4: - resolution: {integrity: sha512-e4hG1hRwoOdRb37cIMSgzNsxyzKfayW6VOflrwvR+/bzrkyxY/31WkbgnQpgtrNp1SdpJvpUAGTa/ZoiPNDuRQ==} - dev: false - - /svgo@1.3.2: - resolution: {integrity: sha512-yhy/sQYxR5BkC98CY7o31VGsg014AKLEPxdfhora76l36hD9Rdy5NZA/Ocn6yayNPgSamYdtX2rFJdcv07AYVw==} - engines: {node: '>=4.0.0'} - deprecated: This SVGO version is no longer supported. Upgrade to v2.x.x. - hasBin: true - dependencies: - chalk: 2.4.2 - coa: 2.0.2 - css-select: 2.1.0 - css-select-base-adapter: 0.1.1 - css-tree: 1.0.0-alpha.37 - csso: 4.2.0 - js-yaml: 3.14.1 - mkdirp: 0.5.6 - object.values: 1.1.6 - sax: 1.2.4 - stable: 0.1.8 - unquote: 1.1.1 - util.promisify: 1.0.1 - dev: false - - /svgo@2.8.0: - resolution: {integrity: sha512-+N/Q9kV1+F+UeWYoSiULYo4xYSDQlTgb+ayMobAXPwMnLvop7oxKMo9OzIrX5x3eS4L4f2UHhc9axXwY8DpChg==} - engines: {node: '>=10.13.0'} - hasBin: true - dependencies: - '@trysound/sax': 0.2.0 - commander: 7.2.0 - css-select: 4.3.0 - css-tree: 1.1.3 - csso: 4.2.0 - picocolors: 1.0.0 - stable: 0.1.8 - dev: false + dev: true /sweetalert2@11.10.6: resolution: {integrity: sha512-CINZPLZXZRSZqSOE7H7j1F7X8e8O1kLOiXPmtJn1DYxvXsKBr3d16d90+IcwTTs7dJww20h8r8QIxIwsLGX+6A==} @@ -11942,112 +5014,10 @@ resolution: {integrity: sha512-9QNk5KwDF+Bvz+PyObkmSYjI5ksVUYtjW7AU22r2NKcfLJcXp96hkDWU3+XndOsUb+AQ9QhfzfCT2O+CNWT5Tw==} dev: false - /tailwindcss@3.3.3: - resolution: {integrity: sha512-A0KgSkef7eE4Mf+nKJ83i75TMyq8HqY3qmFIJSWy8bNt0v1lG7jUcpGpoTFxAwYcWOphcTBLPPJg+bDfhDf52w==} - engines: {node: '>=14.0.0'} - hasBin: true - dependencies: - '@alloc/quick-lru': 5.2.0 - arg: 5.0.2 - chokidar: 3.5.3 - didyoumean: 1.2.2 - dlv: 1.1.3 - fast-glob: 3.3.0 - glob-parent: 6.0.2 - is-glob: 4.0.3 - jiti: 1.19.1 - lilconfig: 2.1.0 - micromatch: 4.0.5 - normalize-path: 3.0.0 - object-hash: 3.0.0 - picocolors: 1.0.0 - postcss: 8.4.26 - postcss-import: 15.1.0(postcss@8.4.26) - postcss-js: 4.0.1(postcss@8.4.26) - postcss-load-config: 4.0.1(postcss@8.4.26) - postcss-nested: 6.0.1(postcss@8.4.26) - postcss-selector-parser: 6.0.13 - resolve: 1.22.2 - sucrase: 3.33.0 - transitivePeerDependencies: - - ts-node - dev: false - - /tapable@1.1.3: - resolution: {integrity: sha512-4WK/bYZmj8xLr+HUCODHGF1ZFzsYffasLUgEiMBY4fgtltdO6B4WJtlSbPaDTLpYTcGVwM2qLnFTICEcNxs3kA==} - engines: {node: '>=6'} - dev: false - /tapable@2.2.1: resolution: {integrity: sha512-GNzQvQTOIP6RyTfE2Qxb8ZVlNmw0n88vp1szwWRimP02mnTsx3Wtn5qRdqY9w2XduFNUgvOwhNnQsjwCp+kqaQ==} engines: {node: '>=6'} - - /temp-dir@2.0.0: - resolution: {integrity: sha512-aoBAniQmmwtcKp/7BzsH8Cxzv8OL736p7v1ihGb5e9DJ9kTwGWHrQrVB5+lfVDzfGrdRzXch+ig7LHaY1JTOrg==} - engines: {node: '>=8'} - dev: false - - /tempy@0.6.0: - resolution: {integrity: sha512-G13vtMYPT/J8A4X2SjdtBTphZlrp1gKv6hZiOjw14RCWg6GbHuQBGtjlx75xLbYV/wEc0D7G5K4rxKP/cXk8Bw==} - engines: {node: '>=10'} - dependencies: - is-stream: 2.0.1 - temp-dir: 2.0.0 - type-fest: 0.16.0 - unique-string: 2.0.0 - dev: false - - /terminal-link@2.1.1: - resolution: {integrity: sha512-un0FmiRUQNr5PJqy9kP7c40F5BOfpGlYTrxonDChEZB7pzZxRNp/bt+ymiy9/npwXya9KH99nJ/GXFIiUkYGFQ==} - engines: {node: '>=8'} - dependencies: - ansi-escapes: 4.3.2 - supports-hyperlinks: 2.3.0 - dev: false - - /terser-webpack-plugin@5.3.9(webpack@5.88.1): - resolution: {integrity: sha512-ZuXsqE07EcggTWQjXUj+Aot/OMcD0bMKGgF63f7UxYcu5/AJF53aIpK1YoP5xR9l6s/Hy2b+t1AM0bLNPRuhwA==} - engines: {node: '>= 10.13.0'} - peerDependencies: - '@swc/core': '*' - esbuild: '*' - uglify-js: '*' - webpack: ^5.1.0 - peerDependenciesMeta: - '@swc/core': - optional: true - esbuild: - optional: true - uglify-js: - optional: true - dependencies: - '@jridgewell/trace-mapping': 0.3.18 - jest-worker: 27.5.1 - schema-utils: 3.3.0 - serialize-javascript: 6.0.1 - terser: 5.19.0 - webpack: 5.88.1 - dev: false - - /terser@5.19.0: - resolution: {integrity: sha512-JpcpGOQLOXm2jsomozdMDpd5f8ZHh1rR48OFgWUH3QsyZcfPgv2qDCYbcDEAYNd4OZRj2bWYKpwdll/udZCk/Q==} - engines: {node: '>=10'} - hasBin: true - dependencies: - '@jridgewell/source-map': 0.3.5 - acorn: 8.10.0 - commander: 2.20.3 - source-map-support: 0.5.21 - dev: false - - /test-exclude@6.0.0: - resolution: {integrity: sha512-cAGWPIyOHU6zlmg88jwm7VRyXnMN7iV68OGAbYDk/Mh/xC/pzVPlQtY6ngoIH/5/tciuhGfvESU8GrHrcxD56w==} - engines: {node: '>=8'} - dependencies: - '@istanbuljs/schema': 0.1.3 - glob: 7.2.3 - minimatch: 3.1.2 - dev: false + dev: true /text-hex@1.0.0: resolution: {integrity: sha512-uuVGNWzgJ4yhRaNSiubPY7OjISw4sw4E5Uv0wbjp+OzcbmVU/rsT8ujgcXJhn9ypzsgr5vlzpPqP+MBBKcGvbg==} @@ -12055,41 +5025,13 @@ /text-table@0.2.0: resolution: {integrity: sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw==} - - /thenify-all@1.6.0: - resolution: {integrity: sha512-RNxQH/qI8/t3thXJDwcstUO4zeqo64+Uy/+sNVRBx4Xn2OX+OZ9oP+iJnNFqplFra2ZUVeKCSa2oVWi3T4uVmA==} - engines: {node: '>=0.8'} - dependencies: - thenify: 3.3.1 - dev: false - - /thenify@3.3.1: - resolution: {integrity: sha512-RVZSIV5IG10Hk3enotrhvz0T9em6cyHBLkH/YAZuKqd8hRkKhSfCGIcP2KUY0EPxndzANBmNllzWPwak+bheSw==} - dependencies: - any-promise: 1.3.0 - dev: false - - /throat@6.0.2: - resolution: {integrity: sha512-WKexMoJj3vEuK0yFEapj8y64V0A6xcuPuK9Gt1d0R+dzCSJc0lHqQytAbSB4cDAK0dWh4T0E2ETkoLE2WZ41OQ==} - dev: false + dev: true /throttle-debounce@2.3.0: resolution: {integrity: sha512-H7oLPV0P7+jgvrk+6mwwwBDmxTaxnu9HMXmloNLXwnNO0ZxZ31Orah2n8lU1eMPvsaowP2CX+USCgyovXfdOFQ==} engines: {node: '>=8'} dev: false - /thunky@1.1.0: - resolution: {integrity: sha512-eHY7nBftgThBqOyHGVN+l8gF0BucP09fMo0oO/Lb0w1OF80dJv+lDVpXG60WMQvkcxAkNybKsrEIE3ZtKGmPrA==} - dev: false - - /tmpl@1.0.5: - resolution: {integrity: sha512-3f0uOEAQwIqGuWW2MVzYg8fV/QNnc/IpuJNG837rLuczAaLVHslWHZQj4IGiEl5Hs3kkbhwL9Ab7Hrsmuj+Smw==} - dev: false - - /to-fast-properties@2.0.0: - resolution: {integrity: sha512-/OaKK0xYrs3DmxRYqL/yDc+FxFUVYhDlXMhRmv3z915w2HF1tnN1omB354j8VUGO/hbRzyD6Y3sA7v7GS/ceog==} - engines: {node: '>=4'} - /to-regex-range@5.0.1: resolution: {integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==} engines: {node: '>=8.0'} @@ -12118,19 +5060,6 @@ url-parse: 1.5.10 dev: false - /tr46@1.0.1: - resolution: {integrity: sha512-dTpowEjclQ7Kgx5SdBkqRzVhERQXov8/l9Ft9dVM9fmg0W0KQSVaXX9T4i6twCPNtYiZM53lpSSUAwJbFPOHxA==} - dependencies: - punycode: 2.3.0 - dev: false - - /tr46@2.1.0: - resolution: {integrity: sha512-15Ih7phfcdP5YxqiB+iDtLoaTz4Nd35+IiAv0kQ5FNKHzXgdWqPoTIqEDDJmXceQt4JZk6lVPT8lnDlPpGDppw==} - engines: {node: '>=8'} - dependencies: - punycode: 2.3.0 - dev: false - /tr46@5.0.0: resolution: {integrity: sha512-tk2G5R2KRwBd+ZN0zaEXpmzdKyOYksXwywulIX95MBODjSzMIuQnQ3m8JxgbhnL1LeVo7lqQKsYa1O3Htl7K5g==} engines: {node: '>=18'} @@ -12148,23 +5077,6 @@ engines: {node: '>= 14.0.0'} dev: false - /tryer@1.0.1: - resolution: {integrity: sha512-c3zayb8/kWWpycWYg87P71E1S1ZL6b6IJxfb5fvsUgsf0S2MVGaDhDXXjDMpdCpfWXqptc+4mXwmiy1ypXqRAA==} - dev: false - - /ts-interface-checker@0.1.13: - resolution: {integrity: sha512-Y/arvbn+rrz3JCKl9C4kVNfTfSm2/mEp5FSz5EsZSANGPSlQrpRI5M4PKF+mJnE52jOO90PnPSc3Ur3bTQw0gA==} - dev: false - - /tsconfig-paths@3.14.2: - resolution: {integrity: sha512-o/9iXgCYc5L/JxCHPe3Hvh8Q/2xm5Z+p18PESBU6Ff33695QnCHBEjcytY2q19ua7Mbl/DavtBOLq+oG0RCL+g==} - dependencies: - '@types/json5': 0.0.29 - json5: 1.0.2 - minimist: 1.2.8 - strip-bom: 3.0.0 - dev: false - /tsconfig-paths@3.15.0: resolution: {integrity: sha512-2Ac2RgzDe/cn48GvOe3M+o82pEFewD3UPbyoUHHdKasHwJKjds4fLXWf/Ux5kATBKN20oaFGu+jbElp1pos0mg==} dependencies: @@ -12172,9 +5084,11 @@ json5: 1.0.2 minimist: 1.2.8 strip-bom: 3.0.0 + dev: true /tslib@1.14.1: resolution: {integrity: sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==} + dev: true /tslib@2.6.2: resolution: {integrity: sha512-AEYxH93jGFPn/a2iVAwW87VuUIkR1FVUKB77NwMF7nBTDkDrrT/Hpt/IrCJ0QXhW27jTBDcf5ZY7w6RiqTMw2Q==} @@ -12192,31 +5106,19 @@ dependencies: tslib: 1.14.1 typescript: 5.4.2 + dev: true /type-check@0.4.0: resolution: {integrity: sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==} engines: {node: '>= 0.8.0'} dependencies: prelude-ls: 1.2.1 - - /type-detect@4.0.8: - resolution: {integrity: sha512-0fr/mIH1dlO+x7TlcMy+bIDqKPsw/70tVyeHW787goQjhmqaZe10uwLujubK9q9Lg6Fiho1KUKDYz0Z7k7g5/g==} - engines: {node: '>=4'} - dev: false - - /type-fest@0.16.0: - resolution: {integrity: sha512-eaBzG6MxNzEn9kiwvtre90cXaNLkmadMWa1zQMs3XORCXNbsH/OewwbxC5ia9dCxIxnTAsSxXJaa/p5y8DlvJg==} - engines: {node: '>=10'} - dev: false + dev: true /type-fest@0.20.2: resolution: {integrity: sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ==} engines: {node: '>=10'} - - /type-fest@0.21.3: - resolution: {integrity: sha512-t0rzBq87m3fVcduHDUFhKmyyX+9eo6WQjZvf51Ea/M0Q7+T374Jp1aUiyUl0GKxp8M/OETVHSDvmkyPgvX+X2w==} - engines: {node: '>=10'} - dev: false + dev: true /type-is@1.6.18: resolution: {integrity: sha512-TkRKr9sUTxEH8MdfuCSP7VizJyzRNMjj2J2do2Jr3Kym598JVdEksuzPQCnlFPW4ky9Q+iA+ma9BGm06XQBy8g==} @@ -12233,6 +5135,7 @@ call-bind: 1.0.2 get-intrinsic: 1.2.1 is-typed-array: 1.1.10 + dev: true /typed-array-buffer@1.0.2: resolution: {integrity: sha512-gEymJYKZtKXzzBzM4jqa9w6Q1Jjm7x2d+sh19AdsD4wqnMPDYyvwpsIc2Q/835kHuo3BEQ7CjelGhfTsoBb2MQ==} @@ -12241,6 +5144,7 @@ call-bind: 1.0.7 es-errors: 1.3.0 is-typed-array: 1.1.13 + dev: true /typed-array-byte-length@1.0.0: resolution: {integrity: sha512-Or/+kvLxNpeQ9DtSydonMxCx+9ZXOswtwJn17SNLvhptaXYDJvkFFP5zbfU/uLmvnBJlI4yrnXRxpdWH/M5tNA==} @@ -12250,6 +5154,7 @@ for-each: 0.3.3 has-proto: 1.0.1 is-typed-array: 1.1.10 + dev: true /typed-array-byte-length@1.0.1: resolution: {integrity: sha512-3iMJ9q0ao7WE9tWcaYKIptkNBuOIcZCCT0d4MRvuuH88fEoEH62IuQe0OtraD3ebQEoTRk8XCBoknUNc1Y67pw==} @@ -12260,6 +5165,7 @@ gopd: 1.0.1 has-proto: 1.0.3 is-typed-array: 1.1.13 + dev: true /typed-array-byte-offset@1.0.0: resolution: {integrity: sha512-RD97prjEt9EL8YgAgpOkf3O4IF9lhJFr9g0htQkm0rchFp/Vx7LW5Q8fSXXub7BXAODyUQohRMyOc3faCPd0hg==} @@ -12270,6 +5176,7 @@ for-each: 0.3.3 has-proto: 1.0.1 is-typed-array: 1.1.10 + dev: true /typed-array-byte-offset@1.0.2: resolution: {integrity: sha512-Ous0vodHa56FviZucS2E63zkgtgrACj7omjwd/8lTEMEPFFyjfixMZ1ZXenpgCFBBt4EC1J2XsyVS2gkG0eTFA==} @@ -12281,6 +5188,7 @@ gopd: 1.0.1 has-proto: 1.0.3 is-typed-array: 1.1.13 + dev: true /typed-array-length@1.0.4: resolution: {integrity: sha512-KjZypGq+I/H7HI5HlOoGHkWUUGq+Q0TPhQurLbyrVrvnKTBgzLhIJ7j6J/XTQOi0d1RjyZ0wdas8bKs2p0x3Ng==} @@ -12288,6 +5196,7 @@ call-bind: 1.0.2 for-each: 0.3.3 is-typed-array: 1.1.10 + dev: true /typed-array-length@1.0.5: resolution: {integrity: sha512-yMi0PlwuznKHxKmcpoOdeLwxBoVPkqZxd7q2FgMkmD3bNwvF5VW0+UlUQ1k1vmktTu4Yu13Q0RIxEP8+B+wloA==} @@ -12299,17 +5208,13 @@ has-proto: 1.0.3 is-typed-array: 1.1.13 possible-typed-array-names: 1.0.0 - - /typedarray-to-buffer@3.1.5: - resolution: {integrity: sha512-zdu8XMNEDepKKR+XYOXAVPtWui0ly0NtohUscw+UmaHiAWT8hrV1rr//H6V+0DvJ3OQ19S979M0laLfX8rm82Q==} - dependencies: - is-typedarray: 1.0.0 - dev: false + dev: true /typescript@5.4.2: resolution: {integrity: sha512-+2/g0Fds1ERlP6JsakQQDXjZdZMM+rqpamFZJEKh4kwTIn3iDkgKtby0CeNd5ATNZ4Ry1ax15TMx0W2V+miizQ==} engines: {node: '>=14.17'} hasBin: true + dev: true /unbox-primitive@1.0.2: resolution: {integrity: sha512-61pPlCD9h51VoreyJ0BReideM3MDKMKnh6+V9L08331ipq6Q8OFXZYiqP6n/tbHx4s5I9uRhcye6BrbkizkBDw==} @@ -12318,6 +5223,7 @@ has-bigints: 1.0.2 has-symbols: 1.0.3 which-boxed-primitive: 1.0.2 + dev: true /undefsafe@2.0.5: resolution: {integrity: sha512-WxONCrssBM8TSPRqN5EmsjVrsv4A8X12J4ArBiiayv3DyyG3ZlIg6yysuuSYdZsVz3TKcTg2fd//Ujd4CHV1iA==} @@ -12326,74 +5232,21 @@ /undici-types@5.26.5: resolution: {integrity: sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==} - /unicode-canonical-property-names-ecmascript@2.0.0: - resolution: {integrity: sha512-yY5PpDlfVIU5+y/BSCxAJRBIS1Zc2dDG3Ujq+sR0U+JjUevW2JhocOF+soROYDSaAezOzOKuyyixhD6mBknSmQ==} - engines: {node: '>=4'} - dev: false - - /unicode-match-property-ecmascript@2.0.0: - resolution: {integrity: sha512-5kaZCrbp5mmbz5ulBkDkbY0SsPOjKqVS35VpL9ulMPfSl0J0Xsm+9Evphv9CoIZFwre7aJoa94AY6seMKGVN5Q==} - engines: {node: '>=4'} - dependencies: - unicode-canonical-property-names-ecmascript: 2.0.0 - unicode-property-aliases-ecmascript: 2.1.0 - dev: false - - /unicode-match-property-value-ecmascript@2.1.0: - resolution: {integrity: sha512-qxkjQt6qjg/mYscYMC0XKRn3Rh0wFPlfxB0xkt9CfyTvpX1Ra0+rAmdX2QyAobptSEvuy4RtpPRui6XkV+8wjA==} - engines: {node: '>=4'} - dev: false - - /unicode-property-aliases-ecmascript@2.1.0: - resolution: {integrity: sha512-6t3foTQI9qne+OZoVQB/8x8rk2k1eVy1gRXhV3oFQ5T6R1dqQ1xtin3XqSlx3+ATBkliTaR/hHyJBm+LVPNM8w==} - engines: {node: '>=4'} - dev: false - - /unique-string@2.0.0: - resolution: {integrity: sha512-uNaeirEPvpZWSgzwsPGtU2zVSTrn/8L5q/IexZmH0eH6SA73CmAA5U4GwORTxQAZs95TAXLNqeLoPPNO5gZfWg==} - engines: {node: '>=8'} - dependencies: - crypto-random-string: 2.0.0 - dev: false - /universalify@0.2.0: resolution: {integrity: sha512-CJ1QgKmNg3CwvAv/kOFmtnEN05f0D/cn9QntgNOQlQF9dgvVTHj3t+8JPdjqawCHk7V/KA+fbUqzZ9XWhcqPUg==} engines: {node: '>= 4.0.0'} dev: false - /universalify@2.0.0: - resolution: {integrity: sha512-hAZsKq7Yy11Zu1DE0OzWjw7nnLZmJZYTDZZyEFHZdUhV8FkH5MCfoU1XMaxXovpyW5nq5scPqq0ZDP9Zyl04oQ==} - engines: {node: '>= 10.0.0'} - dev: false - /unpipe@1.0.0: resolution: {integrity: sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==} engines: {node: '>= 0.8'} dev: false - /unquote@1.1.1: - resolution: {integrity: sha512-vRCqFv6UhXpWxZPyGDh/F3ZpNv8/qo7w6iufLpQg9aKnQ71qM4B5KiI7Mia9COcjEhrO9LueHpMYjYzsWH3OIg==} - dev: false - - /upath@1.2.0: - resolution: {integrity: sha512-aZwGpamFO61g3OlfT7OQCHqhGnW43ieH9WZeP7QxN/G/jS4jfqUkZxoryvJgVPEcrl5NL/ggHsSmLMHuH64Lhg==} - engines: {node: '>=4'} - dev: false - - /update-browserslist-db@1.0.11(browserslist@4.21.9): - resolution: {integrity: sha512-dCwEFf0/oT85M1fHBg4F0jtLwJrutGoHSQXCh7u4o2t1drG+c0a9Flnqww6XUKSfQMPpJBRjU8d4RXB09qtvaA==} - hasBin: true - peerDependencies: - browserslist: '>= 4.21.0' - dependencies: - browserslist: 4.21.9 - escalade: 3.1.1 - picocolors: 1.0.0 - /uri-js@4.4.1: resolution: {integrity: sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==} dependencies: punycode: 2.3.1 + dev: true /url-parse@1.5.10: resolution: {integrity: sha512-WypcfiRhfeUP9vvF0j6rw0J3hrWrw6iZv3+22h6iRMJ/8z1Tj6XfLP4DsUix5MhMPnXpiHDoKyoZ/bdCkwBCiQ==} @@ -12464,62 +5317,16 @@ resolution: {integrity: sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==} dev: false - /util.promisify@1.0.1: - resolution: {integrity: sha512-g9JpC/3He3bm38zsLupWryXHoEcS22YHthuPQSJdMy6KNrzIRzWqcsHzD/WUnqe45whVou4VIsPew37DoXWNrA==} - dependencies: - define-properties: 1.2.0 - es-abstract: 1.22.1 - has-symbols: 1.0.3 - object.getownpropertydescriptors: 2.1.6 - dev: false - - /utila@0.4.0: - resolution: {integrity: sha512-Z0DbgELS9/L/75wZbro8xAnT50pBVFQZ+hUEueGDU5FN51YSCYM+jdxsfCiHjwNP/4LCDD0i/graKpeBnOXKRA==} - dev: false - - /utils-merge@1.0.1: - resolution: {integrity: sha512-pMZTvIkT1d+TFGvDOqodOclx0QWkkgi6Tdoa8gC8ffGAAqz9pzPTZWAybbsHHoED/ztMtkv/VoYTYyShUn81hA==} - engines: {node: '>= 0.4.0'} - dev: false - - /uuid@8.3.2: - resolution: {integrity: sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==} - hasBin: true - dev: false - /uuid@9.0.1: resolution: {integrity: sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==} hasBin: true dev: false - /v8-to-istanbul@8.1.1: - resolution: {integrity: sha512-FGtKtv3xIpR6BYhvgH8MI/y78oT7d8Au3ww4QIxymrCtZEh5b8gCw2siywE+puhEmuWKDtmfrvF5UlB298ut3w==} - engines: {node: '>=10.12.0'} - dependencies: - '@types/istanbul-lib-coverage': 2.0.4 - convert-source-map: 1.9.0 - source-map: 0.7.4 - dev: false - /vary@1.1.2: resolution: {integrity: sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==} engines: {node: '>= 0.8'} dev: false - /w3c-hr-time@1.0.2: - resolution: {integrity: sha512-z8P5DvDNjKDoFIHK7q8r8lackT6l+jo/Ye3HOle7l9nICP9lf1Ci25fy9vHd0JOWewkIFzXIEig3TdKT7JQ5fQ==} - deprecated: Use your platform's native performance.now() and performance.timeOrigin. - dependencies: - browser-process-hrtime: 1.0.0 - dev: false - - /w3c-xmlserializer@2.0.0: - resolution: {integrity: sha512-4tzD0mF8iSiMiNs30BiLO3EpfGLZUT2MSX/G+o7ZywDzliWQ3OPtTZ0PTC3B3ca1UAf4cJMHB+2Bf56EriJuRA==} - engines: {node: '>=10'} - dependencies: - xml-name-validator: 3.0.0 - dev: false - /w3c-xmlserializer@5.0.0: resolution: {integrity: sha512-o8qghlI8NZHU1lLPrpi2+Uq7abh4GGPpYANlalzWxyWteJOCsr/P+oPBA49TOLu5FTZO4d3F9MnWJfiMo4BkmA==} engines: {node: '>=18'} @@ -12527,207 +5334,17 @@ xml-name-validator: 5.0.0 dev: false - /walker@1.0.8: - resolution: {integrity: sha512-ts/8E8l5b7kY0vlWLewOkDXMmPdLcVV4GmOQLyxuSswIJsweeFZtAsMF7k1Nszz+TYBQrlYRmzOnr398y1JemQ==} - dependencies: - makeerror: 1.0.12 - dev: false - /warning@4.0.3: resolution: {integrity: sha512-rpJyN222KWIvHJ/F53XSZv0Zl/accqHR8et1kpaMTD/fLCRxtV8iX8czMzY7sVZupTI3zcUTg8eycS2kNF9l6w==} dependencies: loose-envify: 1.4.0 dev: false - /watchpack@2.4.0: - resolution: {integrity: sha512-Lcvm7MGST/4fup+ifyKi2hjyIAwcdI4HRgtvTpIUxBRhB+RFtUh8XtDOxUfctVCnhVi+QQj49i91OyvzkJl6cg==} - engines: {node: '>=10.13.0'} - dependencies: - glob-to-regexp: 0.4.1 - graceful-fs: 4.2.11 - dev: false - - /wbuf@1.7.3: - resolution: {integrity: sha512-O84QOnr0icsbFGLS0O3bI5FswxzRr8/gHwWkDlQFskhSPryQXvrTMxjxGP4+iWYoauLoBvfDpkrOauZ+0iZpDA==} - dependencies: - minimalistic-assert: 1.0.1 - dev: false - - /webidl-conversions@4.0.2: - resolution: {integrity: sha512-YQ+BmxuTgd6UXZW3+ICGfyqRyHXVlD5GtQr5+qjiNW7bF0cqrzX500HVXPBOvgXb5YnzDd+h0zqyv61KUD7+Sg==} - dev: false - - /webidl-conversions@5.0.0: - resolution: {integrity: sha512-VlZwKPCkYKxQgeSbH5EyngOmRp7Ww7I9rQLERETtf5ofd9pGeswWiOtogpEO850jziPRarreGxn5QIiTqpb2wA==} - engines: {node: '>=8'} - dev: false - - /webidl-conversions@6.1.0: - resolution: {integrity: sha512-qBIvFLGiBpLjfwmYAaHPXsn+ho5xZnGvyGvsarywGNc8VyQJUMHJ8OBKGGrPER0okBeMDaan4mNBlgBROxuI8w==} - engines: {node: '>=10.4'} - dev: false - /webidl-conversions@7.0.0: resolution: {integrity: sha512-VwddBukDzu71offAQR975unBIGqfKZpM+8ZX6ySk8nYhVoo5CYaZyzt3YBvYtRtO+aoGlqxPg/B87NGVZ/fu6g==} engines: {node: '>=12'} dev: false - /webpack-dev-middleware@5.3.3(webpack@5.88.1): - resolution: {integrity: sha512-hj5CYrY0bZLB+eTO+x/j67Pkrquiy7kWepMHmUMoPsmcUaeEnQJqFzHJOyxgWlq746/wUuA64p9ta34Kyb01pA==} - engines: {node: '>= 12.13.0'} - peerDependencies: - webpack: ^4.0.0 || ^5.0.0 - dependencies: - colorette: 2.0.20 - memfs: 3.5.3 - mime-types: 2.1.35 - range-parser: 1.2.1 - schema-utils: 4.2.0 - webpack: 5.88.1 - dev: false - - /webpack-dev-server@4.15.1(webpack@5.88.1): - resolution: {integrity: sha512-5hbAst3h3C3L8w6W4P96L5vaV0PxSmJhxZvWKYIdgxOQm8pNZ5dEOmmSLBVpP85ReeyRt6AS1QJNyo/oFFPeVA==} - engines: {node: '>= 12.13.0'} - hasBin: true - peerDependencies: - webpack: ^4.37.0 || ^5.0.0 - webpack-cli: '*' - peerDependenciesMeta: - webpack: - optional: true - webpack-cli: - optional: true - dependencies: - '@types/bonjour': 3.5.10 - '@types/connect-history-api-fallback': 1.5.0 - '@types/express': 4.17.17 - '@types/serve-index': 1.9.1 - '@types/serve-static': 1.15.2 - '@types/sockjs': 0.3.33 - '@types/ws': 8.5.5 - ansi-html-community: 0.0.8 - bonjour-service: 1.1.1 - chokidar: 3.5.3 - colorette: 2.0.20 - compression: 1.7.4 - connect-history-api-fallback: 2.0.0 - default-gateway: 6.0.3 - express: 4.18.2 - graceful-fs: 4.2.11 - html-entities: 2.4.0 - http-proxy-middleware: 2.0.6(@types/express@4.17.17) - ipaddr.js: 2.1.0 - launch-editor: 2.6.0 - open: 8.4.2 - p-retry: 4.6.2 - rimraf: 3.0.2 - schema-utils: 4.2.0 - selfsigned: 2.1.1 - serve-index: 1.9.1 - sockjs: 0.3.24 - spdy: 4.0.2 - webpack: 5.88.1 - webpack-dev-middleware: 5.3.3(webpack@5.88.1) - ws: 8.13.0 - transitivePeerDependencies: - - bufferutil - - debug - - supports-color - - utf-8-validate - dev: false - - /webpack-manifest-plugin@4.1.1(webpack@5.88.1): - resolution: {integrity: sha512-YXUAwxtfKIJIKkhg03MKuiFAD72PlrqCiwdwO4VEXdRO5V0ORCNwaOwAZawPZalCbmH9kBDmXnNeQOw+BIEiow==} - engines: {node: '>=12.22.0'} - peerDependencies: - webpack: ^4.44.2 || ^5.47.0 - dependencies: - tapable: 2.2.1 - webpack: 5.88.1 - webpack-sources: 2.3.1 - dev: false - - /webpack-sources@1.4.3: - resolution: {integrity: sha512-lgTS3Xhv1lCOKo7SA5TjKXMjpSM4sBjNV5+q2bqesbSPs5FjGmU6jjtBSkX9b4qW87vDIsCIlUPOEhbZrMdjeQ==} - dependencies: - source-list-map: 2.0.1 - source-map: 0.6.1 - dev: false - - /webpack-sources@2.3.1: - resolution: {integrity: sha512-y9EI9AO42JjEcrTJFOYmVywVZdKVUfOvDUPsJea5GIr1JOEGFVqwlY2K098fFoIjOkDzHn2AjRvM8dsBZu+gCA==} - engines: {node: '>=10.13.0'} - dependencies: - source-list-map: 2.0.1 - source-map: 0.6.1 - dev: false - - /webpack-sources@3.2.3: - resolution: {integrity: sha512-/DyMEOrDgLKKIG0fmvtz+4dUX/3Ghozwgm6iPp8KRhvn+eQf9+Q7GWxVNMk3+uCPWfdXYC4ExGBckIXdFEfH1w==} - engines: {node: '>=10.13.0'} - dev: false - - /webpack@5.88.1: - resolution: {integrity: sha512-FROX3TxQnC/ox4N+3xQoWZzvGXSuscxR32rbzjpXgEzWudJFEJBpdlkkob2ylrv5yzzufD1zph1OoFsLtm6stQ==} - engines: {node: '>=10.13.0'} - hasBin: true - peerDependencies: - webpack-cli: '*' - peerDependenciesMeta: - webpack-cli: - optional: true - dependencies: - '@types/eslint-scope': 3.7.4 - '@types/estree': 1.0.5 - '@webassemblyjs/ast': 1.11.6 - '@webassemblyjs/wasm-edit': 1.11.6 - '@webassemblyjs/wasm-parser': 1.11.6 - acorn: 8.10.0 - acorn-import-assertions: 1.9.0(acorn@8.10.0) - browserslist: 4.21.9 - chrome-trace-event: 1.0.3 - enhanced-resolve: 5.15.0 - es-module-lexer: 1.3.0 - eslint-scope: 5.1.1 - events: 3.3.0 - glob-to-regexp: 0.4.1 - graceful-fs: 4.2.11 - json-parse-even-better-errors: 2.3.1 - loader-runner: 4.3.0 - mime-types: 2.1.35 - neo-async: 2.6.2 - schema-utils: 3.3.0 - tapable: 2.2.1 - terser-webpack-plugin: 5.3.9(webpack@5.88.1) - watchpack: 2.4.0 - webpack-sources: 3.2.3 - transitivePeerDependencies: - - '@swc/core' - - esbuild - - uglify-js - dev: false - - /websocket-driver@0.7.4: - resolution: {integrity: sha512-b17KeDIQVjvb0ssuSDF2cYXSg2iztliJ4B9WdsuB6J952qCPKmnVq4DyW5motImXHDC1cBT/1UezrJVsKw5zjg==} - engines: {node: '>=0.8.0'} - dependencies: - http-parser-js: 0.5.8 - safe-buffer: 5.2.1 - websocket-extensions: 0.1.4 - dev: false - - /websocket-extensions@0.1.4: - resolution: {integrity: sha512-OqedPIGOfsDlo31UNwYbCFMSaO9m9G/0faIHj5/dZFDMFqPTcx6UwqyOy3COEaEOg/9VsGIpdqn62W5KhoKSpg==} - engines: {node: '>=0.8.0'} - dev: false - - /whatwg-encoding@1.0.5: - resolution: {integrity: sha512-b5lim54JOPN9HtzvK9HFXvBma/rnfFeqsic0hSpjtDbVxR3dJKLc+KB4V6GgiGOvl7CY/KNh8rxSo9DKQrnUEw==} - dependencies: - iconv-lite: 0.4.24 - dev: false - /whatwg-encoding@3.1.1: resolution: {integrity: sha512-6qN4hJdMwfYBtE3YBTTHhoeuUrDBPZmbQaxWAqSALV/MeEnR5z1xd8UKud2RAkFoPkmB+hli1TZSnyi84xz1vQ==} engines: {node: '>=18'} @@ -12735,14 +5352,6 @@ iconv-lite: 0.6.3 dev: false - /whatwg-fetch@3.6.2: - resolution: {integrity: sha512-bJlen0FcuU/0EMLrdbJ7zOnW6ITZLrZMIarMUVmdKtsGvZna8vxKYaexICWPfZ8qwf9fzNq+UEIZrnSaApt6RA==} - dev: false - - /whatwg-mimetype@2.3.0: - resolution: {integrity: sha512-M4yMwr6mAnQz76TbJm914+gPpB/nCwvZbJU28cUD6dR004SAxDLOOSUaB1JDRqLtaOV/vi0IC5lEAGFgrjGv/g==} - dev: false - /whatwg-mimetype@4.0.0: resolution: {integrity: sha512-QaKxh0eNIi2mE9p2vEdzfagOKHCcj1pJ56EEHGQOVxp8r9/iszLUUV7v89x9O1p/T+NlTM5W7jW6+cz4Fq1YVg==} engines: {node: '>=18'} @@ -12756,23 +5365,6 @@ webidl-conversions: 7.0.0 dev: false - /whatwg-url@7.1.0: - resolution: {integrity: sha512-WUu7Rg1DroM7oQvGWfOiAK21n74Gg+T4elXEQYkOhtyLeWiJFoOGLXPKI/9gzIie9CtwVLm8wtw6YJdKyxSjeg==} - dependencies: - lodash.sortby: 4.7.0 - tr46: 1.0.1 - webidl-conversions: 4.0.2 - dev: false - - /whatwg-url@8.7.0: - resolution: {integrity: sha512-gAojqb/m9Q8a5IV96E3fHJM70AzCkgt4uXYX2O7EmuyOnLrViCQlsEBmF9UQIu3/aeAIp2U17rtbpZWNntQqdg==} - engines: {node: '>=10'} - dependencies: - lodash: 4.17.21 - tr46: 2.1.0 - webidl-conversions: 6.1.0 - dev: false - /which-boxed-primitive@1.0.2: resolution: {integrity: sha512-bwZdv0AKLpplFY2KZRX6TvyuN7ojjr7lwkg6ml0roIy9YeuSr7JS372qlNW18UQYzgYK9ziGcerWqZOmEn9VNg==} dependencies: @@ -12781,6 +5373,7 @@ is-number-object: 1.0.7 is-string: 1.0.7 is-symbol: 1.0.4 + dev: true /which-builtin-type@1.1.3: resolution: {integrity: sha512-YmjsSMDBYsM1CaFiayOVT06+KJeXf0o5M/CAd4o1lTadFAtacTUM49zoYxr/oroopFDfhvN6iEcBxUyc3gvKmw==} @@ -12820,6 +5413,7 @@ gopd: 1.0.1 has-tostringtag: 1.0.0 is-typed-array: 1.1.10 + dev: true /which-typed-array@1.1.15: resolution: {integrity: sha512-oV0jmFtUky6CXfkqehVvBP/LSWJ2sy4vWMioiENyJLePrBO/yKyV9OyJySfAKosh+RYkIl5zJCNZ8/4JncrpdA==} @@ -12830,13 +5424,7 @@ for-each: 0.3.3 gopd: 1.0.1 has-tostringtag: 1.0.2 - - /which@1.3.1: - resolution: {integrity: sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==} - hasBin: true - dependencies: - isexe: 2.0.0 - dev: false + dev: true /which@2.0.2: resolution: {integrity: sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==} @@ -12844,6 +5432,7 @@ hasBin: true dependencies: isexe: 2.0.0 + dev: true /winston-daily-rotate-file@5.0.0(winston@3.12.0): resolution: {integrity: sha512-JDjiXXkM5qvwY06733vf09I2wnMXpZEhxEVOSPenZMii+g7pcDcTBt2MRugnoi8BwVSuCT2jfRXBUy+n1Zz/Yw==} @@ -12884,170 +5473,6 @@ winston-transport: 4.7.0 dev: false - /workbox-background-sync@6.6.0: - resolution: {integrity: sha512-jkf4ZdgOJxC9u2vztxLuPT/UjlH7m/nWRQ/MgGL0v8BJHoZdVGJd18Kck+a0e55wGXdqyHO+4IQTk0685g4MUw==} - dependencies: - idb: 7.1.1 - workbox-core: 6.6.0 - dev: false - - /workbox-broadcast-update@6.6.0: - resolution: {integrity: sha512-nm+v6QmrIFaB/yokJmQ/93qIJ7n72NICxIwQwe5xsZiV2aI93MGGyEyzOzDPVz5THEr5rC3FJSsO3346cId64Q==} - dependencies: - workbox-core: 6.6.0 - dev: false - - /workbox-build@6.6.0: - resolution: {integrity: sha512-Tjf+gBwOTuGyZwMz2Nk/B13Fuyeo0Q84W++bebbVsfr9iLkDSo6j6PST8tET9HYA58mlRXwlMGpyWO8ETJiXdQ==} - engines: {node: '>=10.0.0'} - dependencies: - '@apideck/better-ajv-errors': 0.3.6(ajv@8.12.0) - '@babel/core': 7.22.9 - '@babel/preset-env': 7.22.9(@babel/core@7.22.9) - '@babel/runtime': 7.23.9 - '@rollup/plugin-babel': 5.3.1(@babel/core@7.22.9)(rollup@2.79.1) - '@rollup/plugin-node-resolve': 11.2.1(rollup@2.79.1) - '@rollup/plugin-replace': 2.4.2(rollup@2.79.1) - '@surma/rollup-plugin-off-main-thread': 2.2.3 - ajv: 8.12.0 - common-tags: 1.8.2 - fast-json-stable-stringify: 2.1.0 - fs-extra: 9.1.0 - glob: 7.2.3 - lodash: 4.17.21 - pretty-bytes: 5.6.0 - rollup: 2.79.1 - rollup-plugin-terser: 7.0.2(rollup@2.79.1) - source-map: 0.8.0-beta.0 - stringify-object: 3.3.0 - strip-comments: 2.0.1 - tempy: 0.6.0 - upath: 1.2.0 - workbox-background-sync: 6.6.0 - workbox-broadcast-update: 6.6.0 - workbox-cacheable-response: 6.6.0 - workbox-core: 6.6.0 - workbox-expiration: 6.6.0 - workbox-google-analytics: 6.6.0 - workbox-navigation-preload: 6.6.0 - workbox-precaching: 6.6.0 - workbox-range-requests: 6.6.0 - workbox-recipes: 6.6.0 - workbox-routing: 6.6.0 - workbox-strategies: 6.6.0 - workbox-streams: 6.6.0 - workbox-sw: 6.6.0 - workbox-window: 6.6.0 - transitivePeerDependencies: - - '@types/babel__core' - - supports-color - dev: false - - /workbox-cacheable-response@6.6.0: - resolution: {integrity: sha512-JfhJUSQDwsF1Xv3EV1vWzSsCOZn4mQ38bWEBR3LdvOxSPgB65gAM6cS2CX8rkkKHRgiLrN7Wxoyu+TuH67kHrw==} - deprecated: workbox-background-sync@6.6.0 - dependencies: - workbox-core: 6.6.0 - dev: false - - /workbox-core@6.6.0: - resolution: {integrity: sha512-GDtFRF7Yg3DD859PMbPAYPeJyg5gJYXuBQAC+wyrWuuXgpfoOrIQIvFRZnQ7+czTIQjIr1DhLEGFzZanAT/3bQ==} - dev: false - - /workbox-expiration@6.6.0: - resolution: {integrity: sha512-baplYXcDHbe8vAo7GYvyAmlS4f6998Jff513L4XvlzAOxcl8F620O91guoJ5EOf5qeXG4cGdNZHkkVAPouFCpw==} - dependencies: - idb: 7.1.1 - workbox-core: 6.6.0 - dev: false - - /workbox-google-analytics@6.6.0: - resolution: {integrity: sha512-p4DJa6OldXWd6M9zRl0H6vB9lkrmqYFkRQ2xEiNdBFp9U0LhsGO7hsBscVEyH9H2/3eZZt8c97NB2FD9U2NJ+Q==} - dependencies: - workbox-background-sync: 6.6.0 - workbox-core: 6.6.0 - workbox-routing: 6.6.0 - workbox-strategies: 6.6.0 - dev: false - - /workbox-navigation-preload@6.6.0: - resolution: {integrity: sha512-utNEWG+uOfXdaZmvhshrh7KzhDu/1iMHyQOV6Aqup8Mm78D286ugu5k9MFD9SzBT5TcwgwSORVvInaXWbvKz9Q==} - dependencies: - workbox-core: 6.6.0 - dev: false - - /workbox-precaching@6.6.0: - resolution: {integrity: sha512-eYu/7MqtRZN1IDttl/UQcSZFkHP7dnvr/X3Vn6Iw6OsPMruQHiVjjomDFCNtd8k2RdjLs0xiz9nq+t3YVBcWPw==} - dependencies: - workbox-core: 6.6.0 - workbox-routing: 6.6.0 - workbox-strategies: 6.6.0 - dev: false - - /workbox-range-requests@6.6.0: - resolution: {integrity: sha512-V3aICz5fLGq5DpSYEU8LxeXvsT//mRWzKrfBOIxzIdQnV/Wj7R+LyJVTczi4CQ4NwKhAaBVaSujI1cEjXW+hTw==} - dependencies: - workbox-core: 6.6.0 - dev: false - - /workbox-recipes@6.6.0: - resolution: {integrity: sha512-TFi3kTgYw73t5tg73yPVqQC8QQjxJSeqjXRO4ouE/CeypmP2O/xqmB/ZFBBQazLTPxILUQ0b8aeh0IuxVn9a6A==} - dependencies: - workbox-cacheable-response: 6.6.0 - workbox-core: 6.6.0 - workbox-expiration: 6.6.0 - workbox-precaching: 6.6.0 - workbox-routing: 6.6.0 - workbox-strategies: 6.6.0 - dev: false - - /workbox-routing@6.6.0: - resolution: {integrity: sha512-x8gdN7VDBiLC03izAZRfU+WKUXJnbqt6PG9Uh0XuPRzJPpZGLKce/FkOX95dWHRpOHWLEq8RXzjW0O+POSkKvw==} - dependencies: - workbox-core: 6.6.0 - dev: false - - /workbox-strategies@6.6.0: - resolution: {integrity: sha512-eC07XGuINAKUWDnZeIPdRdVja4JQtTuc35TZ8SwMb1ztjp7Ddq2CJ4yqLvWzFWGlYI7CG/YGqaETntTxBGdKgQ==} - dependencies: - workbox-core: 6.6.0 - dev: false - - /workbox-streams@6.6.0: - resolution: {integrity: sha512-rfMJLVvwuED09CnH1RnIep7L9+mj4ufkTyDPVaXPKlhi9+0czCu+SJggWCIFbPpJaAZmp2iyVGLqS3RUmY3fxg==} - dependencies: - workbox-core: 6.6.0 - workbox-routing: 6.6.0 - dev: false - - /workbox-sw@6.6.0: - resolution: {integrity: sha512-R2IkwDokbtHUE4Kus8pKO5+VkPHD2oqTgl+XJwh4zbF1HyjAbgNmK/FneZHVU7p03XUt9ICfuGDYISWG9qV/CQ==} - dev: false - - /workbox-webpack-plugin@6.6.0(webpack@5.88.1): - resolution: {integrity: sha512-xNZIZHalboZU66Wa7x1YkjIqEy1gTR+zPM+kjrYJzqN7iurYZBctBLISyScjhkJKYuRrZUP0iqViZTh8rS0+3A==} - engines: {node: '>=10.0.0'} - peerDependencies: - webpack: ^4.4.0 || ^5.9.0 - dependencies: - fast-json-stable-stringify: 2.1.0 - pretty-bytes: 5.6.0 - upath: 1.2.0 - webpack: 5.88.1 - webpack-sources: 1.4.3 - workbox-build: 6.6.0 - transitivePeerDependencies: - - '@types/babel__core' - - supports-color - dev: false - - /workbox-window@6.6.0: - resolution: {integrity: sha512-L4N9+vka17d16geaJXXRjENLFldvkWy7JyGxElRD0JvBxvFEd8LOhr+uXCcar/NzAmIBRv9EZ+M+Qr4mOoBITw==} - dependencies: - '@types/trusted-types': 2.0.3 - workbox-core: 6.6.0 - dev: false - /wrap-ansi@7.0.0: resolution: {integrity: sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==} engines: {node: '>=10'} @@ -13055,6 +5480,7 @@ ansi-styles: 4.3.0 string-width: 4.2.3 strip-ansi: 6.0.1 + dev: true /wrap-ansi@8.1.0: resolution: {integrity: sha512-si7QWI6zUMq56bESFvagtmzMdGOtoxfR+Sez11Mobfc7tm+VkUckk9bW2UeffTGVUbOksxmSw0AA2gs8g71NCQ==} @@ -13068,41 +5494,6 @@ /wrappy@1.0.2: resolution: {integrity: sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==} - /write-file-atomic@3.0.3: - resolution: {integrity: sha512-AvHcyZ5JnSfq3ioSyjrBkH9yW4m7Ayk8/9My/DD9onKeu/94fwrMocemO2QAJFAlnnDN+ZDS+ZjAR5ua1/PV/Q==} - dependencies: - imurmurhash: 0.1.4 - is-typedarray: 1.0.0 - signal-exit: 3.0.7 - typedarray-to-buffer: 3.1.5 - dev: false - - /ws@7.5.9: - resolution: {integrity: sha512-F+P9Jil7UiSKSkppIiD94dN07AwvFixvLIj1Og1Rl9GGMuNipJnV9JzjD6XuqmAeiswGvUmNLjr5cFuXwNS77Q==} - engines: {node: '>=8.3.0'} - peerDependencies: - bufferutil: ^4.0.1 - utf-8-validate: ^5.0.2 - peerDependenciesMeta: - bufferutil: - optional: true - utf-8-validate: - optional: true - dev: false - - /ws@8.13.0: - resolution: {integrity: sha512-x9vcZYTrFPC7aSIbj7sRCYo7L/Xb8Iy+pW0ng0wt2vCJv7M9HOMy0UoN3rr+IFC7hb7vXoqS+P9ktyLLLhO+LA==} - engines: {node: '>=10.0.0'} - peerDependencies: - bufferutil: ^4.0.1 - utf-8-validate: '>=5.0.2' - peerDependenciesMeta: - bufferutil: - optional: true - utf-8-validate: - optional: true - dev: false - /ws@8.16.0: resolution: {integrity: sha512-HS0c//TP7Ina87TfiPUz1rQzMhHrl/SG2guqRcTOIUYD2q8uhUdNHZYJUaQ8aTGPzCh+c6oawMKW35nFl1dxyQ==} engines: {node: '>=10.0.0'} @@ -13116,10 +5507,6 @@ optional: true dev: false - /xml-name-validator@3.0.0: - resolution: {integrity: sha512-A5CUptxDsvxKJEU3yO6DuWBSJz/qizqzJKOMIfUJHETbBw/sFaDxgd6fxm1ewUaM0jZ444Fc5vC5ROYurg/4Pw==} - dev: false - /xml-name-validator@5.0.0: resolution: {integrity: sha512-EvGK8EJ3DhaHfbRlETOWAS5pO9MZITeauHKJyb8wyajUfQUenkIg2MvLDTZ4T/TgIcm3HU0TFBgWWboAZ30UHg==} engines: {node: '>=18'} @@ -13132,46 +5519,16 @@ /y18n@5.0.8: resolution: {integrity: sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==} engines: {node: '>=10'} - - /yallist@3.1.1: - resolution: {integrity: sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==} + dev: true /yallist@4.0.0: resolution: {integrity: sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==} - /yaml@1.10.2: - resolution: {integrity: sha512-r3vXyErRCYJ7wg28yvBY5VSoAF8ZvlcW9/BwUzEtUsjvX/DKs24dIkuwjtuprwJJHsbyUbLApepYTR1BN4uHrg==} - engines: {node: '>= 6'} - dev: false - - /yaml@2.3.1: - resolution: {integrity: sha512-2eHWfjaoXgTBC2jNM1LRef62VQa0umtvRiDSk6HSzW7RvS5YtkabJrwYLLEKWBc8a5U2PTSCs+dJjUTJdlHsWQ==} - engines: {node: '>= 14'} - dev: false - - /yargs-parser@20.2.9: - resolution: {integrity: sha512-y11nGElTIV+CT3Zv9t7VKl+Q3hTQoT9a1Qzezhhl6Rp21gJ/IVTW7Z3y9EWXhuUBC2Shnf+DX0antecpAwSP8w==} - engines: {node: '>=10'} - dev: false - /yargs-parser@21.1.1: resolution: {integrity: sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==} engines: {node: '>=12'} dev: true - /yargs@16.2.0: - resolution: {integrity: sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw==} - engines: {node: '>=10'} - dependencies: - cliui: 7.0.4 - escalade: 3.1.1 - get-caller-file: 2.0.5 - require-directory: 2.1.1 - string-width: 4.2.3 - y18n: 5.0.8 - yargs-parser: 20.2.9 - dev: false - /yargs@17.7.2: resolution: {integrity: sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==} engines: {node: '>=12'} @@ -13193,6 +5550,7 @@ /yocto-queue@0.1.0: resolution: {integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==} engines: {node: '>=10'} + dev: true /zod@3.21.4: resolution: {integrity: sha512-m46AKbrzKVzOzs/DZgVnG5H55N1sv1M8qZU3A8RIKbs3mrACDNeIOeilDymVb2HdmP8uwshOCF4uJ8uM9rCqJw==} diff --git a/pnpm-workspace.yaml b/pnpm-workspace.yaml index ad4a4ad..eca1a78 100644 --- a/pnpm-workspace.yaml +++ b/pnpm-workspace.yaml @@ -1,5 +1,5 @@ packages: - - qwilight-fe - taehui-fe - taehui-ts - taehui-www + - qwilight-fe diff --git a/qwilight-fe/.gitignore b/qwilight-fe/.gitignore index 741a54f..2825260 100644 --- a/qwilight-fe/.gitignore +++ b/qwilight-fe/.gitignore @@ -36,4 +36,4 @@ *.tsbuildinfo next-env.d.ts -.turbo +/.turbo diff --git a/qwilight-fe/next.config.mjs b/qwilight-fe/next.config.mjs index 47183c6..c8675b1 100644 --- a/qwilight-fe/next.config.mjs +++ b/qwilight-fe/next.config.mjs @@ -18,5 +18,5 @@ }, ] }, - basePath: "/qwilight" + basePath: "/qwilight", }); diff --git a/qwilight-fe/package.json b/qwilight-fe/package.json index 448ed13..5c4e247 100644 --- a/qwilight-fe/package.json +++ b/qwilight-fe/package.json @@ -39,7 +39,6 @@ "@types/node": "^20.11.27", "@types/react": "^18.2.65", "@types/react-dom": "^18.2.22", - "@types/react-router-dom": "^5.3.3", "eslint-config-next": "^14.1.3", "typescript": "^5.4.2" } diff --git a/qwilight-fe/src/AvatarDrawing.module.scss b/qwilight-fe/src/AvatarDrawing.module.scss deleted file mode 100644 index 596d6c8..0000000 --- a/qwilight-fe/src/AvatarDrawing.module.scss +++ /dev/null @@ -1,16 +0,0 @@ -div { - &.drawing { - position: relative; - } -} - -img { - &.avatar { - position: absolute; - } - - &.edge { - position: absolute; - border: none; - } -} diff --git a/qwilight-fe/src/AvatarDrawing.tsx b/qwilight-fe/src/AvatarDrawing.tsx deleted file mode 100644 index 782ed1e..0000000 --- a/qwilight-fe/src/AvatarDrawing.tsx +++ /dev/null @@ -1,51 +0,0 @@ -import scss from "@/AvatarDrawing.module.scss"; -import { getDefaultAvatarID } from "@/Utility"; -import { wwwAPI } from "@/Www"; -import Image from "next/image"; - -const EDGE_MARGIN = 1.25; -const EDGE_XY = (EDGE_MARGIN - 1.0) / 2; - -export default function AvatarDrawing({ - avatarID, - drawingLength = 48, - drawingHeight = 48, -}: { - avatarID: string; - drawingLength?: number; - drawingHeight?: number; -}) { - return ( -
- - (e.currentTarget.hidden = true)} - /> -
- ); -} diff --git a/qwilight-fe/src/AvatarTitle.tsx b/qwilight-fe/src/AvatarTitle.tsx deleted file mode 100644 index c1f9775..0000000 --- a/qwilight-fe/src/AvatarTitle.tsx +++ /dev/null @@ -1,15 +0,0 @@ -import Title from "@/Title"; -import useGetTitle from "@/useGetTitle"; - -export default function AvatarTitle({ avatarID }: { avatarID: string }) { - const { - data: { title, titleColor }, - isFetched: isTitleLoaded, - } = useGetTitle(avatarID); - - if (!isTitleLoaded) { - return null; - } - - return ; -} diff --git a/qwilight-fe/src/Event_pb.js b/qwilight-fe/src/Event_pb.js index 5a9952f..281e28b 100644 --- a/qwilight-fe/src/Event_pb.js +++ b/qwilight-fe/src/Event_pb.js @@ -946,8 +946,8 @@ * @enum {number} */ proto.Event.EventID = { - SIGN_IN: 0, - NOT_SIGN_IN: 1, + LOG_IN: 0, + NOT_LOG_IN: 1, WARNING: 2, SITE_YELL: 3, CALL_BUNDLE: 4, diff --git a/qwilight-fe/src/Loading.tsx b/qwilight-fe/src/Loading.tsx deleted file mode 100644 index 0162bc6..0000000 --- a/qwilight-fe/src/Loading.tsx +++ /dev/null @@ -1,36 +0,0 @@ -import WwwLevelItem from "@/avatar/WwwLevelItem"; -import AvatarItem from "@/hall/AvatarItem"; -import NoteItem from "@/note/NoteItem"; - -export const NoteLoading = ({ loadingCount }: { loadingCount: number }) => { - return [...Array(loadingCount).keys()].map((i) => ( - <NoteItem - key={i} - noteID="" - artist="" - title="Loading…" - genre="" - levelText="" - level={0} - /> - )); -}; - -export const WwwLevelLoading = ({ loadingCount }: { loadingCount: number }) => { - return [...Array(loadingCount).keys()].map((i) => ( - <WwwLevelItem - key={i} - levelID="" - title="Loading…" - date={0} - levelText="" - level="" - /> - )); -}; - -export const AvatarLoading = ({ loadingCount }: { loadingCount: number }) => { - return [...Array(loadingCount).keys()].map((i) => ( - <AvatarItem key={i} avatarID="" avatarName="Loading…" text="" /> - )); -}; diff --git a/qwilight-fe/src/LoadingLayer.tsx b/qwilight-fe/src/LoadingLayer.tsx deleted file mode 100644 index 7740746..0000000 --- a/qwilight-fe/src/LoadingLayer.tsx +++ /dev/null @@ -1,17 +0,0 @@ -import BarLoader from "react-spinners/BarLoader"; -import { Badge, Col, ListGroup, ListGroupItem, Row } from "reactstrap"; - -export default function LoadingLayer({ text }: { text: string }) { - return ( - <Row className="g-0"> - <Col className="m-1"> - <ListGroup> - <Badge>{text}</Badge> - <ListGroupItem> - <BarLoader width="100%" color="#36d7b7" /> - </ListGroupItem> - </ListGroup> - </Col> - </Row> - ); -} diff --git a/qwilight-fe/src/QwilightView.tsx b/qwilight-fe/src/QwilightView.tsx deleted file mode 100644 index c28cd4f..0000000 --- a/qwilight-fe/src/QwilightView.tsx +++ /dev/null @@ -1,86 +0,0 @@ -"use client"; - -import platform from "@/assets/discord-logo-white.png"; - -import SignInWindow from "@/site/SignInWindow"; -import useSiteComponent from "@/site/useSiteComponent"; -import { useSiteStore } from "@/Stores"; -import { QueryClient, QueryClientProvider } from "@tanstack/react-query"; -import { useTranslations } from "next-intl"; -import Image from "next/image"; -import Link from "next/link"; -import { ReactNode, useEffect, useRef } from "react"; -import { ToastContainer } from "react-toastify"; -import { Button, Col, Container, Navbar, NavbarBrand, Row } from "reactstrap"; -import { useIsPath } from "taehui-ts/fe-utility"; - -const queryClient = new QueryClient(); - -export default function QwilightView({ children }: { children: ReactNode }) { - const t = useTranslations(); - const titleComponent = useRef<HTMLDivElement>(null); - const siteYellsView = useRef<HTMLDivElement>(null); - const { setComponents } = useSiteStore(); - - useSiteComponent(); - - const isPath = useIsPath(); - - const getColor = (route: string) => (isPath(route) ? "primary" : "secondary"); - - const onPlatform = () => { - window.open("https://taehui.ddns.net/qwilight/platform"); - }; - - useEffect(() => { - setComponents(titleComponent, siteYellsView); - }, [setComponents]); - - return ( - <QueryClientProvider client={queryClient}> - <div ref={titleComponent}> - <Navbar> - <NavbarBrand href="/"> - <Image alt="" width={48} height={48} src="/qwilight/favicon.ico" /> - </NavbarBrand> - <Row className="g-0"> - <Col className="m-1" xs="auto"> - <Link href={"/note"}> - <Button color={getColor("/note")}>{t("toNote")}</Button> - </Link> - </Col> - <Col className="m-1" xs="auto"> - <Link href={"/site"}> - <Button color={getColor("/site")}>{t("toSite")}</Button> - </Link> - </Col> - <Col className="m-1" xs="auto"> - <Link href={"/avatar"}> - <Button color={getColor("/avatar")}>{t("toAvatar")}</Button> - </Link> - </Col> - <Col className="m-1" xs="auto"> - <Link href={"/hall"}> - <Button color={getColor("/hall")}>{t("toHall")}</Button> - </Link> - </Col> - <Col className="m-1" xs="auto"> - <Link href={"/etc"}> - <Button color={getColor("/etc")}>{t("toEtc")}</Button> - </Link> - </Col> - <Col className="m-1" xs="auto"> - <Button color="danger" onClick={onPlatform}> - <Image alt="" height={12} src={platform} /> - </Button> - </Col> - </Row> - </Navbar> - </div> - <Container>{children}</Container> - - <ToastContainer theme="dark" closeButton={false} hideProgressBar /> - <SignInWindow /> - </QueryClientProvider> - ); -} diff --git a/qwilight-fe/src/Stores.tsx b/qwilight-fe/src/Stores.tsx deleted file mode 100644 index 58b75d2..0000000 --- a/qwilight-fe/src/Stores.tsx +++ /dev/null @@ -1,45 +0,0 @@ -"use client"; - -import setAvatarStore from "@/avatar/setAvatarStore"; -import setEtcStore from "@/etc/setEtcStore"; -import setHallStore from "@/hall/setHallStore"; -import setNoteStore from "@/note/setNoteStore"; - -import setSiteStore from "@/site/setSiteStore"; -import { useLocalObservable } from "mobx-react-lite"; -import { createContext, FC, PropsWithChildren, useContext } from "react"; - -type QwilightStore = { - noteStore: ReturnType<typeof setNoteStore>; - siteStore: ReturnType<typeof setSiteStore>; - avatarStore: ReturnType<typeof setAvatarStore>; - hallStore: ReturnType<typeof setHallStore>; - etcStore: ReturnType<typeof setEtcStore>; -}; - -const qwilightStore = createContext<QwilightStore>({} as QwilightStore); -const { Provider } = qwilightStore; - -export const Stores: FC<PropsWithChildren> = ({ children }) => ( - <Provider - value={{ - noteStore: useLocalObservable(setNoteStore), - siteStore: useLocalObservable(setSiteStore), - avatarStore: useLocalObservable(setAvatarStore), - hallStore: useLocalObservable(setHallStore), - etcStore: useLocalObservable(setEtcStore), - }} - > - {children} - </Provider> -); - -export const useSiteStore = () => useContext(qwilightStore).siteStore; - -export const useNoteStore = () => useContext(qwilightStore).noteStore; - -export const useAvatarStore = () => useContext(qwilightStore).avatarStore; - -export const useHallStore = () => useContext(qwilightStore).hallStore; - -export const useEtcStore = () => useContext(qwilightStore).etcStore; diff --git a/qwilight-fe/src/Title.tsx b/qwilight-fe/src/Title.tsx deleted file mode 100644 index 5462e49..0000000 --- a/qwilight-fe/src/Title.tsx +++ /dev/null @@ -1,32 +0,0 @@ -import { useMemo } from "react"; - -export default function Title({ - title, - titleColor, -}: { - title: string; - titleColor: string; -}) { - const isLevel = useMemo( - () => - [ - "level0", - "level1", - "level2", - "level3", - "level4", - "level5", - "titleLV2000", - ].includes(titleColor), - [titleColor], - ); - - return ( - <span - className={isLevel ? titleColor : undefined} - style={isLevel ? undefined : { color: titleColor }} - > - {title ? `${title} ` : ""} - </span> - ); -} diff --git a/qwilight-fe/src/Utility.ts b/qwilight-fe/src/Utility.ts deleted file mode 100644 index f8938e7..0000000 --- a/qwilight-fe/src/Utility.ts +++ /dev/null @@ -1,268 +0,0 @@ -import i10 from "@/assets/i10.png"; -import i11 from "@/assets/i11.png"; -import i12 from "@/assets/i12.png"; -import i13 from "@/assets/i13.png"; -import i14 from "@/assets/i14.png"; -import i15 from "@/assets/i15.png"; -import i16 from "@/assets/i16.png"; -import i4 from "@/assets/i4.png"; -import i5 from "@/assets/i5.png"; -import i6 from "@/assets/i6.png"; -import i7 from "@/assets/i7.png"; -import i8 from "@/assets/i8.png"; -import i9 from "@/assets/i9.png"; -import m00 from "@/assets/m00.png"; -import m01 from "@/assets/m01.png"; -import m10 from "@/assets/m10.png"; -import m11 from "@/assets/m11.png"; -import m111 from "@/assets/m111.png"; -import m113 from "@/assets/m113.png"; -import m12 from "@/assets/m12.png"; -import m120 from "@/assets/m120.png"; -import m121 from "@/assets/m121.png"; -import m14 from "@/assets/m14.png"; -import m20 from "@/assets/m20.png"; -import m21 from "@/assets/m21.png"; -import m22 from "@/assets/m22.png"; -import m23 from "@/assets/m23.png"; -import m30 from "@/assets/m30.png"; -import m31 from "@/assets/m31.png"; -import m32 from "@/assets/m32.png"; -import m33 from "@/assets/m33.png"; -import m34 from "@/assets/m34.png"; -import m40 from "@/assets/m40.png"; -import m41 from "@/assets/m41.png"; -import m42 from "@/assets/m42.png"; -import m43 from "@/assets/m43.png"; -import m44 from "@/assets/m44.png"; -import m45 from "@/assets/m45.png"; -import m47 from "@/assets/m47.png"; -import m50 from "@/assets/m50.png"; -import m51 from "@/assets/m51.png"; -import m53 from "@/assets/m53.png"; -import m54 from "@/assets/m54.png"; -import m55 from "@/assets/m55.png"; -import m60 from "@/assets/m60.png"; -import m61 from "@/assets/m61.png"; -import m70 from "@/assets/m70.png"; -import m710 from "@/assets/m710.png"; -import m711 from "@/assets/m711.png"; -import m712 from "@/assets/m712.png"; -import m713 from "@/assets/m713.png"; -import m714 from "@/assets/m714.png"; -import m715 from "@/assets/m715.png"; -import m716 from "@/assets/m716.png"; -import m74 from "@/assets/m74.png"; -import m75 from "@/assets/m75.png"; -import m76 from "@/assets/m76.png"; -import m77 from "@/assets/m77.png"; -import m78 from "@/assets/m78.png"; -import m79 from "@/assets/m79.png"; -import m80 from "@/assets/m80.png"; -import m81 from "@/assets/m81.png"; -import { AbilitySiteYell } from "@/site/Site"; -import {useTranslations} from "next-intl"; - -export const is = [ - "", - "", - "", - "", - i4, - i5, - i6, - i7, - i8, - i9, - i10, - i11, - i12, - i13, - i14, - i15, - i16, -]; -export const m0s = [m00, m01]; -export const m1s = [ - m10, - m11, - m12, - "", - m14, - "", - "", - "", - "", - "", - "", - m111, - "", - m113, - "", -]; -export const m2s = [m20, m21, m22, m23]; -export const m3s = [m30, m31, m32, m33, m34]; -export const m4s = [m40, m41, m42, m43, m44, m45, "", m47]; -export const m5s = [m50, m51, "", m53, m54, m55]; -export const m6s = [m60, m61]; -export const m7s = [ - m70, - "", - "", - "", - m74, - m75, - m76, - m77, - m78, - m79, - m710, - m711, - m712, - m713, - m714, - m715, - m716, -]; -export const m8s = [m80, m81]; -export const m12s = [m120, m121]; - -export const formatText = (value: number) => { - return Number(value.toFixed(2)) - .toString() - .replace(/\B(?=(\d{3})+(?!\d))/g, ","); -}; - -export const getGenreText = (genre: string) => - genre.length === 0 || genre.startsWith("#") ? genre : `#${genre}`; - -export const getAbilityUpText = ( - t: ReturnType<typeof useTranslations>, - { inputMode, ability }: AbilitySiteYell, -) => { - let inputModeText = ""; - switch (inputMode) { - case 10: - inputModeText = "⑤K"; - break; - case 11: - inputModeText = "⑦K"; - break; - case 9: - inputModeText = "9K"; - break; - } - return ability < 0.01 - ? `${inputModeText} < 0.01 Point ↑` - : `${inputModeText} ${ability.toFixed(2)} Point ↑`; -}; - -export const toDate = (date: number) => { - const dateText = new Date(date); - return `${dateText.toLocaleDateString()} ${dateText.toLocaleTimeString()}`; -}; - -export const getSiteName = ( - siteName: string, - t: ReturnType<typeof useTranslations<string>>, -) => { - switch (siteName) { - case "@Comment": - return t("commentSiteName"); - case "@Notify": - return t("toNotifySiteName"); - case "@Default": - return t("defaultSiteName"); - case "@Platform": - return t("platformSiteName"); - default: - return siteName; - } -}; - -export const getQuitStatusValue = ( - point: number, - stand: number, -): { - quitCss: "S+" | "S" | "A+" | "A" | "B" | "C" | "D"; - quit: string; -} => { - const quitCss = - point < 0.8 - ? "D" - : point < 0.85 - ? "C" - : point < 0.9 - ? "B" - : point < 0.95 - ? "A" - : stand < 900000 - ? "A+" - : point < 1.0 - ? "S" - : "S+"; - - return { - quitCss, - quit: quitCss, - }; -}; - -export const getDefaultAvatarID = (avatarID: string) => - avatarID.substring(avatarID.indexOf("@") + 1); - -export const getHitPointsClass = (hitPointsMode: number) => { - switch (hitPointsMode) { - case 0: - return "level2"; - case 2: - return "level4"; - case 3: - case 5: - return "level5"; - case 4: - return "level1"; - default: - return "stand"; - } -}; - -export const getInputMode = ( - tabPosition: number, -): "6K" | "5K" | "7K" | "9K" | "10K" | "14K" | "24K" | "48K" => { - switch (tabPosition) { - case 0: - return "6K"; - case 1: - return "5K"; - case 2: - return "7K"; - case 3: - return "9K"; - case 4: - return "10K"; - case 5: - return "14K"; - case 6: - return "24K"; - case 7: - return "48K"; - default: - throw new Error(tabPosition.toString()); - } -}; - -export const getAbilityInputMode = ( - tabPosition: number, -): "5K" | "7K" | "9K" => { - switch (tabPosition) { - case 0: - return "5K"; - case 1: - return "7K"; - case 2: - return "9K"; - default: - throw new Error(tabPosition.toString()); - } -}; diff --git a/qwilight-fe/src/Www.ts b/qwilight-fe/src/Www.ts deleted file mode 100644 index 93f16ec..0000000 --- a/qwilight-fe/src/Www.ts +++ /dev/null @@ -1,25 +0,0 @@ -import axios, { AxiosError } from "axios"; -import { toast } from "react-toastify"; - -export const wwwAPI = "/qwilight/www"; - -export const wwwAXIOS = axios.create({ - baseURL: wwwAPI, -}); - -wwwAXIOS.interceptors.response.use( - (value) => value, - (e: AxiosError) => { - switch (e.response?.status) { - case 401: - toast.error("Unauthorized"); - window.sessionStorage.removeItem("totem"); - break; - case 502: - toast.error("Bad Gateway"); - break; - } - - throw e; - }, -); diff --git "a/qwilight-fe/src/app/\133language\135/avatar/\133\133...want\135\135/page.tsx" "b/qwilight-fe/src/app/\133language\135/avatar/\133\133...want\135\135/page.tsx" index a10f5ed..56ef8be 100644 --- "a/qwilight-fe/src/app/\133language\135/avatar/\133\133...want\135\135/page.tsx" +++ "b/qwilight-fe/src/app/\133language\135/avatar/\133\133...want\135\135/page.tsx" @@ -1,19 +1,19 @@ "use client"; +import AbilitiesView from "@/app/[language]/avatar/components/AbilitiesView"; +import DateView from "@/app/[language]/avatar/components/DateView"; +import FavoritesView from "@/app/[language]/avatar/components/FavoritesView"; +import IntroView from "@/app/[language]/avatar/components/IntroView"; +import LastsView from "@/app/[language]/avatar/components/LastsView"; +import QuitStatusValues from "@/app/[language]/avatar/components/QuitStatusValues"; +import WwwLevelsView from "@/app/[language]/avatar/components/WwwLevelsView"; import Loading from "@/app/[language]/avatar/loading"; -import AbilitiesView from "@/avatar/AbilitiesView"; -import DateView from "@/avatar/DateView"; -import FavoritesView from "@/avatar/FavoritesView"; -import IntroView from "@/avatar/IntroView"; -import LastsView from "@/avatar/LastsView"; -import QuitStatusValues from "@/avatar/QuitStatusValues"; -import useGetAvatar from "@/avatar/useGetAvatar"; -import WwwLevelsView from "@/avatar/WwwLevelsView"; -import AvatarDrawing from "@/AvatarDrawing"; -import AvatarTitle from "@/AvatarTitle"; -import { useAvatarStore, useSiteStore } from "@/Stores"; -import { getDefaultAvatarID } from "@/Utility"; -import { wwwAPI } from "@/Www"; +import useGetAvatar from "@/app/[language]/avatar/query/useGetAvatar"; +import AvatarDrawing from "@/components/AvatarDrawing"; +import AvatarTitle from "@/components/AvatarTitle"; +import { useAvatarStore, useSiteStore } from "@/store/Stores"; +import { getDefaultAvatarID } from "@/utilities/Utility"; +import { wwwAPIPath } from "@/utilities/wwwAPI"; import { observer } from "mobx-react-lite"; import { useTranslations } from "next-intl"; import Image from "next/image"; @@ -32,24 +32,25 @@ TabContent, TabPane, } from "reactstrap"; -import { useWant } from "taehui-ts/fe-utility"; +import { useWant } from "taehui-ts/fe-utilities"; export default observer(() => { - const { input, setInput, tabPosition, setTabPosition } = useAvatarStore(); - const { siteAvatarID, isSignedIn, setSignInOpened } = useSiteStore(); + const { textInput, setTextInput, tabPosition, setTabPosition } = + useAvatarStore(); + const { siteAvatarID, isLoggedIn, setLogInOpened } = useSiteStore(); const { want, setWant } = useWant("/avatar"); const t = useTranslations(); useEffect(() => { - setInput(want); - }, [want, setInput]); + setTextInput(want); + }, [want, setTextInput]); const { isFetched: isAvatarLoaded, data: avatar } = useGetAvatar(); const onWant = () => { - setWant(input); + setWant(textInput); }; const getProperties = (i: number) => ({ @@ -66,10 +67,10 @@ <Button color="info" onClick={() => { - if (isSignedIn) { + if (isLoggedIn) { setWant(`!${getDefaultAvatarID(siteAvatarID)}`); } else { - setSignInOpened(true); + setLogInOpened(true); } }} > @@ -79,9 +80,9 @@ <Col className="m-1"> <Input type="search" - value={input} + value={textInput} onChange={({ target: { value } }) => { - setInput(value); + setTextInput(value); }} onKeyDown={({ key }) => { if (key === "Enter") { @@ -175,7 +176,7 @@ <Col className="m-1" xs="auto"> <Image alt="" - src={`${wwwAPI}/drawing?abilityClass5K=${ + src={`${wwwAPIPath}/drawing?abilityClass5K=${ avatar.avatarAbility5KClass < 0 ? avatar.avatarAbility5KClass : 100 * avatar.avatarAbility5KClass @@ -198,7 +199,7 @@ <Col className="m-1" xs="auto"> <Image alt="" - src={`${wwwAPI}/drawing?abilityClass7K=${ + src={`${wwwAPIPath}/drawing?abilityClass7K=${ avatar.avatarAbility7KClass < 0 ? avatar.avatarAbility7KClass : 100 * avatar.avatarAbility7KClass @@ -221,7 +222,7 @@ <Col className="m-1" xs="auto"> <Image alt="" - src={`${wwwAPI}/drawing?abilityClass9K=${ + src={`${wwwAPIPath}/drawing?abilityClass9K=${ avatar.avatarAbility9KClass < 0 ? avatar.avatarAbility9KClass : 100 * avatar.avatarAbility9KClass diff --git "a/qwilight-fe/src/app/\133language\135/avatar/components/AbilitiesView.tsx" "b/qwilight-fe/src/app/\133language\135/avatar/components/AbilitiesView.tsx" new file mode 100644 index 0000000..f48c98e --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/avatar/components/AbilitiesView.tsx" @@ -0,0 +1,79 @@ +import { GetAvatar } from "@/app/[language]/avatar/query/useGetAvatar"; +import useGetAvatarAbility from "@/app/[language]/avatar/query/useGetAvatarAbility"; +import NoteItem from "@/app/[language]/note/components/NoteItem"; +import { NoteLoading } from "@/components/Loading"; + +import { useAvatarStore } from "@/store/Stores"; +import { getAbilityInputMode } from "@/utilities/Utility"; +import { observer } from "mobx-react-lite"; +import { useCallback } from "react"; +import { + ListGroup, + Nav, + NavItem, + NavLink, + TabContent, + TabPane, +} from "reactstrap"; + +export default observer(({ avatar: { avatarID } }: { avatar: GetAvatar }) => { + const { abilitiesTabPosition, tabPosition, setAbilitiesTabPosition } = + useAvatarStore(); + + const getProperties = (i: number) => ({ + className: abilitiesTabPosition === i ? "active route" : "route", + onClick: () => { + setAbilitiesTabPosition(i); + }, + }); + + const { isFetched: isAvatarAbilityLoaded, data: avatarAbility } = + useGetAvatarAbility( + getAbilityInputMode(abilitiesTabPosition), + tabPosition === 2 ? avatarID : undefined, + ); + + const AbilityView = useCallback( + ({ tabPosition }: { tabPosition: number }) => { + return ( + <TabPane tabId={tabPosition}> + <ListGroup> + {isAvatarAbilityLoaded ? ( + avatarAbility.map((avatarAbility) => ( + <NoteItem + {...avatarAbility} + key={avatarAbility.noteID} + wantAvatarID={avatarID} + /> + )) + ) : ( + <NoteLoading loadingCount={50} /> + )} + </ListGroup> + </TabPane> + ); + }, + [avatarID, avatarAbility, isAvatarAbilityLoaded], + ); + + return ( + <> + <Nav tabs> + <NavItem> + <NavLink {...getProperties(0)}>⑤K</NavLink> + </NavItem> + <NavItem> + <NavLink {...getProperties(1)}>⑦K</NavLink> + </NavItem> + <NavItem> + <NavLink {...getProperties(2)}>9K</NavLink> + </NavItem> + </Nav> + <TabContent activeTab={abilitiesTabPosition}> + <AbilityView tabPosition={0} /> + <AbilityView tabPosition={1} /> + <AbilityView tabPosition={2} /> + </TabContent> + </> + ); +}); diff --git "a/qwilight-fe/src/app/\133language\135/avatar/components/DateView.tsx" "b/qwilight-fe/src/app/\133language\135/avatar/components/DateView.tsx" new file mode 100644 index 0000000..62741f2 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/avatar/components/DateView.tsx" @@ -0,0 +1,65 @@ +import { GetAvatar } from "@/app/[language]/avatar/query/useGetAvatar"; +import { + BarController, + BarElement, + CategoryScale, + Chart, + LinearScale, +} from "chart.js"; +import { useTranslations } from "next-intl"; +import { useEffect, useRef } from "react"; +import { Badge, ListGroup, ListGroupItem } from "reactstrap"; + +export default function DateView({ + avatar: { dateSet, dateValues }, +}: { + avatar: GetAvatar; +}) { + const dateView = useRef<HTMLCanvasElement>(null); + + const t = useTranslations(); + + useEffect(() => { + const dateView2D = dateView.current?.getContext("2d"); + if (dateView2D) { + Chart.register(BarController, BarElement, CategoryScale, LinearScale); + + const view = new Chart(dateView2D, { + type: "bar", + data: { + labels: dateSet, + datasets: [ + { + data: dateValues, + backgroundColor: "white", + }, + ], + }, + options: { + scales: { + x: { + display: false, + }, + y: { + display: false, + }, + }, + }, + }); + + return () => { + view.destroy(); + Chart.unregister(BarController, BarElement, CategoryScale, LinearScale); + }; + } + }, [dateSet, dateValues]); + + return ( + <ListGroup> + <Badge>{t("avatarDateText")}</Badge> + <ListGroupItem> + <canvas ref={dateView} /> + </ListGroupItem> + </ListGroup> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/avatar/components/FavoritesView.tsx" "b/qwilight-fe/src/app/\133language\135/avatar/components/FavoritesView.tsx" new file mode 100644 index 0000000..782b85e --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/avatar/components/FavoritesView.tsx" @@ -0,0 +1,99 @@ +import { GetAvatar } from "@/app/[language]/avatar/query/useGetAvatar"; +import useGetAvatarFavorites from "@/app/[language]/avatar/query/useGetAvatarFavorites"; +import NoteItem from "@/app/[language]/note/components/NoteItem"; +import { NoteLoading } from "@/components/Loading"; + +import { useAvatarStore } from "@/store/Stores"; +import { getInputMode } from "@/utilities/Utility"; +import { observer } from "mobx-react-lite"; +import { useCallback } from "react"; +import { + ListGroup, + Nav, + NavItem, + NavLink, + TabContent, + TabPane, +} from "reactstrap"; + +export default observer(({ avatar: { avatarID } }: { avatar: GetAvatar }) => { + const { tabPosition, favoritesTabPosition, setFavoritesTabPosition } = + useAvatarStore(); + + const { isFetched: isAvatarFavoritesLoaded, data: avatarFavorites } = + useGetAvatarFavorites( + getInputMode(favoritesTabPosition), + tabPosition === 0 ? avatarID : undefined, + ); + + const getProperties = (i: number) => ({ + className: favoritesTabPosition === i ? "active route" : "route", + onClick: () => { + setFavoritesTabPosition(i); + }, + }); + + const FavoriteView = useCallback( + ({ tabPosition }: { tabPosition: number }) => { + return ( + <TabPane tabId={tabPosition}> + <ListGroup> + {isAvatarFavoritesLoaded ? ( + avatarFavorites.map((avatarFavorite) => ( + <NoteItem + {...avatarFavorite} + key={avatarFavorite.noteID} + wantAvatarID={avatarID} + /> + )) + ) : ( + <NoteLoading loadingCount={50} /> + )} + </ListGroup> + </TabPane> + ); + }, + [avatarFavorites, isAvatarFavoritesLoaded], + ); + + return ( + <> + <Nav tabs> + <NavItem> + <NavLink {...getProperties(0)}>6K</NavLink> + </NavItem> + <NavItem> + <NavLink {...getProperties(1)}>⑤K</NavLink> + </NavItem> + <NavItem> + <NavLink {...getProperties(2)}>⑦K</NavLink> + </NavItem> + <NavItem> + <NavLink {...getProperties(3)}>9K</NavLink> + </NavItem> + <NavItem> + <NavLink {...getProperties(4)}>⑩K</NavLink> + </NavItem> + <NavItem> + <NavLink {...getProperties(5)}>⑭K</NavLink> + </NavItem> + <NavItem> + <NavLink {...getProperties(6)}>24</NavLink> + </NavItem> + <NavItem> + <NavLink {...getProperties(7)}>48</NavLink> + </NavItem> + </Nav> + <TabContent activeTab={favoritesTabPosition}> + <FavoriteView tabPosition={0} /> + <FavoriteView tabPosition={1} /> + <FavoriteView tabPosition={2} /> + <FavoriteView tabPosition={3} /> + <FavoriteView tabPosition={4} /> + <FavoriteView tabPosition={5} /> + <FavoriteView tabPosition={6} /> + <FavoriteView tabPosition={7} /> + </TabContent> + </> + ); +}); diff --git "a/qwilight-fe/src/app/\133language\135/avatar/components/IntroView.tsx" "b/qwilight-fe/src/app/\133language\135/avatar/components/IntroView.tsx" new file mode 100644 index 0000000..f31cca3 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/avatar/components/IntroView.tsx" @@ -0,0 +1,24 @@ +import { GetAvatar } from "@/app/[language]/avatar/query/useGetAvatar"; +import { useTranslations } from "next-intl"; +import { Badge, ListGroup, ListGroupItem } from "reactstrap"; + +export default function IntroView({ + avatar: { avatarIntro }, +}: { + avatar: GetAvatar; +}) { + const t = useTranslations(); + + if (!avatarIntro) { + return null; + } + + return ( + <ListGroup> + <Badge>{t("avatarIntroText")}</Badge> + <ListGroupItem> + <span className="avatarIntro">{avatarIntro}</span> + </ListGroupItem> + </ListGroup> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/avatar/components/LastsView.tsx" "b/qwilight-fe/src/app/\133language\135/avatar/components/LastsView.tsx" new file mode 100644 index 0000000..2327201 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/avatar/components/LastsView.tsx" @@ -0,0 +1,99 @@ +import { GetAvatar } from "@/app/[language]/avatar/query/useGetAvatar"; +import useGetAvatarLasts from "@/app/[language]/avatar/query/useGetAvatarLasts"; +import NoteItem from "@/app/[language]/note/components/NoteItem"; +import { NoteLoading } from "@/components/Loading"; + +import { useAvatarStore } from "@/store/Stores"; +import { getInputMode } from "@/utilities/Utility"; +import { observer } from "mobx-react-lite"; +import { useCallback } from "react"; +import { + ListGroup, + Nav, + NavItem, + NavLink, + TabContent, + TabPane, +} from "reactstrap"; + +export default observer(({ avatar: { avatarID } }: { avatar: GetAvatar }) => { + const { tabPosition, lastsTabPosition, setLastsTabPosition } = + useAvatarStore(); + + const { isFetched: isAvatarLastsLoaded, data: avatarLasts } = + useGetAvatarLasts( + getInputMode(lastsTabPosition), + tabPosition === 1 ? avatarID : undefined, + ); + + const getProperties = (i: number) => ({ + className: lastsTabPosition === i ? "active route" : "route", + onClick: () => { + setLastsTabPosition(i); + }, + }); + + const LastView = useCallback( + ({ tabPosition }: { tabPosition: number }) => { + return ( + <TabPane tabId={tabPosition}> + <ListGroup> + {isAvatarLastsLoaded ? ( + avatarLasts.map((avatarLast) => ( + <NoteItem + {...avatarLast} + key={avatarLast.noteID} + wantAvatarID={avatarID} + /> + )) + ) : ( + <NoteLoading loadingCount={50} /> + )} + </ListGroup> + </TabPane> + ); + }, + [avatarID, avatarLasts, isAvatarLastsLoaded], + ); + + return ( + <> + <Nav tabs> + <NavItem> + <NavLink {...getProperties(0)}>6K</NavLink> + </NavItem> + <NavItem> + <NavLink {...getProperties(1)}>⑤K</NavLink> + </NavItem> + <NavItem> + <NavLink {...getProperties(2)}>⑦K</NavLink> + </NavItem> + <NavItem> + <NavLink {...getProperties(3)}>9K</NavLink> + </NavItem> + <NavItem> + <NavLink {...getProperties(4)}>⑩K</NavLink> + </NavItem> + <NavItem> + <NavLink {...getProperties(5)}>⑭K</NavLink> + </NavItem> + <NavItem> + <NavLink {...getProperties(6)}>24</NavLink> + </NavItem> + <NavItem> + <NavLink {...getProperties(7)}>48</NavLink> + </NavItem> + </Nav> + <TabContent activeTab={lastsTabPosition}> + <LastView tabPosition={0} /> + <LastView tabPosition={1} /> + <LastView tabPosition={2} /> + <LastView tabPosition={3} /> + <LastView tabPosition={4} /> + <LastView tabPosition={5} /> + <LastView tabPosition={6} /> + <LastView tabPosition={7} /> + </TabContent> + </> + ); +}); diff --git "a/qwilight-fe/src/app/\133language\135/avatar/components/QuitStatusValues.tsx" "b/qwilight-fe/src/app/\133language\135/avatar/components/QuitStatusValues.tsx" new file mode 100644 index 0000000..38f663a --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/avatar/components/QuitStatusValues.tsx" @@ -0,0 +1,25 @@ +import { GetAvatar } from "@/app/[language]/avatar/query/useGetAvatar"; +import { useTranslations } from "next-intl"; +import { Badge, ListGroup, ListGroupItem } from "reactstrap"; + +const quitItems = ["S+", "S", "A+", "A", "B", "C", "D"] as const; + +export default function QuitStatusValues({ + avatar: { quitStatusValues }, +}: { + avatar: GetAvatar; +}) { + const t = useTranslations(); + + return ( + <ListGroup> + <Badge>{t("avatarQuitStatusText")}</Badge> + {quitItems.map((quitItem) => ( + <ListGroupItem key={quitItem}> + <span className={quitItem}>{quitItem}</span>{" "} + <span>{quitStatusValues[quitItems.indexOf(quitItem)]}</span> + </ListGroupItem> + ))} + </ListGroup> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/avatar/components/WwwLevelItem.tsx" "b/qwilight-fe/src/app/\133language\135/avatar/components/WwwLevelItem.tsx" new file mode 100644 index 0000000..4dc58c3 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/avatar/components/WwwLevelItem.tsx" @@ -0,0 +1,20 @@ +import { GetAvatarWwwLevelsAPI } from "@/type/wwwAPI"; +import { toDate } from "@/utilities/Utility"; +import { Col, ListGroupItem, Row } from "reactstrap"; + +export default function WwwLevelItem({ + title, + date, +}: GetAvatarWwwLevelsAPI[number]) { + return ( + <ListGroupItem> + <Row className="g-0"> + <Col className="m-1" xs="auto"> + <span>{title}</span> + <br /> + {date && <span className="fittedText">{toDate(date)}</span>} + </Col> + </Row> + </ListGroupItem> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/avatar/components/WwwLevelsView.tsx" "b/qwilight-fe/src/app/\133language\135/avatar/components/WwwLevelsView.tsx" new file mode 100644 index 0000000..56f36b9 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/avatar/components/WwwLevelsView.tsx" @@ -0,0 +1,33 @@ +import WwwLevelItem from "@/app/[language]/avatar/components/WwwLevelItem"; +import { GetAvatar } from "@/app/[language]/avatar/query/useGetAvatar"; +import useGetAvatarWwwLevels from "@/app/[language]/avatar/query/useGetAvatarWwwLevels"; +import { WwwLevelLoading } from "@/components/Loading"; +import { useAvatarStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; +import { ListGroup } from "reactstrap"; + +export default observer(({ avatar: { avatarID } }: { avatar: GetAvatar }) => { + const { tabPosition } = useAvatarStore(); + + const { isFetched: isAvatarWwwLevelsLoaded, data: avatarWwwLevels } = + useGetAvatarWwwLevels(tabPosition === 3 ? avatarID : undefined); + + return ( + <ListGroup> + {isAvatarWwwLevelsLoaded ? ( + avatarWwwLevels.map(({ levelID, title, levelText, level, date }) => ( + <WwwLevelItem + key={levelID} + levelID={levelID} + title={title} + levelText={levelText} + level={level} + date={date} + /> + )) + ) : ( + <WwwLevelLoading loadingCount={1} /> + )} + </ListGroup> + ); +}); diff --git "a/qwilight-fe/src/app/\133language\135/avatar/loading.tsx" "b/qwilight-fe/src/app/\133language\135/avatar/loading.tsx" index b679c9a..8889c7a 100644 --- "a/qwilight-fe/src/app/\133language\135/avatar/loading.tsx" +++ "b/qwilight-fe/src/app/\133language\135/avatar/loading.tsx" @@ -1,4 +1,4 @@ -import LoadingLayer from "@/LoadingLayer"; +import LoadingLayer from "@/components/LoadingLayer"; import { useTranslations } from "next-intl"; export default function Loading() { diff --git "a/qwilight-fe/src/app/\133language\135/avatar/query/useGetAvatar.ts" "b/qwilight-fe/src/app/\133language\135/avatar/query/useGetAvatar.ts" new file mode 100644 index 0000000..0cde76d --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/avatar/query/useGetAvatar.ts" @@ -0,0 +1,88 @@ +import { AvatarAPIAvatar, AvatarAPIWantAvatar } from "@/type/wwwAPI"; +import { formatText, toDate } from "@/utilities/Utility"; + +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { useIsPath, useWant } from "taehui-ts/fe-utilities"; + +export type GetAvatar = { + avatarID: string; + avatarName: string; + avatarIntro: string; + totalCount: string; + totalLength: string; + highestCount: string; + date: string; + avatarLevels: number[]; + avatarAbility5KText: string; + avatarAbility5KClass: number; + avatarAbility5KPlace: number; + avatarAbility5KPlaceText: string; + avatarAbility5KCountText: string; + avatarAbility7KText: string; + avatarAbility7KClass: number; + avatarAbility7KPlace: number; + avatarAbility7KPlaceText: string; + avatarAbility7KCountText: string; + avatarAbility9KText: string; + avatarAbility9KClass: number; + avatarAbility9KPlace: number; + avatarAbility9KPlaceText: string; + avatarAbility9KCountText: string; + dateSet: number[]; + dateValues: number[]; + quitStatusValues: number[]; +}; + +export default function useGetAvatar() { + const { want } = useWant("/avatar"); + + const t = useTranslations(); + + const isPath = useIsPath(); + + return useQuery<AvatarAPIWantAvatar[] | GetAvatar>({ + enabled: !!want && isPath("/avatar"), + queryKey: ["avatar", want], + queryFn: async () => { + const { data } = await wwwAPI.get< + AvatarAPIWantAvatar[] | AvatarAPIAvatar + >("/avatar", { + params: want.startsWith("!") + ? { + avatarID: want.substring(want.indexOf("!") + 1), + } + : { + avatarName: want, + }, + }); + + if (Array.isArray(data)) { + return data; + } else { + return { + ...data, + totalCount: formatText(data.totalCount), + totalLength: t("totalLengthText", { + h: Math.floor(data.totalLength / 1000 / 60 / 60), + m: Math.floor((data.totalLength / 1000 / 60) % 60), + s: Math.floor((data.totalLength / 1000) % 60), + }), + highestCount: formatText(data.highestCount), + date: toDate(data.date), + avatarAbility5KText: formatText(data.avatarAbility5K), + avatarAbility5KPlaceText: formatText(data.avatarAbility5KPlace), + avatarAbility5KCountText: formatText(data.avatarAbility5KCount), + avatarAbility7KText: formatText(data.avatarAbility7K), + avatarAbility7KPlaceText: formatText(data.avatarAbility7KPlace), + avatarAbility7KCountText: formatText(data.avatarAbility7KCount), + avatarAbility9KText: formatText(data.avatarAbility9K), + avatarAbility9KPlaceText: formatText(data.avatarAbility9KPlace), + avatarAbility9KCountText: formatText(data.avatarAbility9KCount), + }; + } + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/avatar/query/useGetAvatarAbility.ts" "b/qwilight-fe/src/app/\133language\135/avatar/query/useGetAvatarAbility.ts" new file mode 100644 index 0000000..e18e6ab --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/avatar/query/useGetAvatarAbility.ts" @@ -0,0 +1,37 @@ +import { GetAvatarAbilitiesAPI } from "@/type/wwwAPI"; +import { formatText } from "@/utilities/Utility"; + +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetAvatarAbility( + inputMode: "5K" | "7K" | "9K", + avatarID?: string, +) { + const t = useTranslations(); + + const isPath = useIsPath(); + + return useQuery({ + enabled: !!avatarID && isPath("/avatar"), + queryKey: ["avatarAbility", inputMode, avatarID], + queryFn: async () => { + const { data } = await wwwAPI.get<GetAvatarAbilitiesAPI>( + `/avatar/ability/${inputMode}`, + { + params: { avatarID }, + }, + ); + return data.map((data) => ({ + ...data, + fittedText: t("abilityFittedText", { + stand: formatText(data.stand), + ability: formatText(data.ability), + }), + })); + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/avatar/query/useGetAvatarFavorites.ts" "b/qwilight-fe/src/app/\133language\135/avatar/query/useGetAvatarFavorites.ts" new file mode 100644 index 0000000..04ed68c --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/avatar/query/useGetAvatarFavorites.ts" @@ -0,0 +1,34 @@ +import { GetAvatarFavoritesAPI } from "@/type/wwwAPI"; +import { formatText } from "@/utilities/Utility"; + +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetAvatarFavorites( + inputMode: "6K" | "5K" | "7K" | "9K" | "10K" | "14K" | "24K" | "48K", + avatarID?: string, +) { + const isPath = useIsPath(); + + const t = useTranslations(); + + return useQuery({ + enabled: !!avatarID && isPath("/avatar"), + queryKey: ["avatarFavorites", inputMode, avatarID], + queryFn: async () => { + const { data } = await wwwAPI.get<GetAvatarFavoritesAPI>( + `/avatar/favorites/${inputMode}`, + { + params: { avatarID }, + }, + ); + return data.map((data) => ({ + ...data, + fittedText: t("textHandled", { value: formatText(data.totalCount) }), + })); + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/avatar/query/useGetAvatarLasts.ts" "b/qwilight-fe/src/app/\133language\135/avatar/query/useGetAvatarLasts.ts" new file mode 100644 index 0000000..73f118c --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/avatar/query/useGetAvatarLasts.ts" @@ -0,0 +1,28 @@ +import { GetAvatarLastsAPI } from "@/type/wwwAPI"; +import { toDate } from "@/utilities/Utility"; + +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetAvatarLasts( + inputMode: "6K" | "5K" | "7K" | "9K" | "10K" | "14K" | "24K" | "48K", + avatarID?: string, +) { + const isPath = useIsPath(); + + return useQuery({ + enabled: !!avatarID && isPath("/avatar"), + queryKey: ["avatarLasts", inputMode, avatarID], + queryFn: async () => { + const { data } = await wwwAPI.get<GetAvatarLastsAPI>( + `/avatar/lasts/${inputMode}`, + { + params: { avatarID }, + }, + ); + return data.map((data) => ({ ...data, fittedText: toDate(data.date) })); + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/avatar/query/useGetAvatarWwwLevels.ts" "b/qwilight-fe/src/app/\133language\135/avatar/query/useGetAvatarWwwLevels.ts" new file mode 100644 index 0000000..f8f23ab --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/avatar/query/useGetAvatarWwwLevels.ts" @@ -0,0 +1,23 @@ +import { GetAvatarWwwLevelsAPI } from "@/type/wwwAPI"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetAvatarWwwLevels(avatarID?: string) { + const isPath = useIsPath(); + + return useQuery({ + enabled: !!avatarID && isPath("/avatar"), + queryKey: ["avatarWwwLevels", avatarID], + queryFn: async () => { + const { data } = await wwwAPI.get<GetAvatarWwwLevelsAPI>( + "/avatar/wwwLevels", + { + params: { avatarID }, + }, + ); + return data; + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/avatar/store/setAvatarStore.ts" "b/qwilight-fe/src/app/\133language\135/avatar/store/setAvatarStore.ts" new file mode 100644 index 0000000..4ec663c --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/avatar/store/setAvatarStore.ts" @@ -0,0 +1,29 @@ +export default function setAvatarStore() { + return { + textInput: "", + tabPosition: 0, + favoritesTabPosition: 0, + lastsTabPosition: 0, + abilitiesTabPosition: 0, + + setTextInput(input: string) { + this.textInput = input; + }, + + setTabPosition(tabPosition: number) { + this.tabPosition = tabPosition; + }, + + setFavoritesTabPosition(favoritesTabPosition: number) { + this.favoritesTabPosition = favoritesTabPosition; + }, + + setLastsTabPosition(lastsTabPosition: number) { + this.lastsTabPosition = lastsTabPosition; + }, + + setAbilitiesTabPosition(abilitiesTabPosition: number) { + this.abilitiesTabPosition = abilitiesTabPosition; + }, + }; +} diff --git "a/qwilight-fe/src/app/\133language\135/etc/components/DateView.tsx" "b/qwilight-fe/src/app/\133language\135/etc/components/DateView.tsx" new file mode 100644 index 0000000..e5fd885 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/etc/components/DateView.tsx" @@ -0,0 +1,69 @@ +import { + BarController, + BarElement, + CategoryScale, + Chart, + LinearScale, + LineController, +} from "chart.js"; +import { observer } from "mobx-react-lite"; +import { useEffect, useRef } from "react"; +import { Badge, ListGroup, ListGroupItem } from "reactstrap"; + +export default observer<{ + title: string; + dateSet: string[]; + dateValues: number[]; +}>(({ title, dateSet, dateValues }) => { + const dateView = useRef<HTMLCanvasElement>(null); + + useEffect(() => { + const view2D = dateView.current?.getContext("2d"); + if (view2D) { + Chart.register( + LineController, + BarController, + BarElement, + CategoryScale, + LinearScale, + ); + + const view = new Chart(view2D, { + type: "bar", + data: { + labels: dateSet, + datasets: [ + { + data: dateValues, + backgroundColor: "white", + }, + ], + }, + options: { + scales: { + x: { + display: false, + }, + y: { + display: false, + }, + }, + }, + }); + + return () => { + view.destroy(); + Chart.unregister(BarController, BarElement, CategoryScale, LinearScale); + }; + } + }, [dateSet, dateValues]); + + return ( + <ListGroup> + <Badge color="primary">{title}</Badge> + <ListGroupItem> + <canvas ref={dateView} /> + </ListGroupItem> + </ListGroup> + ); +}); diff --git "a/qwilight-fe/src/app/\133language\135/etc/components/EdgeItem.tsx" "b/qwilight-fe/src/app/\133language\135/etc/components/EdgeItem.tsx" new file mode 100644 index 0000000..b73b0ca --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/etc/components/EdgeItem.tsx" @@ -0,0 +1,28 @@ +import Image from "next/image"; +import { Col, ListGroupItem, Row } from "reactstrap"; + +export default function EdgeItem({ + edge, + text, +}: { + edge: string; + text: string; +}) { + return ( + <ListGroupItem> + <Row className="g-0"> + <Col className="m-1" xs="auto"> + <Image + alt="" + src={`data:image/png;base64,${edge}`} + width={60} + height={60} + /> + </Col> + <Col className="m-1" xs="auto"> + <span>{text}</span> + </Col> + </Row> + </ListGroupItem> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/etc/components/FavoritesView.tsx" "b/qwilight-fe/src/app/\133language\135/etc/components/FavoritesView.tsx" new file mode 100644 index 0000000..231c221 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/etc/components/FavoritesView.tsx" @@ -0,0 +1,31 @@ +import NoteItem from "@/app/[language]/note/components/NoteItem"; +import { EtcAPINoteFile } from "@/type/wwwAPI"; +import { Badge, ListGroup } from "reactstrap"; + +export default function FavoritesView({ + title, + favorites, +}: { + title: string; + favorites: EtcAPINoteFile[]; +}) { + return ( + <ListGroup> + <Badge>{title}</Badge> + {favorites.map( + ({ noteID, artist, title, genre, levelText, level, value }) => ( + <NoteItem + key={noteID} + noteID={noteID} + artist={artist} + title={title} + genre={genre} + levelText={levelText} + level={level} + fittedText={`👍 ${value}`} + /> + ), + )} + </ListGroup> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/etc/components/ModeItem.tsx" "b/qwilight-fe/src/app/\133language\135/etc/components/ModeItem.tsx" new file mode 100644 index 0000000..8bc77d3 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/etc/components/ModeItem.tsx" @@ -0,0 +1,39 @@ +import { EtcAPIMode } from "@/type/wwwAPI"; +import { formatText } from "@/utilities/Utility"; +import { useTranslations } from "next-intl"; +import Image, { StaticImageData } from "next/image"; +import { Badge, Col, ListGroup, ListGroupItem, Row } from "reactstrap"; + +export default function ModeItem({ + title, + modes, + drawings, +}: { + title: string; + modes: EtcAPIMode[]; + drawings: (string | StaticImageData)[]; +}) { + const t = useTranslations(); + + return ( + <ListGroup> + <Badge color="success">{title}</Badge> + {modes.map(({ mode, value }) => { + return ( + value > 0 && ( + <ListGroupItem key={mode}> + <Row className="g-0"> + <Col className="m-1"> + <Image height={24} alt="" src={drawings[mode]} /> + </Col> + <Col className="m-1" xs="auto"> + <span>{t("textHandled", { value: formatText(value) })}</span> + </Col> + </Row> + </ListGroupItem> + ) + ); + })} + </ListGroup> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/etc/components/TitleItem.tsx" "b/qwilight-fe/src/app/\133language\135/etc/components/TitleItem.tsx" new file mode 100644 index 0000000..db5d68f --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/etc/components/TitleItem.tsx" @@ -0,0 +1,24 @@ +import Title from "@/components/Title"; +import { Col, ListGroupItem, Row } from "reactstrap"; + +export default function TitleItem({ + title, + titleColor, + text, +}: { + title: string; + titleColor: string; + text: string; +}) { + return ( + <ListGroupItem> + <Row className="g-0"> + <Col className="m-1" xs="auto"> + <Title title={title} titleColor={titleColor} /> + <br /> + <span>{text}</span> + </Col> + </Row> + </ListGroupItem> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/etc/components/TotalEdgesView.tsx" "b/qwilight-fe/src/app/\133language\135/etc/components/TotalEdgesView.tsx" new file mode 100644 index 0000000..738aecd --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/etc/components/TotalEdgesView.tsx" @@ -0,0 +1,25 @@ +import EdgeItem from "@/app/[language]/etc/components/EdgeItem"; +import { EtcAPIEdge } from "@/type/wwwAPI"; +import { useTranslations } from "next-intl"; +import { Badge, ListGroup } from "reactstrap"; + +export default function TotalEdgesView({ + totalEdges, +}: { + totalEdges: EtcAPIEdge[]; +}) { + const t = useTranslations(); + + return ( + <ListGroup> + <Badge>{t("etcTotalEdges")}</Badge> + {totalEdges.map(({ edge, value }) => ( + <EdgeItem + key={edge} + edge={edge} + text={t("avatarCountText", { avatarCount: value })} + /> + ))} + </ListGroup> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/etc/components/TotalNoteFilesView.tsx" "b/qwilight-fe/src/app/\133language\135/etc/components/TotalNoteFilesView.tsx" new file mode 100644 index 0000000..96f3e96 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/etc/components/TotalNoteFilesView.tsx" @@ -0,0 +1,32 @@ +import NoteItem from "@/app/[language]/note/components/NoteItem"; +import { EtcAPINoteFile } from "@/type/wwwAPI"; +import { useTranslations } from "next-intl"; +import { Badge, ListGroup } from "reactstrap"; + +export default function TotalNoteFilesView({ + totalNoteFiles, +}: { + totalNoteFiles: EtcAPINoteFile[]; +}) { + const t = useTranslations(); + + return ( + <ListGroup> + <Badge>{t("etcTotalNoteFiles")}</Badge> + {totalNoteFiles.map( + ({ noteID, artist, title, genre, levelText, level, value }) => ( + <NoteItem + key={noteID} + noteID={noteID} + artist={artist} + title={title} + genre={genre} + levelText={levelText} + level={level} + fittedText={t("textHandled", { value })} + /> + ), + )} + </ListGroup> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/etc/components/TotalTitlesView.tsx" "b/qwilight-fe/src/app/\133language\135/etc/components/TotalTitlesView.tsx" new file mode 100644 index 0000000..cfe541a --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/etc/components/TotalTitlesView.tsx" @@ -0,0 +1,26 @@ +import TitleItem from "@/app/[language]/etc/components/TitleItem"; +import { EtcAPITitle } from "@/type/wwwAPI"; +import { useTranslations } from "next-intl"; +import { Badge, ListGroup } from "reactstrap"; + +export default function TotalTitlesView({ + totalTitles, +}: { + totalTitles: EtcAPITitle[]; +}) { + const t = useTranslations(); + + return ( + <ListGroup> + <Badge>{t("etcTotalTitles")}</Badge> + {totalTitles.map(({ title, titleColor, value }) => ( + <TitleItem + key={title} + title={title} + titleColor={titleColor} + text={t("avatarCountText", { avatarCount: value })} + /> + ))} + </ListGroup> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/etc/loading.tsx" "b/qwilight-fe/src/app/\133language\135/etc/loading.tsx" index 5ba11ca..d6f4948 100644 --- "a/qwilight-fe/src/app/\133language\135/etc/loading.tsx" +++ "b/qwilight-fe/src/app/\133language\135/etc/loading.tsx" @@ -1,4 +1,4 @@ -import LoadingLayer from "@/LoadingLayer"; +import LoadingLayer from "@/components/LoadingLayer"; import { useTranslations } from "next-intl"; export default function Loading() { diff --git "a/qwilight-fe/src/app/\133language\135/etc/page.tsx" "b/qwilight-fe/src/app/\133language\135/etc/page.tsx" index 99ac7fd..5d4dc4b 100644 --- "a/qwilight-fe/src/app/\133language\135/etc/page.tsx" +++ "b/qwilight-fe/src/app/\133language\135/etc/page.tsx" @@ -1,12 +1,12 @@ "use client"; -import DateView from "@/etc/DateView"; -import FavoritesView from "@/etc/FavoritesView"; -import ModeItem from "@/etc/ModeItem"; -import TotalEdgesView from "@/etc/TotalEdgesView"; -import TotalNoteFilesView from "@/etc/TotalNoteFilesView"; -import TotalTitlesView from "@/etc/TotalTitlesView"; -import useGetEtc from "@/etc/useGetEtc"; +import DateView from "@/app/[language]/etc/components/DateView"; +import FavoritesView from "@/app/[language]/etc/components/FavoritesView"; +import ModeItem from "@/app/[language]/etc/components/ModeItem"; +import TotalEdgesView from "@/app/[language]/etc/components/TotalEdgesView"; +import TotalNoteFilesView from "@/app/[language]/etc/components/TotalNoteFilesView"; +import TotalTitlesView from "@/app/[language]/etc/components/TotalTitlesView"; +import useGetEtc from "@/app/[language]/etc/query/useGetEtc"; import { is, m0s, @@ -19,7 +19,7 @@ m6s, m7s, m8s, -} from "@/Utility"; +} from "@/utilities/Utility"; import { useTranslations } from "next-intl"; import { Col, Row } from "reactstrap"; diff --git "a/qwilight-fe/src/app/\133language\135/etc/query/useGetEtc.ts" "b/qwilight-fe/src/app/\133language\135/etc/query/useGetEtc.ts" new file mode 100644 index 0000000..c3ad143 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/etc/query/useGetEtc.ts" @@ -0,0 +1,45 @@ +import { GetEtcAPI } from "@/type/wwwAPI"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useIsPath } from "taehui-ts/fe-utilities"; +import { getLanguage } from "taehui-ts/language"; + +export default function useGetEtc() { + const isPath = useIsPath(); + + const language = getLanguage(); + return useQuery({ + enabled: isPath("/etc"), + queryKey: ["etc"], + queryFn: async () => { + const { data } = await wwwAPI.get<GetEtcAPI>("/etc", { + params: { language }, + }); + return data; + }, + initialData: { + totalDateSet: [], + totalDateValues: [], + signUpDateSet: [], + signUpDateValues: [], + avatarDateSet: [], + avatarDateValues: [], + totalNoteFiles: [], + totalTitles: [], + totalEdges: [], + favorites: [], + favoritesAt: [], + inputModes: [], + autoModes: [], + noteSaltModes: [], + faintNoteModes: [], + judgmentModes: [], + hitPointsModes: [], + noteMobilityModes: [], + longNoteModes: [], + inputFavorModes: [], + noteModifyModes: [], + lowestJudgmentConditionModes: [], + }, + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/hall/components/AvatarItem.tsx" "b/qwilight-fe/src/app/\133language\135/hall/components/AvatarItem.tsx" new file mode 100644 index 0000000..466d987 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/hall/components/AvatarItem.tsx" @@ -0,0 +1,30 @@ +import { Hall } from "@/app/[language]/hall/type"; +import AvatarDrawing from "@/components/AvatarDrawing"; +import AvatarTitle from "@/components/AvatarTitle"; +import { Col, ListGroupItem, Row } from "reactstrap"; +import { useTo } from "taehui-ts/fe-utilities"; + +export default function AvatarItem({ avatarID, avatarName, text }: Hall) { + const to = useTo(); + + return ( + <ListGroupItem key={avatarID}> + <Row + className="g-0 route" + onClick={() => { + to(`/avatar/${encodeURIComponent("#")}${avatarID}`); + }} + > + <Col className="m-1" xs="auto"> + <AvatarDrawing avatarID={avatarID} /> + </Col> + <Col className="m-1" xs="auto"> + {avatarID && <AvatarTitle avatarID={avatarID} />} + <span>{avatarName}</span> + <br /> + <span>{text}</span> + </Col> + </Row> + </ListGroupItem> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/hall/loading.tsx" "b/qwilight-fe/src/app/\133language\135/hall/loading.tsx" index d51e131..8c40023 100644 --- "a/qwilight-fe/src/app/\133language\135/hall/loading.tsx" +++ "b/qwilight-fe/src/app/\133language\135/hall/loading.tsx" @@ -1,4 +1,4 @@ -import LoadingLayer from "@/LoadingLayer"; +import LoadingLayer from "@/components/LoadingLayer"; import { useTranslations } from "next-intl"; export default function Loading() { diff --git "a/qwilight-fe/src/app/\133language\135/hall/page.tsx" "b/qwilight-fe/src/app/\133language\135/hall/page.tsx" index dabe44e..8097e9e 100644 --- "a/qwilight-fe/src/app/\133language\135/hall/page.tsx" +++ "b/qwilight-fe/src/app/\133language\135/hall/page.tsx" @@ -1,22 +1,22 @@ "use client"; -import AvatarItem from "@/hall/AvatarItem"; -import { Hall } from "@/hall/Hall"; -import useGetAbility5KHall from "@/hall/useGetAbility5KHall"; -import useGetAbility7KHall from "@/hall/useGetAbility7KHall"; -import useGetAbility9KHall from "@/hall/useGetAbility9KHall"; -import useGetAtBandHall from "@/hall/useGetAtBandHall"; -import useGetAtHighestHall from "@/hall/useGetAtHighestHall"; -import useGetAtStandHall from "@/hall/useGetAtStandHall"; -import useGetAtTotalHall from "@/hall/useGetAtTotalHall"; -import useGetLevelHall from "@/hall/useGetLevelHall"; -import useGetTotalBandHall from "@/hall/useGetTotalBandHall"; -import useGetTotalHighestHall from "@/hall/useGetTotalHighestHall"; -import useGetTotalStandHall from "@/hall/useGetTotalStandHall"; -import useGetTotalTotalHall from "@/hall/useGetTotalTotalHall"; -import { AvatarLoading } from "@/Loading"; +import AvatarItem from "@/app/[language]/hall/components/AvatarItem"; +import useGetAbility5KHall from "@/app/[language]/hall/query/useGetAbility5KHall"; +import useGetAbility7KHall from "@/app/[language]/hall/query/useGetAbility7KHall"; +import useGetAbility9KHall from "@/app/[language]/hall/query/useGetAbility9KHall"; +import useGetAtBandHall from "@/app/[language]/hall/query/useGetAtBandHall"; +import useGetAtHighestHall from "@/app/[language]/hall/query/useGetAtHighestHall"; +import useGetAtStandHall from "@/app/[language]/hall/query/useGetAtStandHall"; +import useGetAtTotalHall from "@/app/[language]/hall/query/useGetAtTotalHall"; +import useGetLevelHall from "@/app/[language]/hall/query/useGetLevelHall"; +import useGetTotalBandHall from "@/app/[language]/hall/query/useGetTotalBandHall"; +import useGetTotalHighestHall from "@/app/[language]/hall/query/useGetTotalHighestHall"; +import useGetTotalStandHall from "@/app/[language]/hall/query/useGetTotalStandHall"; +import useGetTotalTotalHall from "@/app/[language]/hall/query/useGetTotalTotalHall"; +import { Hall } from "@/app/[language]/hall/type"; +import { AvatarLoading } from "@/components/Loading"; -import { useHallStore } from "@/Stores"; +import { useHallStore } from "@/store/Stores"; import { observer } from "mobx-react-lite"; import { useTranslations } from "next-intl"; import { diff --git "a/qwilight-fe/src/app/\133language\135/hall/query/useGetAbility5KHall.ts" "b/qwilight-fe/src/app/\133language\135/hall/query/useGetAbility5KHall.ts" new file mode 100644 index 0000000..07b968f --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/hall/query/useGetAbility5KHall.ts" @@ -0,0 +1,26 @@ +import { Hall } from "@/app/[language]/hall/type"; +import { useHallStore } from "@/store/Stores"; +import { GetHallAPI } from "@/type/wwwAPI"; +import { formatText } from "@/utilities/Utility"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetAbility5KHall() { + const { tabPosition, abilityTabPosition } = useHallStore(); + + const isPath = useIsPath(); + + return useQuery<Hall[]>({ + enabled: tabPosition === 2 && abilityTabPosition === 0 && isPath("/hall"), + queryKey: ["ability5KHall"], + queryFn: async () => { + const { data } = await wwwAPI.get<GetHallAPI[]>("/hall/ability/5K"); + return data.map((hall) => ({ + ...hall, + text: `${formatText(hall.value)} Point`, + })); + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/hall/query/useGetAbility7KHall.ts" "b/qwilight-fe/src/app/\133language\135/hall/query/useGetAbility7KHall.ts" new file mode 100644 index 0000000..1afb37d --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/hall/query/useGetAbility7KHall.ts" @@ -0,0 +1,26 @@ +import { Hall } from "@/app/[language]/hall/type"; +import { useHallStore } from "@/store/Stores"; +import { GetHallAPI } from "@/type/wwwAPI"; +import { formatText } from "@/utilities/Utility"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetAbility7KHall() { + const { tabPosition, abilityTabPosition } = useHallStore(); + + const isPath = useIsPath(); + + return useQuery<Hall[]>({ + enabled: tabPosition === 2 && abilityTabPosition === 1 && isPath("/hall"), + queryKey: ["ability7KHall"], + queryFn: async () => { + const { data } = await wwwAPI.get<GetHallAPI[]>("/hall/ability/7K"); + return data.map((hall) => ({ + ...hall, + text: `${formatText(hall.value)} Point`, + })); + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/hall/query/useGetAbility9KHall.ts" "b/qwilight-fe/src/app/\133language\135/hall/query/useGetAbility9KHall.ts" new file mode 100644 index 0000000..569f4d3 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/hall/query/useGetAbility9KHall.ts" @@ -0,0 +1,26 @@ +import { Hall } from "@/app/[language]/hall/type"; +import { useHallStore } from "@/store/Stores"; +import { GetHallAPI } from "@/type/wwwAPI"; +import { formatText } from "@/utilities/Utility"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetAbility9KHall() { + const { tabPosition, abilityTabPosition } = useHallStore(); + + const isPath = useIsPath(); + + return useQuery<Hall[]>({ + enabled: tabPosition === 2 && abilityTabPosition === 2 && isPath("/hall"), + queryKey: ["ability9KHall"], + queryFn: async () => { + const { data } = await wwwAPI.get<GetHallAPI[]>("/hall/ability/9K"); + return data.map((hall) => ({ + ...hall, + text: `${formatText(hall.value)} Point`, + })); + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/hall/query/useGetAtBandHall.ts" "b/qwilight-fe/src/app/\133language\135/hall/query/useGetAtBandHall.ts" new file mode 100644 index 0000000..9d8eefc --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/hall/query/useGetAtBandHall.ts" @@ -0,0 +1,29 @@ +import { Hall } from "@/app/[language]/hall/type"; +import { useHallStore } from "@/store/Stores"; +import { GetHallAPI } from "@/type/wwwAPI"; +import { formatText } from "@/utilities/Utility"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetAtBandHall() { + const { tabPosition, atTabPosition } = useHallStore(); + + const t = useTranslations(); + + const isPath = useIsPath(); + + return useQuery<Hall[]>({ + enabled: tabPosition === 1 && atTabPosition === 3 && isPath("/hall"), + queryKey: ["atBandHall"], + queryFn: async () => { + const { data } = await wwwAPI.get<GetHallAPI[]>("/hall/atBand"); + return data.map((hall) => ({ + ...hall, + text: t("textBand", { value: formatText(hall.value) }), + })); + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/hall/query/useGetAtHighestHall.ts" "b/qwilight-fe/src/app/\133language\135/hall/query/useGetAtHighestHall.ts" new file mode 100644 index 0000000..6933ed0 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/hall/query/useGetAtHighestHall.ts" @@ -0,0 +1,29 @@ +import { Hall } from "@/app/[language]/hall/type"; +import { useHallStore } from "@/store/Stores"; +import { GetHallAPI } from "@/type/wwwAPI"; +import { formatText } from "@/utilities/Utility"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetAtHighestHall() { + const { tabPosition, atTabPosition } = useHallStore(); + + const t = useTranslations(); + + const isPath = useIsPath(); + + return useQuery<Hall[]>({ + enabled: tabPosition === 1 && atTabPosition === 1 && isPath("/hall"), + queryKey: ["atHighestHall"], + queryFn: async () => { + const { data } = await wwwAPI.get<GetHallAPI[]>("/hall/atHighest"); + return data.map((hall) => ({ + ...hall, + text: t("textCount", { value: formatText(hall.value) }), + })); + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/hall/query/useGetAtStandHall.ts" "b/qwilight-fe/src/app/\133language\135/hall/query/useGetAtStandHall.ts" new file mode 100644 index 0000000..e155d84 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/hall/query/useGetAtStandHall.ts" @@ -0,0 +1,29 @@ +import { Hall } from "@/app/[language]/hall/type"; +import { useHallStore } from "@/store/Stores"; +import { GetHallAPI } from "@/type/wwwAPI"; +import { formatText } from "@/utilities/Utility"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetAtStandHall() { + const { tabPosition, atTabPosition } = useHallStore(); + + const t = useTranslations(); + + const isPath = useIsPath(); + + return useQuery<Hall[]>({ + enabled: tabPosition === 1 && atTabPosition === 2 && isPath("/hall"), + queryKey: ["atStandHall"], + queryFn: async () => { + const { data } = await wwwAPI.get<GetHallAPI[]>("/hall/atStand"); + return data.map((hall) => ({ + ...hall, + text: t("textStand", { value: formatText(hall.value) }), + })); + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/hall/query/useGetAtTotalHall.ts" "b/qwilight-fe/src/app/\133language\135/hall/query/useGetAtTotalHall.ts" new file mode 100644 index 0000000..ddfdfc6 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/hall/query/useGetAtTotalHall.ts" @@ -0,0 +1,29 @@ +import { Hall } from "@/app/[language]/hall/type"; +import { useHallStore } from "@/store/Stores"; +import { GetHallAPI } from "@/type/wwwAPI"; +import { formatText } from "@/utilities/Utility"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetAtTotalHall() { + const { tabPosition, atTabPosition } = useHallStore(); + + const t = useTranslations(); + + const isPath = useIsPath(); + + return useQuery<Hall[]>({ + enabled: tabPosition === 1 && atTabPosition === 0 && isPath("/hall"), + queryKey: ["atTotalHall"], + queryFn: async () => { + const { data } = await wwwAPI.get<GetHallAPI[]>("/hall/atTotal"); + return data.map((hall) => ({ + ...hall, + text: t("textHandled", { value: formatText(hall.value) }), + })); + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/hall/query/useGetLevelHall.ts" "b/qwilight-fe/src/app/\133language\135/hall/query/useGetLevelHall.ts" new file mode 100644 index 0000000..d9ad647 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/hall/query/useGetLevelHall.ts" @@ -0,0 +1,26 @@ +import { Hall } from "@/app/[language]/hall/type"; +import { useHallStore } from "@/store/Stores"; +import { GetHallAPI } from "@/type/wwwAPI"; +import { formatText } from "@/utilities/Utility"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetLevelHall() { + const { tabPosition } = useHallStore(); + + const isPath = useIsPath(); + + return useQuery<Hall[]>({ + enabled: tabPosition === 3 && isPath("/hall"), + queryKey: ["levelHall"], + queryFn: async () => { + const { data } = await wwwAPI.get<GetHallAPI[]>("/hall/level"); + return data.map((hall) => ({ + ...hall, + text: `LV.${formatText(hall.value)}`, + })); + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/hall/query/useGetTotalBandHall.ts" "b/qwilight-fe/src/app/\133language\135/hall/query/useGetTotalBandHall.ts" new file mode 100644 index 0000000..85799c5 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/hall/query/useGetTotalBandHall.ts" @@ -0,0 +1,29 @@ +import { Hall } from "@/app/[language]/hall/type"; +import { useHallStore } from "@/store/Stores"; +import { GetHallAPI } from "@/type/wwwAPI"; +import { formatText } from "@/utilities/Utility"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetTotalBandHall() { + const { tabPosition, totalTabPosition } = useHallStore(); + + const t = useTranslations(); + + const isPath = useIsPath(); + + return useQuery<Hall[]>({ + enabled: tabPosition === 0 && totalTabPosition === 3 && isPath("/hall"), + queryKey: ["totalBandHall"], + queryFn: async () => { + const { data } = await wwwAPI.get<GetHallAPI[]>("/hall/totalBand"); + return data.map((hall) => ({ + ...hall, + text: t("textBand", { value: formatText(hall.value) }), + })); + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/hall/query/useGetTotalHighestHall.ts" "b/qwilight-fe/src/app/\133language\135/hall/query/useGetTotalHighestHall.ts" new file mode 100644 index 0000000..759e028 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/hall/query/useGetTotalHighestHall.ts" @@ -0,0 +1,29 @@ +import { Hall } from "@/app/[language]/hall/type"; +import { useHallStore } from "@/store/Stores"; +import { GetHallAPI } from "@/type/wwwAPI"; +import { formatText } from "@/utilities/Utility"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetTotalHighestHall() { + const { tabPosition, totalTabPosition } = useHallStore(); + + const t = useTranslations(); + + const isPath = useIsPath(); + + return useQuery<Hall[]>({ + enabled: tabPosition === 0 && totalTabPosition === 1 && isPath("/hall"), + queryKey: ["totalHighestHall"], + queryFn: async () => { + const { data } = await wwwAPI.get<GetHallAPI[]>("/hall/totalHighest"); + return data.map((hall) => ({ + ...hall, + text: t("textCount", { value: formatText(hall.value) }), + })); + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/hall/query/useGetTotalStandHall.ts" "b/qwilight-fe/src/app/\133language\135/hall/query/useGetTotalStandHall.ts" new file mode 100644 index 0000000..99eaa7f --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/hall/query/useGetTotalStandHall.ts" @@ -0,0 +1,29 @@ +import { Hall } from "@/app/[language]/hall/type"; +import { useHallStore } from "@/store/Stores"; +import { GetHallAPI } from "@/type/wwwAPI"; +import { formatText } from "@/utilities/Utility"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetTotalStandHall() { + const { tabPosition, totalTabPosition } = useHallStore(); + + const t = useTranslations(); + + const isPath = useIsPath(); + + return useQuery<Hall[]>({ + enabled: tabPosition === 0 && totalTabPosition === 2 && isPath("/hall"), + queryKey: ["totalStandHall"], + queryFn: async () => { + const { data } = await wwwAPI.get<GetHallAPI[]>("/hall/totalStand"); + return data.map((hall) => ({ + ...hall, + text: t("textStand", { value: formatText(hall.value) }), + })); + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/hall/query/useGetTotalTotalHall.ts" "b/qwilight-fe/src/app/\133language\135/hall/query/useGetTotalTotalHall.ts" new file mode 100644 index 0000000..68d07c7 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/hall/query/useGetTotalTotalHall.ts" @@ -0,0 +1,29 @@ +import { Hall } from "@/app/[language]/hall/type"; +import { useHallStore } from "@/store/Stores"; +import { GetHallAPI } from "@/type/wwwAPI"; +import { formatText } from "@/utilities/Utility"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetTotalTotalHall() { + const { tabPosition, totalTabPosition } = useHallStore(); + + const t = useTranslations(); + + const isPath = useIsPath(); + + return useQuery<Hall[]>({ + enabled: tabPosition === 0 && totalTabPosition === 0 && isPath("/hall"), + queryKey: ["totalTotalHall"], + queryFn: async () => { + const { data } = await wwwAPI.get<GetHallAPI[]>("/hall/totalTotal"); + return data.map((hall) => ({ + ...hall, + text: t("textHandled", { value: formatText(hall.value) }), + })); + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/hall/store/setHallStore.ts" "b/qwilight-fe/src/app/\133language\135/hall/store/setHallStore.ts" new file mode 100644 index 0000000..22d76c6 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/hall/store/setHallStore.ts" @@ -0,0 +1,24 @@ +export default function setHallStore() { + return { + tabPosition: 0, + totalTabPosition: 0, + atTabPosition: 0, + abilityTabPosition: 0, + + setTabPosition(tabPosition: number) { + this.tabPosition = tabPosition; + }, + + setTotalTabPosition(totalTabPosition: number) { + this.totalTabPosition = totalTabPosition; + }, + + setAtTabPosition(atTabPosition: number) { + this.atTabPosition = atTabPosition; + }, + + setAbilityTabPosition(abilityTabPosition: number) { + this.abilityTabPosition = abilityTabPosition; + }, + }; +} diff --git "a/qwilight-fe/src/app/\133language\135/hall/type/index.d.ts" "b/qwilight-fe/src/app/\133language\135/hall/type/index.d.ts" new file mode 100644 index 0000000..e4c8b20 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/hall/type/index.d.ts" @@ -0,0 +1,5 @@ +export type Hall = { + avatarID: string; + avatarName: string; + text: string; +}; diff --git "a/qwilight-fe/src/app/\133language\135/layout.tsx" "b/qwilight-fe/src/app/\133language\135/layout.tsx" index 1ffd607..b2e22ef 100644 --- "a/qwilight-fe/src/app/\133language\135/layout.tsx" +++ "b/qwilight-fe/src/app/\133language\135/layout.tsx" @@ -1,5 +1,5 @@ -import QwilightView from "@/QwilightView"; -import { Stores } from "@/Stores"; +import QwilightView from "@/components/QwilightView"; +import { Stores } from "@/store/Stores"; import { NextIntlClientProvider } from "next-intl"; import { getMessages } from "next-intl/server"; import { ReactNode } from "react"; @@ -10,7 +10,7 @@ import "@/app/globals.scss"; -export default async function RootLayout({ +export default async function Layout({ children, params: { language }, }: { diff --git "a/qwilight-fe/src/app/\133language\135/note/\133\133...want\135\135/page.tsx" "b/qwilight-fe/src/app/\133language\135/note/\133\133...want\135\135/page.tsx" index 61579c2..81cd007 100644 --- "a/qwilight-fe/src/app/\133language\135/note/\133\133...want\135\135/page.tsx" +++ "b/qwilight-fe/src/app/\133language\135/note/\133\133...want\135\135/page.tsx" @@ -1,19 +1,19 @@ "use client"; -import FitInput from "@/note/FitInput"; -import NoteItems from "@/note/NoteItems"; -import PositionInput from "@/note/PositionInput"; -import SrcInput from "@/note/SrcInput"; -import useGetNote from "@/note/useGetNote"; -import WantInput from "@/note/WantInput"; +import FitInput from "@/app/[language]/note/components/FitInput"; +import NoteItems from "@/app/[language]/note/components/NoteItems"; +import PositionInput from "@/app/[language]/note/components/PositionInput"; +import SrcInput from "@/app/[language]/note/components/SrcInput"; +import WantInput from "@/app/[language]/note/components/WantInput"; +import useGetNote from "@/app/[language]/note/query/useGetNote"; -import { useNoteStore } from "@/Stores"; -import { formatText } from "@/Utility"; +import { useNoteStore } from "@/store/Stores"; +import { formatText } from "@/utilities/Utility"; import { observer } from "mobx-react-lite"; import { useTranslations } from "next-intl"; import { useEffect } from "react"; import { Button, Col, Row } from "reactstrap"; -import { useIntParam, useWant } from "taehui-ts/fe-utility"; +import { useIntParam, useWant } from "taehui-ts/fe-utilities"; export default observer(() => { const { diff --git "a/qwilight-fe/src/app/\133language\135/note/components/CommentItem.tsx" "b/qwilight-fe/src/app/\133language\135/note/components/CommentItem.tsx" new file mode 100644 index 0000000..52f1d1d --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/note/components/CommentItem.tsx" @@ -0,0 +1,103 @@ +import w0 from "@/assets/w0.png"; +import w1 from "@/assets/w1.png"; +import w2 from "@/assets/w2.png"; +import w4 from "@/assets/w4.png"; +import w5 from "@/assets/w5.png"; +import w6 from "@/assets/w6.png"; +import w7 from "@/assets/w7.png"; +import AvatarDrawing from "@/components/AvatarDrawing"; +import AvatarTitle from "@/components/AvatarTitle"; + +import { GetCommentAPI } from "@/type/wwwAPI"; +import { + formatText, + getHitPointsClass, + getQuitStatusValue, + toDate, +} from "@/utilities/Utility"; +import { useTranslations } from "next-intl"; +import Image from "next/image"; +import { useMemo } from "react"; +import { Col, Row } from "reactstrap"; +import { useTo } from "taehui-ts/fe-utilities"; + +const ws = [w0, w1, w2, "", w4, w5, w6, w7]; + +export default function CommentItem({ + date, + avatarID, + avatarName, + stand, + band, + point, + isP, + commentary, + isTargetAvatar, + judgmentMode, + hitPointsMode, + isPaused, + handled, +}: GetCommentAPI["comments"][number]) { + const { quit, quitCss } = useMemo( + () => getQuitStatusValue(point, stand), + [point, stand], + ); + const to = useTo(); + const t = useTranslations(); + + return ( + <Row + onClick={() => { + to(`/avatar/${encodeURIComponent("#")}${avatarID}`); + }} + className={`g-0 route ${isTargetAvatar ? "target" : ""}`} + > + <Col className="m-1" xs="auto"> + <AvatarDrawing avatarID={avatarID} /> + </Col> + <Col className="m-1" xs="auto"> + <Image src={ws[handled]} width={10} height={60} alt="" /> + </Col> + <Col className="m-1" xs="auto"> + <span className={quitCss}>{quit}</span> + {isP && ( + <> + <br /> + <span>FULL</span> + </> + )} + </Col> + <Col className="m-1" xs="auto"> + <AvatarTitle avatarID={avatarID} /> + <span className="avatar">{avatarName}</span>{" "} + <span className="date">{toDate(date)}</span> + <br /> + <span className={getHitPointsClass(hitPointsMode)}> + {t("textStand", { value: formatText(stand) })} + </span>{" "} + <span + className={(() => { + switch (judgmentMode) { + case 0: + return "level2"; + case 2: + return "level4"; + case 3: + return "level1"; + case 5: + return "level5"; + default: + return "point"; + } + })()} + > + {(100 * point).toFixed(2)}% + </span>{" "} + <span className="band">{t("textBand", { value: band })}</span> + {isPaused && " ⏸️"} + <br /> + {commentary && <span>💬 {commentary}</span>} + </Col> + </Row> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/note/components/CommentItems.tsx" "b/qwilight-fe/src/app/\133language\135/note/components/CommentItems.tsx" new file mode 100644 index 0000000..b1b99f0 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/note/components/CommentItems.tsx" @@ -0,0 +1,64 @@ +import CommentItem from "@/app/[language]/note/components/CommentItem"; +import { GetCommentAPI } from "@/type/wwwAPI"; +import { formatText } from "@/utilities/Utility"; + +export default function CommentItems({ + comments, + commentPlace, + totalCount, + wantAvatarID, + wantAvatarName, +}: { + comments: GetCommentAPI["comments"]; + commentPlace: number; + totalCount: number; + wantAvatarID?: string; + wantAvatarName?: string; +}) { + return ( + <> + {commentPlace !== -1 && ( + <> + <span className="avatarPlace">#{formatText(commentPlace + 1)}</span> + <span>/{formatText(totalCount)}</span> + </> + )} + {comments.map( + ({ + date, + avatarID, + avatarName, + stand, + band, + point, + commentary, + isP, + judgmentMode, + hitPointsMode, + isPaused, + handled, + }) => ( + <CommentItem + key={avatarID} + date={date} + avatarID={avatarID} + avatarName={avatarName} + stand={stand} + band={band} + point={point} + isP={isP} + commentary={commentary} + isTargetAvatar={ + !!(wantAvatarID && wantAvatarID === avatarID) || + !!(wantAvatarName && wantAvatarName === avatarName) + } + judgmentMode={judgmentMode} + hitPointsMode={hitPointsMode} + isPaused={isPaused} + handled={handled} + /> + ), + )} + </> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/note/components/FitInput.tsx" "b/qwilight-fe/src/app/\133language\135/note/components/FitInput.tsx" new file mode 100644 index 0000000..2192f2c --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/note/components/FitInput.tsx" @@ -0,0 +1,40 @@ +import { useTranslations } from "next-intl"; +import { useState } from "react"; +import { + Dropdown, + DropdownItem, + DropdownMenu, + DropdownToggle, +} from "reactstrap"; +import { useIntParam } from "taehui-ts/fe-utilities"; + +export default function FitInput() { + const [isFitOpened, setFitOpened] = useState(false); + const { param: fit, setParam: setFit } = useIntParam("fit", 0); + + const t = useTranslations(); + + const onInput = (fit: number) => () => { + setFit(fit); + }; + + return ( + <Dropdown + isOpen={isFitOpened} + toggle={() => { + setFitOpened((prevState) => !prevState); + }} + > + <DropdownToggle caret>{t(`toFit${fit}`)}</DropdownToggle> + <DropdownMenu> + <DropdownItem onClick={onInput(0)}>{t("toFit0")}</DropdownItem> + <DropdownItem onClick={onInput(1)}>{t("toFit1")}</DropdownItem> + <DropdownItem onClick={onInput(2)}>{t("toFit2")}</DropdownItem> + <DropdownItem onClick={onInput(3)}>{t("toFit3")}</DropdownItem> + <DropdownItem onClick={onInput(4)}>{t("toFit4")}</DropdownItem> + <DropdownItem onClick={onInput(5)}>{t("toFit5")}</DropdownItem> + <DropdownItem onClick={onInput(6)}>{t("toFit6")}</DropdownItem> + </DropdownMenu> + </Dropdown> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/note/components/NoteItem.tsx" "b/qwilight-fe/src/app/\133language\135/note/components/NoteItem.tsx" new file mode 100644 index 0000000..082d285 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/note/components/NoteItem.tsx" @@ -0,0 +1,123 @@ +import CommentItems from "@/app/[language]/note/components/CommentItems"; +import useGetComment from "@/app/[language]/note/query/useGetComment"; +import usePostToil from "@/app/[language]/note/query/usePostToil"; +import w0 from "@/assets/w0.png"; +import w1 from "@/assets/w1.png"; +import w2 from "@/assets/w2.png"; +import w4 from "@/assets/w4.png"; +import w5 from "@/assets/w5.png"; +import w6 from "@/assets/w6.png"; +import w7 from "@/assets/w7.png"; +import { GetNoteAPI } from "@/type/wwwAPI"; +import { formatText, getGenreText } from "@/utilities/Utility"; +import { useTranslations } from "next-intl"; +import Image from "next/image"; +import { useState } from "react"; +import { Item, Menu, useContextMenu } from "react-contexify"; +import { Col, Collapse, ListGroupItem, Row, Spinner } from "reactstrap"; +import Swal from "sweetalert2"; + +const ws = [w0, w1, w2, "", w4, w5, w6, w7]; + +export default function NoteItem({ + noteID, + artist, + title, + genre, + levelText, + level, + highestCount, + totalCount, + fittedText, + wantAvatarID, + wantAvatarName, + handled, +}: GetNoteAPI["notes"][number] & { handled?: number }) { + const t = useTranslations(); + + const [isCommentOpened, setCommentOpened] = useState(false); + + const { show: viewToilInput } = useContextMenu({ + id: `toil-${noteID}`, + }); + + const { + data: { comments, commentPlace, totalComments }, + isFetched: isCommentLoaded, + } = useGetComment(noteID, isCommentOpened); + + const { mutateAsync: postToil } = usePostToil(); + + return ( + <ListGroupItem> + <Row + className="g-0 route" + onClick={() => { + setCommentOpened((prevState) => !prevState); + }} + onContextMenu={(event) => { + event.preventDefault(); + viewToilInput({ event, props: { noteID } }); + }} + > + {typeof handled === "number" && ( + <Col className="m-1" xs="auto"> + <Image src={ws[handled]} width={10} height={60} alt="" /> + </Col> + )} + <Col className="m-1" xs="auto"> + <span className={`level${level}`}>{levelText}</span>{" "} + <span className="title">{title}</span>{" "} + {isCommentOpened && !isCommentLoaded && ( + <Spinner size="sm" color="primary" /> + )} + <br /> + {fittedText && <span className="fittedText">{fittedText}</span>}{" "} + <span className="artist">{artist}</span>{" "} + <span className="genre">{getGenreText(genre)}</span> + <br /> + {typeof highestCount === "number" && + typeof totalCount === "number" && ( + <> + <span className="fittedText"> + {t("highestCountText", { + highestCount: formatText(highestCount), + })} + </span> + <br /> + <span className="fittedText"> + {t("totalCountText", { totalCount: formatText(totalCount) })} + </span> + </> + )} + </Col> + </Row> + {noteID && ( + <Menu id={`toil-${noteID}`}> + <Item + onClick={async ({ props: { noteID } }) => { + const { isConfirmed, value } = await Swal.fire({ + title: t("toilNoteFileText"), + input: "text", + }); + if (isConfirmed) { + await postToil({ noteID, commentary: value }); + } + }} + > + <span>{t("toilNoteFile")}</span> + </Item> + </Menu> + )} + <Collapse isOpen={isCommentOpened}> + <CommentItems + comments={comments} + commentPlace={commentPlace} + totalCount={totalComments} + wantAvatarID={wantAvatarID} + wantAvatarName={wantAvatarName} + /> + </Collapse> + </ListGroupItem> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/note/components/NoteItems.tsx" "b/qwilight-fe/src/app/\133language\135/note/components/NoteItems.tsx" new file mode 100644 index 0000000..46fd714 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/note/components/NoteItems.tsx" @@ -0,0 +1,75 @@ +import NoteItem from "@/app/[language]/note/components/NoteItem"; +import useGetNote from "@/app/[language]/note/query/useGetNote"; +import { NoteLoading } from "@/components/Loading"; + +import { useNoteStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; +import { useLayoutEffect, useState } from "react"; +import { Col, ListGroup, Row } from "reactstrap"; +import { useWindowArea } from "taehui-ts/fe-utilities"; + +export default observer(() => { + const { wantAvatar, viewUnit } = useNoteStore(); + + const { + data: { notes }, + isFetched: isNoteLoaded, + } = useGetNote(); + + const { windowLength } = useWindowArea(); + const [table, setTable] = useState(1); + + useLayoutEffect(() => { + setTable(windowLength < 992 ? 1 : 2); + }, [windowLength]); + + return ( + <Row className="g-0"> + {[...Array(table).keys()].map((i) => { + if (isNoteLoaded) { + return ( + <Col className="m-1" key={i}> + <ListGroup> + {notes + .slice((viewUnit / table) * i, (viewUnit / table) * (i + 1)) + .map( + ({ + noteID, + artist, + title, + genre, + levelText, + level, + highestCount, + totalCount, + }) => ( + <NoteItem + key={noteID} + noteID={noteID} + artist={artist} + title={title} + genre={genre} + levelText={levelText} + level={level} + highestCount={highestCount} + totalCount={totalCount} + wantAvatarName={wantAvatar} + /> + ), + )} + </ListGroup> + </Col> + ); + } + + return ( + <Col className="m-1" key={i}> + <ListGroup> + <NoteLoading loadingCount={viewUnit / table} /> + </ListGroup> + </Col> + ); + })} + </Row> + ); +}); diff --git "a/qwilight-fe/src/app/\133language\135/note/components/PositionInput.tsx" "b/qwilight-fe/src/app/\133language\135/note/components/PositionInput.tsx" new file mode 100644 index 0000000..66ba96f --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/note/components/PositionInput.tsx" @@ -0,0 +1,78 @@ +import { useNoteStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; +import { useMemo } from "react"; +import { Pagination, PaginationItem, PaginationLink } from "reactstrap"; +import { useIntParam } from "taehui-ts/fe-utilities"; + +export default observer(() => { + const { pageUnit, lastPage, lastWant, lastSrc } = useNoteStore(); + + const { param: page, setParam: setPage } = useIntParam("page", 1); + + const targetPages = useMemo(() => { + const targetPages = []; + for ( + let i = 1 + Math.floor((page - 1) / pageUnit) * pageUnit; + i <= + Math.min( + lastPage, + Math.floor((page - 1) / pageUnit) * pageUnit + pageUnit, + ); + ++i + ) { + targetPages.push(i); + } + return targetPages; + }, [lastPage, page, pageUnit]); + + const isLowestPage = useMemo(() => page === 1, [page]); + const isHighestPage = useMemo(() => page === lastPage, [lastPage, page]); + + return ( + <Pagination> + <PaginationItem disabled={isLowestPage}> + <PaginationLink + first + onClick={() => { + setPage(1); + }} + /> + </PaginationItem> + <PaginationItem disabled={isLowestPage}> + <PaginationLink + previous + onClick={() => { + setPage(page - 1); + }} + /> + </PaginationItem> + {targetPages.map((targetPage) => ( + <PaginationItem key={targetPage} active={targetPage === page}> + <PaginationLink + onClick={() => { + setPage(targetPage); + }} + > + {targetPage} + </PaginationLink> + </PaginationItem> + ))} + <PaginationItem disabled={isHighestPage}> + <PaginationLink + next + onClick={() => { + setPage(page + 1); + }} + /> + </PaginationItem> + <PaginationItem disabled={isHighestPage}> + <PaginationLink + last + onClick={() => { + setPage(lastPage); + }} + /> + </PaginationItem> + </Pagination> + ); +}); diff --git "a/qwilight-fe/src/app/\133language\135/note/components/SrcInput.tsx" "b/qwilight-fe/src/app/\133language\135/note/components/SrcInput.tsx" new file mode 100644 index 0000000..954def3 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/note/components/SrcInput.tsx" @@ -0,0 +1,43 @@ +import { useNoteStore } from "@/store/Stores"; +import { useTranslations } from "next-intl"; +import { useEffect, useState } from "react"; +import { + Dropdown, + DropdownItem, + DropdownMenu, + DropdownToggle, +} from "reactstrap"; +import { useIntParam } from "taehui-ts/fe-utilities"; + +export default function SrcInput() { + const { setLastSrc, setWantAvatar } = useNoteStore(); + const [isSrcOpened, setSrcOpened] = useState(false); + const { param: src, setParam: setSrc } = useIntParam("src", 0); + + const t = useTranslations(); + + const onInput = (src: number) => () => { + setSrc(src); + }; + + useEffect(() => { + setLastSrc(src); + }, [setLastSrc, src]); + + return ( + <Dropdown + isOpen={isSrcOpened} + toggle={() => { + setSrcOpened((prevState) => !prevState); + }} + > + <DropdownToggle caret>{t(`toSrc${src}`)}</DropdownToggle> + <DropdownMenu> + <DropdownItem onClick={onInput(0)}>{t("toSrc0")}</DropdownItem> + <DropdownItem onClick={onInput(1)}>{t("toSrc1")}</DropdownItem> + <DropdownItem onClick={onInput(2)}>{t("toSrc2")}</DropdownItem> + <DropdownItem onClick={onInput(3)}>{t("toSrc3")}</DropdownItem> + </DropdownMenu> + </Dropdown> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/note/components/WantInput.tsx" "b/qwilight-fe/src/app/\133language\135/note/components/WantInput.tsx" new file mode 100644 index 0000000..d26212b --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/note/components/WantInput.tsx" @@ -0,0 +1,37 @@ +import { useNoteStore } from "@/store/Stores"; +import { useEffect } from "react"; +import { Input } from "reactstrap"; +import { useWant } from "taehui-ts/fe-utilities"; + +export default function SrcInput() { + const { wantInput, setWantInput, setLastWant } = useNoteStore(); + + const { want, setWant } = useWant("/note"); + + const onWant = () => { + setWant(wantInput); + }; + + useEffect(() => { + setWantInput(want); + }, [setWantInput, want]); + + useEffect(() => { + setLastWant(want); + }, [setLastWant, want]); + + return ( + <Input + type="search" + value={wantInput} + onChange={({ target: { value } }) => { + setWantInput(value); + }} + onKeyDown={({ key }) => { + if (key === "Enter") { + onWant(); + } + }} + /> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/note/loading.tsx" "b/qwilight-fe/src/app/\133language\135/note/loading.tsx" index 075a6db..0743e4d 100644 --- "a/qwilight-fe/src/app/\133language\135/note/loading.tsx" +++ "b/qwilight-fe/src/app/\133language\135/note/loading.tsx" @@ -1,4 +1,4 @@ -import LoadingLayer from "@/LoadingLayer"; +import LoadingLayer from "@/components/LoadingLayer"; import { useTranslations } from "next-intl"; export default function Loading() { diff --git "a/qwilight-fe/src/app/\133language\135/note/query/useGetComment.ts" "b/qwilight-fe/src/app/\133language\135/note/query/useGetComment.ts" new file mode 100644 index 0000000..f849822 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/note/query/useGetComment.ts" @@ -0,0 +1,34 @@ +import { useSiteStore } from "@/store/Stores"; +import { GetCommentAPI } from "@/type/wwwAPI"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { getLanguage } from "taehui-ts/language"; + +export default function useGetComment( + noteID: string, + isCommentOpened: boolean, +) { + const { siteAvatarID } = useSiteStore(); + + const language = getLanguage(); + return useQuery({ + enabled: isCommentOpened, + queryKey: ["comment", noteID, siteAvatarID, language], + queryFn: async () => { + const { data } = await wwwAPI.get<GetCommentAPI>("/comment", { + params: { + noteID, + avatarID: siteAvatarID, + language, + }, + }); + + return data; + }, + initialData: { + comments: [], + commentPlace: -1, + totalComments: 0, + }, + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/note/query/useGetNote.ts" "b/qwilight-fe/src/app/\133language\135/note/query/useGetNote.ts" new file mode 100644 index 0000000..bdc43da --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/note/query/useGetNote.ts" @@ -0,0 +1,42 @@ +import { useNoteStore } from "@/store/Stores"; +import { GetNoteAPI } from "@/type/wwwAPI"; + +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useIntParam, useIsPath, useWant } from "taehui-ts/fe-utilities"; + +export default function useGetNote() { + const { viewUnit } = useNoteStore(); + + const { param: page } = useIntParam("page", 1); + const { param: fit } = useIntParam("fit", 0); + const { param: src } = useIntParam("src", 0); + + const { want } = useWant("/note"); + + const isPath = useIsPath(); + + return useQuery({ + enabled: isPath("/note"), + queryKey: ["note", fit, src, want, page, viewUnit], + queryFn: async () => { + const { data } = await wwwAPI.get<GetNoteAPI>("/note", { + params: { + fit, + src, + want, + page, + viewUnit, + }, + }); + + return data; + }, + initialData: { + totalCount: 0, + highestCount: 0, + noteCount: 0, + notes: [], + }, + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/note/query/usePostToil.ts" "b/qwilight-fe/src/app/\133language\135/note/query/usePostToil.ts" new file mode 100644 index 0000000..d63ac67 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/note/query/usePostToil.ts" @@ -0,0 +1,19 @@ +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useMutation } from "@tanstack/react-query"; + +export default function usePostToil() { + return useMutation({ + mutationFn: async ({ + noteID, + commentary, + }: { + noteID: string; + commentary: string; + }) => { + await wwwAPI.post("/toil", { + noteID, + commentary, + }); + }, + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/note/store/setNoteStore.ts" "b/qwilight-fe/src/app/\133language\135/note/store/setNoteStore.ts" new file mode 100644 index 0000000..1526734 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/note/store/setNoteStore.ts" @@ -0,0 +1,31 @@ +export default function setNoteStore() { + return { + lastWant: "", + lastSrc: 0, + wantAvatar: "", + wantInput: "", + lastPage: 1, + pageUnit: 10, + viewUnit: 20, + + setLastWant(lastWant: string) { + this.lastWant = lastWant; + }, + + setLastSrc(lastSrc: number) { + this.lastSrc = lastSrc; + }, + + setWantInput(wantInput: string) { + this.wantInput = wantInput; + }, + + setWantAvatar(wantAvatar: string) { + this.wantAvatar = wantAvatar; + }, + + setLastPage(lastPage: number) { + this.lastPage = lastPage; + }, + }; +} diff --git "a/qwilight-fe/src/app/\133language\135/site/components/AvatarItem.module.scss" "b/qwilight-fe/src/app/\133language\135/site/components/AvatarItem.module.scss" new file mode 100644 index 0000000..3a2522b --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/components/AvatarItem.module.scss" @@ -0,0 +1,5 @@ +span { + &.audioInput { + color: green; + } +} diff --git "a/qwilight-fe/src/app/\133language\135/site/components/AvatarItem.tsx" "b/qwilight-fe/src/app/\133language\135/site/components/AvatarItem.tsx" new file mode 100644 index 0000000..2b8e289 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/components/AvatarItem.tsx" @@ -0,0 +1,76 @@ +import scss from "@/app/[language]/site/components/AvatarItem.module.scss"; +import { OnAvatarInput } from "@/app/[language]/site/type"; +import ac1 from "@/assets/ac1.png"; +import ac2 from "@/assets/ac2.png"; +import ac3 from "@/assets/ac3.png"; +import ac4 from "@/assets/ac4.png"; +import valve from "@/assets/valve.png"; +import AvatarDrawing from "@/components/AvatarDrawing"; +import AvatarTitle from "@/components/AvatarTitle"; +import Image from "next/image"; +import { Col, Row } from "reactstrap"; + +const acs = ["", ac1, ac2, ac3, ac4]; + +export default function AvatarItem({ + avatarID, + avatarName, + avatarConfigure, + isSiteHand, + isMe, + isValve, + isAudioInput, + onAvatarInput, +}: { + avatarID: string; + avatarName: string; + avatarConfigure: number; + isSiteHand: boolean; + isMe: boolean; + isValve: boolean; + isAudioInput: boolean; + onAvatarInput: OnAvatarInput; +}) { + return ( + <Row + className={`g-0 ${isMe ? "target" : ""}`} + onContextMenu={(e) => { + e.preventDefault(); + onAvatarInput(e, avatarID); + }} + > + <Col className="m-1" xs="auto"> + <AvatarDrawing avatarID={avatarID} /> + </Col> + <Col className="m-1" xs="auto"> + {avatarID && <AvatarTitle avatarID={avatarID} />} + <span className={isAudioInput ? scss.audioInput : undefined}> + {avatarName} + </span> + <br /> + {isValve && ( + <> + {" "} + <Image alt="" src={valve} height={24} /> + </> + )} + {acs[avatarConfigure] && ( + <> + {" "} + <Image + alt="" + src={acs[avatarConfigure]} + className={scss.avatarConfigure} + /> + </> + )} + {isSiteHand && ( + <> + {" "} + <Image alt="" src={acs[1]} className={scss.avatarConfigure} /> + </> + )} + </Col> + </Row> + ); +} diff --git "a/qwilight-fe/src/app/\133language\135/site/components/AvatarItems.tsx" "b/qwilight-fe/src/app/\133language\135/site/components/AvatarItems.tsx" new file mode 100644 index 0000000..8cf761a --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/components/AvatarItems.tsx" @@ -0,0 +1,39 @@ +import AvatarItem from "@/app/[language]/site/components/AvatarItem"; +import { OnAvatarInput } from "@/app/[language]/site/type"; + +import { useSiteStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; + +export default observer( + ({ onAvatarInput }: { onAvatarInput: OnAvatarInput }) => { + const { avatars } = useSiteStore(); + + return ( + <> + {avatars.map( + ({ + avatarID, + avatarName, + avatarConfigure, + isSiteHand, + isMe, + isValve, + isAudioInput, + }) => ( + <AvatarItem + key={avatarID} + avatarID={avatarID} + avatarName={avatarName} + avatarConfigure={avatarConfigure} + isSiteHand={isSiteHand} + isMe={isMe} + isValve={isValve} + isAudioInput={isAudioInput} + onAvatarInput={onAvatarInput} + /> + ), + )} + </> + ); + }, +); diff --git "a/qwilight-fe/src/app/\133language\135/site/components/ConfigureWindow.tsx" "b/qwilight-fe/src/app/\133language\135/site/components/ConfigureWindow.tsx" new file mode 100644 index 0000000..b04dbeb --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/components/ConfigureWindow.tsx" @@ -0,0 +1,88 @@ +import { useSiteStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; +import { Button, Col, Modal, Row } from "reactstrap"; + +export default observer(() => { + const { + isConfigureOpened, + setConfigureOpened, + saveTraffic, + setSaveTraffic, + autoEnterNotify, + setAutoEnterNotify, + autoEnterDefault, + setAutoEnterDefault, + autoEnterPlatform, + setAutoEnterPlatform, + } = useSiteStore(); + const t = useTranslations(); + + return ( + <Modal + isOpen={isConfigureOpened} + toggle={() => { + window.localStorage.setItem("saveTraffic", saveTraffic.toString()); + window.localStorage.setItem( + "autoEnterNotify", + autoEnterNotify.toString(), + ); + window.localStorage.setItem( + "autoEnterDefault", + autoEnterDefault.toString(), + ); + window.localStorage.setItem( + "autoEnterPlatform", + autoEnterPlatform.toString(), + ); + setConfigureOpened(false); + }} + centered + > + <Row className="justify-content-center g-0"> + <Col className="m-1" xs="auto"> + <Button + color={saveTraffic ? "success" : "danger"} + onClick={() => { + setSaveTraffic(!saveTraffic); + }} + > + {t("siteSaveTraffic")} + </Button> + </Col> + </Row> + <Row className="justify-content-center g-0"> + <Col className="m-1" xs="auto"> + <Button + color={autoEnterNotify ? "success" : "danger"} + onClick={() => { + setAutoEnterNotify(!autoEnterNotify); + }} + > + {t("siteAutoEnterNotify")} + </Button> + </Col> + <Col className="m-1" xs="auto"> + <Button + color={autoEnterDefault ? "success" : "danger"} + onClick={() => { + setAutoEnterDefault(!autoEnterDefault); + }} + > + {t("siteAutoEnterDefault")} + </Button> + </Col> + <Col className="m-1" xs="auto"> + <Button + color={autoEnterPlatform ? "success" : "danger"} + onClick={() => { + setAutoEnterPlatform(!autoEnterPlatform); + }} + > + {t("siteAutoEnterPlatform")} + </Button> + </Col> + </Row> + </Modal> + ); +}); diff --git "a/qwilight-fe/src/app/\133language\135/site/components/LogInWindow.tsx" "b/qwilight-fe/src/app/\133language\135/site/components/LogInWindow.tsx" new file mode 100644 index 0000000..ee0f632 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/components/LogInWindow.tsx" @@ -0,0 +1,86 @@ +import SiteComponent from "@/app/[language]/site/components/SiteComponent"; +import { useSiteStore } from "@/store/Stores"; +import CryptoJS from "crypto-js"; +import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; +import { useState } from "react"; +import { Button, Col, Input, Modal, Row } from "reactstrap"; + +const EventPB = require("@/Event_pb"); + +export default observer(() => { + const { isLogInOpened, setLogInOpened } = useSiteStore(); + const t = useTranslations(); + + const [avatarID, setAvatarID] = useState(""); + const [avatarCipher, setAvatarCipher] = useState(""); + const [autoLogIn, setAutoLogIn] = useState(false); + + const onLogIn = () => { + if (autoLogIn) { + window.localStorage.setItem("avatarID", avatarID); + window.localStorage.setItem( + "avatarCipher", + CryptoJS.AES.encrypt( + avatarCipher, + "591A6F91-2A27-4A88-88FA-0FEB7CB5FD94", + ).toString(), + ); + } + window.localStorage.setItem("autoLogIn", autoLogIn.toString()); + SiteComponent.send({ + eventID: EventPB.Event.EventID.LOG_IN, + text: JSON.stringify({ avatarID, avatarCipher }), + }); + }; + + return ( + <Modal isOpen={isLogInOpened} toggle={() => setLogInOpened(false)} centered> + <Row className="g-0"> + <Col className="m-1"> + <Input + value={avatarID} + onChange={({ target: { value } }) => { + setAvatarID(value); + }} + placeholder={t("logInID")} + /> + </Col> + </Row> + <Row className="g-0"> + <Col className="m-1"> + <Input + value={avatarCipher} + onChange={({ target: { value } }) => { + setAvatarCipher(value); + }} + type="password" + placeholder={t("logInCipher")} + onKeyDown={({ key }) => { + if (key === "Enter") { + onLogIn(); + } + }} + /> + </Col> + </Row> + <Row className="justify-content-center g-0"> + <Col className="m-1" xs="auto"> + <Button color="success" onClick={onLogIn}> + {t("logIn")} + </Button> + </Col> + <Col className="m-1" xs="auto"> + <Button + color={autoLogIn ? "success" : "danger"} + onClick={() => { + setAutoLogIn((prevState) => !prevState); + }} + > + {t("autoLogIn")} + </Button> + </Col> + </Row> + </Modal> + ); +}); diff --git "a/qwilight-fe/src/app/\133language\135/site/components/NewSiteWindow.tsx" "b/qwilight-fe/src/app/\133language\135/site/components/NewSiteWindow.tsx" new file mode 100644 index 0000000..d286498 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/components/NewSiteWindow.tsx" @@ -0,0 +1,76 @@ +import SiteComponent from "@/app/[language]/site/components/SiteComponent"; + +import { useSiteStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; +import { useState } from "react"; +import { Button, Col, Input, Modal, Row } from "reactstrap"; + +const EventPB = require("@/Event_pb"); + +export default observer(() => { + const { isNewSiteWindowOpened, setSiteWindowOpened, setNewSiteWindowOpened } = + useSiteStore(); + const [siteName, setSiteName] = useState(""); + const [siteCipher, setSiteCipher] = useState(""); + const t = useTranslations(); + + const onNewSite = () => { + SiteComponent.send({ + eventID: EventPB.Event.EventID.NEW_SITE, + text: JSON.stringify({ + siteName: siteName, + siteCipher: siteCipher, + isNetSite: false, + }), + }); + setNewSiteWindowOpened(false); + setSiteWindowOpened(false); + }; + + return ( + <Modal + isOpen={isNewSiteWindowOpened} + toggle={() => { + setNewSiteWindowOpened(false); + }} + centered + > + <Row className="g-0"> + <Col className="m-1"> + <Input + autoComplete="off" + value={siteName} + onChange={({ target: { value } }) => { + setSiteName(value); + }} + placeholder={t("siteName")} + /> + </Col> + </Row> + <Row className="g-0"> + <Col className="m-1"> + <Input + autoComplete="off" + value={siteCipher} + onChange={({ target: { value } }) => { + setSiteCipher(value); + }} + type="password" + placeholder={t("siteCipher")} + onKeyDown={({ key }) => { + if (key === "Enter") { + onNewSite(); + } + }} + /> + </Col> + </Row> + <Row className="justify-content-center g-0"> + <Col className="m-1" xs="auto"> + <Button onClick={onNewSite}>{t("inputNewSite")}</Button> + </Col> + </Row> + </Modal> + ); +}); diff --git "a/qwilight-fe/src/app/\133language\135/site/components/SiteCipherWindow.tsx" "b/qwilight-fe/src/app/\133language\135/site/components/SiteCipherWindow.tsx" new file mode 100644 index 0000000..974ca7d --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/components/SiteCipherWindow.tsx" @@ -0,0 +1,69 @@ +import SiteComponent from "@/app/[language]/site/components/SiteComponent"; + +import { useSiteStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; +import { useState } from "react"; +import { Button, Col, Input, Modal, Row } from "reactstrap"; + +const EventPB = require("@/Event_pb"); + +export default observer( + ({ siteID, siteName }: { siteID: string; siteName: string }) => { + const { + setSiteWindowOpened, + isSiteCipherWindowOpened, + setSiteCipherWindowOpened, + } = useSiteStore(); + const [siteCipher, setSiteCipher] = useState(""); + const t = useTranslations(); + + const onEnterSite = () => { + SiteComponent.send({ + eventID: EventPB.Event.EventID.ENTER_SITE, + text: JSON.stringify({ siteID, siteCipher }), + }); + setSiteCipherWindowOpened(false); + setSiteWindowOpened(false); + }; + + return ( + <Modal + isOpen={isSiteCipherWindowOpened} + toggle={() => { + setSiteCipherWindowOpened(false); + }} + centered + > + <Row className="g-0"> + <Col className="m-1"> + <Input value={siteName} disabled /> + </Col> + </Row> + <Row className="g-0"> + <Col className="m-1"> + <Input + autoComplete="new-password" + value={siteCipher} + onChange={({ target: { value } }) => { + setSiteCipher(value); + }} + type="password" + placeholder={t("siteCipher")} + onKeyDown={({ key }) => { + if (key === "Enter") { + onEnterSite(); + } + }} + /> + </Col> + </Row> + <Row className="justify-content-center g-0"> + <Col className="m-1" xs="auto"> + <Button onClick={onEnterSite}>{t("enterSite")}</Button> + </Col> + </Row> + </Modal> + ); + }, +); diff --git "a/qwilight-fe/src/app/\133language\135/site/components/SiteComponent.ts" "b/qwilight-fe/src/app/\133language\135/site/components/SiteComponent.ts" new file mode 100644 index 0000000..d8fd26c --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/components/SiteComponent.ts" @@ -0,0 +1,97 @@ +import { + CloseEventHandler, + Event, + EventHandler, +} from "@/app/[language]/site/type"; +import { getMillis } from "taehui-ts/date"; +import { getLanguage } from "taehui-ts/language"; + +const EventPB = require("@/Event_pb"); + +const siteComponent = new (class { + ws?: WebSocket; + avatarID: string; + eventDefaultHandler: EventHandler; + eventCloseHandler: CloseEventHandler; + onLoaded: () => void; + onData: ({ data }: { data: MessageEvent }) => void; + onClosed: () => void; + + constructor() { + this.ws = undefined; + this.avatarID = ""; + this.eventDefaultHandler = () => {}; + this.eventCloseHandler = () => {}; + + this.onLoaded = () => { + this.send({ + eventID: EventPB.Event.EventID.ESTABLISH, + text: JSON.stringify({ + language: getLanguage(), + }), + }); + }; + + this.onData = ({ data }) => { + try { + const { array } = EventPB.Event.deserializeBinary(data); + this.eventDefaultHandler({ + eventID: array[2], + text: array[3], + data: array[4], + }); + } catch (e) {} + }; + + this.onClosed = () => { + this.eventCloseHandler(); + this.connect(); + }; + } + + connect() { + this.ws = new WebSocket( + `${process.env.WS_API ?? "wss://taehui.ddns.net"}/qwilight/ws`, + ); + this.ws.binaryType = "arraybuffer"; + this.ws.addEventListener("open", this.onLoaded); + this.ws.addEventListener("message", this.onData); + this.ws.addEventListener("close", this.onClosed); + } + + disconnect() { + this.eventCloseHandler(); + this.ws?.removeEventListener("open", this.onLoaded); + this.ws?.removeEventListener("message", this.onData); + this.ws?.removeEventListener("close", this.onClosed); + this.ws?.close(); + } + + send({ eventID, text, data }: Event) { + try { + const event = new EventPB.Event(); + event.setMillis(getMillis()); + event.setAvatarid(this.avatarID); + event.setEventid(eventID); + event.setText(text); + data?.forEach((dataItem) => { + event.addData(dataItem); + }); + this.ws?.send(event.serializeBinary()); + } catch (e) {} + } + + setEventDefaultHandler(eventDefaultHandler: EventHandler) { + this.eventDefaultHandler = eventDefaultHandler; + } + + setEventCloseHandler(eventCloseHandler: CloseEventHandler) { + this.eventCloseHandler = eventCloseHandler; + } + + setAvatarID(avatarID: string) { + this.avatarID = avatarID; + } +})(); + +export default siteComponent; diff --git "a/qwilight-fe/src/app/\133language\135/site/components/SiteInput.tsx" "b/qwilight-fe/src/app/\133language\135/site/components/SiteInput.tsx" new file mode 100644 index 0000000..560febc --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/components/SiteInput.tsx" @@ -0,0 +1,134 @@ +import SiteComponent from "@/app/[language]/site/components/SiteComponent"; + +import { useSiteStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; +import { Button, Col, Input, Row } from "reactstrap"; + +const EventPB = require("@/Event_pb"); + +export default observer(() => { + const { + targetSiteID, + isEditable, + input, + setInput, + isLoggedIn, + setAvatarsOpened, + setConfigureOpened, + setLogInOpened, + } = useSiteStore(); + const t = useTranslations(); + + const postFile = (file: File) => { + const fr = new FileReader(); + fr.readAsArrayBuffer(file); + fr.addEventListener("loadend", () => { + const { result } = fr; + SiteComponent.send({ + eventID: EventPB.Event.EventID.POST_FILE, + text: file.name, + data: [new Uint8Array(result as ArrayBufferLike)], + }); + }); + }; + + return ( + <Row className="g-0"> + <Col className="m-1" xs="auto"> + <Button + onClick={() => { + const inputElement = document.createElement("input"); + inputElement.type = "file"; + inputElement.accept = "audio/*,image/*,video/*"; + inputElement.addEventListener("change", ({ target }) => { + const file = (target as HTMLInputElement).files?.[0]; + if (file) { + postFile(file); + } + }); + inputElement.click(); + }} + > + {t("postFile")} + </Button> + </Col> + <Col className="m-1"> + <Input + disabled={!isEditable} + value={input} + onChange={({ target: { value } }) => { + setInput(value); + }} + onKeyDown={({ key }) => { + if (key === "Enter") { + if (input.length > 0) { + SiteComponent.send({ + eventID: EventPB.Event.EventID.SITE_YELL, + text: JSON.stringify({ + siteID: targetSiteID, + siteYell: input, + }), + }); + setInput(""); + } + } + }} + onPaste={({ clipboardData: { items } }) => { + const data = items[0]; + if (data && data.kind === "file") { + const file = data.getAsFile(); + if (file) { + postFile(file); + } + } + }} + /> + </Col> + <Col className="m-1" xs="auto"> + {isLoggedIn ? ( + <Button + color="danger" + onClick={() => { + window.localStorage.removeItem("avatarCipher"); + window.localStorage.removeItem("autoLogIn"); + SiteComponent.send({ + eventID: EventPB.Event.EventID.NOT_LOG_IN, + }); + }} + > + {t("notLogIn")} + </Button> + ) : ( + <Button + color="success" + onClick={() => { + setLogInOpened(true); + }} + > + {t("logIn")} + </Button> + )} + </Col> + <Col className="m-1" xs="auto"> + <Button + color="info" + onClick={() => { + setAvatarsOpened(true); + }} + > + {t("onAvatars")} + </Button> + </Col> + <Col className="m-1" xs="auto"> + <Button + onClick={() => { + setConfigureOpened(true); + }} + > + {t("onConfigure")} + </Button> + </Col> + </Row> + ); +}); diff --git "a/qwilight-fe/src/app/\133language\135/site/components/SiteWindow.tsx" "b/qwilight-fe/src/app/\133language\135/site/components/SiteWindow.tsx" new file mode 100644 index 0000000..dbb7e25 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/components/SiteWindow.tsx" @@ -0,0 +1,103 @@ +import NewSiteWindow from "@/app/[language]/site/components/NewSiteWindow"; +import SiteCipherWindow from "@/app/[language]/site/components/SiteCipherWindow"; +import SiteComponent from "@/app/[language]/site/components/SiteComponent"; + +import useGetSites from "@/app/[language]/site/query/useGetSites"; +import sc from "@/assets/sc.png"; + +import sc0 from "@/assets/sc0.png"; +import sc2 from "@/assets/sc2.png"; + +import { useSiteStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; +import Image from "next/image"; +import { useState } from "react"; +import { Button, Col, Modal, Row } from "reactstrap"; + +const EventPB = require("@/Event_pb"); + +const scs = [sc0, "", sc2]; + +export default observer(() => { + const { + siteAvatarID, + isSiteWindowOpened, + setSiteWindowOpened, + setSiteCipherWindowOpened, + targetSiteID, + setNewSiteWindowOpened, + } = useSiteStore(); + const t = useTranslations(); + + const [siteID, setSiteID] = useState(""); + const [siteName, setSiteName] = useState(""); + + const { data: sites } = useGetSites(); + + const onClose = () => { + setSiteWindowOpened(false); + }; + + return ( + <Modal isOpen={isSiteWindowOpened} toggle={onClose} centered> + <Row className="g-0"> + <Col className="m-1" xs="auto"> + {sites.map( + ({ siteID, hasCipher, siteConfigure, siteName, avatarCount }) => ( + <Row + key={siteID} + className={`g-0 ${targetSiteID === siteID ? "target" : ""}`} + > + <Col className="m-1" xs="auto"> + {scs[siteConfigure] && ( + <Image alt="" src={scs[siteConfigure]} height={24} /> + )}{" "} + <span + className="route" + onClick={() => { + if (hasCipher) { + setSiteID(siteID); + setSiteName(siteName); + setSiteCipherWindowOpened(true); + } else { + SiteComponent.send({ + eventID: EventPB.Event.EventID.ENTER_SITE, + text: JSON.stringify({ siteID, siteCipher: "" }), + }); + onClose(); + } + }} + > + {siteName} ({t("avatarCountText", { avatarCount })}) + {hasCipher && ( + <> + {" "} + <Image alt="" src={sc} height={24} /> + </> + )} + </span> + </Col> + </Row> + ), + )} + </Col> + </Row> + <Row className="justify-content-center g-0"> + <Col className="m-1" xs="auto"> + <Button + onClick={() => { + setNewSiteWindowOpened(true); + }} + disabled={!siteAvatarID} + > + {t("siteWindowNew")} + </Button> + </Col> + </Row> + + <SiteCipherWindow siteID={siteID} siteName={siteName} /> + <NewSiteWindow /> + </Modal> + ); +}); diff --git "a/qwilight-fe/src/app/\133language\135/site/components/SiteYellItem.module.scss" "b/qwilight-fe/src/app/\133language\135/site/components/SiteYellItem.module.scss" new file mode 100644 index 0000000..7c1bd2b --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/components/SiteYellItem.module.scss" @@ -0,0 +1,32 @@ +@mixin file() { + border: thin white solid; + max-height: 9rem; +} + +img { + &.file { + @include file(); + } +} + +video { + &.file { + @include file(); + } +} + +audio { + &.file { + @include file(); + } +} + +span { + &.enter { + color: deepskyblue; + } + + &.quit { + color: deeppink; + } +} diff --git "a/qwilight-fe/src/app/\133language\135/site/components/SiteYellItem.tsx" "b/qwilight-fe/src/app/\133language\135/site/components/SiteYellItem.tsx" new file mode 100644 index 0000000..41a49fb --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/components/SiteYellItem.tsx" @@ -0,0 +1,411 @@ +import SiteComponent from "@/app/[language]/site/components/SiteComponent"; +import scss from "@/app/[language]/site/components/SiteYellItem.module.scss"; +import { + AbilitySiteYell, + CommentSiteYell, + InviteSiteYell, + LevelSiteYell, + OnSiteYellInput, + SiteYell, + TVSiteYell, +} from "@/app/[language]/site/type"; +import TV0 from "@/assets/tv0.svg"; +import tv1 from "@/assets/tv1.png"; +import AvatarDrawing from "@/components/AvatarDrawing"; +import AvatarTitle from "@/components/AvatarTitle"; + +import { useSiteStore } from "@/store/Stores"; +import { + formatText, + getAbilityUpText, + getGenreText, + getHitPointsClass, +} from "@/utilities/Utility"; +import { sanitize } from "isomorphic-dompurify"; +import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; +import Image from "next/image"; +import { Col, Row } from "reactstrap"; + +const EventPB = require("@/Event_pb"); + +export default observer( + ({ + data, + onSiteYellInput, + }: { + data: SiteYell; + onSiteYellInput: OnSiteYellInput; + }) => { + const { siteYellVariety, date, avatarID, avatarName, siteYell } = data; + const { saveTraffic } = useSiteStore(); + const t = useTranslations(); + + const doSiteYell = (siteYell: string) => { + siteYell = siteYell.replace(" ", " "); + const m = siteYell.match(/(http|https|mailto|rtmp):\/\/[^ ]+/i); + if (m != null) { + const t = m[0]; + + if ( + !saveTraffic && + t.match(/(\.aac|\.flac|\.mid|\.midi|\.mp3|\.ogg|\.wav|\.wma)($|\?)/i) + ) { + return siteYell.replace( + t, + `<audio class="${scss.file}" src="${t}" controls></audio>`, + ); + } + + if ( + !saveTraffic && + t.match(/(\.bmp|\.gif|\.heic|\.jpeg|\.jpg|\.png|\.webp)($|\?)/i) + ) { + return siteYell.replace( + t, + `<a href="${t}" target="_blank"> + <img class="${scss.file}" src="${t}" alt=""> + </a>`, + ); + } + + if ( + !saveTraffic && + t.match(/(\.avi|\.mkv|\.mp4|\.mpeg|\.mpg|\.wmv)($|\?)/i) + ) { + return siteYell.replace( + t, + `<video class="${scss.file}" src="${t}" controls></video>`, + ); + } + + return siteYell.replace(t, `<a href="${t}" target="_blank">${t}</a>`); + } + + return siteYell; + }; + + switch (siteYellVariety) { + case "@Enter": + return ( + <Row + className="g-0" + style={{ flexWrap: "nowrap" }} + onContextMenu={(e) => { + e.preventDefault(); + avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); + }} + > + {avatarID && ( + <Col className="m-1" xs="auto"> + <AvatarDrawing avatarID={avatarID} /> + </Col> + )} + <Col className="m-1" xs="auto"> + {avatarID && <AvatarTitle avatarID={avatarID} />} + <span>{avatarName}</span> <span className="date">{date}</span> + <br /> + <span className={scss.enter}>{t("siteYellEnter")}</span> + </Col> + </Row> + ); + case "@Quit": + return ( + <Row + className="g-0" + style={{ flexWrap: "nowrap" }} + onContextMenu={(e) => { + e.preventDefault(); + avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); + }} + > + {avatarID && ( + <Col className="m-1" xs="auto"> + <AvatarDrawing avatarID={avatarID} /> + </Col> + )} + <Col className="m-1" xs="auto"> + {avatarID && <AvatarTitle avatarID={avatarID} />} + <span>{avatarName}</span> <span className="date">{date}</span> + <br /> + <span className={scss.quit}>{t("siteYellQuit")}</span> + </Col> + </Row> + ); + case "@Site": + return ( + <Row + className="g-0" + style={{ flexWrap: "nowrap" }} + onContextMenu={(e) => { + e.preventDefault(); + avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); + }} + > + {avatarID && ( + <Col className="m-1" xs="auto"> + <AvatarDrawing avatarID={avatarID} /> + </Col> + )} + <Col className="m-1" xs="auto"> + {avatarID && <AvatarTitle avatarID={avatarID} />} + <span>{avatarName}</span> <span className="date">{date}</span> + <br /> + <span className={scss.enter}>{t("siteYellNewSite")}</span> + </Col> + </Row> + ); + case "@Net": + return ( + <Row + className="g-0" + style={{ flexWrap: "nowrap" }} + onContextMenu={(e) => { + e.preventDefault(); + avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); + }} + > + {avatarID && ( + <Col className="m-1" xs="auto"> + <AvatarDrawing avatarID={avatarID} /> + </Col> + )} + <Col className="m-1" xs="auto"> + {avatarID && <AvatarTitle avatarID={avatarID} />} + <span>{avatarName}</span> <span className="date">{date}</span> + <br /> + <span className={scss.enter}>{t("siteYellNewNetSite")}</span> + </Col> + </Row> + ); + case "@Notify": + return ( + <Row className="g-0" style={{ flexWrap: "nowrap" }}> + <Col className="m-1" xs="auto"> + <span className="taehui">{t("siteYellTaehui")}</span>{" "} + <span className="date">{date}</span> + <br /> + <span + dangerouslySetInnerHTML={{ + __html: doSiteYell(siteYell as string), + }} + /> + </Col> + </Row> + ); + case "@Invite": { + const { siteID, siteName, avatarName } = siteYell as InviteSiteYell; + return ( + <Row + className="g-0" + style={{ flexWrap: "nowrap" }} + onContextMenu={(e) => { + e.preventDefault(); + avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); + }} + > + {avatarID && ( + <Col className="m-1" xs="auto"> + <AvatarDrawing avatarID={avatarID} /> + </Col> + )} + <Col className="m-1" xs="auto"> + {avatarID && <AvatarTitle avatarID={avatarID} />} + <span>{avatarName}</span> <span className="date">{date}</span> + <br /> + <span + className="route" + onClick={() => { + SiteComponent.send({ + eventID: EventPB.Event.EventID.ENTER_SITE, + text: JSON.stringify({ + siteID, + siteCipher: "", + }), + }); + }} + > + {t("siteYellInvite", { siteName })} + </span> + </Col> + </Row> + ); + } + case "@TV": + const { href, title, text } = siteYell as TVSiteYell; + return ( + <Row className="g-0" style={{ flexWrap: "nowrap" }}> + <Col className="m-1" xs="auto"> + {href.startsWith("https://www.twitch.tv") && ( + <TV0 width={60} height={60} /> + )} + {href.startsWith("https://chzzk.naver.com") && ( + <Image src={tv1} alt="" width={60} height={60} /> + )} + </Col> + <Col className="m-1" xs="auto"> + <span>{text}</span> <span className="date">{date}</span> + <br /> + <span + className="route" + onClick={() => { + window.open(href); + }} + > + {t("siteYellTV", { title })} + </span> + </Col> + </Row> + ); + case "@Wiped": + return ( + <Row className="g-0" style={{ flexWrap: "nowrap" }}> + <Col + className="m-1" + xs="auto" + onContextMenu={(e) => { + e.preventDefault(); + avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); + }} + > + {avatarID && <AvatarDrawing avatarID={avatarID} />} + </Col> + <Col className="m-1" xs="auto"> + {avatarID && <AvatarTitle avatarID={avatarID} />} + <span>{avatarName}</span> <span className="date">{date}</span> + <br /> + <span>{t("wipedSiteYell")}</span> + </Col> + </Row> + ); + case "@Comment": { + const { + avatarID, + avatarName, + title, + artist, + genre, + level, + levelText, + stand, + hitPointsMode, + } = siteYell as CommentSiteYell; + return ( + <Row + className="g-0" + style={{ flexWrap: "nowrap" }} + onContextMenu={(e) => { + e.preventDefault(); + avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); + }} + > + {avatarID && ( + <Col className="m-1" xs="auto"> + <AvatarDrawing avatarID={avatarID} /> + </Col> + )} + <Col className="m-1" xs="auto"> + {avatarID && <AvatarTitle avatarID={avatarID} />} + <span>{avatarName}</span> <span className="date">{date}</span> + <br /> + <span className={`level${level}`}>{levelText}</span>{" "} + <span className="artist">{artist}</span>{" "} + <span className="title">{title}</span>{" "} + <span className="genre">{getGenreText(genre)}</span> + <br /> + <span className={getHitPointsClass(hitPointsMode)}> + {t("textStand", { value: formatText(stand) })} + </span> + </Col> + </Row> + ); + } + case "@Ability": { + const { avatarID, avatarName } = siteYell as AbilitySiteYell; + return ( + <Row + className="g-0" + style={{ flexWrap: "nowrap" }} + onContextMenu={(e) => { + e.preventDefault(); + avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); + }} + > + {avatarID && ( + <Col className="m-1" xs="auto"> + <AvatarDrawing avatarID={avatarID} /> + </Col> + )} + <Col className="m-1" xs="auto"> + {avatarID && <AvatarTitle avatarID={avatarID} />} + <span>{avatarName}</span> <span className="date">{date}</span> + <br /> + <span>{getAbilityUpText(t, siteYell as AbilitySiteYell)}</span> + <br /> + </Col> + </Row> + ); + } + case "@Level": { + const { avatarID, avatarName, title } = siteYell as LevelSiteYell; + return ( + <Row + className="g-0" + style={{ flexWrap: "nowrap" }} + onContextMenu={(e) => { + e.preventDefault(); + avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); + }} + > + {avatarID && ( + <Col className="m-1" xs="auto"> + <AvatarDrawing avatarID={avatarID} /> + </Col> + )} + <Col className="m-1" xs="auto"> + {avatarID && <AvatarTitle avatarID={avatarID} />} + <span>{avatarName}</span> <span className="date">{date}</span> + <br /> + <span>{t("wwwLevelClearText", { title })}</span> + <br /> + </Col> + </Row> + ); + } + case "": + return ( + <> + <span>{siteYell as string}</span> + <br /> + </> + ); + case null: + return ( + <Row className="g-0" style={{ flexWrap: "nowrap" }}> + <Col + className="m-1" + xs="auto" + onContextMenu={(e) => { + e.preventDefault(); + avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); + }} + > + {avatarID && <AvatarDrawing avatarID={avatarID} />} + </Col> + <Col className="m-1" xs="auto"> + {avatarID && <AvatarTitle avatarID={avatarID} />} + <span>{avatarName}</span> <span className="date">{date}</span> + <br /> + <span + dangerouslySetInnerHTML={{ + __html: doSiteYell(sanitize(siteYell as string)), + }} + /> + </Col> + </Row> + ); + default: + return null; + } + }, +); diff --git "a/qwilight-fe/src/app/\133language\135/site/components/SiteYellItems.tsx" "b/qwilight-fe/src/app/\133language\135/site/components/SiteYellItems.tsx" new file mode 100644 index 0000000..3947262 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/components/SiteYellItems.tsx" @@ -0,0 +1,24 @@ +import SiteYellItem from "@/app/[language]/site/components/SiteYellItem"; +import { OnSiteYellInput } from "@/app/[language]/site/type"; +import { useSiteStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; + +export default observer( + ({ onSiteYellInput }: { onSiteYellInput: OnSiteYellInput }) => { + const { siteYells } = useSiteStore(); + + return ( + <> + {siteYells.map((siteYell) => + siteYell ? ( + <SiteYellItem + key={siteYell.siteYellID} + data={siteYell} + onSiteYellInput={onSiteYellInput} + /> + ) : null, + )} + </> + ); + }, +); diff --git "a/qwilight-fe/src/app/\133language\135/site/loading.tsx" "b/qwilight-fe/src/app/\133language\135/site/loading.tsx" index 2daeb32..3f6c8ce 100644 --- "a/qwilight-fe/src/app/\133language\135/site/loading.tsx" +++ "b/qwilight-fe/src/app/\133language\135/site/loading.tsx" @@ -1,4 +1,4 @@ -import LoadingLayer from "@/LoadingLayer"; +import LoadingLayer from "@/components/LoadingLayer"; import { useTranslations } from "next-intl"; export default function Loading() { diff --git "a/qwilight-fe/src/app/\133language\135/site/page.tsx" "b/qwilight-fe/src/app/\133language\135/site/page.tsx" index ad68086..17e3e17 100644 --- "a/qwilight-fe/src/app/\133language\135/site/page.tsx" +++ "b/qwilight-fe/src/app/\133language\135/site/page.tsx" @@ -1,17 +1,17 @@ "use client"; +import AvatarItems from "@/app/[language]/site/components/AvatarItems"; +import ConfigureWindow from "@/app/[language]/site/components/ConfigureWindow"; +import SiteComponent from "@/app/[language]/site/components/SiteComponent"; +import SiteInput from "@/app/[language]/site/components/SiteInput"; +import SiteWindow from "@/app/[language]/site/components/SiteWindow"; +import SiteYellItem from "@/app/[language]/site/components/SiteYellItem"; +import SiteYellItems from "@/app/[language]/site/components/SiteYellItems"; import scss from "@/app/[language]/site/page.module.scss"; -import AvatarItems from "@/site/AvatarItems"; -import ConfigureWindow from "@/site/ConfigureWindow"; -import { OnSiteYellInput } from "@/site/Site"; -import SiteComponent from "@/site/SiteComponent"; -import SiteInput from "@/site/SiteInput"; -import SiteWindow from "@/site/SiteWindow"; -import SiteYellItem from "@/site/SiteYellItem"; -import SiteYellItems from "@/site/SiteYellItems"; +import { OnSiteYellInput } from "@/app/[language]/site/type"; -import { useSiteStore } from "@/Stores"; -import { getDefaultAvatarID } from "@/Utility"; +import { useSiteStore } from "@/store/Stores"; +import { getDefaultAvatarID } from "@/utilities/Utility"; import { useQueryClient } from "@tanstack/react-query"; import { observer } from "mobx-react-lite"; import { useTranslations } from "next-intl"; @@ -29,7 +29,7 @@ Row, } from "reactstrap"; import Swal from "sweetalert2"; -import { useTo } from "taehui-ts/fe-utility"; +import { useTo } from "taehui-ts/fe-utilities"; const EventPB = require("@/Event_pb"); diff --git "a/qwilight-fe/src/app/\133language\135/site/query/useGetSites.ts" "b/qwilight-fe/src/app/\133language\135/site/query/useGetSites.ts" new file mode 100644 index 0000000..93287d7 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/query/useGetSites.ts" @@ -0,0 +1,34 @@ +import { useSiteStore } from "@/store/Stores"; +import { GetSitesAPI } from "@/type/wwwAPI"; +import { getSiteName } from "@/utilities/Utility"; + +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default function useGetSites() { + const { isSiteWindowOpened } = useSiteStore(); + + const t = useTranslations(); + + const isPath = useIsPath(); + + return useQuery({ + enabled: isSiteWindowOpened && isPath("/site"), + queryKey: ["sites"], + queryFn: async () => { + const { data } = await wwwAPI.get<GetSitesAPI>("/sites"); + return data.map( + ({ siteID, siteName, siteConfigure, hasCipher, avatarCount }) => ({ + siteID, + siteName: getSiteName(siteName, t), + siteConfigure, + hasCipher, + avatarCount, + }), + ); + }, + initialData: [], + }); +} diff --git "a/qwilight-fe/src/app/\133language\135/site/query/useSiteComponent.tsx" "b/qwilight-fe/src/app/\133language\135/site/query/useSiteComponent.tsx" new file mode 100644 index 0000000..fab26f2 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/query/useSiteComponent.tsx" @@ -0,0 +1,46 @@ +import SiteComponent from "@/app/[language]/site/components/SiteComponent"; +import { useSiteStore } from "@/store/Stores"; +import { useTranslations } from "next-intl"; +import { useEffect } from "react"; + +export default function useSiteComponent() { + const { + targetSiteID, + getSiteView, + setVisible, + setEventHandler, + setEventCloseHandler, + } = useSiteStore(); + const t = useTranslations(); + + useEffect(() => { + const onVisibilityModified = () => { + if (setVisible()) { + const siteView = getSiteView(targetSiteID); + if (siteView) { + siteView.wasNotify = false; + } + } + }; + + document.addEventListener("visibilitychange", onVisibilityModified); + + return () => { + document.removeEventListener("visibilitychange", onVisibilityModified); + }; + }, [getSiteView, setVisible, targetSiteID]); + + useEffect(() => { + setVisible(); + setEventHandler(t); + setEventCloseHandler(); + }, [setEventCloseHandler, setEventHandler, setVisible, t]); + + useEffect(() => { + SiteComponent.connect(); + + return () => { + SiteComponent.disconnect(); + }; + }, []); +} diff --git "a/qwilight-fe/src/app/\133language\135/site/store/setSiteStore.ts" "b/qwilight-fe/src/app/\133language\135/site/store/setSiteStore.ts" new file mode 100644 index 0000000..57a675d --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/store/setSiteStore.ts" @@ -0,0 +1,741 @@ +import SiteComponent from "@/app/[language]/site/components/SiteComponent"; +import { + AbilitySiteYell, + Avatar, + SiteView, + SiteYell, +} from "@/app/[language]/site/type"; +import { + formatText, + getAbilityUpText, + getDefaultAvatarID, + getGenreText, + getSiteName, +} from "@/utilities/Utility"; +import { wwwAPIPath } from "@/utilities/wwwAPI"; +import CryptoJS from "crypto-js"; +import { runInAction } from "mobx"; +import { useTranslations } from "next-intl"; +import { RefObject } from "react"; +import { toast } from "react-toastify"; + +const EventPB = require("@/Event_pb"); + +const getSiteYellItem = ({ + avatarID, + avatarName, + siteYell, + date, + siteYellID, +}: { + avatarID: string; + avatarName: string; + siteYell: string; + date: number; + siteYellID: number; +}): SiteYell | null => { + const dateText = new Date(date).toLocaleTimeString(); + switch (avatarName) { + case "@Enter": + return { + siteYellID, + avatarID, + avatarName: siteYell, + siteYellVariety: avatarName, + date: dateText, + }; + case "@Quit": + return { + siteYellID, + avatarID, + avatarName: siteYell, + siteYellVariety: avatarName, + date: dateText, + }; + case "@Site": + return { + siteYellID, + avatarID, + avatarName: siteYell, + siteYellVariety: avatarName, + date: dateText, + }; + case "@Net": + return { + siteYellID, + avatarID, + avatarName: siteYell, + siteYellVariety: avatarName, + date: dateText, + }; + case "@Notify": + return { + siteYellID, + avatarID, + siteYellVariety: avatarName, + date: dateText, + siteYell, + }; + case "@Wiped": + return { + siteYellID, + avatarID, + avatarName: siteYell, + siteYellVariety: avatarName, + date: dateText, + }; + case "@Invite": + case "@Comment": + case "@Ability": + case "@Level": + case "@TV": + return { + siteYellID, + avatarID, + siteYellVariety: avatarName, + date: dateText, + siteYell: JSON.parse(siteYell), + }; + case "": + return { + siteYellID, + siteYellVariety: "", + siteYell, + }; + default: + return { + siteYellID, + siteYellVariety: null, + date: dateText, + avatarID, + avatarName, + siteYell, + }; + } +}; + +export default function setSiteStore() { + return { + titleComponent: undefined as RefObject<HTMLDivElement> | undefined, + siteYellsView: undefined as RefObject<HTMLDivElement> | undefined, + avatars: [] as Avatar[], + siteYells: [] as SiteYell[], + isLogInOpened: false, + isSiteWindowOpened: false, + isSiteCipherWindowOpened: false, + isNewSiteWindowOpened: false, + isConfigureOpened: false, + targetSiteID: "", + siteNotify: "", + saveTraffic: + typeof window === "object" && + window.localStorage.getItem("saveTraffic") === "true", + autoEnterNotify: + typeof window === "object" && + window.localStorage.getItem("autoEnterNotify") !== "false", + autoEnterDefault: + typeof window === "object" && + window.localStorage.getItem("autoEnterDefault") !== "false", + autoEnterPlatform: + typeof window === "object" && + window.localStorage.getItem("autoEnterPlatform") !== "false", + isEditable: true, + input: "", + siteViews: [] as SiteView[], + siteAvatarID: "", + siteAvatarName: "", + isLoggedIn: false, + isSiteYellsViewLowest: true, + isVisible: false, + isLoading: true, + lastPendingSiteYell: undefined as SiteYell | undefined, + isPendingSiteYellOpened: false, + isAvatarsOpened: false, + + setComponents( + titleComponent: RefObject<HTMLDivElement>, + siteYellsView: RefObject<HTMLDivElement>, + ) { + this.titleComponent = titleComponent; + this.siteYellsView = siteYellsView; + }, + + setEventHandler(t: ReturnType<typeof useTranslations<string>>) { + const autoEnter = () => { + SiteComponent.send({ + eventID: EventPB.Event.EventID.ENTER_SITE, + text: JSON.stringify({ + siteID: "00000000-0000-0000-0000-000000000003", + siteCipher: "", + }), + }); + if (this.autoEnterNotify) { + SiteComponent.send({ + eventID: EventPB.Event.EventID.ENTER_SITE, + text: JSON.stringify({ + siteID: "00000000-0000-0000-0000-000000000000", + siteCipher: "", + }), + }); + } + if (this.autoEnterDefault) { + SiteComponent.send({ + eventID: EventPB.Event.EventID.ENTER_SITE, + text: JSON.stringify({ + siteID: "00000000-0000-0000-0000-000000000001", + siteCipher: "", + }), + }); + } + if (this.autoEnterPlatform) { + SiteComponent.send({ + eventID: EventPB.Event.EventID.ENTER_SITE, + text: JSON.stringify({ + siteID: "00000000-0000-0000-0000-000000000002", + siteCipher: "", + }), + }); + } + }; + + const autoLogIn = () => { + if (window.localStorage.getItem("autoLogIn") === "true") { + SiteComponent.send({ + eventID: EventPB.Event.EventID.LOG_IN, + text: JSON.stringify({ + avatarID: window.localStorage.getItem("avatarID") ?? "", + avatarCipher: CryptoJS.AES.decrypt( + window.localStorage.getItem("avatarCipher") ?? "", + "591A6F91-2A27-4A88-88FA-0FEB7CB5FD94", + ).toString(CryptoJS.enc.Utf8), + }), + }); + } + }; + + const doNotify = (avatarID: string, toNotify: string, siteID: string) => { + if ( + !["denied", "default"].includes(Notification?.permission) && + !this.isVisible + ) { + const siteView = this.getSiteView(siteID); + if (siteView?.wasNotify === false) { + new Notification("Qwilight", { + body: toNotify, + icon: `${wwwAPIPath}/drawing?avatarID=${encodeURIComponent( + getDefaultAvatarID(avatarID), + )}&drawingVariety=0`, + }); + siteView.wasNotify = true; + } + } + }; + + SiteComponent.setEventDefaultHandler(({ eventID, text }) => { + switch (eventID) { + case EventPB.Event.EventID.ESTABLISH: + if (text) { + const { avatarID, avatarName } = JSON.parse(text); + this.setSiteAvatar(avatarID, avatarName); + this.setLoading(false); + autoEnter(); + const totem = window.sessionStorage.getItem("totem"); + if (totem) { + SiteComponent.send({ + eventID: EventPB.Event.EventID.LOG_IN, + text: totem, + }); + } else { + autoLogIn(); + } + } + break; + case EventPB.Event.EventID.FAILED_VALIDATE_TOTEM: + autoLogIn(); + break; + // EventPB.Event.EventID.LOG_IN + case undefined: + if (text) { + this.setLogInOpened(false); + const { totem, avatarID, avatarName } = JSON.parse(text); + if (totem !== window.sessionStorage.getItem("totem")) { + toast.success(t("loggedInText", { avatarName })); + } + window.sessionStorage.setItem("totem", totem); + this.setSiteAvatar(avatarID, avatarName); + this.setLoggedIn(true); + autoEnter(); + } + break; + case EventPB.Event.EventID.NOT_LOG_IN: + if (text) { + toast.success( + t("notLoggedInText", { + avatarName: this.siteAvatarName, + }), + ); + window.sessionStorage.removeItem("totem"); + const { avatarID, avatarName } = JSON.parse(text); + this.setSiteAvatar(avatarID, avatarName); + this.setLoggedIn(false); + autoEnter(); + } + break; + case EventPB.Event.EventID.SITE_YELL: + if (text) { + const { + siteID, + avatarID, + avatarName, + siteYell, + siteYellID, + date, + } = JSON.parse(text); + const siteYellItem = getSiteYellItem({ + avatarID, + avatarName, + siteYell, + date, + siteYellID, + }); + if (siteYellItem) { + this.putSiteYell(siteID, siteYellItem, false); + if (this.targetSiteID === siteID) { + this.putTargetSiteYell(siteYellItem, false); + if ( + avatarID === this.siteAvatarID || + this.isSiteYellsViewLowest + ) { + this.siteYellsViewMove(); + } else { + runInAction(() => { + this.lastPendingSiteYell = siteYellItem; + }); + this.setPendingSiteYellOpened(true); + } + } else { + this.setModifiedSiteViews(siteID, (siteView) => { + siteView.isNew = true; + }); + } + } + const ltDate = new Date(Number(date)).toLocaleTimeString(); + let toNotify = ""; + switch (avatarName) { + case "@Notify": + if (this.targetSiteID === siteID) { + this.siteNotify = siteYell; + } else { + const siteView = this.getSiteView(siteID); + if (siteView) { + siteView.siteNotify = siteYell; + } + } + toNotify = `${t("siteYellTaehui")} (${ltDate}) ${siteYell}`; + break; + case "@Comment": { + const { avatarName, artist, title, genre, levelText, stand } = + JSON.parse(siteYell); + toNotify = `${avatarName} (${ltDate}) ${levelText} ${artist} - ${title} ${getGenreText( + genre, + )} ${t("textStand", { value: formatText(stand) })}`; + break; + } + case "@Ability": { + toNotify = getAbilityUpText( + t, + JSON.parse(siteYell) as AbilitySiteYell, + ); + break; + } + case "@Level": { + const { title } = JSON.parse(siteYell); + toNotify = t("wwwLevelClearText", { title }); + break; + } + case "@Enter": { + toNotify = `${siteYell} ${ltDate} ${t("siteYellEnter")}`; + break; + } + case "@Quit": { + toNotify = `${siteYell} ${ltDate} ${t("siteYellQuit")}`; + break; + } + case "@Invite": { + const { avatarName, siteName } = JSON.parse(siteYell); + toNotify = `${avatarName} (${ltDate}) ${t("siteYellInvite", { + siteName, + })}`; + break; + } + case "@TV": { + const { title, text } = JSON.parse(siteYell); + toNotify = `${text} (${ltDate}) ${t("siteYellTV", { + title, + })}`; + break; + } + case "@Wiped": + toNotify = `${avatarName} (${ltDate}) ${t("wipedSiteYell")}`; + break; + case "": + toNotify = siteYell; + break; + case null: + toNotify = `${avatarName} (${ltDate}) ${siteYell}`; + break; + } + if (toNotify) { + doNotify(avatarID, toNotify, siteID); + } + } + break; + case EventPB.Event.EventID.MODIFY_SITE_YELL: + if (text) { + const { siteID, siteYell, siteYellID } = JSON.parse(text); + this.doModifySiteYell(siteID, siteYell, siteYellID); + if (this.targetSiteID === siteID) { + this.doModifyTargetSiteYell(siteYell, siteYellID); + } + } + break; + case EventPB.Event.EventID.WIPE_SITE_YELL: + if (text) { + const { siteID, siteYellID } = JSON.parse(text); + this.wipeSiteYell(siteID, siteYellID); + if (this.targetSiteID === siteID) { + this.wipeTargetSiteYell(siteYellID); + } + } + break; + case EventPB.Event.EventID.GET_SITE_YELLS: + if (text) { + if (this.siteYellsView) { + const { current } = this.siteYellsView; + if (current) { + const lastPosition1BeforeCalled = + current.scrollHeight - current.clientHeight; + const { siteID, data } = JSON.parse(text); + + data + .reverse() + .map(getSiteYellItem) + .forEach((siteYellItem: SiteYell) => { + this.putSiteYell(siteID, siteYellItem, true); + if (this.targetSiteID === siteID) { + this.putTargetSiteYell(siteYellItem, true); + } + }); + + setTimeout(() => { + current.scrollTop = + current.scrollHeight - + current.clientHeight - + lastPosition1BeforeCalled; + }, 0); + } + } + } + break; + case EventPB.Event.EventID.CALL_SITE_AVATAR: + if (text) { + const { siteID, siteName, situationValue, data, siteHand } = + JSON.parse(text); + const avatars = data.map( + ({ + avatarID, + avatarName, + avatarConfigure, + isValve, + isAudioInput, + }: { + avatarID: string; + avatarName: string; + avatarConfigure: number; + isValve: boolean; + isAudioInput: boolean; + }) => { + return { + avatarID, + avatarName, + avatarConfigure, + isSiteHand: avatarID === siteHand, + isMe: this.siteAvatarID === avatarID, + isValve, + isAudioInput, + }; + }, + ); + this.setModifiedSiteViews(siteID, (siteView) => { + siteView.siteName = getSiteName(siteName, t); + siteView.avatars = avatars; + siteView.siteHand = siteHand; + siteView.situationValue = situationValue; + }); + if (siteID === this.targetSiteID) { + this.setAvatars(avatars); + } + } + break; + case EventPB.Event.EventID.ENTER_SITE: + if (text) { + const { siteID, siteNotify, isEditable, isNetMode, data } = + JSON.parse(text); + this.putSiteView({ + siteID, + isEditable, + isNew: false, + wasNotify: false, + siteNotify, + siteName: "", + siteHand: "", + situationValue: 0, + isNetMode, + avatars: [], + siteYells: data.map(getSiteYellItem), + }); + this.onSiteIDModified(siteID); + } + break; + case EventPB.Event.EventID.QUIT_SITE: + if (text) { + this.quitSiteView(text); + this.onSiteIDModified( + this.siteViews[this.siteViews.length - 1]?.siteID, + ); + } + break; + case EventPB.Event.EventID.WARNING: + toast.warning(text); + break; + case EventPB.Event.EventID.NOTIFY_YES: + toast.success(text); + break; + case EventPB.Event.EventID.NOTIFY_INFO: + toast.info(text); + break; + case EventPB.Event.EventID.POST_FILE: + if (text) { + this.setInput(text); + } + break; + } + }); + }, + + setEventCloseHandler() { + SiteComponent.setEventCloseHandler(() => { + this.setSiteAvatar("", ""); + this.setLoggedIn(false); + this.onSiteIDModified(""); + this.wipeSiteViews(); + this.setLoading(true); + }); + }, + + setPendingSiteYellOpened(isPendingSiteYellOpened: boolean) { + this.isPendingSiteYellOpened = isPendingSiteYellOpened; + }, + + setLoading(isLoading: boolean) { + this.isLoading = isLoading; + }, + + setSiteAvatar(siteAvatarID: string, siteAvatarName: string) { + this.siteAvatarID = siteAvatarID; + this.siteAvatarName = siteAvatarName; + SiteComponent.setAvatarID(this.siteAvatarID); + }, + + putSiteYell(siteID: string, siteYell: SiteYell, isGetSiteYell: boolean) { + const siteView = this.getSiteView(siteID); + if (isGetSiteYell) { + siteView?.siteYells?.unshift(siteYell); + } else { + siteView?.siteYells?.push(siteYell); + } + }, + + putTargetSiteYell(siteYell: SiteYell, isGetSiteYell: boolean) { + if (isGetSiteYell) { + this.siteYells.unshift(siteYell); + } else { + this.siteYells.push(siteYell); + } + }, + + doModifySiteYell(siteID: string, siteYell: string, siteYellID: number) { + const targetSiteYell = this.getSiteView(siteID)?.siteYells?.find( + (siteYell) => siteYell.siteYellID === siteYellID, + ); + if (targetSiteYell) { + targetSiteYell.siteYell = siteYell; + } + }, + + doModifyTargetSiteYell(siteYell: string, siteYellID: number) { + const targetSiteYell = this.siteYells?.find( + (siteYell) => siteYell.siteYellID === siteYellID, + ); + if (targetSiteYell) { + targetSiteYell.siteYell = siteYell; + } + }, + + wipeSiteYell(siteID: string, siteYellID: number) { + const siteYells = this.getSiteView(siteID)?.siteYells; + if (siteYells) { + const i = siteYells.findIndex( + (siteYell) => siteYell.siteYellID === siteYellID, + ); + const siteYell = siteYells[i]; + siteYells.splice(i, 1, { + siteYellID, + avatarID: siteYell.avatarID, + avatarName: siteYell.avatarName, + siteYellVariety: "@Wiped", + date: siteYell.date, + }); + } + }, + + wipeTargetSiteYell(siteYellID: number) { + const i = this.siteYells.findIndex( + (siteYell) => siteYell.siteYellID === siteYellID, + ); + const siteYell = this.siteYells[i]; + this.siteYells.splice(i, 1, { + siteYellID, + avatarID: siteYell.avatarID, + avatarName: siteYell.avatarName, + siteYellVariety: "@Wiped", + date: siteYell.date, + }); + }, + + setModifiedSiteViews( + targetSiteID: string, + onModified: (siteView: SiteView) => void, + ) { + const tmpSiteView = this.siteViews.find( + ({ siteID }) => targetSiteID === siteID, + ); + if (tmpSiteView) { + onModified(tmpSiteView); + } + }, + + setInput(input: string) { + this.input = input; + }, + + setSaveTraffic(SaveTraffic: boolean) { + this.saveTraffic = SaveTraffic; + }, + + setAutoEnterNotify(autoEnterNotify: boolean) { + this.autoEnterNotify = autoEnterNotify; + }, + + setAutoEnterDefault(autoEnterDefault: boolean) { + this.autoEnterDefault = autoEnterDefault; + }, + + setAutoEnterPlatform(autoEnterPlatform: boolean) { + this.autoEnterPlatform = autoEnterPlatform; + }, + + setLogInOpened(isLogInOpened: boolean) { + this.isLogInOpened = isLogInOpened; + }, + + setSiteWindowOpened(isSiteWindowOpened: boolean) { + this.isSiteWindowOpened = isSiteWindowOpened; + }, + + setSiteCipherWindowOpened(isSiteCipherWindowOpened: boolean) { + this.isSiteCipherWindowOpened = isSiteCipherWindowOpened; + }, + + setNewSiteWindowOpened(isNewSiteWindowOpened: boolean) { + this.isNewSiteWindowOpened = isNewSiteWindowOpened; + }, + + setConfigureOpened(isConfigureOpened: boolean) { + this.isConfigureOpened = isConfigureOpened; + }, + + setSiteYellsViewLowest(isSiteYellsViewLowest: boolean) { + this.isSiteYellsViewLowest = isSiteYellsViewLowest; + }, + + getSiteView(targetSiteID: string) { + return this.siteViews.find(({ siteID }) => siteID === targetSiteID); + }, + + onSiteIDModified(siteID: string) { + this.targetSiteID = siteID; + const siteView = this.getSiteView(siteID); + if (siteView) { + if (this.isVisible) { + siteView.wasNotify = false; + } + this.setModifiedSiteViews(siteID, (siteView) => { + siteView.isNew = false; + }); + this.isEditable = siteView.isEditable; + this.siteNotify = siteView.siteNotify; + this.avatars = [...siteView.avatars]; + this.siteYells = [...siteView.siteYells]; + this.siteYellsViewMove(); + } else { + this.isEditable = false; + this.siteNotify = ""; + this.avatars = []; + this.siteYells = []; + } + }, + + setVisible() { + return (this.isVisible = document.visibilityState === "visible"); + }, + + siteYellsViewMove() { + setTimeout(() => { + if (this.siteYellsView) { + const { current } = this.siteYellsView; + if (current) { + current.scrollTop = current.scrollHeight; + } + } + }, 0); + }, + + setAvatarsOpened(isAvatarsOpened: boolean) { + this.isAvatarsOpened = isAvatarsOpened; + }, + + setLoggedIn(isLoggedIn: boolean) { + this.isLoggedIn = isLoggedIn; + }, + + setAvatars(avatars: Avatar[]) { + this.avatars = avatars; + }, + + putSiteView(siteView: SiteView) { + this.siteViews.push(siteView); + }, + + quitSiteView(siteID: string) { + this.siteViews.splice( + this.siteViews.findIndex((siteView) => siteView.siteID === siteID), + 1, + ); + }, + + wipeSiteViews() { + this.siteViews = []; + }, + }; +} diff --git "a/qwilight-fe/src/app/\133language\135/site/type/index.d.ts" "b/qwilight-fe/src/app/\133language\135/site/type/index.d.ts" new file mode 100644 index 0000000..ac2bda1 --- /dev/null +++ "b/qwilight-fe/src/app/\133language\135/site/type/index.d.ts" @@ -0,0 +1,87 @@ +import { TriggerEvent } from "react-contexify"; + +export type Avatar = { + avatarID: string; + avatarName: string; + avatarConfigure: number; + isSiteHand: boolean; + isMe: boolean; + isValve: boolean; + isAudioInput: boolean; +}; + +export type SiteYell = { + avatarID?: string; + avatarName?: string; + siteYellVariety: ?string; + date?: string; + siteYell?: + | string + | CommentSiteYell + | AbilitySiteYell + | LevelSiteYell + | InviteSiteYell + | TVSiteYell; + siteYellID: number; +}; + +export type CommentSiteYell = { + avatarID: string; + avatarName: string; + title: string; + artist: string; + genre: string; + level: number; + levelText: string; + stand: number; + hitPointsMode: number; +}; + +export type AbilitySiteYell = { + avatarID: string; + avatarName: string; + inputMode: number; + ability: number; +}; + +export type LevelSiteYell = { + avatarID: string; + avatarName: string; + title: string; +}; + +export type InviteSiteYell = { + siteID: string; + siteName: string; + avatarName: string; +}; + +export type TVSiteYell = { + href: string; + title: string; + text: string; +}; + +export type SiteView = { + siteID: string; + isEditable: boolean; + isNew: boolean; + wasNotify: boolean; + siteNotify: string; + siteName: string; + isNetMode: boolean; + avatars: Avatar[]; + siteHand: string; + situationValue: number; + siteYells: SiteYell[]; +}; + +export type Event = { eventID: number; text?: string; data?: ArrayBuffer[] }; + +export type EventHandler = (data: Event) => void; + +export type CloseEventHandler = () => void; + +export type OnAvatarInput = (e: TriggerEvent, avatarID: string) => void; + +export type OnSiteYellInput = (e: TriggerEvent, avatarID: string) => void; diff --git a/qwilight-fe/src/assets/language/en.json b/qwilight-fe/src/assets/language/en.json index 9cc9211..a7b0a59 100644 --- a/qwilight-fe/src/assets/language/en.json +++ b/qwilight-fe/src/assets/language/en.json @@ -1,7 +1,7 @@ { "abilityFittedText": "{stand} Points (+ {ability} Points)", "audioMultiplier": "Music speed", - "autoSignIn": "Automatic login", + "autoLogIn": "Automatic login", "avatarAbilitiesText": "Rating TOP 50", "avatarCountText": "{avatarCount} people", "avatarDate": "Last Connection Date: {date}", @@ -45,8 +45,8 @@ "hallTotalText": "All", "inputNewSite": "Create Chat Room", "notAvatarViewFault": "Non-member profiles are not available.", - "notSignedInText": "Thank you, {avatarName}.", - "notSignIn": "Sign out", + "notLoggedInText": "Thank you, {avatarName}.", + "notLogIn": "Sign out", "onAvatars": "User list.", "onClose": "Clear", "onConfigure": "Preferences", @@ -61,10 +61,10 @@ "setSiteHand": "Delegation of the Director", "setSiteName": "Modify Room Name", "setSiteNameText": "Please enter a name to modify", - "signedInText": "Welcome, {avatarName}.", - "signIn": "Login", - "signInCipher": "Password", - "signInID": "ID", + "loggedInText": "Welcome, {avatarName}.", + "logIn": "Login", + "logInCipher": "Password", + "logInID": "ID", "silentSiteNew": "One-on-one conversation", "siteAudio": "Alarm sound.", "siteAutoEnterDefault": "Automatically enter the regular chat room.", diff --git a/qwilight-fe/src/assets/language/ko.json b/qwilight-fe/src/assets/language/ko.json index 5058085..0aca0f3 100644 --- a/qwilight-fe/src/assets/language/ko.json +++ b/qwilight-fe/src/assets/language/ko.json @@ -1,7 +1,7 @@ { "abilityFittedText": "{stand} 점 (+ {ability} Point)", "audioMultiplier": "음악 속도", - "autoSignIn": "자동 로그인", + "autoLogIn": "자동 로그인", "avatarAbilitiesText": "성과 TOP 50", "avatarCountText": "{avatarCount} 명", "avatarDate": "마지막 접속일: {date}", @@ -45,8 +45,8 @@ "hallTotalText": "전체", "inputNewSite": "대화방 만들기", "notAvatarViewFault": "비회원의 프로필은 제공되지 않습니다.", - "notSignedInText": "{avatarName}님 감사합니다.", - "notSignIn": "로그아웃", + "notLoggedInText": "{avatarName}님 감사합니다.", + "notLogIn": "로그아웃", "onAvatars": "사용자 목록", "onClose": "지우기", "onConfigure": "환경 설정", @@ -61,10 +61,10 @@ "setSiteHand": "방장 위임", "setSiteName": "방 이름 수정", "setSiteNameText": "수정할 이름을 입력하세요", - "signedInText": "{avatarName}님 환영합니다.", - "signIn": "로그인", - "signInCipher": "비밀번호", - "signInID": "아이디", + "loggedInText": "{avatarName}님 환영합니다.", + "logIn": "로그인", + "logInCipher": "비밀번호", + "logInID": "아이디", "silentSiteNew": "1대1 대화", "siteAudio": "알림 사운드", "siteAutoEnterDefault": "일반 대화방 자동 입장", diff --git a/qwilight-fe/src/avatar/AbilitiesView.tsx b/qwilight-fe/src/avatar/AbilitiesView.tsx deleted file mode 100644 index 8949313..0000000 --- a/qwilight-fe/src/avatar/AbilitiesView.tsx +++ /dev/null @@ -1,79 +0,0 @@ -import { GetAvatar } from "@/avatar/useGetAvatar"; -import useGetAvatarAbility from "@/avatar/useGetAvatarAbility"; -import { NoteLoading } from "@/Loading"; -import NoteItem from "@/note/NoteItem"; - -import { useAvatarStore } from "@/Stores"; -import { getAbilityInputMode } from "@/Utility"; -import { observer } from "mobx-react-lite"; -import { useCallback } from "react"; -import { - ListGroup, - Nav, - NavItem, - NavLink, - TabContent, - TabPane, -} from "reactstrap"; - -export default observer(({ avatar: { avatarID } }: { avatar: GetAvatar }) => { - const { abilitiesTabPosition, tabPosition, setAbilitiesTabPosition } = - useAvatarStore(); - - const getProperties = (i: number) => ({ - className: abilitiesTabPosition === i ? "active route" : "route", - onClick: () => { - setAbilitiesTabPosition(i); - }, - }); - - const { isFetched: isAvatarAbilityLoaded, data: avatarAbility } = - useGetAvatarAbility( - getAbilityInputMode(abilitiesTabPosition), - tabPosition === 2 ? avatarID : undefined, - ); - - const AbilityView = useCallback( - ({ tabPosition }: { tabPosition: number }) => { - return ( - <TabPane tabId={tabPosition}> - <ListGroup> - {isAvatarAbilityLoaded ? ( - avatarAbility.map((avatarAbility) => ( - <NoteItem - {...avatarAbility} - key={avatarAbility.noteID} - wantAvatarID={avatarID} - /> - )) - ) : ( - <NoteLoading loadingCount={50} /> - )} - </ListGroup> - </TabPane> - ); - }, - [avatarID, avatarAbility, isAvatarAbilityLoaded], - ); - - return ( - <> - <Nav tabs> - <NavItem> - <NavLink {...getProperties(0)}>⑤K</NavLink> - </NavItem> - <NavItem> - <NavLink {...getProperties(1)}>⑦K</NavLink> - </NavItem> - <NavItem> - <NavLink {...getProperties(2)}>9K</NavLink> - </NavItem> - </Nav> - <TabContent activeTab={abilitiesTabPosition}> - <AbilityView tabPosition={0} /> - <AbilityView tabPosition={1} /> - <AbilityView tabPosition={2} /> - </TabContent> - </> - ); -}); diff --git a/qwilight-fe/src/avatar/DateView.tsx b/qwilight-fe/src/avatar/DateView.tsx deleted file mode 100644 index 51959fd..0000000 --- a/qwilight-fe/src/avatar/DateView.tsx +++ /dev/null @@ -1,65 +0,0 @@ -import { GetAvatar } from "@/avatar/useGetAvatar"; -import { - BarController, - BarElement, - CategoryScale, - Chart, - LinearScale, -} from "chart.js"; -import { useTranslations } from "next-intl"; -import { useEffect, useRef } from "react"; -import { Badge, ListGroup, ListGroupItem } from "reactstrap"; - -export default function DateView({ - avatar: { dateSet, dateValues }, -}: { - avatar: GetAvatar; -}) { - const dateView = useRef<HTMLCanvasElement>(null); - - const t = useTranslations(); - - useEffect(() => { - const dateView2D = dateView.current?.getContext("2d"); - if (dateView2D) { - Chart.register(BarController, BarElement, CategoryScale, LinearScale); - - const view = new Chart(dateView2D, { - type: "bar", - data: { - labels: dateSet, - datasets: [ - { - data: dateValues, - backgroundColor: "white", - }, - ], - }, - options: { - scales: { - x: { - display: false, - }, - y: { - display: false, - }, - }, - }, - }); - - return () => { - view.destroy(); - Chart.unregister(BarController, BarElement, CategoryScale, LinearScale); - }; - } - }, [dateSet, dateValues]); - - return ( - <ListGroup> - <Badge>{t("avatarDateText")}</Badge> - <ListGroupItem> - <canvas ref={dateView} /> - </ListGroupItem> - </ListGroup> - ); -} diff --git a/qwilight-fe/src/avatar/FavoritesView.tsx b/qwilight-fe/src/avatar/FavoritesView.tsx deleted file mode 100644 index b987c80..0000000 --- a/qwilight-fe/src/avatar/FavoritesView.tsx +++ /dev/null @@ -1,99 +0,0 @@ -import { GetAvatar } from "@/avatar/useGetAvatar"; -import useGetAvatarFavorites from "@/avatar/useGetAvatarFavorites"; -import { NoteLoading } from "@/Loading"; -import NoteItem from "@/note/NoteItem"; - -import { useAvatarStore } from "@/Stores"; -import { getInputMode } from "@/Utility"; -import { observer } from "mobx-react-lite"; -import { useCallback } from "react"; -import { - ListGroup, - Nav, - NavItem, - NavLink, - TabContent, - TabPane, -} from "reactstrap"; - -export default observer(({ avatar: { avatarID } }: { avatar: GetAvatar }) => { - const { tabPosition, favoritesTabPosition, setFavoritesTabPosition } = - useAvatarStore(); - - const { isFetched: isAvatarFavoritesLoaded, data: avatarFavorites } = - useGetAvatarFavorites( - getInputMode(favoritesTabPosition), - tabPosition === 0 ? avatarID : undefined, - ); - - const getProperties = (i: number) => ({ - className: favoritesTabPosition === i ? "active route" : "route", - onClick: () => { - setFavoritesTabPosition(i); - }, - }); - - const FavoriteView = useCallback( - ({ tabPosition }: { tabPosition: number }) => { - return ( - <TabPane tabId={tabPosition}> - <ListGroup> - {isAvatarFavoritesLoaded ? ( - avatarFavorites.map((avatarFavorite) => ( - <NoteItem - {...avatarFavorite} - key={avatarFavorite.noteID} - wantAvatarID={avatarID} - /> - )) - ) : ( - <NoteLoading loadingCount={50} /> - )} - </ListGroup> - </TabPane> - ); - }, - [avatarFavorites, isAvatarFavoritesLoaded], - ); - - return ( - <> - <Nav tabs> - <NavItem> - <NavLink {...getProperties(0)}>6K</NavLink> - </NavItem> - <NavItem> - <NavLink {...getProperties(1)}>⑤K</NavLink> - </NavItem> - <NavItem> - <NavLink {...getProperties(2)}>⑦K</NavLink> - </NavItem> - <NavItem> - <NavLink {...getProperties(3)}>9K</NavLink> - </NavItem> - <NavItem> - <NavLink {...getProperties(4)}>⑩K</NavLink> - </NavItem> - <NavItem> - <NavLink {...getProperties(5)}>⑭K</NavLink> - </NavItem> - <NavItem> - <NavLink {...getProperties(6)}>24</NavLink> - </NavItem> - <NavItem> - <NavLink {...getProperties(7)}>48</NavLink> - </NavItem> - </Nav> - <TabContent activeTab={favoritesTabPosition}> - <FavoriteView tabPosition={0} /> - <FavoriteView tabPosition={1} /> - <FavoriteView tabPosition={2} /> - <FavoriteView tabPosition={3} /> - <FavoriteView tabPosition={4} /> - <FavoriteView tabPosition={5} /> - <FavoriteView tabPosition={6} /> - <FavoriteView tabPosition={7} /> - </TabContent> - </> - ); -}); diff --git a/qwilight-fe/src/avatar/IntroView.tsx b/qwilight-fe/src/avatar/IntroView.tsx deleted file mode 100644 index c54023b..0000000 --- a/qwilight-fe/src/avatar/IntroView.tsx +++ /dev/null @@ -1,24 +0,0 @@ -import { GetAvatar } from "@/avatar/useGetAvatar"; -import { useTranslations } from "next-intl"; -import { Badge, ListGroup, ListGroupItem } from "reactstrap"; - -export default function IntroView({ - avatar: { avatarIntro }, -}: { - avatar: GetAvatar; -}) { - const t = useTranslations(); - - if (!avatarIntro) { - return null; - } - - return ( - <ListGroup> - <Badge>{t("avatarIntroText")}</Badge> - <ListGroupItem> - <span className="avatarIntro">{avatarIntro}</span> - </ListGroupItem> - </ListGroup> - ); -} diff --git a/qwilight-fe/src/avatar/LastsView.tsx b/qwilight-fe/src/avatar/LastsView.tsx deleted file mode 100644 index a550465..0000000 --- a/qwilight-fe/src/avatar/LastsView.tsx +++ /dev/null @@ -1,99 +0,0 @@ -import { GetAvatar } from "@/avatar/useGetAvatar"; -import useGetAvatarLasts from "@/avatar/useGetAvatarLasts"; -import { NoteLoading } from "@/Loading"; -import NoteItem from "@/note/NoteItem"; - -import { useAvatarStore } from "@/Stores"; -import { getInputMode } from "@/Utility"; -import { observer } from "mobx-react-lite"; -import { useCallback } from "react"; -import { - ListGroup, - Nav, - NavItem, - NavLink, - TabContent, - TabPane, -} from "reactstrap"; - -export default observer(({ avatar: { avatarID } }: { avatar: GetAvatar }) => { - const { tabPosition, lastsTabPosition, setLastsTabPosition } = - useAvatarStore(); - - const { isFetched: isAvatarLastsLoaded, data: avatarLasts } = - useGetAvatarLasts( - getInputMode(lastsTabPosition), - tabPosition === 1 ? avatarID : undefined, - ); - - const getProperties = (i: number) => ({ - className: lastsTabPosition === i ? "active route" : "route", - onClick: () => { - setLastsTabPosition(i); - }, - }); - - const LastView = useCallback( - ({ tabPosition }: { tabPosition: number }) => { - return ( - <TabPane tabId={tabPosition}> - <ListGroup> - {isAvatarLastsLoaded ? ( - avatarLasts.map((avatarLast) => ( - <NoteItem - {...avatarLast} - key={avatarLast.noteID} - wantAvatarID={avatarID} - /> - )) - ) : ( - <NoteLoading loadingCount={50} /> - )} - </ListGroup> - </TabPane> - ); - }, - [avatarID, avatarLasts, isAvatarLastsLoaded], - ); - - return ( - <> - <Nav tabs> - <NavItem> - <NavLink {...getProperties(0)}>6K</NavLink> - </NavItem> - <NavItem> - <NavLink {...getProperties(1)}>⑤K</NavLink> - </NavItem> - <NavItem> - <NavLink {...getProperties(2)}>⑦K</NavLink> - </NavItem> - <NavItem> - <NavLink {...getProperties(3)}>9K</NavLink> - </NavItem> - <NavItem> - <NavLink {...getProperties(4)}>⑩K</NavLink> - </NavItem> - <NavItem> - <NavLink {...getProperties(5)}>⑭K</NavLink> - </NavItem> - <NavItem> - <NavLink {...getProperties(6)}>24</NavLink> - </NavItem> - <NavItem> - <NavLink {...getProperties(7)}>48</NavLink> - </NavItem> - </Nav> - <TabContent activeTab={lastsTabPosition}> - <LastView tabPosition={0} /> - <LastView tabPosition={1} /> - <LastView tabPosition={2} /> - <LastView tabPosition={3} /> - <LastView tabPosition={4} /> - <LastView tabPosition={5} /> - <LastView tabPosition={6} /> - <LastView tabPosition={7} /> - </TabContent> - </> - ); -}); diff --git a/qwilight-fe/src/avatar/QuitStatusValues.tsx b/qwilight-fe/src/avatar/QuitStatusValues.tsx deleted file mode 100644 index 9e90a57..0000000 --- a/qwilight-fe/src/avatar/QuitStatusValues.tsx +++ /dev/null @@ -1,25 +0,0 @@ -import { GetAvatar } from "@/avatar/useGetAvatar"; -import { useTranslations } from "next-intl"; -import { Badge, ListGroup, ListGroupItem } from "reactstrap"; - -const quitItems = ["S+", "S", "A+", "A", "B", "C", "D"] as const; - -export default function QuitStatusValues({ - avatar: { quitStatusValues }, -}: { - avatar: GetAvatar; -}) { - const t = useTranslations(); - - return ( - <ListGroup> - <Badge>{t("avatarQuitStatusText")}</Badge> - {quitItems.map((quitItem) => ( - <ListGroupItem key={quitItem}> - <span className={quitItem}>{quitItem}</span>{" "} - <span>{quitStatusValues[quitItems.indexOf(quitItem)]}</span> - </ListGroupItem> - ))} - </ListGroup> - ); -} diff --git a/qwilight-fe/src/avatar/WwwLevelItem.tsx b/qwilight-fe/src/avatar/WwwLevelItem.tsx deleted file mode 100644 index e86cdfe..0000000 --- a/qwilight-fe/src/avatar/WwwLevelItem.tsx +++ /dev/null @@ -1,20 +0,0 @@ -import { toDate } from "@/Utility"; -import { GetAvatarWwwLevelsAPI } from "@/wwwAPI"; -import { Col, ListGroupItem, Row } from "reactstrap"; - -export default function WwwLevelItem({ - title, - date, -}: GetAvatarWwwLevelsAPI[number]) { - return ( - <ListGroupItem> - <Row className="g-0"> - <Col className="m-1" xs="auto"> - <span>{title}</span> - <br /> - {date && <span className="fittedText">{toDate(date)}</span>} - </Col> - </Row> - </ListGroupItem> - ); -} diff --git a/qwilight-fe/src/avatar/WwwLevelsView.tsx b/qwilight-fe/src/avatar/WwwLevelsView.tsx deleted file mode 100644 index 0166c1b..0000000 --- a/qwilight-fe/src/avatar/WwwLevelsView.tsx +++ /dev/null @@ -1,34 +0,0 @@ -import { GetAvatar } from "@/avatar/useGetAvatar"; -import useGetAvatarWwwLevels from "@/avatar/useGetAvatarWwwLevels"; - -import WwwLevelItem from "@/avatar/WwwLevelItem"; -import { WwwLevelLoading } from "@/Loading"; -import { useAvatarStore } from "@/Stores"; -import { observer } from "mobx-react-lite"; -import { ListGroup } from "reactstrap"; - -export default observer(({ avatar: { avatarID } }: { avatar: GetAvatar }) => { - const { tabPosition } = useAvatarStore(); - - const { isFetched: isAvatarWwwLevelsLoaded, data: avatarWwwLevels } = - useGetAvatarWwwLevels(tabPosition === 3 ? avatarID : undefined); - - return ( - <ListGroup> - {isAvatarWwwLevelsLoaded ? ( - avatarWwwLevels.map(({ levelID, title, levelText, level, date }) => ( - <WwwLevelItem - key={levelID} - levelID={levelID} - title={title} - levelText={levelText} - level={level} - date={date} - /> - )) - ) : ( - <WwwLevelLoading loadingCount={1} /> - )} - </ListGroup> - ); -}); diff --git a/qwilight-fe/src/avatar/setAvatarStore.ts b/qwilight-fe/src/avatar/setAvatarStore.ts deleted file mode 100644 index 2fd48c0..0000000 --- a/qwilight-fe/src/avatar/setAvatarStore.ts +++ /dev/null @@ -1,29 +0,0 @@ -export default function setAvatarStore() { - return { - input: "", - tabPosition: 0, - favoritesTabPosition: 0, - lastsTabPosition: 0, - abilitiesTabPosition: 0, - - setInput(input: string) { - this.input = input; - }, - - setTabPosition(tabPosition: number) { - this.tabPosition = tabPosition; - }, - - setFavoritesTabPosition(favoritesTabPosition: number) { - this.favoritesTabPosition = favoritesTabPosition; - }, - - setLastsTabPosition(lastsTabPosition: number) { - this.lastsTabPosition = lastsTabPosition; - }, - - setAbilitiesTabPosition(abilitiesTabPosition: number) { - this.abilitiesTabPosition = abilitiesTabPosition; - }, - }; -} diff --git a/qwilight-fe/src/avatar/useGetAvatar.ts b/qwilight-fe/src/avatar/useGetAvatar.ts deleted file mode 100644 index 3adc068..0000000 --- a/qwilight-fe/src/avatar/useGetAvatar.ts +++ /dev/null @@ -1,88 +0,0 @@ -import { formatText, toDate } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { AvatarAPIAvatar, AvatarAPIWantAvatar } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useTranslations } from "next-intl"; -import { useIsPath, useWant } from "taehui-ts/fe-utility"; - -export type GetAvatar = { - avatarID: string; - avatarName: string; - avatarIntro: string; - totalCount: string; - totalLength: string; - highestCount: string; - date: string; - avatarLevels: number[]; - avatarAbility5KText: string; - avatarAbility5KClass: number; - avatarAbility5KPlace: number; - avatarAbility5KPlaceText: string; - avatarAbility5KCountText: string; - avatarAbility7KText: string; - avatarAbility7KClass: number; - avatarAbility7KPlace: number; - avatarAbility7KPlaceText: string; - avatarAbility7KCountText: string; - avatarAbility9KText: string; - avatarAbility9KClass: number; - avatarAbility9KPlace: number; - avatarAbility9KPlaceText: string; - avatarAbility9KCountText: string; - dateSet: number[]; - dateValues: number[]; - quitStatusValues: number[]; -}; - -export default function useGetAvatar() { - const { want } = useWant("/avatar"); - - const t = useTranslations(); - - const isPath = useIsPath(); - - return useQuery<AvatarAPIWantAvatar[] | GetAvatar>({ - enabled: !!want && isPath("/avatar"), - queryKey: ["avatar", want], - queryFn: async () => { - const { data } = await wwwAXIOS.get< - AvatarAPIWantAvatar[] | AvatarAPIAvatar - >("/avatar", { - params: want.startsWith("!") - ? { - avatarID: want.substring(want.indexOf("!") + 1), - } - : { - avatarName: want, - }, - }); - - if (Array.isArray(data)) { - return data; - } else { - return { - ...data, - totalCount: formatText(data.totalCount), - totalLength: t("totalLengthText", { - h: Math.floor(data.totalLength / 1000 / 60 / 60), - m: Math.floor((data.totalLength / 1000 / 60) % 60), - s: Math.floor((data.totalLength / 1000) % 60), - }), - highestCount: formatText(data.highestCount), - date: toDate(data.date), - avatarAbility5KText: formatText(data.avatarAbility5K), - avatarAbility5KPlaceText: formatText(data.avatarAbility5KPlace), - avatarAbility5KCountText: formatText(data.avatarAbility5KCount), - avatarAbility7KText: formatText(data.avatarAbility7K), - avatarAbility7KPlaceText: formatText(data.avatarAbility7KPlace), - avatarAbility7KCountText: formatText(data.avatarAbility7KCount), - avatarAbility9KText: formatText(data.avatarAbility9K), - avatarAbility9KPlaceText: formatText(data.avatarAbility9KPlace), - avatarAbility9KCountText: formatText(data.avatarAbility9KCount), - }; - } - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/avatar/useGetAvatarAbility.ts b/qwilight-fe/src/avatar/useGetAvatarAbility.ts deleted file mode 100644 index 2292bcc..0000000 --- a/qwilight-fe/src/avatar/useGetAvatarAbility.ts +++ /dev/null @@ -1,37 +0,0 @@ -import { formatText } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { GetAvatarAbilitiesAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useTranslations } from "next-intl"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetAvatarAbility( - inputMode: "5K" | "7K" | "9K", - avatarID?: string, -) { - const t = useTranslations(); - - const isPath = useIsPath(); - - return useQuery({ - enabled: !!avatarID && isPath("/avatar"), - queryKey: ["avatarAbility", inputMode, avatarID], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetAvatarAbilitiesAPI>( - `/avatar/ability/${inputMode}`, - { - params: { avatarID }, - }, - ); - return data.map((data) => ({ - ...data, - fittedText: t("abilityFittedText", { - stand: formatText(data.stand), - ability: formatText(data.ability), - }), - })); - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/avatar/useGetAvatarFavorites.ts b/qwilight-fe/src/avatar/useGetAvatarFavorites.ts deleted file mode 100644 index f6cc5d0..0000000 --- a/qwilight-fe/src/avatar/useGetAvatarFavorites.ts +++ /dev/null @@ -1,34 +0,0 @@ -import { formatText } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { GetAvatarFavoritesAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useTranslations } from "next-intl"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetAvatarFavorites( - inputMode: "6K" | "5K" | "7K" | "9K" | "10K" | "14K" | "24K" | "48K", - avatarID?: string, -) { - const isPath = useIsPath(); - - const t = useTranslations(); - - return useQuery({ - enabled: !!avatarID && isPath("/avatar"), - queryKey: ["avatarFavorites", inputMode, avatarID], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetAvatarFavoritesAPI>( - `/avatar/favorites/${inputMode}`, - { - params: { avatarID }, - }, - ); - return data.map((data) => ({ - ...data, - fittedText: t("textHandled", { value: formatText(data.totalCount) }), - })); - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/avatar/useGetAvatarLasts.ts b/qwilight-fe/src/avatar/useGetAvatarLasts.ts deleted file mode 100644 index 6355911..0000000 --- a/qwilight-fe/src/avatar/useGetAvatarLasts.ts +++ /dev/null @@ -1,28 +0,0 @@ -import { toDate } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { GetAvatarLastsAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetAvatarLasts( - inputMode: "6K" | "5K" | "7K" | "9K" | "10K" | "14K" | "24K" | "48K", - avatarID?: string, -) { - const isPath = useIsPath(); - - return useQuery({ - enabled: !!avatarID && isPath("/avatar"), - queryKey: ["avatarLasts", inputMode, avatarID], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetAvatarLastsAPI>( - `/avatar/lasts/${inputMode}`, - { - params: { avatarID }, - }, - ); - return data.map((data) => ({ ...data, fittedText: toDate(data.date) })); - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/avatar/useGetAvatarWwwLevels.ts b/qwilight-fe/src/avatar/useGetAvatarWwwLevels.ts deleted file mode 100644 index 63cb31e..0000000 --- a/qwilight-fe/src/avatar/useGetAvatarWwwLevels.ts +++ /dev/null @@ -1,23 +0,0 @@ -import { wwwAXIOS } from "@/Www"; -import { GetAvatarWwwLevelsAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetAvatarWwwLevels(avatarID?: string) { - const isPath = useIsPath(); - - return useQuery({ - enabled: !!avatarID && isPath("/avatar"), - queryKey: ["avatarWwwLevels", avatarID], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetAvatarWwwLevelsAPI>( - "/avatar/wwwLevels", - { - params: { avatarID }, - }, - ); - return data; - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/components/AvatarDrawing.module.scss b/qwilight-fe/src/components/AvatarDrawing.module.scss new file mode 100644 index 0000000..596d6c8 --- /dev/null +++ b/qwilight-fe/src/components/AvatarDrawing.module.scss @@ -0,0 +1,16 @@ +div { + &.drawing { + position: relative; + } +} + +img { + &.avatar { + position: absolute; + } + + &.edge { + position: absolute; + border: none; + } +} diff --git a/qwilight-fe/src/components/AvatarDrawing.tsx b/qwilight-fe/src/components/AvatarDrawing.tsx new file mode 100644 index 0000000..4dc007f --- /dev/null +++ b/qwilight-fe/src/components/AvatarDrawing.tsx @@ -0,0 +1,51 @@ +import scss from "@/components/AvatarDrawing.module.scss"; +import { getDefaultAvatarID } from "@/utilities/Utility"; +import { wwwAPIPath } from "@/utilities/wwwAPI"; +import Image from "next/image"; + +const EDGE_MARGIN = 1.25; +const EDGE_XY = (EDGE_MARGIN - 1.0) / 2; + +export default function AvatarDrawing({ + avatarID, + drawingLength = 48, + drawingHeight = 48, +}: { + avatarID: string; + drawingLength?: number; + drawingHeight?: number; +}) { + return ( + <div + className={scss.drawing} + style={{ + width: drawingLength * EDGE_MARGIN, + height: drawingHeight * EDGE_MARGIN, + }} + > + <Image + alt="" + src={`${wwwAPIPath}/drawing?avatarID=${encodeURIComponent( + getDefaultAvatarID(avatarID), + )}&drawingVariety=0`} + className={scss.avatar} + width={drawingLength} + height={drawingHeight} + style={{ + left: drawingLength * EDGE_XY, + top: drawingHeight * EDGE_XY, + }} + /> + <Image + alt="" + src={`${wwwAPIPath}/drawing?avatarID=${encodeURIComponent( + getDefaultAvatarID(avatarID), + )}&drawingVariety=2`} + className={scss.edge} + width={drawingLength * EDGE_MARGIN} + height={drawingHeight * EDGE_MARGIN} + onError={(e) => (e.currentTarget.hidden = true)} + /> + </div> + ); +} diff --git a/qwilight-fe/src/components/AvatarTitle.tsx b/qwilight-fe/src/components/AvatarTitle.tsx new file mode 100644 index 0000000..9d86510 --- /dev/null +++ b/qwilight-fe/src/components/AvatarTitle.tsx @@ -0,0 +1,15 @@ +import Title from "@/components/Title"; +import useGetTitle from "@/query/useGetTitle"; + +export default function AvatarTitle({ avatarID }: { avatarID: string }) { + const { + data: { title, titleColor }, + isFetched: isTitleLoaded, + } = useGetTitle(avatarID); + + if (!isTitleLoaded) { + return null; + } + + return <Title title={title} titleColor={titleColor} />; +} diff --git a/qwilight-fe/src/components/Loading.tsx b/qwilight-fe/src/components/Loading.tsx new file mode 100644 index 0000000..37b84cd --- /dev/null +++ b/qwilight-fe/src/components/Loading.tsx @@ -0,0 +1,43 @@ +import AvatarDrawing from "@/components/AvatarDrawing"; +import { Col, ListGroupItem, Row } from "reactstrap"; + +export const NoteLoading = ({ loadingCount }: { loadingCount: number }) => { + return [...Array(loadingCount).keys()].map((i) => ( + <ListGroupItem key={i}> + <Row className="g-0"> + <Col className="m-1" xs="auto"> + <span className="title">Loading...</span> + <br /> + <br /> + </Col> + </Row> + </ListGroupItem> + )); +}; + +export const WwwLevelLoading = ({ loadingCount }: { loadingCount: number }) => { + return [...Array(loadingCount).keys()].map((i) => ( + <ListGroupItem key={i}> + <Row className="g-0"> + <Col className="m-1" xs="auto"> + <span>Loading...</span> + </Col> + </Row> + </ListGroupItem> + )); +}; + +export const AvatarLoading = ({ loadingCount }: { loadingCount: number }) => { + return [...Array(loadingCount).keys()].map((i) => ( + <ListGroupItem key={i}> + <Row className="g-0"> + <Col className="m-1" xs="auto"> + <AvatarDrawing avatarID="" /> + </Col> + <Col className="m-1" xs="auto"> + <span>Loading...</span> + </Col> + </Row> + </ListGroupItem> + )); +}; diff --git a/qwilight-fe/src/components/LoadingLayer.tsx b/qwilight-fe/src/components/LoadingLayer.tsx new file mode 100644 index 0000000..7740746 --- /dev/null +++ b/qwilight-fe/src/components/LoadingLayer.tsx @@ -0,0 +1,17 @@ +import BarLoader from "react-spinners/BarLoader"; +import { Badge, Col, ListGroup, ListGroupItem, Row } from "reactstrap"; + +export default function LoadingLayer({ text }: { text: string }) { + return ( + <Row className="g-0"> + <Col className="m-1"> + <ListGroup> + <Badge>{text}</Badge> + <ListGroupItem> + <BarLoader width="100%" color="#36d7b7" /> + </ListGroupItem> + </ListGroup> + </Col> + </Row> + ); +} diff --git a/qwilight-fe/src/components/QwilightView.tsx b/qwilight-fe/src/components/QwilightView.tsx new file mode 100644 index 0000000..8e44815 --- /dev/null +++ b/qwilight-fe/src/components/QwilightView.tsx @@ -0,0 +1,83 @@ +"use client"; + +import LogInWindow from "@/app/[language]/site/components/LogInWindow"; +import useSiteComponent from "@/app/[language]/site/query/useSiteComponent"; +import platform from "@/assets/discord-logo-white.png"; +import withQueryClient from "@/hoc/withQueryClient"; +import { useSiteStore } from "@/store/Stores"; +import { useTranslations } from "next-intl"; +import Image from "next/image"; +import Link from "next/link"; +import { ReactNode, useEffect, useRef } from "react"; +import { ToastContainer } from "react-toastify"; +import { Button, Col, Container, Navbar, NavbarBrand, Row } from "reactstrap"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default withQueryClient(({ children }: { children: ReactNode }) => { + const t = useTranslations(); + const titleComponent = useRef<HTMLDivElement>(null); + const siteYellsView = useRef<HTMLDivElement>(null); + const { setComponents } = useSiteStore(); + + useSiteComponent(); + + const isPath = useIsPath(); + + const getColor = (route: string) => (isPath(route) ? "primary" : "secondary"); + + const onPlatform = () => { + window.open("https://taehui.ddns.net/qwilight/platform"); + }; + + useEffect(() => { + setComponents(titleComponent, siteYellsView); + }, [setComponents]); + + return ( + <> + <div ref={titleComponent}> + <Navbar> + <NavbarBrand href="/"> + <Image alt="" width={48} height={48} src="/qwilight/favicon.ico" /> + </NavbarBrand> + <Row className="g-0"> + <Col className="m-1" xs="auto"> + <Link href={"/note"}> + <Button color={getColor("/note")}>{t("toNote")}</Button> + </Link> + </Col> + <Col className="m-1" xs="auto"> + <Link href={"/site"}> + <Button color={getColor("/site")}>{t("toSite")}</Button> + </Link> + </Col> + <Col className="m-1" xs="auto"> + <Link href={"/avatar"}> + <Button color={getColor("/avatar")}>{t("toAvatar")}</Button> + </Link> + </Col> + <Col className="m-1" xs="auto"> + <Link href={"/hall"}> + <Button color={getColor("/hall")}>{t("toHall")}</Button> + </Link> + </Col> + <Col className="m-1" xs="auto"> + <Link href={"/etc"}> + <Button color={getColor("/etc")}>{t("toEtc")}</Button> + </Link> + </Col> + <Col className="m-1" xs="auto"> + <Button color="danger" onClick={onPlatform}> + <Image alt="" height={12} src={platform} /> + </Button> + </Col> + </Row> + </Navbar> + </div> + <Container>{children}</Container> + + <ToastContainer theme="dark" closeButton={false} hideProgressBar /> + <LogInWindow /> + </> + ); +}); diff --git a/qwilight-fe/src/components/Title.tsx b/qwilight-fe/src/components/Title.tsx new file mode 100644 index 0000000..5462e49 --- /dev/null +++ b/qwilight-fe/src/components/Title.tsx @@ -0,0 +1,32 @@ +import { useMemo } from "react"; + +export default function Title({ + title, + titleColor, +}: { + title: string; + titleColor: string; +}) { + const isLevel = useMemo( + () => + [ + "level0", + "level1", + "level2", + "level3", + "level4", + "level5", + "titleLV2000", + ].includes(titleColor), + [titleColor], + ); + + return ( + <span + className={isLevel ? titleColor : undefined} + style={isLevel ? undefined : { color: titleColor }} + > + {title ? `${title} ` : ""} + </span> + ); +} diff --git a/qwilight-fe/src/etc/DateView.tsx b/qwilight-fe/src/etc/DateView.tsx deleted file mode 100644 index e5fd885..0000000 --- a/qwilight-fe/src/etc/DateView.tsx +++ /dev/null @@ -1,69 +0,0 @@ -import { - BarController, - BarElement, - CategoryScale, - Chart, - LinearScale, - LineController, -} from "chart.js"; -import { observer } from "mobx-react-lite"; -import { useEffect, useRef } from "react"; -import { Badge, ListGroup, ListGroupItem } from "reactstrap"; - -export default observer<{ - title: string; - dateSet: string[]; - dateValues: number[]; -}>(({ title, dateSet, dateValues }) => { - const dateView = useRef<HTMLCanvasElement>(null); - - useEffect(() => { - const view2D = dateView.current?.getContext("2d"); - if (view2D) { - Chart.register( - LineController, - BarController, - BarElement, - CategoryScale, - LinearScale, - ); - - const view = new Chart(view2D, { - type: "bar", - data: { - labels: dateSet, - datasets: [ - { - data: dateValues, - backgroundColor: "white", - }, - ], - }, - options: { - scales: { - x: { - display: false, - }, - y: { - display: false, - }, - }, - }, - }); - - return () => { - view.destroy(); - Chart.unregister(BarController, BarElement, CategoryScale, LinearScale); - }; - } - }, [dateSet, dateValues]); - - return ( - <ListGroup> - <Badge color="primary">{title}</Badge> - <ListGroupItem> - <canvas ref={dateView} /> - </ListGroupItem> - </ListGroup> - ); -}); diff --git a/qwilight-fe/src/etc/EdgeItem.tsx b/qwilight-fe/src/etc/EdgeItem.tsx deleted file mode 100644 index b73b0ca..0000000 --- a/qwilight-fe/src/etc/EdgeItem.tsx +++ /dev/null @@ -1,28 +0,0 @@ -import Image from "next/image"; -import { Col, ListGroupItem, Row } from "reactstrap"; - -export default function EdgeItem({ - edge, - text, -}: { - edge: string; - text: string; -}) { - return ( - <ListGroupItem> - <Row className="g-0"> - <Col className="m-1" xs="auto"> - <Image - alt="" - src={`data:image/png;base64,${edge}`} - width={60} - height={60} - /> - </Col> - <Col className="m-1" xs="auto"> - <span>{text}</span> - </Col> - </Row> - </ListGroupItem> - ); -} diff --git a/qwilight-fe/src/etc/FavoritesView.tsx b/qwilight-fe/src/etc/FavoritesView.tsx deleted file mode 100644 index 231981a..0000000 --- a/qwilight-fe/src/etc/FavoritesView.tsx +++ /dev/null @@ -1,31 +0,0 @@ -import NoteItem from "@/note/NoteItem"; -import { EtcAPINoteFile } from "@/wwwAPI"; -import { Badge, ListGroup } from "reactstrap"; - -export default function FavoritesView({ - title, - favorites, -}: { - title: string; - favorites: EtcAPINoteFile[]; -}) { - return ( - <ListGroup> - <Badge>{title}</Badge> - {favorites.map( - ({ noteID, artist, title, genre, levelText, level, value }) => ( - <NoteItem - key={noteID} - noteID={noteID} - artist={artist} - title={title} - genre={genre} - levelText={levelText} - level={level} - fittedText={`👍 ${value}`} - /> - ), - )} - </ListGroup> - ); -} diff --git a/qwilight-fe/src/etc/ModeItem.module.scss b/qwilight-fe/src/etc/ModeItem.module.scss deleted file mode 100644 index 8a57304..0000000 --- a/qwilight-fe/src/etc/ModeItem.module.scss +++ /dev/null @@ -1,5 +0,0 @@ -img { - &.mode { - height: 1.5rem; - } -} diff --git a/qwilight-fe/src/etc/ModeItem.tsx b/qwilight-fe/src/etc/ModeItem.tsx deleted file mode 100644 index 8526c89..0000000 --- a/qwilight-fe/src/etc/ModeItem.tsx +++ /dev/null @@ -1,41 +0,0 @@ -import scss from "@/etc/ModeItem.module.scss"; - -import { formatText } from "@/Utility"; -import { EtcAPIMode } from "@/wwwAPI"; -import { useTranslations } from "next-intl"; -import Image, { StaticImageData } from "next/image"; -import { Badge, Col, ListGroup, ListGroupItem, Row } from "reactstrap"; - -export default function ModeItem({ - title, - modes, - drawings, -}: { - title: string; - modes: EtcAPIMode[]; - drawings: (string | StaticImageData)[]; -}) { - const t = useTranslations(); - - return ( - <ListGroup> - <Badge color="success">{title}</Badge> - {modes.map(({ mode, value }) => { - return ( - value > 0 && ( - <ListGroupItem key={mode}> - <Row className="g-0"> - <Col className="m-1"> - <Image className={scss.mode} alt="" src={drawings[mode]} /> - </Col> - <Col className="m-1" xs="auto"> - <span>{t("textHandled", { value: formatText(value) })}</span> - </Col> - </Row> - </ListGroupItem> - ) - ); - })} - </ListGroup> - ); -} diff --git a/qwilight-fe/src/etc/TitleItem.tsx b/qwilight-fe/src/etc/TitleItem.tsx deleted file mode 100644 index d4bdaba..0000000 --- a/qwilight-fe/src/etc/TitleItem.tsx +++ /dev/null @@ -1,24 +0,0 @@ -import Title from "@/Title"; -import { Col, ListGroupItem, Row } from "reactstrap"; - -export default function TitleItem({ - title, - titleColor, - text, -}: { - title: string; - titleColor: string; - text: string; -}) { - return ( - <ListGroupItem> - <Row className="g-0"> - <Col className="m-1" xs="auto"> - <Title title={title} titleColor={titleColor} /> - <br /> - <span>{text}</span> - </Col> - </Row> - </ListGroupItem> - ); -} diff --git a/qwilight-fe/src/etc/TotalEdgesView.tsx b/qwilight-fe/src/etc/TotalEdgesView.tsx deleted file mode 100644 index 09141ef..0000000 --- a/qwilight-fe/src/etc/TotalEdgesView.tsx +++ /dev/null @@ -1,25 +0,0 @@ -import EdgeItem from "@/etc/EdgeItem"; -import { EtcAPIEdge } from "@/wwwAPI"; -import { useTranslations } from "next-intl"; -import { Badge, ListGroup } from "reactstrap"; - -export default function TotalEdgesView({ - totalEdges, -}: { - totalEdges: EtcAPIEdge[]; -}) { - const t = useTranslations(); - - return ( - <ListGroup> - <Badge>{t("etcTotalEdges")}</Badge> - {totalEdges.map(({ edge, value }) => ( - <EdgeItem - key={edge} - edge={edge} - text={t("avatarCountText", { avatarCount: value })} - /> - ))} - </ListGroup> - ); -} diff --git a/qwilight-fe/src/etc/TotalNoteFilesView.tsx b/qwilight-fe/src/etc/TotalNoteFilesView.tsx deleted file mode 100644 index 235cb9a..0000000 --- a/qwilight-fe/src/etc/TotalNoteFilesView.tsx +++ /dev/null @@ -1,32 +0,0 @@ -import NoteItem from "@/note/NoteItem"; -import { EtcAPINoteFile } from "@/wwwAPI"; -import { useTranslations } from "next-intl"; -import { Badge, ListGroup } from "reactstrap"; - -export default function TotalNoteFilesView({ - totalNoteFiles, -}: { - totalNoteFiles: EtcAPINoteFile[]; -}) { - const t = useTranslations(); - - return ( - <ListGroup> - <Badge>{t("etcTotalNoteFiles")}</Badge> - {totalNoteFiles.map( - ({ noteID, artist, title, genre, levelText, level, value }) => ( - <NoteItem - key={noteID} - noteID={noteID} - artist={artist} - title={title} - genre={genre} - levelText={levelText} - level={level} - fittedText={t("textHandled", { value })} - /> - ), - )} - </ListGroup> - ); -} diff --git a/qwilight-fe/src/etc/TotalTitlesView.tsx b/qwilight-fe/src/etc/TotalTitlesView.tsx deleted file mode 100644 index 1129ceb..0000000 --- a/qwilight-fe/src/etc/TotalTitlesView.tsx +++ /dev/null @@ -1,26 +0,0 @@ -import TitleItem from "@/etc/TitleItem"; -import { EtcAPITitle } from "@/wwwAPI"; -import { useTranslations } from "next-intl"; -import { Badge, ListGroup } from "reactstrap"; - -export default function TotalTitlesView({ - totalTitles, -}: { - totalTitles: EtcAPITitle[]; -}) { - const t = useTranslations(); - - return ( - <ListGroup> - <Badge>{t("etcTotalTitles")}</Badge> - {totalTitles.map(({ title, titleColor, value }) => ( - <TitleItem - key={title} - title={title} - titleColor={titleColor} - text={t("avatarCountText", { avatarCount: value })} - /> - ))} - </ListGroup> - ); -} diff --git a/qwilight-fe/src/etc/setEtcStore.ts b/qwilight-fe/src/etc/setEtcStore.ts deleted file mode 100644 index cdfd017..0000000 --- a/qwilight-fe/src/etc/setEtcStore.ts +++ /dev/null @@ -1,3 +0,0 @@ -export default function setEtcStore() { - return {}; -} diff --git a/qwilight-fe/src/etc/useGetEtc.ts b/qwilight-fe/src/etc/useGetEtc.ts deleted file mode 100644 index a501913..0000000 --- a/qwilight-fe/src/etc/useGetEtc.ts +++ /dev/null @@ -1,45 +0,0 @@ -import { wwwAXIOS } from "@/Www"; -import { GetEtcAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useIsPath } from "taehui-ts/fe-utility"; -import { getLanguage } from "taehui-ts/language"; - -export default function useGetEtc() { - const isPath = useIsPath(); - - const language = getLanguage(); - return useQuery({ - enabled: isPath("/etc"), - queryKey: ["etc"], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetEtcAPI>("/etc", { - params: { language }, - }); - return data; - }, - initialData: { - totalDateSet: [], - totalDateValues: [], - signUpDateSet: [], - signUpDateValues: [], - avatarDateSet: [], - avatarDateValues: [], - totalNoteFiles: [], - totalTitles: [], - totalEdges: [], - favorites: [], - favoritesAt: [], - inputModes: [], - autoModes: [], - noteSaltModes: [], - faintNoteModes: [], - judgmentModes: [], - hitPointsModes: [], - noteMobilityModes: [], - longNoteModes: [], - inputFavorModes: [], - noteModifyModes: [], - lowestJudgmentConditionModes: [], - }, - }); -} diff --git a/qwilight-fe/src/hall/AvatarItem.tsx b/qwilight-fe/src/hall/AvatarItem.tsx deleted file mode 100644 index 76c6809..0000000 --- a/qwilight-fe/src/hall/AvatarItem.tsx +++ /dev/null @@ -1,31 +0,0 @@ -import AvatarDrawing from "@/AvatarDrawing"; -import AvatarTitle from "@/AvatarTitle"; - -import { Hall } from "@/hall/Hall"; -import { Col, ListGroupItem, Row } from "reactstrap"; -import { useTo } from "taehui-ts/fe-utility"; - -export default function AvatarItem({ avatarID, avatarName, text }: Hall) { - const to = useTo(); - - return ( - <ListGroupItem key={avatarID}> - <Row - className="g-0 route" - onClick={() => { - to(`/avatar/${encodeURIComponent("#")}${avatarID}`); - }} - > - <Col className="m-1" xs="auto"> - <AvatarDrawing avatarID={avatarID} /> - </Col> - <Col className="m-1" xs="auto"> - {avatarID && <AvatarTitle avatarID={avatarID} />} - <span>{avatarName}</span> - <br /> - <span>{text}</span> - </Col> - </Row> - </ListGroupItem> - ); -} diff --git a/qwilight-fe/src/hall/Hall.d.ts b/qwilight-fe/src/hall/Hall.d.ts deleted file mode 100644 index e4c8b20..0000000 --- a/qwilight-fe/src/hall/Hall.d.ts +++ /dev/null @@ -1,5 +0,0 @@ -export type Hall = { - avatarID: string; - avatarName: string; - text: string; -}; diff --git a/qwilight-fe/src/hall/setHallStore.ts b/qwilight-fe/src/hall/setHallStore.ts deleted file mode 100644 index 22d76c6..0000000 --- a/qwilight-fe/src/hall/setHallStore.ts +++ /dev/null @@ -1,24 +0,0 @@ -export default function setHallStore() { - return { - tabPosition: 0, - totalTabPosition: 0, - atTabPosition: 0, - abilityTabPosition: 0, - - setTabPosition(tabPosition: number) { - this.tabPosition = tabPosition; - }, - - setTotalTabPosition(totalTabPosition: number) { - this.totalTabPosition = totalTabPosition; - }, - - setAtTabPosition(atTabPosition: number) { - this.atTabPosition = atTabPosition; - }, - - setAbilityTabPosition(abilityTabPosition: number) { - this.abilityTabPosition = abilityTabPosition; - }, - }; -} diff --git a/qwilight-fe/src/hall/useGetAbility5KHall.ts b/qwilight-fe/src/hall/useGetAbility5KHall.ts deleted file mode 100644 index 94b5ef6..0000000 --- a/qwilight-fe/src/hall/useGetAbility5KHall.ts +++ /dev/null @@ -1,32 +0,0 @@ -import { useHallStore } from "@/Stores"; -import { formatText } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { GetHallAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetAbility5KHall() { - const { tabPosition, abilityTabPosition } = useHallStore(); - - const isPath = useIsPath(); - - return useQuery< - { - avatarID: string; - avatarName: string; - text: string; - }[] - >({ - enabled: tabPosition === 2 && abilityTabPosition === 0 && isPath("/hall"), - queryKey: ["ability5KHall"], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetHallAPI[]>("/hall/ability/5K"); - return data.map((hall) => ({ - ...hall, - text: `${formatText(hall.value)} Point`, - })); - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/hall/useGetAbility7KHall.ts b/qwilight-fe/src/hall/useGetAbility7KHall.ts deleted file mode 100644 index 55eb9b6..0000000 --- a/qwilight-fe/src/hall/useGetAbility7KHall.ts +++ /dev/null @@ -1,32 +0,0 @@ -import { useHallStore } from "@/Stores"; -import { formatText } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { GetHallAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetAbility7KHall() { - const { tabPosition, abilityTabPosition } = useHallStore(); - - const isPath = useIsPath(); - - return useQuery< - { - avatarID: string; - avatarName: string; - text: string; - }[] - >({ - enabled: tabPosition === 2 && abilityTabPosition === 1 && isPath("/hall"), - queryKey: ["ability7KHall"], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetHallAPI[]>("/hall/ability/7K"); - return data.map((hall) => ({ - ...hall, - text: `${formatText(hall.value)} Point`, - })); - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/hall/useGetAbility9KHall.ts b/qwilight-fe/src/hall/useGetAbility9KHall.ts deleted file mode 100644 index 1b32a2b..0000000 --- a/qwilight-fe/src/hall/useGetAbility9KHall.ts +++ /dev/null @@ -1,32 +0,0 @@ -import { useHallStore } from "@/Stores"; -import { formatText } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { GetHallAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetAbility9KHall() { - const { tabPosition, abilityTabPosition } = useHallStore(); - - const isPath = useIsPath(); - - return useQuery< - { - avatarID: string; - avatarName: string; - text: string; - }[] - >({ - enabled: tabPosition === 2 && abilityTabPosition === 2 && isPath("/hall"), - queryKey: ["ability9KHall"], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetHallAPI[]>("/hall/ability/9K"); - return data.map((hall) => ({ - ...hall, - text: `${formatText(hall.value)} Point`, - })); - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/hall/useGetAtBandHall.ts b/qwilight-fe/src/hall/useGetAtBandHall.ts deleted file mode 100644 index 931a7c4..0000000 --- a/qwilight-fe/src/hall/useGetAtBandHall.ts +++ /dev/null @@ -1,35 +0,0 @@ -import { useHallStore } from "@/Stores"; -import { formatText } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { GetHallAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useTranslations } from "next-intl"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetAtBandHall() { - const { tabPosition, atTabPosition } = useHallStore(); - - const t = useTranslations(); - - const isPath = useIsPath(); - - return useQuery< - { - avatarID: string; - avatarName: string; - text: string; - }[] - >({ - enabled: tabPosition === 1 && atTabPosition === 3 && isPath("/hall"), - queryKey: ["atBandHall"], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetHallAPI[]>("/hall/atBand"); - return data.map((hall) => ({ - ...hall, - text: t("textBand", { value: formatText(hall.value) }), - })); - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/hall/useGetAtHighestHall.ts b/qwilight-fe/src/hall/useGetAtHighestHall.ts deleted file mode 100644 index 2569c5e..0000000 --- a/qwilight-fe/src/hall/useGetAtHighestHall.ts +++ /dev/null @@ -1,35 +0,0 @@ -import { useHallStore } from "@/Stores"; -import { formatText } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { GetHallAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useTranslations } from "next-intl"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetAtHighestHall() { - const { tabPosition, atTabPosition } = useHallStore(); - - const t = useTranslations(); - - const isPath = useIsPath(); - - return useQuery< - { - avatarID: string; - avatarName: string; - text: string; - }[] - >({ - enabled: tabPosition === 1 && atTabPosition === 1 && isPath("/hall"), - queryKey: ["atHighestHall"], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetHallAPI[]>("/hall/atHighest"); - return data.map((hall) => ({ - ...hall, - text: t("textCount", { value: formatText(hall.value) }), - })); - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/hall/useGetAtStandHall.ts b/qwilight-fe/src/hall/useGetAtStandHall.ts deleted file mode 100644 index cb92131..0000000 --- a/qwilight-fe/src/hall/useGetAtStandHall.ts +++ /dev/null @@ -1,35 +0,0 @@ -import { useHallStore } from "@/Stores"; -import { formatText } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { GetHallAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useTranslations } from "next-intl"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetAtStandHall() { - const { tabPosition, atTabPosition } = useHallStore(); - - const t = useTranslations(); - - const isPath = useIsPath(); - - return useQuery< - { - avatarID: string; - avatarName: string; - text: string; - }[] - >({ - enabled: tabPosition === 1 && atTabPosition === 2 && isPath("/hall"), - queryKey: ["atStandHall"], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetHallAPI[]>("/hall/atStand"); - return data.map((hall) => ({ - ...hall, - text: t("textStand", { value: formatText(hall.value) }), - })); - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/hall/useGetAtTotalHall.ts b/qwilight-fe/src/hall/useGetAtTotalHall.ts deleted file mode 100644 index 1d849d8..0000000 --- a/qwilight-fe/src/hall/useGetAtTotalHall.ts +++ /dev/null @@ -1,35 +0,0 @@ -import { useHallStore } from "@/Stores"; -import { formatText } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { GetHallAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useTranslations } from "next-intl"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetAtTotalHall() { - const { tabPosition, atTabPosition } = useHallStore(); - - const t = useTranslations(); - - const isPath = useIsPath(); - - return useQuery< - { - avatarID: string; - avatarName: string; - text: string; - }[] - >({ - enabled: tabPosition === 1 && atTabPosition === 0 && isPath("/hall"), - queryKey: ["atTotalHall"], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetHallAPI[]>("/hall/atTotal"); - return data.map((hall) => ({ - ...hall, - text: t("textHandled", { value: formatText(hall.value) }), - })); - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/hall/useGetLevelHall.ts b/qwilight-fe/src/hall/useGetLevelHall.ts deleted file mode 100644 index f774af1..0000000 --- a/qwilight-fe/src/hall/useGetLevelHall.ts +++ /dev/null @@ -1,32 +0,0 @@ -import { useHallStore } from "@/Stores"; -import { formatText } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { GetHallAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetLevelHall() { - const { tabPosition } = useHallStore(); - - const isPath = useIsPath(); - - return useQuery< - { - avatarID: string; - avatarName: string; - text: string; - }[] - >({ - enabled: tabPosition === 3 && isPath("/hall"), - queryKey: ["levelHall"], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetHallAPI[]>("/hall/level"); - return data.map((hall) => ({ - ...hall, - text: `LV.${formatText(hall.value)}`, - })); - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/hall/useGetTotalBandHall.ts b/qwilight-fe/src/hall/useGetTotalBandHall.ts deleted file mode 100644 index 2c349a6..0000000 --- a/qwilight-fe/src/hall/useGetTotalBandHall.ts +++ /dev/null @@ -1,35 +0,0 @@ -import { useHallStore } from "@/Stores"; -import { formatText } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { GetHallAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useTranslations } from "next-intl"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetTotalBandHall() { - const { tabPosition, totalTabPosition } = useHallStore(); - - const t = useTranslations(); - - const isPath = useIsPath(); - - return useQuery< - { - avatarID: string; - avatarName: string; - text: string; - }[] - >({ - enabled: tabPosition === 0 && totalTabPosition === 3 && isPath("/hall"), - queryKey: ["totalBandHall"], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetHallAPI[]>("/hall/totalBand"); - return data.map((hall) => ({ - ...hall, - text: t("textBand", { value: formatText(hall.value) }), - })); - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/hall/useGetTotalHighestHall.ts b/qwilight-fe/src/hall/useGetTotalHighestHall.ts deleted file mode 100644 index 26d38a1..0000000 --- a/qwilight-fe/src/hall/useGetTotalHighestHall.ts +++ /dev/null @@ -1,35 +0,0 @@ -import { useHallStore } from "@/Stores"; -import { formatText } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { GetHallAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useTranslations } from "next-intl"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetTotalHighestHall() { - const { tabPosition, totalTabPosition } = useHallStore(); - - const t = useTranslations(); - - const isPath = useIsPath(); - - return useQuery< - { - avatarID: string; - avatarName: string; - text: string; - }[] - >({ - enabled: tabPosition === 0 && totalTabPosition === 1 && isPath("/hall"), - queryKey: ["totalHighestHall"], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetHallAPI[]>("/hall/totalHighest"); - return data.map((hall) => ({ - ...hall, - text: t("textCount", { value: formatText(hall.value) }), - })); - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/hall/useGetTotalStandHall.ts b/qwilight-fe/src/hall/useGetTotalStandHall.ts deleted file mode 100644 index 2fc673b..0000000 --- a/qwilight-fe/src/hall/useGetTotalStandHall.ts +++ /dev/null @@ -1,35 +0,0 @@ -import { useHallStore } from "@/Stores"; -import { formatText } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { GetHallAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useTranslations } from "next-intl"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetTotalStandHall() { - const { tabPosition, totalTabPosition } = useHallStore(); - - const t = useTranslations(); - - const isPath = useIsPath(); - - return useQuery< - { - avatarID: string; - avatarName: string; - text: string; - }[] - >({ - enabled: tabPosition === 0 && totalTabPosition === 2 && isPath("/hall"), - queryKey: ["totalStandHall"], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetHallAPI[]>("/hall/totalStand"); - return data.map((hall) => ({ - ...hall, - text: t("textStand", { value: formatText(hall.value) }), - })); - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/hall/useGetTotalTotalHall.ts b/qwilight-fe/src/hall/useGetTotalTotalHall.ts deleted file mode 100644 index e294882..0000000 --- a/qwilight-fe/src/hall/useGetTotalTotalHall.ts +++ /dev/null @@ -1,35 +0,0 @@ -import { useHallStore } from "@/Stores"; -import { formatText } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { GetHallAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useTranslations } from "next-intl"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetTotalTotalHall() { - const { tabPosition, totalTabPosition } = useHallStore(); - - const t = useTranslations(); - - const isPath = useIsPath(); - - return useQuery< - { - avatarID: string; - avatarName: string; - text: string; - }[] - >({ - enabled: tabPosition === 0 && totalTabPosition === 0 && isPath("/hall"), - queryKey: ["totalTotalHall"], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetHallAPI[]>("/hall/totalTotal"); - return data.map((hall) => ({ - ...hall, - text: t("textHandled", { value: formatText(hall.value) }), - })); - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/hoc/withQueryClient.tsx b/qwilight-fe/src/hoc/withQueryClient.tsx new file mode 100644 index 0000000..f4a7744 --- /dev/null +++ b/qwilight-fe/src/hoc/withQueryClient.tsx @@ -0,0 +1,14 @@ +import { QueryClient, QueryClientProvider } from "@tanstack/react-query"; +import type { FC } from "react"; + +const queryClient = new QueryClient(); + +export default function withQueryClient<T extends object>(Component: FC<T>) { + return (props: T) => { + return ( + <QueryClientProvider client={queryClient}> + <Component {...props} /> + </QueryClientProvider> + ); + }; +} diff --git a/qwilight-fe/src/note/CommentItem.tsx b/qwilight-fe/src/note/CommentItem.tsx deleted file mode 100644 index f26e951..0000000 --- a/qwilight-fe/src/note/CommentItem.tsx +++ /dev/null @@ -1,103 +0,0 @@ -import w0 from "@/assets/w0.png"; -import w1 from "@/assets/w1.png"; -import w2 from "@/assets/w2.png"; -import w4 from "@/assets/w4.png"; -import w5 from "@/assets/w5.png"; -import w6 from "@/assets/w6.png"; -import w7 from "@/assets/w7.png"; -import AvatarDrawing from "@/AvatarDrawing"; -import AvatarTitle from "@/AvatarTitle"; -import { - formatText, - getHitPointsClass, - getQuitStatusValue, - toDate, -} from "@/Utility"; - -import { GetCommentAPI } from "@/wwwAPI"; -import { useTranslations } from "next-intl"; -import Image from "next/image"; -import { useMemo } from "react"; -import { Col, Row } from "reactstrap"; -import { useTo } from "taehui-ts/fe-utility"; - -const ws = [w0, w1, w2, "", w4, w5, w6, w7]; - -export default function CommentItem({ - date, - avatarID, - avatarName, - stand, - band, - point, - isP, - commentary, - isTargetAvatar, - judgmentMode, - hitPointsMode, - isPaused, - handled, -}: GetCommentAPI["comments"][number]) { - const { quit, quitCss } = useMemo( - () => getQuitStatusValue(point, stand), - [point, stand], - ); - const to = useTo(); - const t = useTranslations(); - - return ( - <Row - onClick={() => { - to(`/avatar/${encodeURIComponent("#")}${avatarID}`); - }} - className={`g-0 route ${isTargetAvatar ? "target" : ""}`} - > - <Col className="m-1" xs="auto"> - <AvatarDrawing avatarID={avatarID} /> - </Col> - <Col className="m-1" xs="auto"> - <Image src={ws[handled]} width={10} height={60} alt="" /> - </Col> - <Col className="m-1" xs="auto"> - <span className={quitCss}>{quit}</span> - {isP && ( - <> - <br /> - <span>FULL</span> - </> - )} - </Col> - <Col className="m-1" xs="auto"> - <AvatarTitle avatarID={avatarID} /> - <span className="avatar">{avatarName}</span>{" "} - <span className="date">{toDate(date)}</span> - <br /> - <span className={getHitPointsClass(hitPointsMode)}> - {t("textStand", { value: formatText(stand) })} - </span>{" "} - <span - className={(() => { - switch (judgmentMode) { - case 0: - return "level2"; - case 2: - return "level4"; - case 3: - return "level1"; - case 5: - return "level5"; - default: - return "point"; - } - })()} - > - {(100 * point).toFixed(2)}% - </span>{" "} - <span className="band">{t("textBand", { value: band })}</span> - {isPaused && " ⏸️"} - <br /> - {commentary && <span>💬 {commentary}</span>} - </Col> - </Row> - ); -} diff --git a/qwilight-fe/src/note/CommentItems.tsx b/qwilight-fe/src/note/CommentItems.tsx deleted file mode 100644 index 0e7fa08..0000000 --- a/qwilight-fe/src/note/CommentItems.tsx +++ /dev/null @@ -1,64 +0,0 @@ -import CommentItem from "@/note/CommentItem"; -import { formatText } from "@/Utility"; -import { GetCommentAPI } from "@/wwwAPI"; - -export default function CommentItems({ - comments, - commentPlace, - totalCount, - wantAvatarID, - wantAvatarName, -}: { - comments: GetCommentAPI["comments"]; - commentPlace: number; - totalCount: number; - wantAvatarID?: string; - wantAvatarName?: string; -}) { - return ( - <> - {commentPlace !== -1 && ( - <> - <span className="avatarPlace">#{formatText(commentPlace + 1)}</span> - <span>/{formatText(totalCount)}</span> - </> - )} - {comments.map( - ({ - date, - avatarID, - avatarName, - stand, - band, - point, - commentary, - isP, - judgmentMode, - hitPointsMode, - isPaused, - handled, - }) => ( - <CommentItem - key={avatarID} - date={date} - avatarID={avatarID} - avatarName={avatarName} - stand={stand} - band={band} - point={point} - isP={isP} - commentary={commentary} - isTargetAvatar={ - !!(wantAvatarID && wantAvatarID === avatarID) || - !!(wantAvatarName && wantAvatarName === avatarName) - } - judgmentMode={judgmentMode} - hitPointsMode={hitPointsMode} - isPaused={isPaused} - handled={handled} - /> - ), - )} - </> - ); -} diff --git a/qwilight-fe/src/note/FitInput.tsx b/qwilight-fe/src/note/FitInput.tsx deleted file mode 100644 index 6dfed57..0000000 --- a/qwilight-fe/src/note/FitInput.tsx +++ /dev/null @@ -1,40 +0,0 @@ -import { useTranslations } from "next-intl"; -import { useState } from "react"; -import { - Dropdown, - DropdownItem, - DropdownMenu, - DropdownToggle, -} from "reactstrap"; -import { useIntParam } from "taehui-ts/fe-utility"; - -export default function FitInput() { - const [isFitOpened, setFitOpened] = useState(false); - const { param: fit, setParam: setFit } = useIntParam("fit", 0); - - const t = useTranslations(); - - const onInput = (fit: number) => () => { - setFit(fit); - }; - - return ( - <Dropdown - isOpen={isFitOpened} - toggle={() => { - setFitOpened((prevState) => !prevState); - }} - > - <DropdownToggle caret>{t(`toFit${fit}`)}</DropdownToggle> - <DropdownMenu> - <DropdownItem onClick={onInput(0)}>{t("toFit0")}</DropdownItem> - <DropdownItem onClick={onInput(1)}>{t("toFit1")}</DropdownItem> - <DropdownItem onClick={onInput(2)}>{t("toFit2")}</DropdownItem> - <DropdownItem onClick={onInput(3)}>{t("toFit3")}</DropdownItem> - <DropdownItem onClick={onInput(4)}>{t("toFit4")}</DropdownItem> - <DropdownItem onClick={onInput(5)}>{t("toFit5")}</DropdownItem> - <DropdownItem onClick={onInput(6)}>{t("toFit6")}</DropdownItem> - </DropdownMenu> - </Dropdown> - ); -} diff --git a/qwilight-fe/src/note/NoteItem.tsx b/qwilight-fe/src/note/NoteItem.tsx deleted file mode 100644 index 82163f4..0000000 --- a/qwilight-fe/src/note/NoteItem.tsx +++ /dev/null @@ -1,124 +0,0 @@ -import w0 from "@/assets/w0.png"; -import w1 from "@/assets/w1.png"; -import w2 from "@/assets/w2.png"; -import w4 from "@/assets/w4.png"; -import w5 from "@/assets/w5.png"; -import w6 from "@/assets/w6.png"; -import w7 from "@/assets/w7.png"; - -import CommentItems from "@/note/CommentItems"; -import useGetComment from "@/note/useGetComment"; -import usePostToil from "@/note/usePostToil"; -import { formatText, getGenreText } from "@/Utility"; -import { GetNoteAPI } from "@/wwwAPI"; -import { useTranslations } from "next-intl"; -import Image from "next/image"; -import { useState } from "react"; -import { Item, Menu, useContextMenu } from "react-contexify"; -import { Col, Collapse, ListGroupItem, Row, Spinner } from "reactstrap"; -import Swal from "sweetalert2"; - -const ws = [w0, w1, w2, "", w4, w5, w6, w7]; - -export default function NoteItem({ - noteID, - artist, - title, - genre, - levelText, - level, - highestCount, - totalCount, - fittedText, - wantAvatarID, - wantAvatarName, - handled, -}: GetNoteAPI["notes"][number] & { handled?: number }) { - const t = useTranslations(); - - const [isCommentOpened, setCommentOpened] = useState(false); - - const { show: viewToilInput } = useContextMenu({ - id: `toil-${noteID}`, - }); - - const { - data: { comments, commentPlace, totalComments }, - isFetched: isCommentLoaded, - } = useGetComment(noteID, isCommentOpened); - - const { mutateAsync: postToil } = usePostToil(); - - return ( - <ListGroupItem> - <Row - className="g-0 route" - onClick={() => { - setCommentOpened((prevState) => !prevState); - }} - onContextMenu={(event) => { - event.preventDefault(); - viewToilInput({ event, props: { noteID } }); - }} - > - {typeof handled === "number" && ( - <Col className="m-1" xs="auto"> - <Image src={ws[handled]} width={10} height={60} alt="" /> - </Col> - )} - <Col className="m-1" xs="auto"> - <span className={`level${level}`}>{levelText}</span>{" "} - <span className="title">{title}</span>{" "} - {isCommentOpened && !isCommentLoaded && ( - <Spinner size="sm" color="primary" /> - )} - <br /> - {fittedText && <span className="fittedText">{fittedText}</span>}{" "} - <span className="artist">{artist}</span>{" "} - <span className="genre">{getGenreText(genre)}</span> - <br /> - {typeof highestCount === "number" && - typeof totalCount === "number" && ( - <> - <span className="fittedText"> - {t("highestCountText", { - highestCount: formatText(highestCount), - })} - </span> - <br /> - <span className="fittedText"> - {t("totalCountText", { totalCount: formatText(totalCount) })} - </span> - </> - )} - </Col> - </Row> - {noteID && ( - <Menu id={`toil-${noteID}`}> - <Item - onClick={async ({ props: { noteID } }) => { - const { isConfirmed, value } = await Swal.fire({ - title: t("toilNoteFileText"), - input: "text", - }); - if (isConfirmed) { - await postToil({ noteID, commentary: value }); - } - }} - > - <span>{t("toilNoteFile")}</span> - </Item> - </Menu> - )} - <Collapse isOpen={isCommentOpened}> - <CommentItems - comments={comments} - commentPlace={commentPlace} - totalCount={totalComments} - wantAvatarID={wantAvatarID} - wantAvatarName={wantAvatarName} - /> - </Collapse> - </ListGroupItem> - ); -} diff --git a/qwilight-fe/src/note/NoteItems.tsx b/qwilight-fe/src/note/NoteItems.tsx deleted file mode 100644 index 8af2815..0000000 --- a/qwilight-fe/src/note/NoteItems.tsx +++ /dev/null @@ -1,75 +0,0 @@ -import { NoteLoading } from "@/Loading"; -import NoteItem from "@/note/NoteItem"; -import useGetNote from "@/note/useGetNote"; - -import { useNoteStore } from "@/Stores"; -import { observer } from "mobx-react-lite"; -import { useLayoutEffect, useState } from "react"; -import { Col, ListGroup, Row } from "reactstrap"; -import { useWindowArea } from "taehui-ts/fe-utility"; - -export default observer(() => { - const { wantAvatar, viewUnit } = useNoteStore(); - - const { - data: { notes }, - isFetched: isNoteLoaded, - } = useGetNote(); - - const { windowLength } = useWindowArea(); - const [table, setTable] = useState(1); - - useLayoutEffect(() => { - setTable(windowLength < 992 ? 1 : 2); - }, [windowLength]); - - return ( - <Row className="g-0"> - {[...Array(table).keys()].map((i) => { - if (isNoteLoaded) { - return ( - <Col className="m-1" key={i}> - <ListGroup> - {notes - .slice((viewUnit / table) * i, (viewUnit / table) * (i + 1)) - .map( - ({ - noteID, - artist, - title, - genre, - levelText, - level, - highestCount, - totalCount, - }) => ( - <NoteItem - key={noteID} - noteID={noteID} - artist={artist} - title={title} - genre={genre} - levelText={levelText} - level={level} - highestCount={highestCount} - totalCount={totalCount} - wantAvatarName={wantAvatar} - /> - ), - )} - </ListGroup> - </Col> - ); - } - - return ( - <Col className="m-1" key={i}> - <ListGroup> - <NoteLoading loadingCount={viewUnit / table} /> - </ListGroup> - </Col> - ); - })} - </Row> - ); -}); diff --git a/qwilight-fe/src/note/PositionInput.tsx b/qwilight-fe/src/note/PositionInput.tsx deleted file mode 100644 index 4374c3b..0000000 --- a/qwilight-fe/src/note/PositionInput.tsx +++ /dev/null @@ -1,78 +0,0 @@ -import { useNoteStore } from "@/Stores"; -import { observer } from "mobx-react-lite"; -import { useMemo } from "react"; -import { Pagination, PaginationItem, PaginationLink } from "reactstrap"; -import { useIntParam } from "taehui-ts/fe-utility"; - -export default observer(() => { - const { pageUnit, lastPage, lastWant, lastSrc } = useNoteStore(); - - const { param: page, setParam: setPage } = useIntParam("page", 1); - - const targetPages = useMemo(() => { - const targetPages = []; - for ( - let i = 1 + Math.floor((page - 1) / pageUnit) * pageUnit; - i <= - Math.min( - lastPage, - Math.floor((page - 1) / pageUnit) * pageUnit + pageUnit, - ); - ++i - ) { - targetPages.push(i); - } - return targetPages; - }, [lastPage, page, pageUnit]); - - const isLowestPage = useMemo(() => page === 1, [page]); - const isHighestPage = useMemo(() => page === lastPage, [lastPage, page]); - - return ( - <Pagination> - <PaginationItem disabled={isLowestPage}> - <PaginationLink - first - onClick={() => { - setPage(1); - }} - /> - </PaginationItem> - <PaginationItem disabled={isLowestPage}> - <PaginationLink - previous - onClick={() => { - setPage(page - 1); - }} - /> - </PaginationItem> - {targetPages.map((targetPage) => ( - <PaginationItem key={targetPage} active={targetPage === page}> - <PaginationLink - onClick={() => { - setPage(targetPage); - }} - > - {targetPage} - </PaginationLink> - </PaginationItem> - ))} - <PaginationItem disabled={isHighestPage}> - <PaginationLink - next - onClick={() => { - setPage(page + 1); - }} - /> - </PaginationItem> - <PaginationItem disabled={isHighestPage}> - <PaginationLink - last - onClick={() => { - setPage(lastPage); - }} - /> - </PaginationItem> - </Pagination> - ); -}); diff --git a/qwilight-fe/src/note/SrcInput.tsx b/qwilight-fe/src/note/SrcInput.tsx deleted file mode 100644 index 27b25f2..0000000 --- a/qwilight-fe/src/note/SrcInput.tsx +++ /dev/null @@ -1,43 +0,0 @@ -import { useNoteStore } from "@/Stores"; -import { useTranslations } from "next-intl"; -import { useEffect, useState } from "react"; -import { - Dropdown, - DropdownItem, - DropdownMenu, - DropdownToggle, -} from "reactstrap"; -import { useIntParam } from "taehui-ts/fe-utility"; - -export default function SrcInput() { - const { setLastSrc, setWantAvatar } = useNoteStore(); - const [isSrcOpened, setSrcOpened] = useState(false); - const { param: src, setParam: setSrc } = useIntParam("src", 0); - - const t = useTranslations(); - - const onInput = (src: number) => () => { - setSrc(src); - }; - - useEffect(() => { - setLastSrc(src); - }, [setLastSrc, src]); - - return ( - <Dropdown - isOpen={isSrcOpened} - toggle={() => { - setSrcOpened((prevState) => !prevState); - }} - > - <DropdownToggle caret>{t(`toSrc${src}`)}</DropdownToggle> - <DropdownMenu> - <DropdownItem onClick={onInput(0)}>{t("toSrc0")}</DropdownItem> - <DropdownItem onClick={onInput(1)}>{t("toSrc1")}</DropdownItem> - <DropdownItem onClick={onInput(2)}>{t("toSrc2")}</DropdownItem> - <DropdownItem onClick={onInput(3)}>{t("toSrc3")}</DropdownItem> - </DropdownMenu> - </Dropdown> - ); -} diff --git a/qwilight-fe/src/note/WantInput.tsx b/qwilight-fe/src/note/WantInput.tsx deleted file mode 100644 index 5c68fae..0000000 --- a/qwilight-fe/src/note/WantInput.tsx +++ /dev/null @@ -1,37 +0,0 @@ -import { useNoteStore } from "@/Stores"; -import { useEffect } from "react"; -import { Input } from "reactstrap"; -import { useWant } from "taehui-ts/fe-utility"; - -export default function SrcInput() { - const { wantInput, setWantInput, setLastWant } = useNoteStore(); - - const { want, setWant } = useWant("/note"); - - const onWant = () => { - setWant(wantInput); - }; - - useEffect(() => { - setWantInput(want); - }, [setWantInput, want]); - - useEffect(() => { - setLastWant(want); - }, [setLastWant, want]); - - return ( - <Input - type="search" - value={wantInput} - onChange={({ target: { value } }) => { - setWantInput(value); - }} - onKeyDown={({ key }) => { - if (key === "Enter") { - onWant(); - } - }} - /> - ); -} diff --git a/qwilight-fe/src/note/setNoteStore.ts b/qwilight-fe/src/note/setNoteStore.ts deleted file mode 100644 index 1526734..0000000 --- a/qwilight-fe/src/note/setNoteStore.ts +++ /dev/null @@ -1,31 +0,0 @@ -export default function setNoteStore() { - return { - lastWant: "", - lastSrc: 0, - wantAvatar: "", - wantInput: "", - lastPage: 1, - pageUnit: 10, - viewUnit: 20, - - setLastWant(lastWant: string) { - this.lastWant = lastWant; - }, - - setLastSrc(lastSrc: number) { - this.lastSrc = lastSrc; - }, - - setWantInput(wantInput: string) { - this.wantInput = wantInput; - }, - - setWantAvatar(wantAvatar: string) { - this.wantAvatar = wantAvatar; - }, - - setLastPage(lastPage: number) { - this.lastPage = lastPage; - }, - }; -} diff --git a/qwilight-fe/src/note/useGetComment.ts b/qwilight-fe/src/note/useGetComment.ts deleted file mode 100644 index fc1d327..0000000 --- a/qwilight-fe/src/note/useGetComment.ts +++ /dev/null @@ -1,34 +0,0 @@ -import { useSiteStore } from "@/Stores"; -import { wwwAXIOS } from "@/Www"; -import { GetCommentAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { getLanguage } from "taehui-ts/language"; - -export default function useGetComment( - noteID: string, - isCommentOpened: boolean, -) { - const { siteAvatarID } = useSiteStore(); - - const language = getLanguage(); - return useQuery({ - enabled: isCommentOpened, - queryKey: ["comment", noteID, siteAvatarID, language], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetCommentAPI>("/comment", { - params: { - noteID, - avatarID: siteAvatarID, - language, - }, - }); - - return data; - }, - initialData: { - comments: [], - commentPlace: -1, - totalComments: 0, - }, - }); -} diff --git a/qwilight-fe/src/note/useGetNote.ts b/qwilight-fe/src/note/useGetNote.ts deleted file mode 100644 index f704b63..0000000 --- a/qwilight-fe/src/note/useGetNote.ts +++ /dev/null @@ -1,42 +0,0 @@ -import { useNoteStore } from "@/Stores"; - -import { wwwAXIOS } from "@/Www"; -import { GetNoteAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useIntParam, useIsPath, useWant } from "taehui-ts/fe-utility"; - -export default function useGetNote() { - const { viewUnit } = useNoteStore(); - - const { param: page } = useIntParam("page", 1); - const { param: fit } = useIntParam("fit", 0); - const { param: src } = useIntParam("src", 0); - - const { want } = useWant("/note"); - - const isPath = useIsPath(); - - return useQuery({ - enabled: isPath("/note"), - queryKey: ["note", fit, src, want, page, viewUnit], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetNoteAPI>("/note", { - params: { - fit, - src, - want, - page, - viewUnit, - }, - }); - - return data; - }, - initialData: { - totalCount: 0, - highestCount: 0, - noteCount: 0, - notes: [], - }, - }); -} diff --git a/qwilight-fe/src/note/usePostToil.ts b/qwilight-fe/src/note/usePostToil.ts deleted file mode 100644 index 7342298..0000000 --- a/qwilight-fe/src/note/usePostToil.ts +++ /dev/null @@ -1,19 +0,0 @@ -import { wwwAXIOS } from "@/Www"; -import { useMutation } from "@tanstack/react-query"; - -export default function usePostToil() { - return useMutation({ - mutationFn: async ({ - noteID, - commentary, - }: { - noteID: string; - commentary: string; - }) => { - await wwwAXIOS.post("/toil", { - noteID, - commentary, - }); - }, - }); -} diff --git a/qwilight-fe/src/query/useGetTitle.ts b/qwilight-fe/src/query/useGetTitle.ts new file mode 100644 index 0000000..c56a770 --- /dev/null +++ b/qwilight-fe/src/query/useGetTitle.ts @@ -0,0 +1,33 @@ +import { GetTitleAPI } from "@/type/wwwAPI"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { getLanguage } from "taehui-ts/language"; + +export default function useGetTitle(avatarID: string) { + const language = getLanguage(); + return useQuery({ + queryKey: ["title", avatarID, language], + queryFn: async () => { + const { data } = await wwwAPI.get<GetTitleAPI>("/title", { + params: { + avatarID, + language, + }, + }); + if (data.titleColor.startsWith("#")) { + return { + ...data, + titleColor: `#${data.titleColor.substring( + 3, + )}${data.titleColor.substring(1, 3)}`, + }; + } else { + return data; + } + }, + initialData: { + title: "", + titleColor: "", + }, + }); +} diff --git a/qwilight-fe/src/site/AvatarItem.module.scss b/qwilight-fe/src/site/AvatarItem.module.scss deleted file mode 100644 index 3a2522b..0000000 --- a/qwilight-fe/src/site/AvatarItem.module.scss +++ /dev/null @@ -1,5 +0,0 @@ -span { - &.audioInput { - color: green; - } -} diff --git a/qwilight-fe/src/site/AvatarItem.tsx b/qwilight-fe/src/site/AvatarItem.tsx deleted file mode 100644 index 95d5fd7..0000000 --- a/qwilight-fe/src/site/AvatarItem.tsx +++ /dev/null @@ -1,77 +0,0 @@ -import ac1 from "@/assets/ac1.png"; -import ac2 from "@/assets/ac2.png"; -import ac3 from "@/assets/ac3.png"; -import ac4 from "@/assets/ac4.png"; -import valve from "@/assets/valve.png"; -import AvatarDrawing from "@/AvatarDrawing"; -import AvatarTitle from "@/AvatarTitle"; - -import scss from "@/site/AvatarItem.module.scss"; -import { OnAvatarInput } from "@/site/Site"; -import Image from "next/image"; -import { Col, Row } from "reactstrap"; - -const acs = ["", ac1, ac2, ac3, ac4]; - -export default function AvatarItem({ - avatarID, - avatarName, - avatarConfigure, - isSiteHand, - isMe, - isValve, - isAudioInput, - onAvatarInput, -}: { - avatarID: string; - avatarName: string; - avatarConfigure: number; - isSiteHand: boolean; - isMe: boolean; - isValve: boolean; - isAudioInput: boolean; - onAvatarInput: OnAvatarInput; -}) { - return ( - <Row - className={`g-0 ${isMe ? "target" : ""}`} - onContextMenu={(e) => { - e.preventDefault(); - onAvatarInput(e, avatarID); - }} - > - <Col className="m-1" xs="auto"> - <AvatarDrawing avatarID={avatarID} /> - </Col> - <Col className="m-1" xs="auto"> - {avatarID && <AvatarTitle avatarID={avatarID} />} - <span className={isAudioInput ? scss.audioInput : undefined}> - {avatarName} - </span> - <br /> - {isValve && ( - <> - {" "} - <Image alt="" src={valve} height={24} /> - </> - )} - {acs[avatarConfigure] && ( - <> - {" "} - <Image - alt="" - src={acs[avatarConfigure]} - className={scss.avatarConfigure} - /> - </> - )} - {isSiteHand && ( - <> - {" "} - <Image alt="" src={acs[1]} className={scss.avatarConfigure} /> - </> - )} - </Col> - </Row> - ); -} diff --git a/qwilight-fe/src/site/AvatarItems.tsx b/qwilight-fe/src/site/AvatarItems.tsx deleted file mode 100644 index ff15c71..0000000 --- a/qwilight-fe/src/site/AvatarItems.tsx +++ /dev/null @@ -1,39 +0,0 @@ -import AvatarItem from "@/site/AvatarItem"; -import { OnAvatarInput } from "@/site/Site"; - -import { useSiteStore } from "@/Stores"; -import { observer } from "mobx-react-lite"; - -export default observer( - ({ onAvatarInput }: { onAvatarInput: OnAvatarInput }) => { - const { avatars } = useSiteStore(); - - return ( - <> - {avatars.map( - ({ - avatarID, - avatarName, - avatarConfigure, - isSiteHand, - isMe, - isValve, - isAudioInput, - }) => ( - <AvatarItem - key={avatarID} - avatarID={avatarID} - avatarName={avatarName} - avatarConfigure={avatarConfigure} - isSiteHand={isSiteHand} - isMe={isMe} - isValve={isValve} - isAudioInput={isAudioInput} - onAvatarInput={onAvatarInput} - /> - ), - )} - </> - ); - }, -); diff --git a/qwilight-fe/src/site/ConfigureWindow.tsx b/qwilight-fe/src/site/ConfigureWindow.tsx deleted file mode 100644 index f467e42..0000000 --- a/qwilight-fe/src/site/ConfigureWindow.tsx +++ /dev/null @@ -1,88 +0,0 @@ -import { useSiteStore } from "@/Stores"; -import { observer } from "mobx-react-lite"; -import { useTranslations } from "next-intl"; -import { Button, Col, Modal, Row } from "reactstrap"; - -export default observer(() => { - const { - isConfigureOpened, - setConfigureOpened, - saveTraffic, - setSaveTraffic, - autoEnterNotify, - setAutoEnterNotify, - autoEnterDefault, - setAutoEnterDefault, - autoEnterPlatform, - setAutoEnterPlatform, - } = useSiteStore(); - const t = useTranslations(); - - return ( - <Modal - isOpen={isConfigureOpened} - toggle={() => { - window.localStorage.setItem("saveTraffic", saveTraffic.toString()); - window.localStorage.setItem( - "autoEnterNotify", - autoEnterNotify.toString(), - ); - window.localStorage.setItem( - "autoEnterDefault", - autoEnterDefault.toString(), - ); - window.localStorage.setItem( - "autoEnterPlatform", - autoEnterPlatform.toString(), - ); - setConfigureOpened(false); - }} - centered - > - <Row className="justify-content-center g-0"> - <Col className="m-1" xs="auto"> - <Button - color={saveTraffic ? "success" : "danger"} - onClick={() => { - setSaveTraffic(!saveTraffic); - }} - > - {t("siteSaveTraffic")} - </Button> - </Col> - </Row> - <Row className="justify-content-center g-0"> - <Col className="m-1" xs="auto"> - <Button - color={autoEnterNotify ? "success" : "danger"} - onClick={() => { - setAutoEnterNotify(!autoEnterNotify); - }} - > - {t("siteAutoEnterNotify")} - </Button> - </Col> - <Col className="m-1" xs="auto"> - <Button - color={autoEnterDefault ? "success" : "danger"} - onClick={() => { - setAutoEnterDefault(!autoEnterDefault); - }} - > - {t("siteAutoEnterDefault")} - </Button> - </Col> - <Col className="m-1" xs="auto"> - <Button - color={autoEnterPlatform ? "success" : "danger"} - onClick={() => { - setAutoEnterPlatform(!autoEnterPlatform); - }} - > - {t("siteAutoEnterPlatform")} - </Button> - </Col> - </Row> - </Modal> - ); -}); diff --git a/qwilight-fe/src/site/NewSiteWindow.tsx b/qwilight-fe/src/site/NewSiteWindow.tsx deleted file mode 100644 index aa7aa63..0000000 --- a/qwilight-fe/src/site/NewSiteWindow.tsx +++ /dev/null @@ -1,76 +0,0 @@ -import SiteComponent from "@/site/SiteComponent"; - -import { useSiteStore } from "@/Stores"; -import { observer } from "mobx-react-lite"; -import { useTranslations } from "next-intl"; -import { useState } from "react"; -import { Button, Col, Input, Modal, Row } from "reactstrap"; - -const EventPB = require("@/Event_pb"); - -export default observer(() => { - const { isNewSiteWindowOpened, setSiteWindowOpened, setNewSiteWindowOpened } = - useSiteStore(); - const [siteName, setSiteName] = useState(""); - const [siteCipher, setSiteCipher] = useState(""); - const t = useTranslations(); - - const onNewSite = () => { - SiteComponent.send({ - eventID: EventPB.Event.EventID.NEW_SITE, - text: JSON.stringify({ - siteName: siteName, - siteCipher: siteCipher, - isNetSite: false, - }), - }); - setNewSiteWindowOpened(false); - setSiteWindowOpened(false); - }; - - return ( - <Modal - isOpen={isNewSiteWindowOpened} - toggle={() => { - setNewSiteWindowOpened(false); - }} - centered - > - <Row className="g-0"> - <Col className="m-1"> - <Input - autoComplete="off" - value={siteName} - onChange={({ target: { value } }) => { - setSiteName(value); - }} - placeholder={t("siteName")} - /> - </Col> - </Row> - <Row className="g-0"> - <Col className="m-1"> - <Input - autoComplete="off" - value={siteCipher} - onChange={({ target: { value } }) => { - setSiteCipher(value); - }} - type="password" - placeholder={t("siteCipher")} - onKeyDown={({ key }) => { - if (key === "Enter") { - onNewSite(); - } - }} - /> - </Col> - </Row> - <Row className="justify-content-center g-0"> - <Col className="m-1" xs="auto"> - <Button onClick={onNewSite}>{t("inputNewSite")}</Button> - </Col> - </Row> - </Modal> - ); -}); diff --git a/qwilight-fe/src/site/SignInWindow.tsx b/qwilight-fe/src/site/SignInWindow.tsx deleted file mode 100644 index eeefccd..0000000 --- a/qwilight-fe/src/site/SignInWindow.tsx +++ /dev/null @@ -1,90 +0,0 @@ -import SiteComponent from "@/site/SiteComponent"; -import { useSiteStore } from "@/Stores"; -import CryptoJS from "crypto-js"; -import { observer } from "mobx-react-lite"; -import { useTranslations } from "next-intl"; -import { useState } from "react"; -import { Button, Col, Input, Modal, Row } from "reactstrap"; - -const EventPB = require("@/Event_pb"); - -export default observer(() => { - const { isSignInOpened, setSignInOpened } = useSiteStore(); - const t = useTranslations(); - - const [avatarID, setAvatarID] = useState(""); - const [avatarCipher, setAvatarCipher] = useState(""); - const [autoSignIn, setAutoSignIn] = useState(false); - - const onSignIn = () => { - if (autoSignIn) { - window.localStorage.setItem("avatarID", avatarID); - window.localStorage.setItem( - "avatarCipher", - CryptoJS.AES.encrypt( - avatarCipher, - "591A6F91-2A27-4A88-88FA-0FEB7CB5FD94", - ).toString(), - ); - } - window.localStorage.setItem("autoSignIn", autoSignIn.toString()); - SiteComponent.send({ - eventID: EventPB.Event.EventID.SIGN_IN, - text: JSON.stringify({ avatarID, avatarCipher }), - }); - }; - - return ( - <Modal - isOpen={isSignInOpened} - toggle={() => setSignInOpened(false)} - centered - > - <Row className="g-0"> - <Col className="m-1"> - <Input - value={avatarID} - onChange={({ target: { value } }) => { - setAvatarID(value); - }} - placeholder={t("signInID")} - /> - </Col> - </Row> - <Row className="g-0"> - <Col className="m-1"> - <Input - value={avatarCipher} - onChange={({ target: { value } }) => { - setAvatarCipher(value); - }} - type="password" - placeholder={t("signInCipher")} - onKeyDown={({ key }) => { - if (key === "Enter") { - onSignIn(); - } - }} - /> - </Col> - </Row> - <Row className="justify-content-center g-0"> - <Col className="m-1" xs="auto"> - <Button color="success" onClick={onSignIn}> - {t("signIn")} - </Button> - </Col> - <Col className="m-1" xs="auto"> - <Button - color={autoSignIn ? "success" : "danger"} - onClick={() => { - setAutoSignIn((prevState) => !prevState); - }} - > - {t("autoSignIn")} - </Button> - </Col> - </Row> - </Modal> - ); -}); diff --git a/qwilight-fe/src/site/Site.d.ts b/qwilight-fe/src/site/Site.d.ts deleted file mode 100644 index ac2bda1..0000000 --- a/qwilight-fe/src/site/Site.d.ts +++ /dev/null @@ -1,87 +0,0 @@ -import { TriggerEvent } from "react-contexify"; - -export type Avatar = { - avatarID: string; - avatarName: string; - avatarConfigure: number; - isSiteHand: boolean; - isMe: boolean; - isValve: boolean; - isAudioInput: boolean; -}; - -export type SiteYell = { - avatarID?: string; - avatarName?: string; - siteYellVariety: ?string; - date?: string; - siteYell?: - | string - | CommentSiteYell - | AbilitySiteYell - | LevelSiteYell - | InviteSiteYell - | TVSiteYell; - siteYellID: number; -}; - -export type CommentSiteYell = { - avatarID: string; - avatarName: string; - title: string; - artist: string; - genre: string; - level: number; - levelText: string; - stand: number; - hitPointsMode: number; -}; - -export type AbilitySiteYell = { - avatarID: string; - avatarName: string; - inputMode: number; - ability: number; -}; - -export type LevelSiteYell = { - avatarID: string; - avatarName: string; - title: string; -}; - -export type InviteSiteYell = { - siteID: string; - siteName: string; - avatarName: string; -}; - -export type TVSiteYell = { - href: string; - title: string; - text: string; -}; - -export type SiteView = { - siteID: string; - isEditable: boolean; - isNew: boolean; - wasNotify: boolean; - siteNotify: string; - siteName: string; - isNetMode: boolean; - avatars: Avatar[]; - siteHand: string; - situationValue: number; - siteYells: SiteYell[]; -}; - -export type Event = { eventID: number; text?: string; data?: ArrayBuffer[] }; - -export type EventHandler = (data: Event) => void; - -export type CloseEventHandler = () => void; - -export type OnAvatarInput = (e: TriggerEvent, avatarID: string) => void; - -export type OnSiteYellInput = (e: TriggerEvent, avatarID: string) => void; diff --git a/qwilight-fe/src/site/SiteCipherWindow.tsx b/qwilight-fe/src/site/SiteCipherWindow.tsx deleted file mode 100644 index 8d10884..0000000 --- a/qwilight-fe/src/site/SiteCipherWindow.tsx +++ /dev/null @@ -1,69 +0,0 @@ -import SiteComponent from "@/site/SiteComponent"; - -import { useSiteStore } from "@/Stores"; -import { observer } from "mobx-react-lite"; -import { useTranslations } from "next-intl"; -import { useState } from "react"; -import { Button, Col, Input, Modal, Row } from "reactstrap"; - -const EventPB = require("@/Event_pb"); - -export default observer( - ({ siteID, siteName }: { siteID: string; siteName: string }) => { - const { - setSiteWindowOpened, - isSiteCipherWindowOpened, - setSiteCipherWindowOpened, - } = useSiteStore(); - const [siteCipher, setSiteCipher] = useState(""); - const t = useTranslations(); - - const onEnterSite = () => { - SiteComponent.send({ - eventID: EventPB.Event.EventID.ENTER_SITE, - text: JSON.stringify({ siteID, siteCipher }), - }); - setSiteCipherWindowOpened(false); - setSiteWindowOpened(false); - }; - - return ( - <Modal - isOpen={isSiteCipherWindowOpened} - toggle={() => { - setSiteCipherWindowOpened(false); - }} - centered - > - <Row className="g-0"> - <Col className="m-1"> - <Input value={siteName} disabled /> - </Col> - </Row> - <Row className="g-0"> - <Col className="m-1"> - <Input - autoComplete="new-password" - value={siteCipher} - onChange={({ target: { value } }) => { - setSiteCipher(value); - }} - type="password" - placeholder={t("siteCipher")} - onKeyDown={({ key }) => { - if (key === "Enter") { - onEnterSite(); - } - }} - /> - </Col> - </Row> - <Row className="justify-content-center g-0"> - <Col className="m-1" xs="auto"> - <Button onClick={onEnterSite}>{t("enterSite")}</Button> - </Col> - </Row> - </Modal> - ); - }, -); diff --git a/qwilight-fe/src/site/SiteComponent.ts b/qwilight-fe/src/site/SiteComponent.ts deleted file mode 100644 index 0b1e44d..0000000 --- a/qwilight-fe/src/site/SiteComponent.ts +++ /dev/null @@ -1,93 +0,0 @@ -import { CloseEventHandler, Event, EventHandler } from "@/site/Site"; -import { getMillis } from "taehui-ts/date"; -import { getLanguage } from "taehui-ts/language"; - -const EventPB = require("@/Event_pb"); - -const siteComponent = new (class { - ws?: WebSocket; - avatarID: string; - eventDefaultHandler: EventHandler; - eventCloseHandler: CloseEventHandler; - onLoaded: () => void; - onData: ({ data }: { data: MessageEvent }) => void; - onClosed: () => void; - - constructor() { - this.ws = undefined; - this.avatarID = ""; - this.eventDefaultHandler = () => {}; - this.eventCloseHandler = () => {}; - - this.onLoaded = () => { - this.send({ - eventID: EventPB.Event.EventID.ESTABLISH, - text: JSON.stringify({ - language: getLanguage(), - }), - }); - }; - - this.onData = ({ data }) => { - try { - const { array } = EventPB.Event.deserializeBinary(data); - this.eventDefaultHandler({ - eventID: array[2], - text: array[3], - data: array[4], - }); - } catch (e) {} - }; - - this.onClosed = () => { - this.eventCloseHandler(); - this.connect(); - }; - } - - connect() { - this.ws = new WebSocket( - `${process.env.WS_API ?? "wss://taehui.ddns.net"}/qwilight/ws`, - ); - this.ws.binaryType = "arraybuffer"; - this.ws.addEventListener("open", this.onLoaded); - this.ws.addEventListener("message", this.onData); - this.ws.addEventListener("close", this.onClosed); - } - - disconnect() { - this.eventCloseHandler(); - this.ws?.removeEventListener("open", this.onLoaded); - this.ws?.removeEventListener("message", this.onData); - this.ws?.removeEventListener("close", this.onClosed); - this.ws?.close(); - } - - send({ eventID, text, data }: Event) { - try { - const event = new EventPB.Event(); - event.setMillis(getMillis()); - event.setAvatarid(this.avatarID); - event.setEventid(eventID); - event.setText(text); - data?.forEach((dataItem) => { - event.addData(dataItem); - }); - this.ws?.send(event.serializeBinary()); - } catch (e) {} - } - - setEventDefaultHandler(eventDefaultHandler: EventHandler) { - this.eventDefaultHandler = eventDefaultHandler; - } - - setEventCloseHandler(eventCloseHandler: CloseEventHandler) { - this.eventCloseHandler = eventCloseHandler; - } - - setAvatarID(avatarID: string) { - this.avatarID = avatarID; - } -})(); - -export default siteComponent; diff --git a/qwilight-fe/src/site/SiteInput.tsx b/qwilight-fe/src/site/SiteInput.tsx deleted file mode 100644 index 0076b7e..0000000 --- a/qwilight-fe/src/site/SiteInput.tsx +++ /dev/null @@ -1,134 +0,0 @@ -import SiteComponent from "@/site/SiteComponent"; - -import { useSiteStore } from "@/Stores"; -import { observer } from "mobx-react-lite"; -import { useTranslations } from "next-intl"; -import { Button, Col, Input, Row } from "reactstrap"; - -const EventPB = require("@/Event_pb"); - -export default observer(() => { - const { - targetSiteID, - isEditable, - input, - setInput, - isSignedIn, - setAvatarsOpened, - setConfigureOpened, - setSignInOpened, - } = useSiteStore(); - const t = useTranslations(); - - const postFile = (file: File) => { - const fr = new FileReader(); - fr.readAsArrayBuffer(file); - fr.addEventListener("loadend", () => { - const { result } = fr; - SiteComponent.send({ - eventID: EventPB.Event.EventID.POST_FILE, - text: file.name, - data: [new Uint8Array(result as ArrayBufferLike)], - }); - }); - }; - - return ( - <Row className="g-0"> - <Col className="m-1" xs="auto"> - <Button - onClick={() => { - const inputElement = document.createElement("input"); - inputElement.type = "file"; - inputElement.accept = "audio/*,image/*,video/*"; - inputElement.addEventListener("change", ({ target }) => { - const file = (target as HTMLInputElement).files?.[0]; - if (file) { - postFile(file); - } - }); - inputElement.click(); - }} - > - {t("postFile")} - </Button> - </Col> - <Col className="m-1"> - <Input - disabled={!isEditable} - value={input} - onChange={({ target: { value } }) => { - setInput(value); - }} - onKeyDown={({ key }) => { - if (key === "Enter") { - if (input.length > 0) { - SiteComponent.send({ - eventID: EventPB.Event.EventID.SITE_YELL, - text: JSON.stringify({ - siteID: targetSiteID, - siteYell: input, - }), - }); - setInput(""); - } - } - }} - onPaste={({ clipboardData: { items } }) => { - const data = items[0]; - if (data && data.kind === "file") { - const file = data.getAsFile(); - if (file) { - postFile(file); - } - } - }} - /> - </Col> - <Col className="m-1" xs="auto"> - {isSignedIn ? ( - <Button - color="danger" - onClick={() => { - window.localStorage.removeItem("avatarCipher"); - window.localStorage.removeItem("autoSignIn"); - SiteComponent.send({ - eventID: EventPB.Event.EventID.NOT_SIGN_IN, - }); - }} - > - {t("notSignIn")} - </Button> - ) : ( - <Button - color="success" - onClick={() => { - setSignInOpened(true); - }} - > - {t("signIn")} - </Button> - )} - </Col> - <Col className="m-1" xs="auto"> - <Button - color="info" - onClick={() => { - setAvatarsOpened(true); - }} - > - {t("onAvatars")} - </Button> - </Col> - <Col className="m-1" xs="auto"> - <Button - onClick={() => { - setConfigureOpened(true); - }} - > - {t("onConfigure")} - </Button> - </Col> - </Row> - ); -}); diff --git a/qwilight-fe/src/site/SiteWindow.tsx b/qwilight-fe/src/site/SiteWindow.tsx deleted file mode 100644 index 4da4611..0000000 --- a/qwilight-fe/src/site/SiteWindow.tsx +++ /dev/null @@ -1,103 +0,0 @@ -import sc from "@/assets/sc.png"; - -import sc0 from "@/assets/sc0.png"; -import sc2 from "@/assets/sc2.png"; -import NewSiteWindow from "@/site/NewSiteWindow"; -import SiteCipherWindow from "@/site/SiteCipherWindow"; -import SiteComponent from "@/site/SiteComponent"; - -import useGetSites from "@/site/useGetSites"; - -import { useSiteStore } from "@/Stores"; -import { observer } from "mobx-react-lite"; -import { useTranslations } from "next-intl"; -import Image from "next/image"; -import { useState } from "react"; -import { Button, Col, Modal, Row } from "reactstrap"; - -const EventPB = require("@/Event_pb"); - -const scs = [sc0, "", sc2]; - -export default observer(() => { - const { - siteAvatarID, - isSiteWindowOpened, - setSiteWindowOpened, - setSiteCipherWindowOpened, - targetSiteID, - setNewSiteWindowOpened, - } = useSiteStore(); - const t = useTranslations(); - - const [siteID, setSiteID] = useState(""); - const [siteName, setSiteName] = useState(""); - - const { data: sites } = useGetSites(); - - const onClose = () => { - setSiteWindowOpened(false); - }; - - return ( - <Modal isOpen={isSiteWindowOpened} toggle={onClose} centered> - <Row className="g-0"> - <Col className="m-1" xs="auto"> - {sites.map( - ({ siteID, hasCipher, siteConfigure, siteName, avatarCount }) => ( - <Row - key={siteID} - className={`g-0 ${targetSiteID === siteID ? "target" : ""}`} - > - <Col className="m-1" xs="auto"> - {scs[siteConfigure] && ( - <Image alt="" src={scs[siteConfigure]} height={24} /> - )}{" "} - <span - className="route" - onClick={() => { - if (hasCipher) { - setSiteID(siteID); - setSiteName(siteName); - setSiteCipherWindowOpened(true); - } else { - SiteComponent.send({ - eventID: EventPB.Event.EventID.ENTER_SITE, - text: JSON.stringify({ siteID, siteCipher: "" }), - }); - onClose(); - } - }} - > - {siteName} ({t("avatarCountText", { avatarCount })}) - {hasCipher && ( - <> - {" "} - <Image alt="" src={sc} height={24} /> - </> - )} - </span> - </Col> - </Row> - ), - )} - </Col> - </Row> - <Row className="justify-content-center g-0"> - <Col className="m-1" xs="auto"> - <Button - onClick={() => { - setNewSiteWindowOpened(true); - }} - disabled={!siteAvatarID} - > - {t("siteWindowNew")} - </Button> - </Col> - </Row> - - <SiteCipherWindow siteID={siteID} siteName={siteName} /> - <NewSiteWindow /> - </Modal> - ); -}); diff --git a/qwilight-fe/src/site/SiteYellItem.module.scss b/qwilight-fe/src/site/SiteYellItem.module.scss deleted file mode 100644 index fb8d9ca..0000000 --- a/qwilight-fe/src/site/SiteYellItem.module.scss +++ /dev/null @@ -1,44 +0,0 @@ -@mixin file() { - border: thin white solid; - max-height: 9rem; -} - -img { - &.file { - @include file(); - } - - &.tv { - width: 3.75rem; - height: 3.75rem; - } -} - -video { - &.file { - @include file(); - } -} - -audio { - &.file { - @include file(); - } -} - -svg { - &.tv { - width: 3.75rem; - height: 3.75rem; - } -} - -span { - &.enter { - color: deepskyblue; - } - - &.quit { - color: deeppink; - } -} diff --git a/qwilight-fe/src/site/SiteYellItem.tsx b/qwilight-fe/src/site/SiteYellItem.tsx deleted file mode 100644 index bab8b94..0000000 --- a/qwilight-fe/src/site/SiteYellItem.tsx +++ /dev/null @@ -1,411 +0,0 @@ -import TV0 from "@/assets/tv0.svg"; -import tv1 from "@/assets/tv1.png"; -import AvatarDrawing from "@/AvatarDrawing"; -import AvatarTitle from "@/AvatarTitle"; -import { - AbilitySiteYell, - CommentSiteYell, - InviteSiteYell, - LevelSiteYell, - OnSiteYellInput, - SiteYell, - TVSiteYell, -} from "@/site/Site"; -import SiteComponent from "@/site/SiteComponent"; -import scss from "@/site/SiteYellItem.module.scss"; - -import { useSiteStore } from "@/Stores"; -import { - formatText, - getAbilityUpText, - getGenreText, - getHitPointsClass, -} from "@/Utility"; -import { sanitize } from "isomorphic-dompurify"; -import { observer } from "mobx-react-lite"; -import { useTranslations } from "next-intl"; -import Image from "next/image"; -import { Col, Row } from "reactstrap"; - -const EventPB = require("@/Event_pb"); - -export default observer( - ({ - data, - onSiteYellInput, - }: { - data: SiteYell; - onSiteYellInput: OnSiteYellInput; - }) => { - const { siteYellVariety, date, avatarID, avatarName, siteYell } = data; - const { saveTraffic } = useSiteStore(); - const t = useTranslations(); - - const doSiteYell = (siteYell: string) => { - siteYell = siteYell.replace(" ", " "); - const m = siteYell.match(/(http|https|mailto|rtmp):\/\/[^ ]+/i); - if (m != null) { - const t = m[0]; - - if ( - !saveTraffic && - t.match(/(\.aac|\.flac|\.mid|\.midi|\.mp3|\.ogg|\.wav|\.wma)($|\?)/i) - ) { - return siteYell.replace( - t, - `<audio class="${scss.file}" src="${t}" controls></audio>`, - ); - } - - if ( - !saveTraffic && - t.match(/(\.bmp|\.gif|\.heic|\.jpeg|\.jpg|\.png|\.webp)($|\?)/i) - ) { - return siteYell.replace( - t, - `<a href="${t}" target="_blank"> - <img class="${scss.file}" src="${t}" alt=""> - </a>`, - ); - } - - if ( - !saveTraffic && - t.match(/(\.avi|\.mkv|\.mp4|\.mpeg|\.mpg|\.wmv)($|\?)/i) - ) { - return siteYell.replace( - t, - `<video class="${scss.file}" src="${t}" controls></video>`, - ); - } - - return siteYell.replace(t, `<a href="${t}" target="_blank">${t}</a>`); - } - - return siteYell; - }; - - switch (siteYellVariety) { - case "@Enter": - return ( - <Row - className="g-0" - style={{ flexWrap: "nowrap" }} - onContextMenu={(e) => { - e.preventDefault(); - avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); - }} - > - {avatarID && ( - <Col className="m-1" xs="auto"> - <AvatarDrawing avatarID={avatarID} /> - </Col> - )} - <Col className="m-1" xs="auto"> - {avatarID && <AvatarTitle avatarID={avatarID} />} - <span>{avatarName}</span> <span className="date">{date}</span> - <br /> - <span className={scss.enter}>{t("siteYellEnter")}</span> - </Col> - </Row> - ); - case "@Quit": - return ( - <Row - className="g-0" - style={{ flexWrap: "nowrap" }} - onContextMenu={(e) => { - e.preventDefault(); - avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); - }} - > - {avatarID && ( - <Col className="m-1" xs="auto"> - <AvatarDrawing avatarID={avatarID} /> - </Col> - )} - <Col className="m-1" xs="auto"> - {avatarID && <AvatarTitle avatarID={avatarID} />} - <span>{avatarName}</span> <span className="date">{date}</span> - <br /> - <span className={scss.quit}>{t("siteYellQuit")}</span> - </Col> - </Row> - ); - case "@Site": - return ( - <Row - className="g-0" - style={{ flexWrap: "nowrap" }} - onContextMenu={(e) => { - e.preventDefault(); - avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); - }} - > - {avatarID && ( - <Col className="m-1" xs="auto"> - <AvatarDrawing avatarID={avatarID} /> - </Col> - )} - <Col className="m-1" xs="auto"> - {avatarID && <AvatarTitle avatarID={avatarID} />} - <span>{avatarName}</span> <span className="date">{date}</span> - <br /> - <span className={scss.enter}>{t("siteYellNewSite")}</span> - </Col> - </Row> - ); - case "@Net": - return ( - <Row - className="g-0" - style={{ flexWrap: "nowrap" }} - onContextMenu={(e) => { - e.preventDefault(); - avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); - }} - > - {avatarID && ( - <Col className="m-1" xs="auto"> - <AvatarDrawing avatarID={avatarID} /> - </Col> - )} - <Col className="m-1" xs="auto"> - {avatarID && <AvatarTitle avatarID={avatarID} />} - <span>{avatarName}</span> <span className="date">{date}</span> - <br /> - <span className={scss.enter}>{t("siteYellNewNetSite")}</span> - </Col> - </Row> - ); - case "@Notify": - return ( - <Row className="g-0" style={{ flexWrap: "nowrap" }}> - <Col className="m-1" xs="auto"> - <span className="taehui">{t("siteYellTaehui")}</span>{" "} - <span className="date">{date}</span> - <br /> - <span - dangerouslySetInnerHTML={{ - __html: doSiteYell(siteYell as string), - }} - /> - </Col> - </Row> - ); - case "@Invite": { - const { siteID, siteName, avatarName } = siteYell as InviteSiteYell; - return ( - <Row - className="g-0" - style={{ flexWrap: "nowrap" }} - onContextMenu={(e) => { - e.preventDefault(); - avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); - }} - > - {avatarID && ( - <Col className="m-1" xs="auto"> - <AvatarDrawing avatarID={avatarID} /> - </Col> - )} - <Col className="m-1" xs="auto"> - {avatarID && <AvatarTitle avatarID={avatarID} />} - <span>{avatarName}</span> <span className="date">{date}</span> - <br /> - <span - className="route" - onClick={() => { - SiteComponent.send({ - eventID: EventPB.Event.EventID.ENTER_SITE, - text: JSON.stringify({ - siteID, - siteCipher: "", - }), - }); - }} - > - {t("siteYellInvite", { siteName })} - </span> - </Col> - </Row> - ); - } - case "@TV": - const { href, title, text } = siteYell as TVSiteYell; - return ( - <Row className="g-0" style={{ flexWrap: "nowrap" }}> - <Col className="m-1" xs="auto"> - {href.startsWith("https://www.twitch.tv") && ( - <TV0 className={scss.tv} /> - )} - {href.startsWith("https://chzzk.naver.com") && ( - <Image src={tv1} alt="" className={scss.tv} /> - )} - </Col> - <Col className="m-1" xs="auto"> - <span>{text}</span> <span className="date">{date}</span> - <br /> - <span - className="route" - onClick={() => { - window.open(href); - }} - > - {t("siteYellTV", { title })} - </span> - </Col> - </Row> - ); - case "@Wiped": - return ( - <Row className="g-0" style={{ flexWrap: "nowrap" }}> - <Col - className="m-1" - xs="auto" - onContextMenu={(e) => { - e.preventDefault(); - avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); - }} - > - {avatarID && <AvatarDrawing avatarID={avatarID} />} - </Col> - <Col className="m-1" xs="auto"> - {avatarID && <AvatarTitle avatarID={avatarID} />} - <span>{avatarName}</span> <span className="date">{date}</span> - <br /> - <span>{t("wipedSiteYell")}</span> - </Col> - </Row> - ); - case "@Comment": { - const { - avatarID, - avatarName, - title, - artist, - genre, - level, - levelText, - stand, - hitPointsMode, - } = siteYell as CommentSiteYell; - return ( - <Row - className="g-0" - style={{ flexWrap: "nowrap" }} - onContextMenu={(e) => { - e.preventDefault(); - avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); - }} - > - {avatarID && ( - <Col className="m-1" xs="auto"> - <AvatarDrawing avatarID={avatarID} /> - </Col> - )} - <Col className="m-1" xs="auto"> - {avatarID && <AvatarTitle avatarID={avatarID} />} - <span>{avatarName}</span> <span className="date">{date}</span> - <br /> - <span className={`level${level}`}>{levelText}</span>{" "} - <span className="artist">{artist}</span>{" "} - <span className="title">{title}</span>{" "} - <span className="genre">{getGenreText(genre)}</span> - <br /> - <span className={getHitPointsClass(hitPointsMode)}> - {t("textStand", { value: formatText(stand) })} - </span> - </Col> - </Row> - ); - } - case "@Ability": { - const { avatarID, avatarName } = siteYell as AbilitySiteYell; - return ( - <Row - className="g-0" - style={{ flexWrap: "nowrap" }} - onContextMenu={(e) => { - e.preventDefault(); - avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); - }} - > - {avatarID && ( - <Col className="m-1" xs="auto"> - <AvatarDrawing avatarID={avatarID} /> - </Col> - )} - <Col className="m-1" xs="auto"> - {avatarID && <AvatarTitle avatarID={avatarID} />} - <span>{avatarName}</span> <span className="date">{date}</span> - <br /> - <span>{getAbilityUpText(t, siteYell as AbilitySiteYell)}</span> - <br /> - </Col> - </Row> - ); - } - case "@Level": { - const { avatarID, avatarName, title } = siteYell as LevelSiteYell; - return ( - <Row - className="g-0" - style={{ flexWrap: "nowrap" }} - onContextMenu={(e) => { - e.preventDefault(); - avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); - }} - > - {avatarID && ( - <Col className="m-1" xs="auto"> - <AvatarDrawing avatarID={avatarID} /> - </Col> - )} - <Col className="m-1" xs="auto"> - {avatarID && <AvatarTitle avatarID={avatarID} />} - <span>{avatarName}</span> <span className="date">{date}</span> - <br /> - <span>{t("wwwLevelClearText", { title })}</span> - <br /> - </Col> - </Row> - ); - } - case "": - return ( - <> - <span>{siteYell as string}</span> - <br /> - </> - ); - case null: - return ( - <Row className="g-0" style={{ flexWrap: "nowrap" }}> - <Col - className="m-1" - xs="auto" - onContextMenu={(e) => { - e.preventDefault(); - avatarID && onSiteYellInput && onSiteYellInput(e, avatarID); - }} - > - {avatarID && <AvatarDrawing avatarID={avatarID} />} - </Col> - <Col className="m-1" xs="auto"> - {avatarID && <AvatarTitle avatarID={avatarID} />} - <span>{avatarName}</span> <span className="date">{date}</span> - <br /> - <span - dangerouslySetInnerHTML={{ - __html: doSiteYell(sanitize(siteYell as string)), - }} - /> - </Col> - </Row> - ); - default: - return null; - } - }, -); diff --git a/qwilight-fe/src/site/SiteYellItems.tsx b/qwilight-fe/src/site/SiteYellItems.tsx deleted file mode 100644 index f93e2cc..0000000 --- a/qwilight-fe/src/site/SiteYellItems.tsx +++ /dev/null @@ -1,25 +0,0 @@ -import { OnSiteYellInput } from "@/site/Site"; - -import SiteYellItem from "@/site/SiteYellItem"; -import { useSiteStore } from "@/Stores"; -import { observer } from "mobx-react-lite"; - -export default observer( - ({ onSiteYellInput }: { onSiteYellInput: OnSiteYellInput }) => { - const { siteYells } = useSiteStore(); - - return ( - <> - {siteYells.map((siteYell) => - siteYell ? ( - <SiteYellItem - key={siteYell.siteYellID} - data={siteYell} - onSiteYellInput={onSiteYellInput} - /> - ) : null, - )} - </> - ); - }, -); diff --git a/qwilight-fe/src/site/setSiteStore.ts b/qwilight-fe/src/site/setSiteStore.ts deleted file mode 100644 index 22525e9..0000000 --- a/qwilight-fe/src/site/setSiteStore.ts +++ /dev/null @@ -1,737 +0,0 @@ -import { AbilitySiteYell, Avatar, SiteView, SiteYell } from "@/site/Site"; - -import SiteComponent from "@/site/SiteComponent"; -import { - formatText, - getAbilityUpText, - getDefaultAvatarID, - getGenreText, - getSiteName, -} from "@/Utility"; -import { wwwAPI } from "@/Www"; -import CryptoJS from "crypto-js"; -import { runInAction } from "mobx"; -import { useTranslations } from "next-intl"; -import { RefObject } from "react"; -import { toast } from "react-toastify"; - -const EventPB = require("@/Event_pb"); - -const getSiteYellItem = ({ - avatarID, - avatarName, - siteYell, - date, - siteYellID, -}: { - avatarID: string; - avatarName: string; - siteYell: string; - date: number; - siteYellID: number; -}): SiteYell | null => { - const dateText = new Date(date).toLocaleTimeString(); - switch (avatarName) { - case "@Enter": - return { - siteYellID, - avatarID, - avatarName: siteYell, - siteYellVariety: avatarName, - date: dateText, - }; - case "@Quit": - return { - siteYellID, - avatarID, - avatarName: siteYell, - siteYellVariety: avatarName, - date: dateText, - }; - case "@Site": - return { - siteYellID, - avatarID, - avatarName: siteYell, - siteYellVariety: avatarName, - date: dateText, - }; - case "@Net": - return { - siteYellID, - avatarID, - avatarName: siteYell, - siteYellVariety: avatarName, - date: dateText, - }; - case "@Notify": - return { - siteYellID, - avatarID, - siteYellVariety: avatarName, - date: dateText, - siteYell, - }; - case "@Wiped": - return { - siteYellID, - avatarID, - avatarName: siteYell, - siteYellVariety: avatarName, - date: dateText, - }; - case "@Invite": - case "@Comment": - case "@Ability": - case "@Level": - case "@TV": - return { - siteYellID, - avatarID, - siteYellVariety: avatarName, - date: dateText, - siteYell: JSON.parse(siteYell), - }; - case "": - return { - siteYellID, - siteYellVariety: "", - siteYell, - }; - default: - return { - siteYellID, - siteYellVariety: null, - date: dateText, - avatarID, - avatarName, - siteYell, - }; - } -}; - -export default function setSiteStore() { - return { - titleComponent: undefined as RefObject<HTMLDivElement> | undefined, - siteYellsView: undefined as RefObject<HTMLDivElement> | undefined, - avatars: [] as Avatar[], - siteYells: [] as SiteYell[], - isSignInOpened: false, - isSiteWindowOpened: false, - isSiteCipherWindowOpened: false, - isNewSiteWindowOpened: false, - isConfigureOpened: false, - targetSiteID: "", - siteNotify: "", - saveTraffic: - typeof window === "object" && - window.localStorage.getItem("saveTraffic") === "true", - autoEnterNotify: - typeof window === "object" && - window.localStorage.getItem("autoEnterNotify") !== "false", - autoEnterDefault: - typeof window === "object" && - window.localStorage.getItem("autoEnterDefault") !== "false", - autoEnterPlatform: - typeof window === "object" && - window.localStorage.getItem("autoEnterPlatform") !== "false", - isEditable: true, - input: "", - siteViews: [] as SiteView[], - siteAvatarID: "", - siteAvatarName: "", - isSignedIn: false, - isSiteYellsViewLowest: true, - isVisible: false, - isLoading: true, - lastPendingSiteYell: undefined as SiteYell | undefined, - isPendingSiteYellOpened: false, - isAvatarsOpened: false, - - setComponents( - titleComponent: RefObject<HTMLDivElement>, - siteYellsView: RefObject<HTMLDivElement>, - ) { - this.titleComponent = titleComponent; - this.siteYellsView = siteYellsView; - }, - - setEventHandler(t: ReturnType<typeof useTranslations<string>>) { - const autoEnter = () => { - SiteComponent.send({ - eventID: EventPB.Event.EventID.ENTER_SITE, - text: JSON.stringify({ - siteID: "00000000-0000-0000-0000-000000000003", - siteCipher: "", - }), - }); - if (this.autoEnterNotify) { - SiteComponent.send({ - eventID: EventPB.Event.EventID.ENTER_SITE, - text: JSON.stringify({ - siteID: "00000000-0000-0000-0000-000000000000", - siteCipher: "", - }), - }); - } - if (this.autoEnterDefault) { - SiteComponent.send({ - eventID: EventPB.Event.EventID.ENTER_SITE, - text: JSON.stringify({ - siteID: "00000000-0000-0000-0000-000000000001", - siteCipher: "", - }), - }); - } - if (this.autoEnterPlatform) { - SiteComponent.send({ - eventID: EventPB.Event.EventID.ENTER_SITE, - text: JSON.stringify({ - siteID: "00000000-0000-0000-0000-000000000002", - siteCipher: "", - }), - }); - } - }; - - const autoSignIn = () => { - if (window.localStorage.getItem("autoSignIn") === "true") { - SiteComponent.send({ - eventID: EventPB.Event.EventID.SIGN_IN, - text: JSON.stringify({ - avatarID: window.localStorage.getItem("avatarID") ?? "", - avatarCipher: CryptoJS.AES.decrypt( - window.localStorage.getItem("avatarCipher") ?? "", - "591A6F91-2A27-4A88-88FA-0FEB7CB5FD94", - ).toString(CryptoJS.enc.Utf8), - }), - }); - } - }; - - const doNotify = (avatarID: string, toNotify: string, siteID: string) => { - if ( - !["denied", "default"].includes(Notification?.permission) && - !this.isVisible - ) { - const siteView = this.getSiteView(siteID); - if (siteView?.wasNotify === false) { - new Notification("Qwilight", { - body: toNotify, - icon: `${wwwAPI}/drawing?avatarID=${encodeURIComponent( - getDefaultAvatarID(avatarID), - )}&drawingVariety=0`, - }); - siteView.wasNotify = true; - } - } - }; - - SiteComponent.setEventDefaultHandler(({ eventID, text }) => { - switch (eventID) { - case EventPB.Event.EventID.ESTABLISH: - if (text) { - const { avatarID, avatarName } = JSON.parse(text); - this.setSiteAvatar(avatarID, avatarName); - this.setLoading(false); - autoEnter(); - const totem = window.sessionStorage.getItem("totem"); - if (totem) { - SiteComponent.send({ - eventID: EventPB.Event.EventID.SIGN_IN, - text: totem, - }); - } else { - autoSignIn(); - } - } - break; - case EventPB.Event.EventID.FAILED_VALIDATE_TOTEM: - autoSignIn(); - break; - // EventPB.Event.EventID.SIGN_IN - case undefined: - if (text) { - this.setSignInOpened(false); - const { totem, avatarID, avatarName } = JSON.parse(text); - if (totem !== window.sessionStorage.getItem("totem")) { - toast.success(t("signedInText", { avatarName })); - } - window.sessionStorage.setItem("totem", totem); - this.setSiteAvatar(avatarID, avatarName); - this.setSignedIn(true); - autoEnter(); - } - break; - case EventPB.Event.EventID.NOT_SIGN_IN: - if (text) { - toast.success( - t("notSignedInText", { - avatarName: this.siteAvatarName, - }), - ); - window.sessionStorage.removeItem("totem"); - const { avatarID, avatarName } = JSON.parse(text); - this.setSiteAvatar(avatarID, avatarName); - this.setSignedIn(false); - autoEnter(); - } - break; - case EventPB.Event.EventID.SITE_YELL: - if (text) { - const { - siteID, - avatarID, - avatarName, - siteYell, - siteYellID, - date, - } = JSON.parse(text); - const siteYellItem = getSiteYellItem({ - avatarID, - avatarName, - siteYell, - date, - siteYellID, - }); - if (siteYellItem) { - this.putSiteYell(siteID, siteYellItem, false); - if (this.targetSiteID === siteID) { - this.putTargetSiteYell(siteYellItem, false); - if ( - avatarID === this.siteAvatarID || - this.isSiteYellsViewLowest - ) { - this.siteYellsViewMove(); - } else { - runInAction(() => { - this.lastPendingSiteYell = siteYellItem; - }); - this.setPendingSiteYellOpened(true); - } - } else { - this.setModifiedSiteViews(siteID, (siteView) => { - siteView.isNew = true; - }); - } - } - const ltDate = new Date(Number(date)).toLocaleTimeString(); - let toNotify = ""; - switch (avatarName) { - case "@Notify": - if (this.targetSiteID === siteID) { - this.siteNotify = siteYell; - } else { - const siteView = this.getSiteView(siteID); - if (siteView) { - siteView.siteNotify = siteYell; - } - } - toNotify = `${t("siteYellTaehui")} (${ltDate}) ${siteYell}`; - break; - case "@Comment": { - const { avatarName, artist, title, genre, levelText, stand } = - JSON.parse(siteYell); - toNotify = `${avatarName} (${ltDate}) ${levelText} ${artist} - ${title} ${getGenreText( - genre, - )} ${t("textStand", { value: formatText(stand) })}`; - break; - } - case "@Ability": { - toNotify = getAbilityUpText( - t, - JSON.parse(siteYell) as AbilitySiteYell, - ); - break; - } - case "@Level": { - const { title } = JSON.parse(siteYell); - toNotify = t("wwwLevelClearText", { title }); - break; - } - case "@Enter": { - toNotify = `${siteYell} ${ltDate} ${t("siteYellEnter")}`; - break; - } - case "@Quit": { - toNotify = `${siteYell} ${ltDate} ${t("siteYellQuit")}`; - break; - } - case "@Invite": { - const { avatarName, siteName } = JSON.parse(siteYell); - toNotify = `${avatarName} (${ltDate}) ${t("siteYellInvite", { - siteName, - })}`; - break; - } - case "@TV": { - const { title, text } = JSON.parse(siteYell); - toNotify = `${text} (${ltDate}) ${t("siteYellTV", { - title, - })}`; - break; - } - case "@Wiped": - toNotify = `${avatarName} (${ltDate}) ${t("wipedSiteYell")}`; - break; - case "": - toNotify = siteYell; - break; - case null: - toNotify = `${avatarName} (${ltDate}) ${siteYell}`; - break; - } - if (toNotify) { - doNotify(avatarID, toNotify, siteID); - } - } - break; - case EventPB.Event.EventID.MODIFY_SITE_YELL: - if (text) { - const { siteID, siteYell, siteYellID } = JSON.parse(text); - this.doModifySiteYell(siteID, siteYell, siteYellID); - if (this.targetSiteID === siteID) { - this.doModifyTargetSiteYell(siteYell, siteYellID); - } - } - break; - case EventPB.Event.EventID.WIPE_SITE_YELL: - if (text) { - const { siteID, siteYellID } = JSON.parse(text); - this.wipeSiteYell(siteID, siteYellID); - if (this.targetSiteID === siteID) { - this.wipeTargetSiteYell(siteYellID); - } - } - break; - case EventPB.Event.EventID.GET_SITE_YELLS: - if (text) { - if (this.siteYellsView) { - const { current } = this.siteYellsView; - if (current) { - const lastPosition1BeforeCalled = - current.scrollHeight - current.clientHeight; - const { siteID, data } = JSON.parse(text); - - data - .reverse() - .map(getSiteYellItem) - .forEach((siteYellItem: SiteYell) => { - this.putSiteYell(siteID, siteYellItem, true); - if (this.targetSiteID === siteID) { - this.putTargetSiteYell(siteYellItem, true); - } - }); - - setTimeout(() => { - current.scrollTop = - current.scrollHeight - - current.clientHeight - - lastPosition1BeforeCalled; - }, 0); - } - } - } - break; - case EventPB.Event.EventID.CALL_SITE_AVATAR: - if (text) { - const { siteID, siteName, situationValue, data, siteHand } = - JSON.parse(text); - const avatars = data.map( - ({ - avatarID, - avatarName, - avatarConfigure, - isValve, - isAudioInput, - }: { - avatarID: string; - avatarName: string; - avatarConfigure: number; - isValve: boolean; - isAudioInput: boolean; - }) => { - return { - avatarID, - avatarName, - avatarConfigure, - isSiteHand: avatarID === siteHand, - isMe: this.siteAvatarID === avatarID, - isValve, - isAudioInput, - }; - }, - ); - this.setModifiedSiteViews(siteID, (siteView) => { - siteView.siteName = getSiteName(siteName, t); - siteView.avatars = avatars; - siteView.siteHand = siteHand; - siteView.situationValue = situationValue; - }); - if (siteID === this.targetSiteID) { - this.setAvatars(avatars); - } - } - break; - case EventPB.Event.EventID.ENTER_SITE: - if (text) { - const { siteID, siteNotify, isEditable, isNetMode, data } = - JSON.parse(text); - this.putSiteView({ - siteID, - isEditable, - isNew: false, - wasNotify: false, - siteNotify, - siteName: "", - siteHand: "", - situationValue: 0, - isNetMode, - avatars: [], - siteYells: data.map(getSiteYellItem), - }); - this.onSiteIDModified(siteID); - } - break; - case EventPB.Event.EventID.QUIT_SITE: - if (text) { - this.quitSiteView(text); - this.onSiteIDModified( - this.siteViews[this.siteViews.length - 1]?.siteID, - ); - } - break; - case EventPB.Event.EventID.WARNING: - toast.warning(text); - break; - case EventPB.Event.EventID.NOTIFY_YES: - toast.success(text); - break; - case EventPB.Event.EventID.NOTIFY_INFO: - toast.info(text); - break; - case EventPB.Event.EventID.POST_FILE: - if (text) { - this.setInput(text); - } - break; - } - }); - }, - - setEventCloseHandler() { - SiteComponent.setEventCloseHandler(() => { - this.setSiteAvatar("", ""); - this.setSignedIn(false); - this.onSiteIDModified(""); - this.wipeSiteViews(); - this.setLoading(true); - }); - }, - - setPendingSiteYellOpened(isPendingSiteYellOpened: boolean) { - this.isPendingSiteYellOpened = isPendingSiteYellOpened; - }, - - setLoading(isLoading: boolean) { - this.isLoading = isLoading; - }, - - setSiteAvatar(siteAvatarID: string, siteAvatarName: string) { - this.siteAvatarID = siteAvatarID; - this.siteAvatarName = siteAvatarName; - SiteComponent.setAvatarID(this.siteAvatarID); - }, - - putSiteYell(siteID: string, siteYell: SiteYell, isGetSiteYell: boolean) { - const siteView = this.getSiteView(siteID); - if (isGetSiteYell) { - siteView?.siteYells?.unshift(siteYell); - } else { - siteView?.siteYells?.push(siteYell); - } - }, - - putTargetSiteYell(siteYell: SiteYell, isGetSiteYell: boolean) { - if (isGetSiteYell) { - this.siteYells.unshift(siteYell); - } else { - this.siteYells.push(siteYell); - } - }, - - doModifySiteYell(siteID: string, siteYell: string, siteYellID: number) { - const targetSiteYell = this.getSiteView(siteID)?.siteYells?.find( - (siteYell) => siteYell.siteYellID === siteYellID, - ); - if (targetSiteYell) { - targetSiteYell.siteYell = siteYell; - } - }, - - doModifyTargetSiteYell(siteYell: string, siteYellID: number) { - const targetSiteYell = this.siteYells?.find( - (siteYell) => siteYell.siteYellID === siteYellID, - ); - if (targetSiteYell) { - targetSiteYell.siteYell = siteYell; - } - }, - - wipeSiteYell(siteID: string, siteYellID: number) { - const siteYells = this.getSiteView(siteID)?.siteYells; - if (siteYells) { - const i = siteYells.findIndex( - (siteYell) => siteYell.siteYellID === siteYellID, - ); - const siteYell = siteYells[i]; - siteYells.splice(i, 1, { - siteYellID, - avatarID: siteYell.avatarID, - avatarName: siteYell.avatarName, - siteYellVariety: "@Wiped", - date: siteYell.date, - }); - } - }, - - wipeTargetSiteYell(siteYellID: number) { - const i = this.siteYells.findIndex( - (siteYell) => siteYell.siteYellID === siteYellID, - ); - const siteYell = this.siteYells[i]; - this.siteYells.splice(i, 1, { - siteYellID, - avatarID: siteYell.avatarID, - avatarName: siteYell.avatarName, - siteYellVariety: "@Wiped", - date: siteYell.date, - }); - }, - - setModifiedSiteViews( - targetSiteID: string, - onModified: (siteView: SiteView) => void, - ) { - const tmpSiteView = this.siteViews.find( - ({ siteID }) => targetSiteID === siteID, - ); - if (tmpSiteView) { - onModified(tmpSiteView); - } - }, - - setInput(input: string) { - this.input = input; - }, - - setSaveTraffic(SaveTraffic: boolean) { - this.saveTraffic = SaveTraffic; - }, - - setAutoEnterNotify(autoEnterNotify: boolean) { - this.autoEnterNotify = autoEnterNotify; - }, - - setAutoEnterDefault(autoEnterDefault: boolean) { - this.autoEnterDefault = autoEnterDefault; - }, - - setAutoEnterPlatform(autoEnterPlatform: boolean) { - this.autoEnterPlatform = autoEnterPlatform; - }, - - setSignInOpened(isSignInOpened: boolean) { - this.isSignInOpened = isSignInOpened; - }, - - setSiteWindowOpened(isSiteWindowOpened: boolean) { - this.isSiteWindowOpened = isSiteWindowOpened; - }, - - setSiteCipherWindowOpened(isSiteCipherWindowOpened: boolean) { - this.isSiteCipherWindowOpened = isSiteCipherWindowOpened; - }, - - setNewSiteWindowOpened(isNewSiteWindowOpened: boolean) { - this.isNewSiteWindowOpened = isNewSiteWindowOpened; - }, - - setConfigureOpened(isConfigureOpened: boolean) { - this.isConfigureOpened = isConfigureOpened; - }, - - setSiteYellsViewLowest(isSiteYellsViewLowest: boolean) { - this.isSiteYellsViewLowest = isSiteYellsViewLowest; - }, - - getSiteView(targetSiteID: string) { - return this.siteViews.find(({ siteID }) => siteID === targetSiteID); - }, - - onSiteIDModified(siteID: string) { - this.targetSiteID = siteID; - const siteView = this.getSiteView(siteID); - if (siteView) { - if (this.isVisible) { - siteView.wasNotify = false; - } - this.setModifiedSiteViews(siteID, (siteView) => { - siteView.isNew = false; - }); - this.isEditable = siteView.isEditable; - this.siteNotify = siteView.siteNotify; - this.avatars = [...siteView.avatars]; - this.siteYells = [...siteView.siteYells]; - this.siteYellsViewMove(); - } else { - this.isEditable = false; - this.siteNotify = ""; - this.avatars = []; - this.siteYells = []; - } - }, - - setVisible() { - return (this.isVisible = document.visibilityState === "visible"); - }, - - siteYellsViewMove() { - setTimeout(() => { - if (this.siteYellsView) { - const { current } = this.siteYellsView; - if (current) { - current.scrollTop = current.scrollHeight; - } - } - }, 0); - }, - - setAvatarsOpened(isAvatarsOpened: boolean) { - this.isAvatarsOpened = isAvatarsOpened; - }, - - setSignedIn(isSignedIn: boolean) { - this.isSignedIn = isSignedIn; - }, - - setAvatars(avatars: Avatar[]) { - this.avatars = avatars; - }, - - putSiteView(siteView: SiteView) { - this.siteViews.push(siteView); - }, - - quitSiteView(siteID: string) { - this.siteViews.splice( - this.siteViews.findIndex((siteView) => siteView.siteID === siteID), - 1, - ); - }, - - wipeSiteViews() { - this.siteViews = []; - }, - }; -} diff --git a/qwilight-fe/src/site/useGetSites.ts b/qwilight-fe/src/site/useGetSites.ts deleted file mode 100644 index cafc9b8..0000000 --- a/qwilight-fe/src/site/useGetSites.ts +++ /dev/null @@ -1,34 +0,0 @@ -import { useSiteStore } from "@/Stores"; -import { getSiteName } from "@/Utility"; - -import { wwwAXIOS } from "@/Www"; -import { GetSitesAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { useTranslations } from "next-intl"; -import { useIsPath } from "taehui-ts/fe-utility"; - -export default function useGetSites() { - const { isSiteWindowOpened } = useSiteStore(); - - const t = useTranslations(); - - const isPath = useIsPath(); - - return useQuery({ - enabled: isSiteWindowOpened && isPath("/site"), - queryKey: ["sites"], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetSitesAPI>("/sites"); - return data.map( - ({ siteID, siteName, siteConfigure, hasCipher, avatarCount }) => ({ - siteID, - siteName: getSiteName(siteName, t), - siteConfigure, - hasCipher, - avatarCount, - }), - ); - }, - initialData: [], - }); -} diff --git a/qwilight-fe/src/site/useSiteComponent.tsx b/qwilight-fe/src/site/useSiteComponent.tsx deleted file mode 100644 index 46826b7..0000000 --- a/qwilight-fe/src/site/useSiteComponent.tsx +++ /dev/null @@ -1,46 +0,0 @@ -import SiteComponent from "@/site/SiteComponent"; -import { useSiteStore } from "@/Stores"; -import { useTranslations } from "next-intl"; -import { useEffect } from "react"; - -export default function useSiteComponent() { - const { - targetSiteID, - getSiteView, - setVisible, - setEventHandler, - setEventCloseHandler, - } = useSiteStore(); - const t = useTranslations(); - - useEffect(() => { - const onVisibilityModified = () => { - if (setVisible()) { - const siteView = getSiteView(targetSiteID); - if (siteView) { - siteView.wasNotify = false; - } - } - }; - - document.addEventListener("visibilitychange", onVisibilityModified); - - return () => { - document.removeEventListener("visibilitychange", onVisibilityModified); - }; - }, [getSiteView, setVisible, targetSiteID]); - - useEffect(() => { - setVisible(); - setEventHandler(t); - setEventCloseHandler(); - }, [setEventCloseHandler, setEventHandler, setVisible, t]); - - useEffect(() => { - SiteComponent.connect(); - - return () => { - SiteComponent.disconnect(); - }; - }, []); -} diff --git a/qwilight-fe/src/store/Stores.tsx b/qwilight-fe/src/store/Stores.tsx new file mode 100644 index 0000000..3f27a15 --- /dev/null +++ b/qwilight-fe/src/store/Stores.tsx @@ -0,0 +1,39 @@ +"use client"; + +import setAvatarStore from "@/app/[language]/avatar/store/setAvatarStore"; +import setHallStore from "@/app/[language]/hall/store/setHallStore"; +import setNoteStore from "@/app/[language]/note/store/setNoteStore"; +import setSiteStore from "@/app/[language]/site/store/setSiteStore"; +import { useLocalObservable } from "mobx-react-lite"; +import { createContext, FC, PropsWithChildren, useContext } from "react"; + +type MainStore = { + noteStore: ReturnType<typeof setNoteStore>; + siteStore: ReturnType<typeof setSiteStore>; + avatarStore: ReturnType<typeof setAvatarStore>; + hallStore: ReturnType<typeof setHallStore>; +}; + +const mainStore = createContext<MainStore>({} as MainStore); +const { Provider } = mainStore; + +export const Stores: FC<PropsWithChildren> = ({ children }) => ( + <Provider + value={{ + noteStore: useLocalObservable(setNoteStore), + siteStore: useLocalObservable(setSiteStore), + avatarStore: useLocalObservable(setAvatarStore), + hallStore: useLocalObservable(setHallStore), + }} + > + {children} + </Provider> +); + +export const useSiteStore = () => useContext(mainStore).siteStore; + +export const useNoteStore = () => useContext(mainStore).noteStore; + +export const useAvatarStore = () => useContext(mainStore).avatarStore; + +export const useHallStore = () => useContext(mainStore).hallStore; diff --git a/qwilight-fe/src/type/wwwAPI.d.ts b/qwilight-fe/src/type/wwwAPI.d.ts new file mode 100644 index 0000000..015bb69 --- /dev/null +++ b/qwilight-fe/src/type/wwwAPI.d.ts @@ -0,0 +1,183 @@ +export type GetTitleAPI = { + title: string; + titleColor: string; +}; + +export type GetNoteAPI = { + totalCount: number; + highestCount: number; + noteCount: number; + notes: { + noteID: string; + artist: string; + title: string; + genre: string; + levelText: string; + level: number; + highestCount?: number; + totalCount?: number; + fittedText?: string; + wantAvatarID?: string; + wantAvatarName?: string; + }[]; +}; + +export type GetCommentAPI = { + comments: { + date: number; + avatarID: string; + avatarName: string; + stand: number; + band: number; + point: number; + isP: boolean; + commentary: string; + isTargetAvatar: boolean; + judgmentMode: number; + hitPointsMode: number; + isPaused: boolean; + handled: number; + }[]; + commentPlace: number; + totalComments: number; +}; + +export type GetSitesAPI = { + siteID: string; + siteName: string; + siteConfigure: number; + hasCipher: boolean; + avatarCount: number; +}[]; + +export type AvatarAPIWantAvatar = { + avatarID: string; + avatarName: string; + avatarIntro: string; +}; + +export type AvatarAPIAvatar = { + avatarID: string; + avatarName: string; + avatarIntro: string; + totalCount: number; + totalLength: number; + highestCount: number; + date: number; + avatarLevels: number[]; + avatarAbility5K: number; + avatarAbility5KClass: number; + avatarAbility5KPlace: number; + avatarAbility5KCount: number; + avatarAbility7K: number; + avatarAbility7KClass: number; + avatarAbility7KPlace: number; + avatarAbility7KCount: number; + avatarAbility9K: number; + avatarAbility9KClass: number; + avatarAbility9KPlace: number; + avatarAbility9KCount: number; + dateSet: number[]; + dateValues: number[]; + quitStatusValues: number[]; +}; + +export type GetAvatarFavoritesAPI = { + noteID: string; + artist: string; + title: string; + genre: string; + levelText: string; + level: number; + handled: number; + totalCount: number; +}[]; + +export type GetAvatarLastsAPI = { + noteID: string; + artist: string; + title: string; + genre: string; + levelText: string; + level: number; + handled: number; + date: number; +}[]; + +export type GetAvatarAbilitiesAPI = { + noteID: string; + artist: string; + title: string; + genre: string; + levelText: string; + level: number; + handled: number; + date: number; + stand: number; + ability: number; +}[]; + +export type GetAvatarWwwLevelsAPI = { + levelID: string; + title: string; + levelText: string; + level: string; + date: number; +}[]; + +export type GetEtcAPI = { + totalDateSet: string[]; + totalDateValues: number[]; + signUpDateSet: string[]; + signUpDateValues: number[]; + avatarDateSet: string[]; + avatarDateValues: number[]; + totalNoteFiles: EtcAPINoteFile[]; + totalTitles: EtcAPITitle[]; + totalEdges: EtcAPIEdge[]; + favorites: EtcAPINoteFile[]; + favoritesAt: EtcAPINoteFile[]; + inputModes: EtcAPIMode[]; + autoModes: EtcAPIMode[]; + noteSaltModes: EtcAPIMode[]; + faintNoteModes: EtcAPIMode[]; + judgmentModes: EtcAPIMode[]; + hitPointsModes: EtcAPIMode[]; + noteMobilityModes: EtcAPIMode[]; + longNoteModes: EtcAPIMode[]; + inputFavorModes: EtcAPIMode[]; + noteModifyModes: EtcAPIMode[]; + lowestJudgmentConditionModes: EtcAPIMode[]; +}; + +export type EtcAPINoteFile = { + noteID: string; + title: string; + artist: string; + genre: string; + level: number; + levelText: string; + value: number; +}; + +export type EtcAPITitle = { + title: string; + titleColor: string; + value: number; +}; + +export type EtcAPIEdge = { + edge: string; + value: number; +}; + +export type EtcAPIMode = { + mode: number; + value: number; +}; + +export type GetHallAPI = { + avatarID: string; + avatarName: string; + value: number; +}; diff --git a/qwilight-fe/src/useGetTitle.ts b/qwilight-fe/src/useGetTitle.ts deleted file mode 100644 index d723eb7..0000000 --- a/qwilight-fe/src/useGetTitle.ts +++ /dev/null @@ -1,33 +0,0 @@ -import { wwwAXIOS } from "@/Www"; -import { GetTitleAPI } from "@/wwwAPI"; -import { useQuery } from "@tanstack/react-query"; -import { getLanguage } from "taehui-ts/language"; - -export default function useGetTitle(avatarID: string) { - const language = getLanguage(); - return useQuery({ - queryKey: ["title", avatarID, language], - queryFn: async () => { - const { data } = await wwwAXIOS.get<GetTitleAPI>("/title", { - params: { - avatarID, - language, - }, - }); - if (data.titleColor.startsWith("#")) { - return { - ...data, - titleColor: `#${data.titleColor.substring( - 3, - )}${data.titleColor.substring(1, 3)}`, - }; - } else { - return data; - } - }, - initialData: { - title: "", - titleColor: "", - }, - }); -} diff --git a/qwilight-fe/src/utilities/Utility.ts b/qwilight-fe/src/utilities/Utility.ts new file mode 100644 index 0000000..146a89f --- /dev/null +++ b/qwilight-fe/src/utilities/Utility.ts @@ -0,0 +1,268 @@ +import i10 from "@/assets/i10.png"; +import i11 from "@/assets/i11.png"; +import i12 from "@/assets/i12.png"; +import i13 from "@/assets/i13.png"; +import i14 from "@/assets/i14.png"; +import i15 from "@/assets/i15.png"; +import i16 from "@/assets/i16.png"; +import i4 from "@/assets/i4.png"; +import i5 from "@/assets/i5.png"; +import i6 from "@/assets/i6.png"; +import i7 from "@/assets/i7.png"; +import i8 from "@/assets/i8.png"; +import i9 from "@/assets/i9.png"; +import m00 from "@/assets/m00.png"; +import m01 from "@/assets/m01.png"; +import m10 from "@/assets/m10.png"; +import m11 from "@/assets/m11.png"; +import m111 from "@/assets/m111.png"; +import m113 from "@/assets/m113.png"; +import m12 from "@/assets/m12.png"; +import m120 from "@/assets/m120.png"; +import m121 from "@/assets/m121.png"; +import m14 from "@/assets/m14.png"; +import m20 from "@/assets/m20.png"; +import m21 from "@/assets/m21.png"; +import m22 from "@/assets/m22.png"; +import m23 from "@/assets/m23.png"; +import m30 from "@/assets/m30.png"; +import m31 from "@/assets/m31.png"; +import m32 from "@/assets/m32.png"; +import m33 from "@/assets/m33.png"; +import m34 from "@/assets/m34.png"; +import m40 from "@/assets/m40.png"; +import m41 from "@/assets/m41.png"; +import m42 from "@/assets/m42.png"; +import m43 from "@/assets/m43.png"; +import m44 from "@/assets/m44.png"; +import m45 from "@/assets/m45.png"; +import m47 from "@/assets/m47.png"; +import m50 from "@/assets/m50.png"; +import m51 from "@/assets/m51.png"; +import m53 from "@/assets/m53.png"; +import m54 from "@/assets/m54.png"; +import m55 from "@/assets/m55.png"; +import m60 from "@/assets/m60.png"; +import m61 from "@/assets/m61.png"; +import m70 from "@/assets/m70.png"; +import m710 from "@/assets/m710.png"; +import m711 from "@/assets/m711.png"; +import m712 from "@/assets/m712.png"; +import m713 from "@/assets/m713.png"; +import m714 from "@/assets/m714.png"; +import m715 from "@/assets/m715.png"; +import m716 from "@/assets/m716.png"; +import m74 from "@/assets/m74.png"; +import m75 from "@/assets/m75.png"; +import m76 from "@/assets/m76.png"; +import m77 from "@/assets/m77.png"; +import m78 from "@/assets/m78.png"; +import m79 from "@/assets/m79.png"; +import m80 from "@/assets/m80.png"; +import m81 from "@/assets/m81.png"; +import { AbilitySiteYell } from "@/app/[language]/site/type"; +import { useTranslations } from "next-intl"; + +export const is = [ + "", + "", + "", + "", + i4, + i5, + i6, + i7, + i8, + i9, + i10, + i11, + i12, + i13, + i14, + i15, + i16, +]; +export const m0s = [m00, m01]; +export const m1s = [ + m10, + m11, + m12, + "", + m14, + "", + "", + "", + "", + "", + "", + m111, + "", + m113, + "", +]; +export const m2s = [m20, m21, m22, m23]; +export const m3s = [m30, m31, m32, m33, m34]; +export const m4s = [m40, m41, m42, m43, m44, m45, "", m47]; +export const m5s = [m50, m51, "", m53, m54, m55]; +export const m6s = [m60, m61]; +export const m7s = [ + m70, + "", + "", + "", + m74, + m75, + m76, + m77, + m78, + m79, + m710, + m711, + m712, + m713, + m714, + m715, + m716, +]; +export const m8s = [m80, m81]; +export const m12s = [m120, m121]; + +export const formatText = (value: number) => { + return Number(value.toFixed(2)) + .toString() + .replace(/\B(?=(\d{3})+(?!\d))/g, ","); +}; + +export const getGenreText = (genre: string) => + genre.length === 0 || genre.startsWith("#") ? genre : `#${genre}`; + +export const getAbilityUpText = ( + t: ReturnType<typeof useTranslations>, + { inputMode, ability }: AbilitySiteYell, +) => { + let inputModeText = ""; + switch (inputMode) { + case 10: + inputModeText = "⑤K"; + break; + case 11: + inputModeText = "⑦K"; + break; + case 9: + inputModeText = "9K"; + break; + } + return ability < 0.01 + ? `${inputModeText} < 0.01 Point ↑` + : `${inputModeText} ${ability.toFixed(2)} Point ↑`; +}; + +export const toDate = (date: number) => { + const dateText = new Date(date); + return `${dateText.toLocaleDateString()} ${dateText.toLocaleTimeString()}`; +}; + +export const getSiteName = ( + siteName: string, + t: ReturnType<typeof useTranslations<string>>, +) => { + switch (siteName) { + case "@Comment": + return t("commentSiteName"); + case "@Notify": + return t("toNotifySiteName"); + case "@Default": + return t("defaultSiteName"); + case "@Platform": + return t("platformSiteName"); + default: + return siteName; + } +}; + +export const getQuitStatusValue = ( + point: number, + stand: number, +): { + quitCss: "S+" | "S" | "A+" | "A" | "B" | "C" | "D"; + quit: string; +} => { + const quitCss = + point < 0.8 + ? "D" + : point < 0.85 + ? "C" + : point < 0.9 + ? "B" + : point < 0.95 + ? "A" + : stand < 900000 + ? "A+" + : point < 1.0 + ? "S" + : "S+"; + + return { + quitCss, + quit: quitCss, + }; +}; + +export const getDefaultAvatarID = (avatarID: string) => + avatarID.substring(avatarID.indexOf("@") + 1); + +export const getHitPointsClass = (hitPointsMode: number) => { + switch (hitPointsMode) { + case 0: + return "level2"; + case 2: + return "level4"; + case 3: + case 5: + return "level5"; + case 4: + return "level1"; + default: + return "stand"; + } +}; + +export const getInputMode = ( + tabPosition: number, +): "6K" | "5K" | "7K" | "9K" | "10K" | "14K" | "24K" | "48K" => { + switch (tabPosition) { + case 0: + return "6K"; + case 1: + return "5K"; + case 2: + return "7K"; + case 3: + return "9K"; + case 4: + return "10K"; + case 5: + return "14K"; + case 6: + return "24K"; + case 7: + return "48K"; + default: + throw new Error(tabPosition.toString()); + } +}; + +export const getAbilityInputMode = ( + tabPosition: number, +): "5K" | "7K" | "9K" => { + switch (tabPosition) { + case 0: + return "5K"; + case 1: + return "7K"; + case 2: + return "9K"; + default: + throw new Error(tabPosition.toString()); + } +}; diff --git a/qwilight-fe/src/utilities/wwwAPI.ts b/qwilight-fe/src/utilities/wwwAPI.ts new file mode 100644 index 0000000..5b2fce8 --- /dev/null +++ b/qwilight-fe/src/utilities/wwwAPI.ts @@ -0,0 +1,25 @@ +import axios, { AxiosError } from "axios"; +import { toast } from "react-toastify"; + +export const wwwAPIPath = "/qwilight/www"; + +export const wwwAPI = axios.create({ + baseURL: wwwAPIPath, +}); + +wwwAPI.interceptors.response.use( + (value) => value, + (e: AxiosError) => { + switch (e.response?.status) { + case 401: + toast.error("Unauthorized"); + window.sessionStorage.removeItem("totem"); + break; + case 502: + toast.error("Bad Gateway"); + break; + } + + throw e; + }, +); diff --git a/qwilight-fe/src/wwwAPI.d.ts b/qwilight-fe/src/wwwAPI.d.ts deleted file mode 100644 index 015bb69..0000000 --- a/qwilight-fe/src/wwwAPI.d.ts +++ /dev/null @@ -1,183 +0,0 @@ -export type GetTitleAPI = { - title: string; - titleColor: string; -}; - -export type GetNoteAPI = { - totalCount: number; - highestCount: number; - noteCount: number; - notes: { - noteID: string; - artist: string; - title: string; - genre: string; - levelText: string; - level: number; - highestCount?: number; - totalCount?: number; - fittedText?: string; - wantAvatarID?: string; - wantAvatarName?: string; - }[]; -}; - -export type GetCommentAPI = { - comments: { - date: number; - avatarID: string; - avatarName: string; - stand: number; - band: number; - point: number; - isP: boolean; - commentary: string; - isTargetAvatar: boolean; - judgmentMode: number; - hitPointsMode: number; - isPaused: boolean; - handled: number; - }[]; - commentPlace: number; - totalComments: number; -}; - -export type GetSitesAPI = { - siteID: string; - siteName: string; - siteConfigure: number; - hasCipher: boolean; - avatarCount: number; -}[]; - -export type AvatarAPIWantAvatar = { - avatarID: string; - avatarName: string; - avatarIntro: string; -}; - -export type AvatarAPIAvatar = { - avatarID: string; - avatarName: string; - avatarIntro: string; - totalCount: number; - totalLength: number; - highestCount: number; - date: number; - avatarLevels: number[]; - avatarAbility5K: number; - avatarAbility5KClass: number; - avatarAbility5KPlace: number; - avatarAbility5KCount: number; - avatarAbility7K: number; - avatarAbility7KClass: number; - avatarAbility7KPlace: number; - avatarAbility7KCount: number; - avatarAbility9K: number; - avatarAbility9KClass: number; - avatarAbility9KPlace: number; - avatarAbility9KCount: number; - dateSet: number[]; - dateValues: number[]; - quitStatusValues: number[]; -}; - -export type GetAvatarFavoritesAPI = { - noteID: string; - artist: string; - title: string; - genre: string; - levelText: string; - level: number; - handled: number; - totalCount: number; -}[]; - -export type GetAvatarLastsAPI = { - noteID: string; - artist: string; - title: string; - genre: string; - levelText: string; - level: number; - handled: number; - date: number; -}[]; - -export type GetAvatarAbilitiesAPI = { - noteID: string; - artist: string; - title: string; - genre: string; - levelText: string; - level: number; - handled: number; - date: number; - stand: number; - ability: number; -}[]; - -export type GetAvatarWwwLevelsAPI = { - levelID: string; - title: string; - levelText: string; - level: string; - date: number; -}[]; - -export type GetEtcAPI = { - totalDateSet: string[]; - totalDateValues: number[]; - signUpDateSet: string[]; - signUpDateValues: number[]; - avatarDateSet: string[]; - avatarDateValues: number[]; - totalNoteFiles: EtcAPINoteFile[]; - totalTitles: EtcAPITitle[]; - totalEdges: EtcAPIEdge[]; - favorites: EtcAPINoteFile[]; - favoritesAt: EtcAPINoteFile[]; - inputModes: EtcAPIMode[]; - autoModes: EtcAPIMode[]; - noteSaltModes: EtcAPIMode[]; - faintNoteModes: EtcAPIMode[]; - judgmentModes: EtcAPIMode[]; - hitPointsModes: EtcAPIMode[]; - noteMobilityModes: EtcAPIMode[]; - longNoteModes: EtcAPIMode[]; - inputFavorModes: EtcAPIMode[]; - noteModifyModes: EtcAPIMode[]; - lowestJudgmentConditionModes: EtcAPIMode[]; -}; - -export type EtcAPINoteFile = { - noteID: string; - title: string; - artist: string; - genre: string; - level: number; - levelText: string; - value: number; -}; - -export type EtcAPITitle = { - title: string; - titleColor: string; - value: number; -}; - -export type EtcAPIEdge = { - edge: string; - value: number; -}; - -export type EtcAPIMode = { - mode: number; - value: number; -}; - -export type GetHallAPI = { - avatarID: string; - avatarName: string; - value: number; -}; diff --git a/taehui-fe/.eslintrc.json b/taehui-fe/.eslintrc.json new file mode 100644 index 0000000..bffb357 --- /dev/null +++ b/taehui-fe/.eslintrc.json @@ -0,0 +1,3 @@ +{ + "extends": "next/core-web-vitals" +} diff --git a/taehui-fe/.gitignore b/taehui-fe/.gitignore index 201c98c..2825260 100644 --- a/taehui-fe/.gitignore +++ b/taehui-fe/.gitignore @@ -4,23 +4,36 @@ /node_modules /.pnp .pnp.js +.yarn/install-state.gz # testing /coverage +# next.js +/.next/ +/out/ + # production /build # misc .DS_Store -.env.local -.env.development.local -.env.test.local -.env.production.local +*.pem +# debug npm-debug.log* yarn-debug.log* yarn-error.log* -/.env +# local env files +.env*.local +.env.local + +# vercel +.vercel + +# typescript +*.tsbuildinfo +next-env.d.ts + /.turbo diff --git a/taehui-fe/README.md b/taehui-fe/README.md index b87cb00..a75ac52 100644 --- a/taehui-fe/README.md +++ b/taehui-fe/README.md @@ -1,46 +1,40 @@ -# Getting Started with Create React App +This is a [Next.js](https://nextjs.org/) project bootstrapped with [`create-next-app`](https://github.com/vercel/next.js/tree/canary/packages/create-next-app). -This project was bootstrapped with [Create React App](https://github.com/facebook/create-react-app). +## Getting Started -## Available Scripts +First, run the development server: -In the project directory, you can run: +```bash +npm run dev +# or +yarn dev +# or +pnpm dev +# or +bun dev +``` -### `npm start` +Open [http://localhost:3000](http://localhost:3000) with your browser to see the result. -Runs the app in the development mode.\ -Open [http://localhost:3000](http://localhost:3000) to view it in the browser. +You can start editing the page by modifying `pages/index.tsx`. The page auto-updates as you edit the file. -The page will reload if you make edits.\ -You will also see any lint errors in the console. +[API routes](https://nextjs.org/docs/api-routes/introduction) can be accessed on [http://localhost:3000/api/hello](http://localhost:3000/api/hello). This endpoint can be edited in `pages/api/hello.ts`. -### `npm test` +The `pages/api` directory is mapped to `/api/*`. Files in this directory are treated as [API routes](https://nextjs.org/docs/api-routes/introduction) instead of React pages. -Launches the test runner in the interactive watch mode.\ -See the section about [running tests](https://facebook.github.io/create-react-app/docs/running-tests) for more information. - -### `npm run build` - -Builds the app for production to the `build` folder.\ -It correctly bundles React in production mode and optimizes the build for the best performance. - -The build is minified and the filenames include the hashes.\ -Your app is ready to be deployed! - -See the section about [deployment](https://facebook.github.io/create-react-app/docs/deployment) for more information. - -### `npm run eject` - -**Note: this is a one-way operation. Once you `eject`, you can’t go back!** - -If you aren’t satisfied with the build tool and configuration choices, you can `eject` at any time. This command will remove the single build dependency from your project. - -Instead, it will copy all the configuration files and the transitive dependencies (webpack, Babel, ESLint, etc) right into your project so you have full control over them. All of the commands except `eject` will still work, but they will point to the copied scripts so you can tweak them. At this point you’re on your own. - -You don’t have to ever use `eject`. The curated feature set is suitable for small and middle deployments, and you shouldn’t feel obligated to use this feature. However we understand that this tool wouldn’t be useful if you couldn’t customize it when you are ready for it. +This project uses [`next/font`](https://nextjs.org/docs/basic-features/font-optimization) to automatically optimize and load Inter, a custom Google Font. ## Learn More -You can learn more in the [Create React App documentation](https://facebook.github.io/create-react-app/docs/getting-started). +To learn more about Next.js, take a look at the following resources: -To learn React, check out the [React documentation](https://reactjs.org/). +- [Next.js Documentation](https://nextjs.org/docs) - learn about Next.js features and API. +- [Learn Next.js](https://nextjs.org/learn) - an interactive Next.js tutorial. + +You can check out [the Next.js GitHub repository](https://github.com/vercel/next.js/) - your feedback and contributions are welcome! + +## Deploy on Vercel + +The easiest way to deploy your Next.js app is to use the [Vercel Platform](https://vercel.com/new?utm_medium=default-template&filter=next.js&utm_source=create-next-app&utm_campaign=create-next-app-readme) from the creators of Next.js. + +Check out our [Next.js deployment documentation](https://nextjs.org/docs/deployment) for more details. diff --git a/taehui-fe/next.config.mjs b/taehui-fe/next.config.mjs new file mode 100644 index 0000000..6b50496 --- /dev/null +++ b/taehui-fe/next.config.mjs @@ -0,0 +1,12 @@ +import createNextIntlPlugin from 'next-intl/plugin'; + +export default createNextIntlPlugin()({ + async rewrites() { + return [ + { + source: "/www/:path*", + destination: `${process.env.API ?? "https://taehui.ddns.net"}/www/:path*` + }, + ] + }, +}); diff --git a/taehui-fe/package.json b/taehui-fe/package.json index 0e2bda8..f5b403c 100644 --- a/taehui-fe/package.json +++ b/taehui-fe/package.json @@ -2,6 +2,13 @@ "name": "taehui-fe", "version": "1.0.0", "private": true, + "scripts": { + "dev": "next dev", + "build": "next build", + "start": "next start", + "lint": "next lint", + "deploy": "qwilight-fe.cmd" + }, "dependencies": { "@tanstack/react-query": "^5.28.0", "axios": "^1.6.7", @@ -18,11 +25,9 @@ "react-contexify": "^6.0.0", "react-dom": "^18.2.0", "react-infinite-scroll-component": "^6.1.0", - "react-scripts": "5.0.1", "react-textarea-autosize": "^8.5.3", "react-toastify": "^10.0.4", "reactstrap": "^9.2.2", - "sprintf-js": "^1.1.3", "sweetalert2": "^11.10.6", "taehui-ts": "workspace:^" }, @@ -34,32 +39,7 @@ "@types/react": "^18.2.65", "@types/react-dom": "^18.2.22", "@types/showdown": "^2.0.6", - "@types/sprintf-js": "^1.1.4", "eslint-config-next": "^14.1.3", "typescript": "^5.4.2" - }, - "scripts": { - "start": "react-scripts start", - "build": "react-scripts build", - "eject": "react-scripts eject", - "deploy": "taehui-fe.cmd" - }, - "eslintConfig": { - "extends": [ - "react-app", - "react-app/jest" - ] - }, - "browserslist": { - "production": [ - ">0.2%", - "not dead", - "not op_mini all" - ], - "development": [ - "last 1 chrome version", - "last 1 firefox version", - "last 1 safari version" - ] } } diff --git a/taehui-fe/public/favicon.ico b/taehui-fe/public/favicon.ico deleted file mode 100644 index e4e0dc5..0000000 --- a/taehui-fe/public/favicon.ico +++ /dev/null Binary files differ diff --git a/taehui-fe/public/index.html b/taehui-fe/public/index.html deleted file mode 100644 index f46dae2..0000000 --- a/taehui-fe/public/index.html +++ /dev/null @@ -1,44 +0,0 @@ -<!doctype html> -<html lang="ko"> - <head> - <meta charset="utf-8" /> - <link rel="icon" href="%PUBLIC_URL%/favicon.ico" /> - <meta name="viewport" content="width=device-width, initial-scale=1" /> - <meta name="theme-color" content="#FFFFFF" /> - <meta name="description" content="Taehui" /> - <link rel="apple-touch-icon" href="%PUBLIC_URL%/logo192.png" /> - <!-- - manifest.json provides metadata used when your web app is installed on a - user's mobile device or desktop. See https://developers.google.com/web/fundamentals/web-app-manifest/ - --> - <link rel="manifest" href="%PUBLIC_URL%/manifest.json" /> - <!-- - Notice the use of %PUBLIC_URL% in the tags above. - It will be replaced with the URL of the `public` folder during the build. - Only files inside the `public` folder can be referenced from the HTML. - - Unlike "/favicon.ico" or "favicon.ico", "%PUBLIC_URL%/favicon.ico" will - work correctly both with client-side routing and a non-root public URL. - Learn how to configure a non-root public URL by running `npm run build`. - --> - <title>Taehui - - - - - - - -
- - - diff --git a/taehui-fe/public/logo192.png b/taehui-fe/public/logo192.png deleted file mode 100644 index 0e55d4e..0000000 --- a/taehui-fe/public/logo192.png +++ /dev/null Binary files differ diff --git a/taehui-fe/public/logo512.png b/taehui-fe/public/logo512.png deleted file mode 100644 index 2e7660b..0000000 --- a/taehui-fe/public/logo512.png +++ /dev/null Binary files differ diff --git a/taehui-fe/public/manifest.json b/taehui-fe/public/manifest.json deleted file mode 100644 index bc4a444..0000000 --- a/taehui-fe/public/manifest.json +++ /dev/null @@ -1,25 +0,0 @@ -{ - "short_name": "Taehui", - "name": "Taehui", - "icons": [ - { - "src": "favicon.ico", - "sizes": "64x64 32x32 24x24 16x16", - "type": "image/x-icon" - }, - { - "src": "logo192.png", - "type": "image/png", - "sizes": "192x192" - }, - { - "src": "logo512.png", - "type": "image/png", - "sizes": "512x512" - } - ], - "start_url": ".", - "display": "standalone", - "theme_color": "#000000", - "background_color": "#ffffff" -} diff --git a/taehui-fe/public/robots.txt b/taehui-fe/public/robots.txt deleted file mode 100644 index e9e57dc..0000000 --- a/taehui-fe/public/robots.txt +++ /dev/null @@ -1,3 +0,0 @@ -# https://www.robotstxt.org/robotstxt.html -User-agent: * -Disallow: diff --git a/taehui-fe/src/AvatarTitle.tsx b/taehui-fe/src/AvatarTitle.tsx deleted file mode 100644 index ca75089..0000000 --- a/taehui-fe/src/AvatarTitle.tsx +++ /dev/null @@ -1,37 +0,0 @@ -import { ReactNode } from "react"; -import { Col } from "reactstrap"; - -const AvatarTitle = ({ - avatarID, - avatarName, - children, -}: { - avatarID: string; - avatarName: string; - children: ReactNode; -}) => { - return ( - <> - { - e.stopPropagation(); - }} - > - - - - {avatarName} -
- {children} - - - ); -}; - -export default AvatarTitle; diff --git a/taehui-fe/src/Language.json b/taehui-fe/src/Language.json deleted file mode 100644 index 6d1ff43..0000000 --- a/taehui-fe/src/Language.json +++ /dev/null @@ -1,150 +0,0 @@ -{ - "ko-KR": { - "translation": { - "alreadyAvatarID": "이미 가입된 아이디입니다.", - "assistForum": "매뉴얼", - "autoEssay": "자동 저장", - "autoEssays": "자동 저장 목록", - "autoSignIn": "자동 로그인", - "avatarCipher": "비밀번호", - "avatarCipherModified": "수정할 비밀번호", - "avatarCipherTest": "비밀번호 확인", - "avatarID": "아이디", - "avatarIntro": "자기소개", - "avatarName": "닉네임", - "comment": "덧글", - "commentary": "방명록", - "commentCount": "덧글 %d 개", - "dateForum": "업데이트 내역", - "doModifiedAvatar": "비밀번호가 수정되어 다시 로그인하세요", - "doModifyAvatar": "정보 수정", - "doModifyComment": "덧글 수정", - "doModifyCommentary": "방명록 수정", - "doModifyEssay": "게시글 수정", - "essay": "게시글", - "essayBefore": "이전 게시글", - "essayLater": "다음 게시글", - "failedValidateCipher": "올바르지 않은 비밀번호입니다.", - "failedValidation": "입력이 올바르지 않습니다.", - "fax": "이메일", - "fileUpload": "파일 업로드", - "fileUploading": "업로드하는 중입니다.", - "forums": "모든 게시판", - "hit00": "방문자 통계", - "hit01": "어제 방문자 %d 명", - "hit02": "오늘 방문자 %d 명", - "hit03": "방문자 수는 2022-11-07 부터 집계됩니다.", - "hitCount": "조회수 %d 회", - "hitFileCount": "(%d 회 다운로드)", - "latestAvatarsView0": "가입한 회원", - "latestAvatarsView1": "방문한 회원", - "latestCommentsView": "작성된 덧글", - "latestEssaysView": "작성된 게시글", - "notSignedIn": "로그아웃", - "notSignedInText": "%s님 감사합니다.", - "onWant": "검색", - "postComment": "덧글 쓰기", - "postCommentary": "방명록 쓰기", - "postedAutoEssay": "게시글이 자동으로 저장됩니다.", - "postEssay": "게시글 쓰기", - "quit": "나가기", - "qwilightForum": "Qwilight 게시판", - "setAutoEssayQuestion": "자동 저장된 게시글을 불러올까요? 작성중인 글은 사라집니다.", - "signedInText": "%s님 환영합니다.", - "signIn": "로그인", - "signUp": "회원 가입", - "softwareForum": "소프트웨어", - "taehuiInfo": "개발자 프로필", - "taehuiIntro": "홈으로", - "taehuiIntro00": "안녕하세요", - "taehuiIntro01": "Taehui가 운영하는 불로그입니다.", - "taehuiIntro02": "제가 만든 소프트웨어의 제공과 운영을 담당합니다.", - "taehuiIntro03": "이 사이트는 아직 개발 중입니다.", - "text": "본문", - "textTag": "글자", - "title": "제목", - "viewEditedEssay": "미리 보기", - "wantView": "검색 결과", - "wipeComment": "덧글 삭제", - "wipeCommentary": "방명록 삭제", - "wipeCommentQuestion": "덧글을 삭제할까요?", - "wipeEssay": "게시글 삭제", - "wipeEssayQuestion": "게시글을 삭제할까요?", - "wrongAvatar": "올바르지 않은 계정입니다." - } - }, - "en-US": { - "translation": { - "alreadyAvatarID": "This ID is already registered.", - "assistForum": "Manual", - "autoEssay": "Auto Save", - "autoEssays": "Auto Save List", - "autoSignIn": "Automatic login", - "avatarCipher": "Password", - "avatarCipherModified": "Password to be modified", - "avatarCipherTest": "Confirm password", - "avatarID": "ID", - "avatarIntro": "Introduce yourself", - "avatarName": "Nickname", - "comment": "Comment", - "commentary": "Guestbook", - "commentCount": "%d comments", - "dateForum": "Update History", - "doModifiedAvatar": "Please log in again because your password has been modified", - "doModifyAvatar": "Edit information", - "doModifyComment": "Edit comment", - "doModifyCommentary": "Edit guestbook", - "doModifyEssay": "Edit post", - "essay": "Bulletin", - "essayBefore": "Previous post", - "essayLater": "Next post", - "failedValidateCipher": "Invalid password.", - "failedValidation": "The input is not valid.", - "fax": "E-mail", - "fileUpload": "Upload File", - "fileUploading": "Uploading.", - "forums": "All Bulletins", - "hit00": "Visitor statistics", - "hit01": "%d visitors yesterday", - "hit02": "%d visitors today", - "hit03": "Visits count from 2022-11-07.", - "hitCount": "%d views", - "hitFileCount": "(Download %d times)", - "latestAvatarsView0": "Registered member", - "latestAvatarsView1": "Member visited", - "latestCommentsView": "Comment written", - "latestEssaysView": "Posts Created", - "notSignedIn": "Sign out", - "notSignedInText": "Thank you, %s.", - "onWant": "Search", - "postComment": "Write comment", - "postCommentary": "Write guestbook", - "postedAutoEssay": "Your post will be saved automatically.", - "postEssay": "Write post", - "quit": "Exit", - "qwilightForum": "Qwilight Bulletin", - "setAutoEssayQuestion": "Do you want to load auto-saved posts? The text you are writing will disappear.", - "signedInText": "Welcome, %s.", - "signIn": "Login", - "signUp": "Join membership", - "softwareForum": "Software", - "taehuiInfo": "Developer Profile", - "taehuiIntro": "Home", - "taehuiIntro00": "Hello", - "taehuiIntro01": "This is 불로그 run by Taehui.", - "taehuiIntro02": "I am in charge of providing and operating the software I made.", - "taehuiIntro03": "This site is still under development.", - "text": "Main text", - "textTag": "Letter", - "title": "Title", - "viewEditedEssay": "Preview", - "wantView": "Search Results", - "wipeComment": "Delete Comment", - "wipeCommentary": "Delete guestbook", - "wipeCommentQuestion": "Are you sure you want to delete the comment?", - "wipeEssay": "Delete post", - "wipeEssayQuestion": "Are you sure you want to delete the post?", - "wrongAvatar": "This account is not valid." - } - } -} diff --git a/taehui-fe/src/Loading.tsx b/taehui-fe/src/Loading.tsx deleted file mode 100644 index 583fbe3..0000000 --- a/taehui-fe/src/Loading.tsx +++ /dev/null @@ -1,83 +0,0 @@ -import { FC, PropsWithChildren } from "react"; -import { Col, Row } from "reactstrap"; -import { Code, List } from "react-content-loader"; - -const LoadingLayer: FC = ({ children }) => { - return ( - - {children} - - ); -}; - -export const ForumsViewLoading = () => { - return ( - - - - ); -}; - -export const ForumViewLoading = () => { - return ( - - - - ); -}; - -export const HitViewLoading = () => { - return ; -}; - -export const LatestEssaysViewLoading = () => { - return ; -}; - -export const LatestCommentsViewLoading = () => { - return ; -}; - -export const LatestAvatarViewLoading = () => { - return ( - - - - ); -}; - -export const AvatarViewLoading = () => { - return ( - - - - ); -}; - -export const EssayViewLoading = () => { - return ( - - - - ); -}; - -export const CommentaryViewLoading = () => { - return ( - - - - ); -}; - -export const WantViewLoading = () => { - return ( - - - - ); -}; - -export const AutoEssayViewLoading = () => { - return ; -}; diff --git a/taehui-fe/src/Stores.tsx b/taehui-fe/src/Stores.tsx deleted file mode 100644 index 1c4eeb8..0000000 --- a/taehui-fe/src/Stores.tsx +++ /dev/null @@ -1,33 +0,0 @@ -import { createContext, FC, PropsWithChildren, useContext } from "react"; -import { useLocalObservable } from "mobx-react-lite"; - -import setTaehuiStore from "src/taehui/setTaehuiStore"; -import setAvatarStore from "src/avatar/setAvatarStore"; -import setForumStore from "src/forum/setForumStore"; - -type MainStore = { - taehuiStore: ReturnType; - avatarStore: ReturnType; - forumStore: ReturnType; -}; - -const mainStore = createContext({} as MainStore); -const { Provider } = mainStore; - -export const Stores: FC = ({ children }) => ( - - {children} - -); - -export const useTaehuiStore = () => useContext(mainStore).taehuiStore; - -export const useAvatarStore = () => useContext(mainStore).avatarStore; - -export const useForumStore = () => useContext(mainStore).forumStore; diff --git a/taehui-fe/src/Utility.ts b/taehui-fe/src/Utility.ts deleted file mode 100644 index 989f3be..0000000 --- a/taehui-fe/src/Utility.ts +++ /dev/null @@ -1,53 +0,0 @@ -import { TFunction } from "i18next"; -import { sprintf } from "sprintf-js"; - -export const getHitTexts = (text: string) => { - const pathBefore = window.location.href.substring( - 0, - window.location.href.lastIndexOf("/"), - ); - const textHtml = new DOMParser().parseFromString(text, "text/html"); - return Array.from(textHtml.getElementsByTagName("a")) - .filter(({ href }) => href.startsWith(pathBefore)) - .map(({ href }) => href.substring(href.lastIndexOf("/") + 1)); -}; - -export const tag = ( - t: TFunction, - text: string, - hits: { [fileName: string]: number }, - tagClass: string, -) => { - const textHtml = new DOMParser().parseFromString(text, "text/html"); - Array.from(textHtml.getElementsByTagName("img")).forEach((tag) => { - const src = tag.getAttribute("src"); - if (src?.includes("/") === false) { - tag.src = `/www/file/${src}`; - tag.className = tagClass; - } - }); - Array.from(textHtml.getElementsByTagName("audio")).forEach((tag) => { - const src = tag.getAttribute("src"); - if (src?.includes("/") === false) { - tag.src = `/www/file/${src}`; - tag.className = tagClass; - } - }); - Array.from(textHtml.getElementsByTagName("video")).forEach((tag) => { - const src = tag.getAttribute("src"); - if (src?.includes("/") === false) { - tag.src = `/www/file/${src}`; - tag.className = tagClass; - } - }); - Array.from(textHtml.getElementsByTagName("a")).forEach((tag) => { - const href = tag.getAttribute("href"); - if (href?.includes("/") === false) { - tag.href = `/www/file/${href}`; - if (hits[href] >= 0) { - tag.innerHTML += " " + sprintf(t("hitFileCount"), hits[href]); - } - } - }); - return textHtml.body.innerHTML; -}; diff --git a/taehui-fe/src/Www.ts b/taehui-fe/src/Www.ts deleted file mode 100644 index e4eaef6..0000000 --- a/taehui-fe/src/Www.ts +++ /dev/null @@ -1,29 +0,0 @@ -import axios, { AxiosError, isAxiosError } from "axios"; -import { toast } from "react-toastify"; - -export const wwwAXIOS = axios.create({ - baseURL: "/www", -}); - -wwwAXIOS.interceptors.response.use( - (value) => value, - (e: AxiosError) => { - switch (e.response?.status) { - case 401: - toast.error("Unauthorized"); - window.sessionStorage.removeItem("totem"); - break; - case 413: - toast.error("Payload Too Large"); - break; - case 502: - toast.error("Bad Gateway"); - break; - } - - throw e; - }, -); - -export const isClientFault = (e: Error) => - isAxiosError(e) && e.response?.status === 403; diff --git "a/taehui-fe/src/app/\133language\135/commentary/components/CommentaryItem.tsx" "b/taehui-fe/src/app/\133language\135/commentary/components/CommentaryItem.tsx" new file mode 100644 index 0000000..e8cdbd8 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/commentary/components/CommentaryItem.tsx" @@ -0,0 +1,106 @@ +import usePutCommentary from "@/app/[language]/commentary/query/usePutCommentary"; +import useWipeCommentary from "@/app/[language]/commentary/query/useWipeCommentary"; +import { GetCommentaryAPI } from "@/type/wwwAPI"; +import { useTranslations } from "next-intl"; +import { useState } from "react"; +import ReactTextareaAutosize from "react-textarea-autosize"; +import { toast } from "react-toastify"; +import { Button, Col, Collapse, Input, ListGroupItem, Row } from "reactstrap"; +import { getDatetime } from "taehui-ts/date"; + +const CommentaryItem = ({ + commentary: { commentaryID, avatarName, text, date }, +}: { + commentary: GetCommentaryAPI[number]; +}) => { + const t = useTranslations(); + + const [isModifyOpened, setModifyOpened] = useState(false); + const [avatarCipher, setAvatarCipher] = useState(""); + const [textInput, setTextInput] = useState(""); + + const { mutateAsync: wipeCommentary } = useWipeCommentary(); + const { mutateAsync: putCommentary } = usePutCommentary(); + + return ( + + + + {avatarName} + + { + setModifyOpened(true); + }} + > + {isModifyOpened ? ( + { + setTextInput(value); + }} + /> + ) : ( + {text} + )} + + + {getDatetime(date)} + + + + + + { + setAvatarCipher(value); + }} + /> + + + + + + + + + + + ); +}; + +export default CommentaryItem; diff --git "a/taehui-fe/src/app/\133language\135/commentary/loading.tsx" "b/taehui-fe/src/app/\133language\135/commentary/loading.tsx" new file mode 100644 index 0000000..32a6627 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/commentary/loading.tsx" @@ -0,0 +1,10 @@ +import LoadingLayer from "@/components/LoadingLayer"; +import { List } from "react-content-loader"; + +export default function Loading() { + return ( + + + + ); +} diff --git "a/taehui-fe/src/app/\133language\135/commentary/page.tsx" "b/taehui-fe/src/app/\133language\135/commentary/page.tsx" new file mode 100644 index 0000000..aa95b16 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/commentary/page.tsx" @@ -0,0 +1,99 @@ +"use client"; + +import CommentaryItem from "@/app/[language]/commentary/components/CommentaryItem"; +import Loading from "@/app/[language]/commentary/loading"; +import useGetCommentary from "@/app/[language]/commentary/query/useGetCommentary"; +import usePostCommentary from "@/app/[language]/commentary/query/usePostCommentary"; +import { useTranslations } from "next-intl"; +import { useState } from "react"; +import ReactTextareaAutosize from "react-textarea-autosize"; +import { toast } from "react-toastify"; +import { Button, Col, Input, ListGroup, Row } from "reactstrap"; + +const Page = () => { + const t = useTranslations(); + + const [avatarName, setAvatarName] = useState(""); + const [avatarCipher, setAvatarCipher] = useState(""); + const [textInput, setTextInput] = useState(""); + + const { data: commentary, isFetched: isCommentaryLoaded } = + useGetCommentary(); + const { mutateAsync: postCommentary } = usePostCommentary(); + + return ( + <> + + + { + setAvatarName(value); + }} + /> + + + { + setAvatarCipher(value); + }} + /> + + + + + { + setTextInput(value); + }} + /> + + + + + + {isCommentaryLoaded ? ( + + + + {commentary.map((commentary) => ( + + ))} + + + + ) : ( + + )} + + ); +}; + +export default Page; diff --git "a/taehui-fe/src/app/\133language\135/commentary/query/useGetCommentary.ts" "b/taehui-fe/src/app/\133language\135/commentary/query/useGetCommentary.ts" new file mode 100644 index 0000000..5563dab --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/commentary/query/useGetCommentary.ts" @@ -0,0 +1,15 @@ +import { useQuery } from "@tanstack/react-query"; + +import { wwwAPI } from "@/utilities/wwwAPI"; +import { GetCommentaryAPI } from "@/type/wwwAPI"; + +export default function useGetCommentary() { + return useQuery({ + queryKey: ["commentary"], + queryFn: async () => { + const { data } = await wwwAPI.get("/commentary"); + return data; + }, + initialData: [], + }); +} diff --git "a/taehui-fe/src/app/\133language\135/commentary/query/usePostCommentary.ts" "b/taehui-fe/src/app/\133language\135/commentary/query/usePostCommentary.ts" new file mode 100644 index 0000000..28fee98 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/commentary/query/usePostCommentary.ts" @@ -0,0 +1,28 @@ +import { useMutation, useQueryClient } from "@tanstack/react-query"; + +import { wwwAPI } from "@/utilities/wwwAPI"; + +export default function usePostCommentary() { + const queryClient = useQueryClient(); + + return useMutation({ + mutationFn: async ({ + avatarName, + avatarCipher, + text, + }: { + avatarName: string; + avatarCipher: string; + text: string; + }) => { + await wwwAPI.post("/commentary", { + avatarName, + avatarCipher, + text, + }); + }, + onSuccess: async () => { + await queryClient.invalidateQueries({ queryKey: ["commentary"] }); + }, + }); +} diff --git "a/taehui-fe/src/app/\133language\135/commentary/query/usePutCommentary.ts" "b/taehui-fe/src/app/\133language\135/commentary/query/usePutCommentary.ts" new file mode 100644 index 0000000..cba778b --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/commentary/query/usePutCommentary.ts" @@ -0,0 +1,36 @@ +import { isClientFault, wwwAPI } from "@/utilities/wwwAPI"; +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { toast } from "react-toastify"; + +export default function usePutCommentary() { + const queryClient = useQueryClient(); + + const t = useTranslations(); + + return useMutation({ + mutationFn: async ({ + commentaryID, + avatarCipher, + text, + }: { + commentaryID: number; + avatarCipher: string; + text: string; + }) => { + await wwwAPI.put("/commentary", { + commentaryID, + avatarCipher, + text, + }); + }, + onSuccess: async () => { + await queryClient.invalidateQueries({ queryKey: ["commentary"] }); + }, + onError: (e) => { + if (isClientFault(e)) { + toast.error(t("failedValidateCipher")); + } + }, + }); +} diff --git "a/taehui-fe/src/app/\133language\135/commentary/query/useWipeCommentary.ts" "b/taehui-fe/src/app/\133language\135/commentary/query/useWipeCommentary.ts" new file mode 100644 index 0000000..579fd89 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/commentary/query/useWipeCommentary.ts" @@ -0,0 +1,36 @@ +import { isClientFault, wwwAPI } from "@/utilities/wwwAPI"; +import { GetCommentaryAPI } from "@/type/wwwAPI"; +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { toast } from "react-toastify"; + +export default function useWipeCommentary() { + const queryClient = useQueryClient(); + + const t = useTranslations(); + + return useMutation({ + mutationFn: async ({ + commentaryID, + avatarCipher, + }: { + commentaryID: number; + avatarCipher: string; + }) => { + await wwwAPI.delete("/commentary", { + params: { + commentaryID, + avatarCipher, + }, + }); + }, + onSuccess: async () => { + await queryClient.invalidateQueries({ queryKey: ["commentary"] }); + }, + onError: (e) => { + if (isClientFault(e)) { + toast.error(t("failedValidateCipher")); + } + }, + }); +} diff --git "a/taehui-fe/src/app/\133language\135/components/HitView.tsx" "b/taehui-fe/src/app/\133language\135/components/HitView.tsx" new file mode 100644 index 0000000..9c27657 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/components/HitView.tsx" @@ -0,0 +1,39 @@ +import useGetHit from "@/app/[language]/query/useGetHit"; +import usePostHit from "@/app/[language]/query/usePostHit"; +import { HitViewLoading } from "@/components/Loading"; +import { useTranslations } from "next-intl"; +import { useEffect } from "react"; + +export default function HitView() { + const t = useTranslations(); + + const { + data: [hitBefore, hit], + isFetched: isHitLoaded, + } = useGetHit(); + + const { mutateAsync: postHit } = usePostHit(); + + useEffect(() => { + (async () => { + await postHit(); + })(); + }, [postHit]); + + return ( + <> +
{t("hit00")}
+ {isHitLoaded ? ( + + {t("hit01", { hitBefore })} +
+ {t("hit02", { hit })} +
+ {t("hit03")} +
+ ) : ( + + )} + + ); +} diff --git "a/taehui-fe/src/app/\133language\135/components/LatestAvatarsView.tsx" "b/taehui-fe/src/app/\133language\135/components/LatestAvatarsView.tsx" new file mode 100644 index 0000000..969110e --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/components/LatestAvatarsView.tsx" @@ -0,0 +1,34 @@ +import AvatarTitle from "@/components/AvatarTitle"; +import { LatestAvatarViewLoading } from "@/components/Loading"; +import useGetLatestAvatar from "@/app/[language]/query/useGetLatestAvatar"; +import { useTranslations } from "next-intl"; +import { Col, Row } from "reactstrap"; +import { getDatetime } from "taehui-ts/date"; + +export default function LatestAvatarsView() { + const t = useTranslations(); + + const { data: latestAvatar, isFetched: isLatestAvatarLoaded } = + useGetLatestAvatar(); + + return ( + + {isLatestAvatarLoaded ? ( + latestAvatar.map((latestAvatar, i) => ( + +
{t(`latestAvatarsView${i}`)}
+ {latestAvatar.map(({ avatarID, avatarName, date }) => ( + + + {getDatetime(date)} + + + ))} + + )) + ) : ( + + )} +
+ ); +} diff --git "a/taehui-fe/src/app/\133language\135/components/LatestCommentsView.tsx" "b/taehui-fe/src/app/\133language\135/components/LatestCommentsView.tsx" new file mode 100644 index 0000000..83d6314 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/components/LatestCommentsView.tsx" @@ -0,0 +1,37 @@ +import CommentTitleView from "@/app/[language]/forum/components/CommentTitleView"; + +import { LatestCommentsViewLoading } from "@/components/Loading"; +import useGetLatestComment from "@/app/[language]/query/useGetLatestComment"; +import { useTranslations } from "next-intl"; +import { ListGroup, ListGroupItemHeading } from "reactstrap"; + +const LatestCommentsView = () => { + const t = useTranslations(); + + const { data: latestComment, isFetched: isLatestCommentLoaded } = + useGetLatestComment(); + + return ( + <> + + {t("latestCommentsView")} + {isLatestCommentLoaded ? ( + latestComment.map((latestComment) => { + return ( + + ); + }) + ) : ( + + )} + + + ); +}; + +export default LatestCommentsView; diff --git "a/taehui-fe/src/app/\133language\135/components/LatestEssaysView.tsx" "b/taehui-fe/src/app/\133language\135/components/LatestEssaysView.tsx" new file mode 100644 index 0000000..dff15f5 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/components/LatestEssaysView.tsx" @@ -0,0 +1,37 @@ +import EssayTitleView from "@/app/[language]/forum/components/EssayTitleView"; + +import { LatestEssaysViewLoading } from "@/components/Loading"; +import useGetLatestEssay from "@/app/[language]/query/useGetLatestEssay"; +import { useTranslations } from "next-intl"; +import { ListGroup, ListGroupItemHeading } from "reactstrap"; + +const LatestEssaysView = () => { + const t = useTranslations(); + + const { data: latestEssay, isFetched: isLatestEssayLoaded } = + useGetLatestEssay(); + + return ( + <> + + {t("latestEssaysView")} + {isLatestEssayLoaded ? ( + latestEssay.map((latestEssay) => { + return ( + + ); + }) + ) : ( + + )} + + + ); +}; + +export default LatestEssaysView; diff --git "a/taehui-fe/src/app/\133language\135/forum/\133forumID\135/\133essayID\135/page.tsx" "b/taehui-fe/src/app/\133language\135/forum/\133forumID\135/\133essayID\135/page.tsx" new file mode 100644 index 0000000..b3f977c --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/\133forumID\135/\133essayID\135/page.tsx" @@ -0,0 +1,130 @@ +"use client"; + +import CommentView from "@/app/[language]/forum/components/CommentView"; +import EssayTitleView from "@/app/[language]/forum/components/EssayTitleView"; +import TextView from "@/app/[language]/forum/components/TextView"; +import Loading from "@/app/[language]/forum/loading"; +import useGetEssay from "@/app/[language]/forum/query/useGetEssay"; +import useWipeEssay from "@/app/[language]/forum/query/useWipeEssay"; + +import { useAvatarStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; +import { useParams } from "next/navigation"; +import { Button, Col, Row } from "reactstrap"; +import Swal from "sweetalert2"; +import { useTo } from "taehui-ts/fe-utilities"; + +export default observer(() => { + const t = useTranslations(); + + const { taehuiAvatarID, isSU } = useAvatarStore(); + + const { forumID, essayID } = useParams<{ + forumID: string; + essayID: string; + }>(); + + const to = useTo(); + + const { mutateAsync: wipeEssay } = useWipeEssay(); + + const { + data: { + forumTitle, + title, + text, + avatarID, + avatarName, + date, + hitCount, + essayLater, + essayBefore, + }, + isFetched: isEssayLoaded, + } = useGetEssay(essayID); + + const onWipeEssay = async () => { + if ( + ( + await Swal.fire({ + title: "Taehui", + text: t("wipeEssayQuestion"), + icon: "question", + showDenyButton: true, + }) + ).isConfirmed + ) { + await wipeEssay({ essayID }); + to(`/forum/${forumID}`); + } + }; + + const onQuit = () => { + to(`/forum/${forumID}`); + }; + + if (!isEssayLoaded) { + return ; + } + + const isAllowModify = isSU || taehuiAvatarID === avatarID; + + return ( + <> + + {isAllowModify && ( + <> + + + + + + + + )} + + + + +
+ +
+ {essayLater && ( + + )} + {essayBefore && ( + + )} +
+ + + ); +}); diff --git "a/taehui-fe/src/app/\133language\135/forum/\133forumID\135/edit/\133\133...essayID\135\135/page.tsx" "b/taehui-fe/src/app/\133language\135/forum/\133forumID\135/edit/\133\133...essayID\135\135/page.tsx" new file mode 100644 index 0000000..dcac118 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/\133forumID\135/edit/\133\133...essayID\135\135/page.tsx" @@ -0,0 +1,400 @@ +"use client"; + +import AutoEssayTitleView from "@/app/[language]/forum/components/AutoEssayTitleView"; +import TextView from "@/app/[language]/forum/components/TextView"; +import useGetAutoEssay from "@/app/[language]/forum/query/useGetAutoEssay"; +import useGetEssay from "@/app/[language]/forum/query/useGetEssay"; +import usePostAutoEssay from "@/app/[language]/forum/query/usePostAutoEssay"; +import usePostEssay from "@/app/[language]/forum/query/usePostEssay"; +import usePostFile from "@/app/[language]/forum/query/usePostFile"; +import usePutAutoEssay from "@/app/[language]/forum/query/usePutAutoEssay"; +import usePutEssay from "@/app/[language]/forum/query/usePutEssay"; +import { AutoEssayViewLoading } from "@/components/Loading"; +import withTotem from "@/hoc/withTotem"; +import { useAvatarStore, useForumStore, useTaehuiStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; +import { useParams } from "next/navigation"; +import { useEffect, useLayoutEffect, useRef, useState } from "react"; +import { toast } from "react-toastify"; +import { + Button, + Col, + Collapse, + Input, + ListGroup, + Modal, + ModalBody, + Row, + TabContent, + TabPane, +} from "reactstrap"; +import { useTo, useWindowArea } from "taehui-ts/fe-utilities"; + +export default withTotem( + observer(() => { + const { + isTitleTextFilled, + title, + text, + setTitle, + setText, + autoEssayID, + setAutoEssayID, + } = useForumStore(); + const { titleViewHeight, avatarViewHeight } = useTaehuiStore(); + const { taehuiAvatarID, taehuiAvatarName } = useAvatarStore(); + + const t = useTranslations(); + const [isTestMode, setTestMode] = useState(false); + const [testText, setTestText] = useState(""); + const [textViewHeight, setTextViewHeight] = useState(100); + const [isAutoEssayOpened, setAutoEssayOpened] = useState(false); + + const { forumID, essayID } = useParams<{ + forumID: string; + essayID?: string; + }>(); + + const { isFetched: isAutoEssayLoaded, data: autoEssay } = useGetAutoEssay( + forumID, + isAutoEssayOpened, + ); + + const editView = useRef(null); + const textView = useRef(null); + const inputView = useRef(null); + + const { mutateAsync: postAutoEssay } = usePostAutoEssay(); + const { mutateAsync: putAutoEssay } = usePutAutoEssay(); + const { mutateAsync: putEssay } = usePutEssay(); + const { isPending, mutateAsync: postFile } = usePostFile(); + const { mutateAsync: postEssay } = usePostEssay(); + + const { + data: essay, + data: { forumTitle }, + isFetched: isEssayLoaded, + } = useGetEssay(essayID); + + useEffect(() => { + if (isEssayLoaded) { + setTitle(essay.title); + setText(essay.text); + } + }, [essay, isEssayLoaded, setText, setTitle]); + + const { windowHeight } = useWindowArea(); + + const to = useTo(); + + const setTag = (tag: string) => { + const { current } = textView; + if (current) { + const { selectionStart, selectionEnd } = current; + const t = text.substring(selectionStart, selectionEnd); + const tag0 = "<" + tag + ">"; + const tag1 = ""; + if (t.startsWith(tag0) || t.endsWith(tag1)) { + setText( + text.substring(0, selectionStart) + + text.substring( + selectionStart + tag0.length, + selectionStart + t.length - tag1.length, + ) + + text.substring(selectionEnd), + ); + setTimeout(() => { + current.selectionStart = selectionStart; + current.selectionEnd = selectionEnd - tag0.length - tag1.length; + current.focus(); + }, 0); + } else { + setText( + text.substring(0, selectionStart) + + tag0 + + text.substring(selectionStart, selectionEnd) + + tag1 + + text.substring(selectionEnd), + ); + setTimeout(() => { + current.selectionStart = selectionStart; + current.selectionEnd = selectionEnd + tag0.length + tag1.length; + current.focus(); + }, 0); + } + } + }; + + useEffect(() => { + setTextViewHeight( + windowHeight - + titleViewHeight - + avatarViewHeight - + (editView.current?.clientHeight ?? 0) - + (inputView.current?.clientHeight ?? 0), + ); + }, [avatarViewHeight, titleViewHeight, windowHeight]); + + useEffect(() => { + if (!essayID) { + setTitle(""); + setText(""); + } + }, [essayID, setText, setTitle]); + + useEffect(() => { + const postAutoEssaysID = setInterval(async () => { + if (isTitleTextFilled) { + if (typeof autoEssayID === "number") { + await putAutoEssay({ autoEssayID, title, text }); + } else { + const { autoEssayID } = await postAutoEssay({ + forumID, + title, + text, + }); + setAutoEssayID(autoEssayID); + } + } + }, 60000); + + return () => { + clearInterval(postAutoEssaysID); + }; + }, [ + autoEssayID, + forumID, + isTitleTextFilled, + postAutoEssay, + putAutoEssay, + setAutoEssayID, + t, + text, + title, + ]); + + useLayoutEffect(() => { + if (isTestMode) { + setTestText(text); + } + }, [isTestMode, text]); + + return ( + <> + {!isTestMode && ( +
+ + + { + setTitle(value); + }} + /> + + + + + + + + + + + + + + + {isAutoEssayLoaded ? ( + autoEssay.map((autoEssay) => ( + + )) + ) : ( + + )} + + + + +
+ )} + + + + + { + setText(value); + }} + innerRef={textView} + style={{ height: textViewHeight }} + /> + + + + + + + +
+ + + + + + + + + + + + + + + + + + + {essayID ? ( + + + + ) : ( + + + + )} + + + + +
+ + + {t("fileUploading")} + + + + ); + }), +); diff --git "a/taehui-fe/src/app/\133language\135/forum/\133forumID\135/page.tsx" "b/taehui-fe/src/app/\133language\135/forum/\133forumID\135/page.tsx" new file mode 100644 index 0000000..5b75837 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/\133forumID\135/page.tsx" @@ -0,0 +1,97 @@ +"use client"; + +import EssayTitleView from "@/app/[language]/forum/components/EssayTitleView"; +import PositionInput from "@/app/[language]/forum/components/PositionInput"; +import Loading from "@/app/[language]/forum/loading"; +import useGetForum from "@/app/[language]/forum/query/useGetForum"; +import { useAvatarStore, useForumStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; +import Link from "next/link"; +import { useParams } from "next/navigation"; +import { useEffect } from "react"; +import { + Badge, + Button, + Col, + ListGroup, + ListGroupItemHeading, + Row, +} from "reactstrap"; +import { useIntParam, useTo } from "taehui-ts/fe-utilities"; + +export default observer(() => { + const { taehuiLevel } = useAvatarStore(); + const { viewUnit, setLastPage } = useForumStore(); + const t = useTranslations(); + + const { forumID } = useParams<{ + forumID: string; + }>(); + const { param: page } = useIntParam("page", 1); + + const to = useTo(); + + const { + data: { title, essays, essayCount, level }, + isFetched: isForumLoaded, + } = useGetForum(forumID, page, viewUnit); + + useEffect(() => { + if (isForumLoaded) { + setLastPage(Math.ceil(essayCount / viewUnit)); + } + }, [essayCount, isForumLoaded, setLastPage, viewUnit]); + + return ( + <> + + + + + {title} + + {isForumLoaded ? ( + essays.map((essay) => ( + + )) + ) : ( + + )} + + + + + + + + + + {taehuiLevel >= level && ( + + + + + + )} + = level ? "auto" : undefined} + > + + + + + ); +}); diff --git "a/taehui-fe/src/app/\133language\135/forum/components/AutoEssayTitleView.tsx" "b/taehui-fe/src/app/\133language\135/forum/components/AutoEssayTitleView.tsx" new file mode 100644 index 0000000..fda946a --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/components/AutoEssayTitleView.tsx" @@ -0,0 +1,54 @@ +import useWipeAutoEssay from "@/app/[language]/forum/query/useWipeAutoEssay"; + +import { useForumStore } from "@/store/Stores"; +import { GetAutoEssayAPI } from "@/type/wwwAPI"; +import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; +import { Col, ListGroupItem, Row } from "reactstrap"; +import Swal from "sweetalert2"; +import { getDatetime } from "taehui-ts/date"; + +const AutoEssayTitleView = observer<{ autoEssay: GetAutoEssayAPI[0] }>( + ({ autoEssay: { autoEssayID, title, text, date } }) => { + const { mutateAsync: wipeAutoEssay } = useWipeAutoEssay(); + + const { setTitle, setText, setAutoEssayID } = useForumStore(); + const t = useTranslations(); + + return ( + { + const { isConfirmed, isDenied } = await Swal.fire({ + title: t("autoEssay"), + text: t("setAutoEssayQuestion"), + icon: "question", + showDenyButton: true, + denyButtonText: t("wipeEssay"), + }); + + if (isConfirmed) { + setTitle(title); + setText(text); + setAutoEssayID(autoEssayID); + } + + if (isDenied) { + await wipeAutoEssay({ autoEssayID }); + } + }} + > + + + {title} + + + {getDatetime(date)} + + + + ); + }, +); + +export default AutoEssayTitleView; diff --git "a/taehui-fe/src/app/\133language\135/forum/components/CommentItem.tsx" "b/taehui-fe/src/app/\133language\135/forum/components/CommentItem.tsx" new file mode 100644 index 0000000..36088fd --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/components/CommentItem.tsx" @@ -0,0 +1,163 @@ +import usePostComment from "@/app/[language]/forum/query/usePostComment"; +import usePutComment from "@/app/[language]/forum/query/usePutComment"; +import useWipeComment from "@/app/[language]/forum/query/useWipeComment"; +import AvatarTitle from "@/components/AvatarTitle"; +import { useAvatarStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; +import { useParams } from "next/navigation"; +import { useMemo, useState } from "react"; +import ReactTextareaAutosize from "react-textarea-autosize"; +import { toast } from "react-toastify"; +import { Button, Col, Collapse, Row } from "reactstrap"; +import Swal from "sweetalert2"; +import { getDatetime } from "taehui-ts/date"; + +export default observer( + ({ + commentID, + text, + avatarID, + avatarName, + date, + level, + }: { + commentID: number; + text: string; + date: string; + avatarID: string; + avatarName: string; + level: number; + }) => { + const t = useTranslations(); + const { totem, taehuiAvatarID, taehuiAvatarName, isSU } = useAvatarStore(); + + const { essayID } = useParams<{ essayID: string }>(); + + const [textInput, setTextInput] = useState(""); + const [targetTextInput, setTargetTextInput] = useState(""); + const [isTargetOpened, setTargetOpened] = useState(false); + + const isAllowModify = useMemo( + () => isSU || taehuiAvatarID === avatarID, + [isSU, avatarID, taehuiAvatarID], + ); + + const { mutateAsync: wipeComment } = useWipeComment(); + const { mutateAsync: putComment } = usePutComment(); + const { mutateAsync: postComment } = usePostComment(); + + return ( +
+ + +
{ + if (totem && !isTargetOpened) { + setTargetOpened(true); + } + }} + > + {isTargetOpened && isAllowModify ? ( + + + { + setTextInput(value); + }} + /> + + + + + + + + + ) : ( + {text} + )} +
+
+ + {getDatetime(date)} + +
+ + + + + + { + setTargetTextInput(value); + }} + /> + + + + + + + + +
+ ); + }, +); diff --git "a/taehui-fe/src/app/\133language\135/forum/components/CommentTitleView.tsx" "b/taehui-fe/src/app/\133language\135/forum/components/CommentTitleView.tsx" new file mode 100644 index 0000000..3ab5257 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/components/CommentTitleView.tsx" @@ -0,0 +1,38 @@ +import AvatarTitle from "@/components/AvatarTitle"; +import { GetLatestCommentAPI } from "@/type/wwwAPI"; +import { Col, ListGroupItem, Row } from "reactstrap"; +import { getDatetime } from "taehui-ts/date"; +import { useTo } from "taehui-ts/fe-utilities"; + +const CommentTitleView = ({ + forumID, + essayID, + comment: { avatarID, avatarName, date, text }, +}: { + forumID: string; + essayID: number; + comment: GetLatestCommentAPI[number]; +}) => { + const to = useTo(); + + return ( + { + to(`/forum/${forumID}/${essayID}`); + }} + > + + + {text} + + + {getDatetime(date)} + + + + ); +}; + +export default CommentTitleView; diff --git "a/taehui-fe/src/app/\133language\135/forum/components/CommentView.tsx" "b/taehui-fe/src/app/\133language\135/forum/components/CommentView.tsx" new file mode 100644 index 0000000..2d7809e --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/components/CommentView.tsx" @@ -0,0 +1,108 @@ +import CommentItem from "@/app/[language]/forum/components/CommentItem"; +import useGetComment from "@/app/[language]/forum/query/useGetComment"; +import usePostComment from "@/app/[language]/forum/query/usePostComment"; +import AvatarTitle from "@/components/AvatarTitle"; +import { useAvatarStore } from "@/store/Stores"; +import { GetCommentAPI } from "@/type/wwwAPI"; +import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; +import { useParams } from "next/navigation"; +import { ReactNode, useMemo, useState } from "react"; +import ReactTextareaAutosize from "react-textarea-autosize"; +import { toast } from "react-toastify"; +import { Badge, Button, Col, Row } from "reactstrap"; + +export default observer(() => { + const t = useTranslations(); + const { taehuiAvatarID, taehuiAvatarName, taehuiLevel } = useAvatarStore(); + const [textInput, setTextInput] = useState(""); + + const { essayID } = useParams<{ essayID: string }>(); + + const { data: comment } = useGetComment(essayID); + const { mutateAsync: postComment } = usePostComment(); + + const commentComponents = useMemo(() => { + const commentComponents: ReactNode[] = []; + + const setCommentComponents = + (level: number) => + ({ + commentID, + avatarID, + avatarName, + date, + text, + comments, + }: GetCommentAPI[number]) => { + commentComponents.push( + , + ); + + comments.forEach(setCommentComponents(level + 1)); + }; + + comment.forEach((comment) => { + setCommentComponents(0)(comment); + }); + + return commentComponents; + }, [comment]); + + return ( + <> + + + + {t("commentCount", { commentCount: commentComponents.length })} + + + + {commentComponents} + {taehuiLevel >= 1 && ( + + + + + { + setTextInput(value); + }} + /> + + + + + + + + )} + + ); +}); diff --git "a/taehui-fe/src/app/\133language\135/forum/components/EssayTitleView.tsx" "b/taehui-fe/src/app/\133language\135/forum/components/EssayTitleView.tsx" new file mode 100644 index 0000000..de34928 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/components/EssayTitleView.tsx" @@ -0,0 +1,43 @@ +import AvatarTitle from "@/components/AvatarTitle"; +import { EssayAPIEssay } from "@/type/wwwAPI"; +import { useTranslations } from "next-intl"; +import { Col, ListGroupItem, Row } from "reactstrap"; +import { getDatetime } from "taehui-ts/date"; +import { useTo } from "taehui-ts/fe-utilities"; + +const EssayTitleView = ({ + forumID, + forumTitle, + essay: { essayID, title, avatarID, avatarName, date, commentCount, hitCount }, +}: { + forumID?: string; + forumTitle?: string; + essay: EssayAPIEssay; +}) => { + const t = useTranslations(); + const to = useTo(); + + return ( + { + to(`/forum/${forumID}/${essayID}`); + }} + > + + + + {forumTitle && `[${forumTitle}]`} {title} [{commentCount}] + + + + {getDatetime(date)} +
+ {t("hitCount", { hitCount })} + +
+
+ ); +}; + +export default EssayTitleView; diff --git "a/taehui-fe/src/app/\133language\135/forum/components/ForumItem.tsx" "b/taehui-fe/src/app/\133language\135/forum/components/ForumItem.tsx" new file mode 100644 index 0000000..612ecbe --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/components/ForumItem.tsx" @@ -0,0 +1,27 @@ +import EssayTitleView from "@/app/[language]/forum/components/EssayTitleView"; +import { EssayAPIEssay } from "@/type/wwwAPI"; +import Link from "next/link"; +import { Badge, ListGroup, ListGroupItemHeading } from "reactstrap"; + +export default function ForumItem({ + forum: { forumID, title, essays }, +}: { + forum: { + forumID: string; + title: string; + essays: EssayAPIEssay[]; + }; +}) { + return ( + + + + {title} + + + {essays.map((essay) => ( + + ))} + + ); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/components/PositionInput.tsx" "b/taehui-fe/src/app/\133language\135/forum/components/PositionInput.tsx" new file mode 100644 index 0000000..298738c --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/components/PositionInput.tsx" @@ -0,0 +1,78 @@ +import { useForumStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; +import { useMemo } from "react"; +import { Pagination, PaginationItem, PaginationLink } from "reactstrap"; +import { useIntParam } from "taehui-ts/fe-utilities"; + +export default observer(() => { + const { pageUnit, lastPage } = useForumStore(); + + const { param: page, setParam: setPage } = useIntParam("page", 1); + + const targetPages = useMemo(() => { + const targetPages = []; + for ( + let i = 1 + Math.floor((page - 1) / pageUnit) * pageUnit; + i <= + Math.min( + lastPage, + Math.floor((page - 1) / pageUnit) * pageUnit + pageUnit, + ); + ++i + ) { + targetPages.push(i); + } + return targetPages; + }, [lastPage, page, pageUnit]); + + const isLowestPage = useMemo(() => page === 1, [page]); + const isHighestPage = useMemo(() => page === lastPage, [lastPage, page]); + + return ( + + + { + setPage(1); + }} + /> + + + { + setPage(page - 1); + }} + /> + + {targetPages.map((targetPage) => ( + + { + setPage(targetPage); + }} + > + {targetPage} + + + ))} + + { + setPage(page + 1); + }} + /> + + + { + setPage(lastPage); + }} + /> + + + ); +}); diff --git "a/taehui-fe/src/app/\133language\135/forum/components/TextView.module.scss" "b/taehui-fe/src/app/\133language\135/forum/components/TextView.module.scss" new file mode 100644 index 0000000..f097979 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/components/TextView.module.scss" @@ -0,0 +1,22 @@ +@mixin essay() { + border: thin black solid; + max-width: 100%; +} + +img { + &.essay { + @include essay(); + } +} + +audio { + &.essay { + @include essay(); + } +} + +video { + &.essay { + @include essay(); + } +} diff --git "a/taehui-fe/src/app/\133language\135/forum/components/TextView.tsx" "b/taehui-fe/src/app/\133language\135/forum/components/TextView.tsx" new file mode 100644 index 0000000..2bee83c --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/components/TextView.tsx" @@ -0,0 +1,96 @@ +import scss from "@/app/[language]/forum/components/TextView.module.scss"; +import useGetHit from "@/app/[language]/forum/query/useGetHit"; +import AvatarTitle from "@/components/AvatarTitle"; +import { getHitTexts, tag } from "@/utilities/Utility"; +import { sanitize } from "dompurify"; +import { useTranslations } from "next-intl"; +import { useEffect, useMemo, useState } from "react"; +import { Badge, Col, Row } from "reactstrap"; +import { getDatetime } from "taehui-ts/date"; + +const TextView = ({ + forumTitle, + title, + text, + avatarID, + avatarName, + date, + hitCount, +}: { + forumTitle: string; + title: string; + text: string; + avatarID: string; + avatarName: string; + date?: string; + hitCount?: number; +}) => { + const hitTexts = useMemo(() => getHitTexts(text), [text]); + const [textHTMLContents, setTextHTMLContents] = useState(""); + + const t = useTranslations(); + + const { data: hit, isFetched: isHitLoaded } = useGetHit(hitTexts); + + useEffect(() => { + setTextHTMLContents( + sanitize(tag(t, text, {}, scss.essay), { + ADD_ATTR: ["target"], + }), + ); + }, [t, text]); + + useEffect(() => { + if (isHitLoaded) { + setTextHTMLContents( + sanitize( + tag( + t, + text, + Object.fromEntries(hitTexts.map((hitText, i) => [hitText, hit[i]])), + scss.essay, + ), + { + ADD_ATTR: ["target"], + }, + ), + ); + } + }, [hit, hitTexts, isHitLoaded, t, text]); + + return ( + <> + + + {forumTitle} + + + + + {title} + + + {typeof hitCount === "number" && ( + <> + {getDatetime(date)} +
+ {t("hitCount", { hitCount })} + + )} + +
+ + + + + + + ); +}; + +export default TextView; diff --git "a/taehui-fe/src/app/\133language\135/forum/loading.tsx" "b/taehui-fe/src/app/\133language\135/forum/loading.tsx" new file mode 100644 index 0000000..32a6627 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/loading.tsx" @@ -0,0 +1,10 @@ +import LoadingLayer from "@/components/LoadingLayer"; +import { List } from "react-content-loader"; + +export default function Loading() { + return ( + + + + ); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/query/useGetAutoEssay.ts" "b/taehui-fe/src/app/\133language\135/forum/query/useGetAutoEssay.ts" new file mode 100644 index 0000000..668431a --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/query/useGetAutoEssay.ts" @@ -0,0 +1,30 @@ +import { useQuery } from "@tanstack/react-query"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { GetAutoEssayAPI } from "@/type/wwwAPI"; +import { getMillis } from "taehui-ts/date"; +import { useAvatarStore } from "@/store/Stores"; + +export default function useGetAutoEssay( + forumID: string, + isAutoEssayOpened: boolean, +) { + const { totem } = useAvatarStore(); + + return useQuery({ + enabled: isAutoEssayOpened, + queryKey: ["autoEssay", forumID, totem], + queryFn: async () => { + const { data } = await wwwAPI.get( + `/autoEssay/${forumID}`, + { + headers: { + millis: getMillis(), + totem, + }, + }, + ); + return data; + }, + initialData: [], + }); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/query/useGetComment.ts" "b/taehui-fe/src/app/\133language\135/forum/query/useGetComment.ts" new file mode 100644 index 0000000..b08db14 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/query/useGetComment.ts" @@ -0,0 +1,14 @@ +import { useQuery } from "@tanstack/react-query"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { GetCommentAPI } from "@/type/wwwAPI"; + +export default function useGetComment(essayID: string) { + return useQuery({ + queryKey: ["comment", essayID], + queryFn: async () => { + const { data } = await wwwAPI.get(`/comment/${essayID}`); + return data; + }, + initialData: [], + }); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/query/useGetEssay.ts" "b/taehui-fe/src/app/\133language\135/forum/query/useGetEssay.ts" new file mode 100644 index 0000000..9fcbcd9 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/query/useGetEssay.ts" @@ -0,0 +1,38 @@ +import { useQuery } from "@tanstack/react-query"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { EssayAPIEssay, GetEssayAPI } from "@/type/wwwAPI"; +import { getLanguage } from "taehui-ts/language"; + +export default function useGetEssay(essayID?: string) { + return useQuery<{ + forumTitle: string; + title: string; + text: string; + date: string; + avatarID: string; + avatarName: string; + hitCount: number; + essayBefore?: EssayAPIEssay; + essayLater?: EssayAPIEssay; + }>({ + enabled: !!essayID, + queryKey: ["essay", essayID], + queryFn: async () => { + const { data } = await wwwAPI.get(`/essay/${essayID}`, { + params: { language: getLanguage() }, + }); + return data; + }, + initialData: { + forumTitle: "", + title: "", + text: "", + date: "", + avatarID: "", + avatarName: "", + hitCount: 0, + essayBefore: undefined, + essayLater: undefined, + }, + }); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/query/useGetForum.ts" "b/taehui-fe/src/app/\133language\135/forum/query/useGetForum.ts" new file mode 100644 index 0000000..7475dff --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/query/useGetForum.ts" @@ -0,0 +1,33 @@ +import { useQuery } from "@tanstack/react-query"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { GetForumAPI } from "@/type/wwwAPI"; +import { getLanguage } from "taehui-ts/language"; + +export default function useGetForum( + forumID: string, + page: number, + viewUnit: number, +) { + const language = getLanguage(); + + return useQuery({ + queryKey: ["forum", forumID, page, viewUnit, language], + queryFn: async () => { + const { data } = await wwwAPI.get(`/forum/${forumID}`, { + params: { + page, + viewUnit, + language, + }, + }); + return data; + }, + initialData: { + title: "", + text: "", + essays: [], + essayCount: 0, + level: 0, + }, + }); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/query/useGetHit.ts" "b/taehui-fe/src/app/\133language\135/forum/query/useGetHit.ts" new file mode 100644 index 0000000..c0d5f95 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/query/useGetHit.ts" @@ -0,0 +1,25 @@ +import { useQuery } from "@tanstack/react-query"; +import { wwwAPI } from "@/utilities/wwwAPI"; + +export default function useGetHit(hitTexts: string[]) { + return useQuery({ + queryKey: ["hit", hitTexts], + queryFn: async () => { + return ( + await Promise.allSettled( + hitTexts.map(async (hitText) => + wwwAPI.get(`/file/${hitText}/hit`), + ), + ) + ).map((value) => { + switch (value.status) { + case "fulfilled": + return value.value.data; + default: + return 0; + } + }); + }, + initialData: [], + }); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/query/usePostAutoEssay.ts" "b/taehui-fe/src/app/\133language\135/forum/query/usePostAutoEssay.ts" new file mode 100644 index 0000000..8e2679b --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/query/usePostAutoEssay.ts" @@ -0,0 +1,48 @@ +import { useAvatarStore } from "@/store/Stores"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { toast } from "react-toastify"; +import { getMillis } from "taehui-ts/date"; + +export default function usePostAutoEssay() { + const { totem } = useAvatarStore(); + + const t = useTranslations(); + + const queryClient = useQueryClient(); + + return useMutation({ + mutationFn: async ({ + forumID, + title, + text, + }: { + forumID: string; + title: string; + text: string; + }) => { + const { + data: { autoEssayID }, + } = await wwwAPI.post( + `/autoEssay/${forumID}`, + { + title, + text, + }, + { + headers: { + millis: getMillis(), + totem, + }, + }, + ); + + return autoEssayID; + }, + onSuccess: async (data) => { + await queryClient.invalidateQueries({ queryKey: ["autoEssay"] }); + toast.success(t("postedAutoEssay")); + }, + }); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/query/usePostComment.ts" "b/taehui-fe/src/app/\133language\135/forum/query/usePostComment.ts" new file mode 100644 index 0000000..e705ab5 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/query/usePostComment.ts" @@ -0,0 +1,37 @@ +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { getMillis } from "taehui-ts/date"; + +import { useAvatarStore } from "@/store/Stores"; + +export default function usePostComment() { + const { totem } = useAvatarStore(); + + const queryClient = useQueryClient(); + + return useMutation({ + mutationFn: async ({ + essayID, + targetCommentID, + text, + }: { + essayID: string; + targetCommentID: number; + text: string; + }) => { + await wwwAPI.post( + `/comment/${essayID}`, + { targetCommentID, text }, + { + headers: { + millis: getMillis(), + totem, + }, + }, + ); + }, + onSuccess: async (data) => { + await queryClient.invalidateQueries({ queryKey: ["comment"] }); + }, + }); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/query/usePostEssay.ts" "b/taehui-fe/src/app/\133language\135/forum/query/usePostEssay.ts" new file mode 100644 index 0000000..6e71ece --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/query/usePostEssay.ts" @@ -0,0 +1,40 @@ +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { getMillis } from "taehui-ts/date"; + +import { useAvatarStore } from "@/store/Stores"; + +export default function usePostEssay() { + const { totem } = useAvatarStore(); + + const queryClient = useQueryClient(); + + return useMutation({ + mutationFn: async ({ + forumID, + title, + text, + }: { + forumID: string; + title: string; + text: string; + }) => { + await wwwAPI.post( + `/essay/${forumID}`, + { + title, + text, + }, + { + headers: { + millis: getMillis(), + totem, + }, + }, + ); + }, + onSuccess: async (data) => { + await queryClient.invalidateQueries({ queryKey: ["essay"] }); + }, + }); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/query/usePostFile.ts" "b/taehui-fe/src/app/\133language\135/forum/query/usePostFile.ts" new file mode 100644 index 0000000..44960ae --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/query/usePostFile.ts" @@ -0,0 +1,51 @@ +import { useMutation } from "@tanstack/react-query"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { getMillis } from "taehui-ts/date"; + +import { useAvatarStore } from "@/store/Stores"; + +export default function usePostFile() { + const { totem } = useAvatarStore(); + + return useMutation({ + mutationFn: async ({ + file, + textView, + }: { + file: File; + textView: HTMLTextAreaElement; + }) => { + const form = new FormData(); + form.append("data", file); + const { + status, + data: { fileName }, + } = await wwwAPI.post("/file", form, { + headers: { + millis: getMillis(), + totem, + }, + }); + if (status === 201) { + const { selectionStart, value } = textView; + const textBefore = value.substring(0, selectionStart); + const textLater = value.substring(selectionStart, value.length); + if (fileName.match(/^.*\.(bmp|gif|jpeg|jpg|png|webp)$/i)) { + return `${textBefore}${textLater}`; + } else if ( + fileName.match( + /^.*\.(aif|aiff|asf|flac|m4a|mid|midi|mp2|mp3|ogg|opus|raw|wav|wma)$/i, + ) + ) { + return `${textBefore}${textLater}`; + } else if ( + fileName.match(/^.*\.(avi|flv|m1v|mkv|mov|mp4|mpeg|mpg|webm|wmv)$/i) + ) { + return `${textBefore}${textLater}`; + } else { + return `${textBefore}${file.name}${textLater}`; + } + } + }, + }); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/query/usePutAutoEssay.ts" "b/taehui-fe/src/app/\133language\135/forum/query/usePutAutoEssay.ts" new file mode 100644 index 0000000..4525320 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/query/usePutAutoEssay.ts" @@ -0,0 +1,44 @@ +import { useAvatarStore } from "@/store/Stores"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { toast } from "react-toastify"; +import { getMillis } from "taehui-ts/date"; + +export default function usePutAutoEssay() { + const { totem } = useAvatarStore(); + + const t = useTranslations(); + + const queryClient = useQueryClient(); + + return useMutation({ + mutationFn: async ({ + autoEssayID, + title, + text, + }: { + autoEssayID: number; + title: string; + text: string; + }) => { + await wwwAPI.put( + `/autoEssay/${autoEssayID}`, + { + title, + text, + }, + { + headers: { + millis: getMillis(), + totem, + }, + }, + ); + }, + onSuccess: async () => { + await queryClient.invalidateQueries({ queryKey: ["autoEssay"] }); + toast.success(t("postedAutoEssay")); + }, + }); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/query/usePutComment.ts" "b/taehui-fe/src/app/\133language\135/forum/query/usePutComment.ts" new file mode 100644 index 0000000..a0f5c18 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/query/usePutComment.ts" @@ -0,0 +1,35 @@ +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { getMillis } from "taehui-ts/date"; + +import { useAvatarStore } from "@/store/Stores"; + +export default function usePutComment() { + const { totem } = useAvatarStore(); + + const queryClient = useQueryClient(); + + return useMutation({ + mutationFn: async ({ + commentID, + text, + }: { + commentID: number; + text: string; + }) => { + await wwwAPI.put( + `/comment/${commentID}`, + { text }, + { + headers: { + millis: getMillis(), + totem, + }, + }, + ); + }, + onSuccess: async () => { + await queryClient.invalidateQueries({ queryKey: ["comment"] }); + }, + }); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/query/usePutEssay.ts" "b/taehui-fe/src/app/\133language\135/forum/query/usePutEssay.ts" new file mode 100644 index 0000000..5a0c009 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/query/usePutEssay.ts" @@ -0,0 +1,41 @@ +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { getMillis } from "taehui-ts/date"; + +import { useAvatarStore } from "@/store/Stores"; + +export default function usePutEssay() { + const { totem } = useAvatarStore(); + + const queryClient = useQueryClient(); + + return useMutation({ + mutationFn: async ({ + essayID, + title, + text, + }: { + essayID: string; + title: string; + text: string; + }) => { + await wwwAPI.put( + `/essay/${essayID}`, + { + title, + text, + }, + { + headers: { + millis: getMillis(), + totem, + }, + }, + ); + }, + onSuccess: async (data, { essayID }) => { + await queryClient.invalidateQueries({ queryKey: ["forum"] }); + await queryClient.invalidateQueries({ queryKey: ["essay"] }); + }, + }); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/query/useWipeAutoEssay.ts" "b/taehui-fe/src/app/\133language\135/forum/query/useWipeAutoEssay.ts" new file mode 100644 index 0000000..abc2a7e --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/query/useWipeAutoEssay.ts" @@ -0,0 +1,22 @@ +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { getMillis } from "taehui-ts/date"; + +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useAvatarStore, useForumStore } from "@/store/Stores"; + +export default function useWipeAutoEssay() { + const { totem } = useAvatarStore(); + + const queryClient = useQueryClient(); + + return useMutation({ + mutationFn: async ({ autoEssayID }: { autoEssayID: number }) => { + await wwwAPI.delete(`/autoEssay/${autoEssayID}`, { + headers: { millis: getMillis(), totem }, + }); + }, + onSuccess: async () => { + await queryClient.invalidateQueries({ queryKey: ["autoEssay"] }); + }, + }); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/query/useWipeComment.ts" "b/taehui-fe/src/app/\133language\135/forum/query/useWipeComment.ts" new file mode 100644 index 0000000..834bbb4 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/query/useWipeComment.ts" @@ -0,0 +1,36 @@ +import { isClientFault, wwwAPI } from "@/utilities/wwwAPI"; +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { useTranslations } from "next-intl"; +import { toast } from "react-toastify"; +import { getMillis } from "taehui-ts/date"; + +export default function useWipeComment() { + const queryClient = useQueryClient(); + + const t = useTranslations(); + + return useMutation({ + mutationFn: async ({ + commentID, + totem, + }: { + commentID: number; + totem: string; + }) => { + await wwwAPI.delete(`/comment/${commentID}`, { + headers: { + millis: getMillis(), + totem, + }, + }); + }, + onSuccess: async () => { + await queryClient.invalidateQueries({ queryKey: ["comment"] }); + }, + onError: (e) => { + if (isClientFault(e)) { + toast.error(t("failedValidateCipher")); + } + }, + }); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/query/useWipeEssay.ts" "b/taehui-fe/src/app/\133language\135/forum/query/useWipeEssay.ts" new file mode 100644 index 0000000..8114818 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/query/useWipeEssay.ts" @@ -0,0 +1,24 @@ +import { useAvatarStore } from "@/store/Stores"; +import { wwwAPI } from "@/utilities/wwwAPI"; +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { getMillis } from "taehui-ts/date"; + +export default function useWipeEssay() { + const { totem } = useAvatarStore(); + + const queryClient = useQueryClient(); + + return useMutation({ + mutationFn: async ({ essayID }: { essayID: string }) => { + await wwwAPI.delete(`/essay/${essayID}`, { + headers: { + millis: getMillis(), + totem, + }, + }); + }, + onSuccess: async () => { + await queryClient.invalidateQueries({ queryKey: ["forum"] }); + }, + }); +} diff --git "a/taehui-fe/src/app/\133language\135/forum/store/setForumStore.ts" "b/taehui-fe/src/app/\133language\135/forum/store/setForumStore.ts" new file mode 100644 index 0000000..cefc759 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forum/store/setForumStore.ts" @@ -0,0 +1,36 @@ +export default function setForumStore() { + return { + title: "", + text: "", + autoEssayID: undefined as number | undefined, + + lastPage: 0, + pageUnit: 10, + viewUnit: 10, + level: 0, + + setTitle(title: string) { + this.title = title; + }, + + setText(text: string) { + this.text = text; + }, + + setAutoEssayID(autoEssayID?: number) { + this.autoEssayID = autoEssayID; + }, + + setLastPage(lastPage: number) { + this.lastPage = lastPage; + }, + + setLevel(level: number) { + this.level = level; + }, + + get isTitleTextFilled() { + return this.title && this.text; + }, + }; +} diff --git "a/taehui-fe/src/app/\133language\135/forums/\133\133...forumGroup\135\135/page.tsx" "b/taehui-fe/src/app/\133language\135/forums/\133\133...forumGroup\135\135/page.tsx" new file mode 100644 index 0000000..be20196 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forums/\133\133...forumGroup\135\135/page.tsx" @@ -0,0 +1,37 @@ +"use client"; + +import ForumItem from "@/app/[language]/forum/components/ForumItem"; +import Loading from "@/app/[language]/forums/loading"; +import useGetForums from "@/app/[language]/forums/query/useGetForums"; +import { useParams } from "next/navigation"; +import { useEffect, useState } from "react"; +import { Col, Row } from "reactstrap"; +import { useWindowArea } from "taehui-ts/fe-utilities"; + +export default function Page() { + const [table, setTable] = useState(1); + + const { windowLength } = useWindowArea(); + + useEffect(() => { + setTable(windowLength < 992 ? 1 : 2); + }, [windowLength]); + + const { forumGroup } = useParams<{ forumGroup?: string }>(); + + const { data: forums, isFetched: isForumsLoaded } = useGetForums(forumGroup); + + if (!isForumsLoaded) { + return ; + } + + return [...Array(Math.ceil(forums.length / table)).keys()].map((i) => ( + + {forums.slice(table * i, table * i + table).map((forum) => ( + + + + ))} + + )); +} diff --git "a/taehui-fe/src/app/\133language\135/forums/loading.tsx" "b/taehui-fe/src/app/\133language\135/forums/loading.tsx" new file mode 100644 index 0000000..32a6627 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forums/loading.tsx" @@ -0,0 +1,10 @@ +import LoadingLayer from "@/components/LoadingLayer"; +import { List } from "react-content-loader"; + +export default function Loading() { + return ( + + + + ); +} diff --git "a/taehui-fe/src/app/\133language\135/forums/query/useGetForums.ts" "b/taehui-fe/src/app/\133language\135/forums/query/useGetForums.ts" new file mode 100644 index 0000000..2ba026b --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/forums/query/useGetForums.ts" @@ -0,0 +1,20 @@ +import { wwwAPI } from "@/utilities/wwwAPI"; +import { GetForumsAPI } from "@/type/wwwAPI"; +import { useQuery } from "@tanstack/react-query"; +import { getLanguage } from "taehui-ts/language"; + +export default function useGetForums(forumGroup?: string) { + return useQuery({ + queryKey: ["forums", forumGroup], + queryFn: async () => { + const { data } = await wwwAPI.get( + forumGroup ? `/forums/${forumGroup}` : "/forums", + { + params: { language: getLanguage() }, + }, + ); + return data; + }, + initialData: [], + }); +} diff --git "a/taehui-fe/src/app/\133language\135/layout.tsx" "b/taehui-fe/src/app/\133language\135/layout.tsx" new file mode 100644 index 0000000..f84b424 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/layout.tsx" @@ -0,0 +1,37 @@ +import { Stores } from "@/store/Stores"; +import TaehuiView from "@/components/TaehuiView"; +import { NextIntlClientProvider } from "next-intl"; +import { getMessages } from "next-intl/server"; +import { ReactNode } from "react"; + +import "bootstrap/dist/css/bootstrap.min.css"; +import "react-contexify/dist/ReactContexify.css"; +import "react-toastify/dist/ReactToastify.css"; + +import "@/app/globals.scss"; + +export default async function RootLayout({ + children, + params: { language }, +}: { + children: ReactNode; + params: { language: string }; +}) { + return ( + + + Taehui + + + + + {children} + + + + + ); +} diff --git "a/taehui-fe/src/app/\133language\135/page.tsx" "b/taehui-fe/src/app/\133language\135/page.tsx" new file mode 100644 index 0000000..7425dfc --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/page.tsx" @@ -0,0 +1,37 @@ +"use client"; + +import HitView from "@/app/[language]/components/HitView"; +import LatestAvatarsView from "@/app/[language]/components/LatestAvatarsView"; +import LatestCommentsView from "@/app/[language]/components/LatestCommentsView"; +import LatestEssaysView from "@/app/[language]/components/LatestEssaysView"; +import WantInput from "@/app/[language]/want/components/WantInput"; +import { useTranslations } from "next-intl"; + +const Page = () => { + const t = useTranslations(); + + return ( + <> + +
+
{t("main00")}
+ + {t("main01")} +
+ {t("main02")} +
+ {t("main03")} +
+
+ +
+ +
+ +
+ + + ); +}; + +export default Page; diff --git "a/taehui-fe/src/app/\133language\135/ppt/page.tsx" "b/taehui-fe/src/app/\133language\135/ppt/page.tsx" new file mode 100644 index 0000000..d650e1b --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/ppt/page.tsx" @@ -0,0 +1,156 @@ +export default function Page() { + return ( + <> + + 이름: 박태희 +
+ 생년월일: 1994년 12월 21일 +
+ 메일 주소:{" "} + taehui@taehui.ddns.net +
+
직장
+
    +
  • + (주) 네이버파이낸셜{" "} + 프론트엔드 개발자 (2020년 3월 12일 ~) +
    + 경기도 성남시 분당구 정자일로 95 1784 +
  • +
  • + (주) 네이버 2020 신입 프론트엔드 + 2020 신입 프론트엔드 개발자 (2020년 1월 2일 ~ 2020년 3월 11일) +
    + 경기도 성남시 분당구 불정로 6 NAVER +
  • +
+
+
거주지
+
    +
  • 경기도 성남시 분당구 (2020년)
  • +
  • 세종특별자치시 (2018년 ~ 2020년)
  • +
  • 대전광역시 유성구 (1994년 ~ 2018년)
  • +
+
+
경력
+ +
+
학력
+ +
+
군 복무
+
    +
  • + 대전시립박물관{" "} + 사회복무요원 (2015년 3월 9일 ~ 2017년 3월 8일) +
    + 대전광역시 유성구 도안대로 398 +
  • +
  • + + {`"판, 세상을 담다"`} + {" "} + 골패점 개발자 (2015년 4월 30일 ~ 2015년 8월 30일) +
    + 대전광역시 유성구 도안대로 398 +
  • +
+
+
자격증
+ +
+
공모전
+ +
+ + ); +} diff --git "a/taehui-fe/src/app/\133language\135/query/useGetHit.ts" "b/taehui-fe/src/app/\133language\135/query/useGetHit.ts" new file mode 100644 index 0000000..8b93a6a --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/query/useGetHit.ts" @@ -0,0 +1,14 @@ +import { useQuery } from "@tanstack/react-query"; + +import { wwwAPI } from "@/utilities/wwwAPI"; + +export default function useGetHit() { + return useQuery({ + queryKey: ["hit"], + queryFn: async () => { + const { data } = await wwwAPI.get("/hit"); + return data; + }, + initialData: [], + }); +} diff --git "a/taehui-fe/src/app/\133language\135/query/useGetLatestAvatar.ts" "b/taehui-fe/src/app/\133language\135/query/useGetLatestAvatar.ts" new file mode 100644 index 0000000..2653082 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/query/useGetLatestAvatar.ts" @@ -0,0 +1,15 @@ +import { useQuery } from "@tanstack/react-query"; + +import { wwwAPI } from "@/utilities/wwwAPI"; +import { GetLatestAvatarAPI } from "@/type/wwwAPI"; + +export default function useGetLatestAvatar() { + return useQuery({ + queryKey: ["latestAvatar"], + queryFn: async () => { + const { data } = await wwwAPI.get("/avatar/latest"); + return data; + }, + initialData: [], + }); +} diff --git "a/taehui-fe/src/app/\133language\135/query/useGetLatestComment.ts" "b/taehui-fe/src/app/\133language\135/query/useGetLatestComment.ts" new file mode 100644 index 0000000..5053411 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/query/useGetLatestComment.ts" @@ -0,0 +1,15 @@ +import { useQuery } from "@tanstack/react-query"; + +import { wwwAPI } from "@/utilities/wwwAPI"; +import { GetLatestCommentAPI } from "@/type/wwwAPI"; + +export default function useGetLatestComment() { + return useQuery({ + queryKey: ["latestComment"], + queryFn: async () => { + const { data } = await wwwAPI.get("/comment/latest"); + return data; + }, + initialData: [], + }); +} diff --git "a/taehui-fe/src/app/\133language\135/query/useGetLatestEssay.ts" "b/taehui-fe/src/app/\133language\135/query/useGetLatestEssay.ts" new file mode 100644 index 0000000..8afa48a --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/query/useGetLatestEssay.ts" @@ -0,0 +1,19 @@ +import { useQuery } from "@tanstack/react-query"; +import { getLanguage } from "taehui-ts/language"; + +import { wwwAPI } from "@/utilities/wwwAPI"; +import { GetLatestEssayAPI } from "@/type/wwwAPI"; + +export default function useGetLatestEssay() { + const language = getLanguage(); + return useQuery({ + queryKey: ["latestEssay"], + queryFn: async () => { + const { data } = await wwwAPI.get("/essay/latest", { + params: { language }, + }); + return data; + }, + initialData: [], + }); +} diff --git "a/taehui-fe/src/app/\133language\135/query/usePostHit.ts" "b/taehui-fe/src/app/\133language\135/query/usePostHit.ts" new file mode 100644 index 0000000..867b205 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/query/usePostHit.ts" @@ -0,0 +1,22 @@ +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import { getMillis } from "taehui-ts/date"; + +import { wwwAPI } from "@/utilities/wwwAPI"; + +export default function usePostHit() { + const queryClient = useQueryClient(); + + return useMutation({ + mutationFn: async () => { + const { data } = await wwwAPI.post("/hit", null, { + headers: { + millis: getMillis(), + }, + }); + return data; + }, + onSuccess: async () => { + await queryClient.invalidateQueries({ queryKey: ["hit"] }); + }, + }); +} diff --git "a/taehui-fe/src/app/\133language\135/query/useSession.ts" "b/taehui-fe/src/app/\133language\135/query/useSession.ts" new file mode 100644 index 0000000..54dc9c5 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/query/useSession.ts" @@ -0,0 +1,30 @@ +import useAutoLogIn from "@/avatar/useAutoLogIn"; + +import { useAvatarStore } from "@/store/Stores"; +import { useEffect, useState } from "react"; + +const useSession = () => { + const { loadTotem, totem } = useAvatarStore(); + const [isLoading, setLoading] = useState(true); + + const autoLogIn = useAutoLogIn(); + + useEffect(() => { + (async () => { + await loadTotem(); + setLoading(false); + })(); + }, [loadTotem]); + + useEffect(() => { + (async () => { + if (!isLoading && !totem) { + await autoLogIn(); + } + })(); + }, [autoLogIn, isLoading, totem]); + + return isLoading; +}; + +export default useSession; diff --git "a/taehui-fe/src/app/\133language\135/want/\133wantVariety\135/\133\133...want\135\135/page.tsx" "b/taehui-fe/src/app/\133language\135/want/\133wantVariety\135/\133\133...want\135\135/page.tsx" new file mode 100644 index 0000000..8712355 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/want/\133wantVariety\135/\133\133...want\135\135/page.tsx" @@ -0,0 +1,88 @@ +"use client"; + +import CommentTitleView from "@/app/[language]/forum/components/CommentTitleView"; +import EssayTitleView from "@/app/[language]/forum/components/EssayTitleView"; +import WantInput from "@/app/[language]/want/components/WantInput"; +import Loading from "@/app/[language]/want/loading"; +import useGetWant from "@/app/[language]/want/query/useGetWant"; +import { useWantStore } from "@/store/Stores"; +import { GetWantAPIComment, GetWantAPIEssay } from "@/type/wwwAPI"; +import { useTranslations } from "next-intl"; +import { useParams } from "next/navigation"; +import { useEffect } from "react"; +import InfiniteScroll from "react-infinite-scroll-component"; +import { Col, ListGroup, ListGroupItemHeading, Row } from "reactstrap"; +import { useWant } from "taehui-ts/fe-utilities"; + +const Page = () => { + const t = useTranslations(); + + const { setTextInput } = useWantStore(); + + const { wantVariety } = useParams<{ + wantVariety: "essay" | "comment"; + }>(); + const { want } = useWant("/want"); + + const { + fetchNextPage, + hasNextPage, + data: { pages }, + isFetched: isWantLoaded, + } = useGetWant(wantVariety, want); + + useEffect(() => { + setTextInput(want); + }, [setTextInput, want]); + + return ( + <> + +
+ {isWantLoaded ? ( + + + + {t("wantView")} + fetchNextPage()} + hasMore={hasNextPage} + loader={null} + > + {wantVariety === "essay" && + (pages as GetWantAPIEssay[]).flatMap((wantedEssayTitle) => { + return ( + + ); + })} + {wantVariety === "comment" && + (pages as GetWantAPIComment[]).flatMap( + (wantedCommentTitle) => { + return ( + + ); + }, + )} + + + + + ) : ( + + )} + + ); +}; + +export default Page; diff --git "a/taehui-fe/src/app/\133language\135/want/components/WantInput.tsx" "b/taehui-fe/src/app/\133language\135/want/components/WantInput.tsx" new file mode 100644 index 0000000..edf16ab --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/want/components/WantInput.tsx" @@ -0,0 +1,83 @@ +import { useWantStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; +import { ChangeEventHandler, KeyboardEventHandler, useState } from "react"; +import { + Button, + Col, + Dropdown, + DropdownItem, + DropdownMenu, + DropdownToggle, + Input, + Row, +} from "reactstrap"; +import { useTo } from "taehui-ts/fe-utilities"; + +export default observer(() => { + const { textInput, setTextInput, wantVariety, setWantVariety } = + useWantStore(); + + const [isWantVarietyOpened, setWantVarietyOpened] = useState(false); + + const t = useTranslations(); + + const to = useTo(); + + const onWant = () => { + if (textInput) { + to(`/want/${wantVariety}/${encodeURIComponent(textInput)}`); + } + }; + + const onWantInput: ChangeEventHandler = ({ + target: { value }, + }) => { + setTextInput(value); + }; + + const onInputLower: KeyboardEventHandler = ({ key }) => { + if (key === "Enter") { + onWant(); + } + }; + + const onCloseWantVariety = () => { + setWantVarietyOpened(!isWantVarietyOpened); + }; + + const onInputWantVariety = (wantVariety: "essay" | "comment") => () => { + setWantVariety(wantVariety); + }; + + return ( + + + + {t(wantVariety)} + + + {t("essay")} + + + {t("comment")} + + + + + + + + + + + + ); +}); diff --git "a/taehui-fe/src/app/\133language\135/want/loading.tsx" "b/taehui-fe/src/app/\133language\135/want/loading.tsx" new file mode 100644 index 0000000..32a6627 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/want/loading.tsx" @@ -0,0 +1,10 @@ +import LoadingLayer from "@/components/LoadingLayer"; +import { List } from "react-content-loader"; + +export default function Loading() { + return ( + + + + ); +} diff --git "a/taehui-fe/src/app/\133language\135/want/query/useGetWant.ts" "b/taehui-fe/src/app/\133language\135/want/query/useGetWant.ts" new file mode 100644 index 0000000..8cdc33f --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/want/query/useGetWant.ts" @@ -0,0 +1,31 @@ +import { wwwAPI } from "@/utilities/wwwAPI"; +import { GetWantAPIComment, GetWantAPIEssay } from "@/type/wwwAPI"; +import { useInfiniteQuery } from "@tanstack/react-query"; + +export default function useGetWant( + wantVariety: "essay" | "comment", + want?: string, +) { + return useInfiniteQuery({ + enabled: !!want, + queryKey: ["want", wantVariety, want], + queryFn: async ({ pageParam }) => { + const { data } = await wwwAPI.get< + (GetWantAPIEssay | GetWantAPIComment)[] + >(`/want/${wantVariety}/${want}/${pageParam}`); + return data; + }, + initialPageParam: 1, + initialData: { + pages: [], + pageParams: [1], + }, + getNextPageParam: (lastPage, allPages, lastPageParam) => { + return !lastPage || lastPage.length > 0 ? lastPageParam + 1 : undefined; + }, + select: (data) => ({ + pages: data.pages.flatMap((page) => page), + pageParams: data.pageParams, + }), + }); +} diff --git "a/taehui-fe/src/app/\133language\135/want/store/setWantStore.ts" "b/taehui-fe/src/app/\133language\135/want/store/setWantStore.ts" new file mode 100644 index 0000000..6e5c3d4 --- /dev/null +++ "b/taehui-fe/src/app/\133language\135/want/store/setWantStore.ts" @@ -0,0 +1,14 @@ +export default function setWantStore() { + return { + textInput: "", + wantVariety: "essay", + + setTextInput(textInput: string) { + this.textInput = textInput; + }, + + setWantVariety(wantVariety: string) { + this.wantVariety = wantVariety; + }, + }; +} diff --git a/taehui-fe/src/app/favicon.ico b/taehui-fe/src/app/favicon.ico new file mode 100644 index 0000000..e4e0dc5 --- /dev/null +++ b/taehui-fe/src/app/favicon.ico Binary files differ diff --git a/taehui-fe/src/app/globals.scss b/taehui-fe/src/app/globals.scss new file mode 100644 index 0000000..44e25fc --- /dev/null +++ b/taehui-fe/src/app/globals.scss @@ -0,0 +1,79 @@ +* { + margin: 0; + font-family: "Century Gothic", + -apple-system, + BlinkMacSystemFont, + "Segoe UI", + "Roboto", + "Oxygen", + "Ubuntu", + "Cantarell", + "Fira Sans", + "Droid Sans", + "Helvetica Neue", + sans-serif; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; + + &.route { + cursor: pointer; + } +} + +@mixin default() { + font-size: 0.75rem; +} + +body { + background: url("../assets/hexellence.png"); +} + +button { + &.btn { + @include default(); + } +} + +input[type="search"], +input[type="submit"], +input[type="text"], +input[type="email"], +input[type="password"] { + @include default(); +} + +button { + &.page-link { + @include default(); + } + + &.dropdown-item { + @include default(); + } +} + +textarea { + &.form-control { + @include default(); + } +} + +img { + &.avatar { + border: thin black solid; + border-radius: 50%; + } +} + +span { + @include default(); + + &.badge { + @include default(); + font-weight: normal; + } + + &.ln { + white-space: break-spaces; + } +} diff --git a/taehui-fe/src/assets/language/en.json b/taehui-fe/src/assets/language/en.json new file mode 100644 index 0000000..e816da3 --- /dev/null +++ b/taehui-fe/src/assets/language/en.json @@ -0,0 +1,72 @@ +{ + "alreadyAvatarID": "This ID is already registered.", + "assistForum": "Manual", + "autoEssay": "Auto Save", + "autoEssays": "Auto Save List", + "autoLogIn": "Automatic login", + "avatarCipher": "Password", + "avatarCipherModified": "Password to be modified", + "avatarCipherTest": "Confirm password", + "avatarID": "ID", + "avatarIntro": "Introduce yourself", + "avatarName": "Nickname", + "comment": "Comment", + "commentary": "Guestbook", + "commentCount": "{commentCount} comments", + "dateForum": "Update History", + "doModifiedAvatar": "Please log in again because your password has been modified", + "doModifyAvatar": "Edit information", + "doModifyComment": "Edit comment", + "doModifyCommentary": "Edit guestbook", + "doModifyEssay": "Edit post", + "essay": "Bulletin", + "essayBefore": "Previous post", + "essayLater": "Next post", + "failedValidateCipher": "Invalid password.", + "failedValidation": "The input is not valid.", + "fax": "E-mail", + "fileUpload": "Upload File", + "fileUploading": "Uploading.", + "forums": "All Bulletins", + "hit00": "Visitor statistics", + "hit01": "{hitBefore} visitors yesterday", + "hit02": "{hit} visitors today", + "hit03": "Visits count from 2022-11-07.", + "hitCount": "{hitCount} views", + "hitFileCount": "Download {hit} times", + "latestAvatarsView0": "Registered member", + "latestAvatarsView1": "Member visited", + "latestCommentsView": "Comment written", + "latestEssaysView": "Posts Created", + "notLoggedIn": "Sign out", + "notLoggedInText": "Thank you, {avatarName}.", + "onWant": "Search", + "postComment": "Write comment", + "postCommentary": "Write guestbook", + "postedAutoEssay": "Your post will be saved automatically.", + "postEssay": "Write post", + "quit": "Exit", + "qwilightForum": "Qwilight Bulletin", + "setAutoEssayQuestion": "Do you want to load auto-saved posts? The text you are writing will disappear.", + "loggedInText": "Welcome, {avatarName}.", + "logIn": "Login", + "signUp": "Join membership", + "softwareForum": "Software", + "ppt": "Developer Profile", + "main": "Home", + "main00": "Hello", + "main01": "This is 불로그 run by Taehui.", + "main02": "I am in charge of providing and operating the software I made.", + "main03": "This site is still under development.", + "text": "Main text", + "textTag": "Letter", + "title": "Title", + "viewEditedEssay": "Preview", + "wantView": "Search Results", + "wipeComment": "Delete Comment", + "wipeCommentary": "Delete guestbook", + "wipeCommentQuestion": "Are you sure you want to delete the comment?", + "wipeEssay": "Delete post", + "wipeEssayQuestion": "Are you sure you want to delete the post?", + "wrongAvatar": "This account is not valid." +} diff --git a/taehui-fe/src/assets/language/ko.json b/taehui-fe/src/assets/language/ko.json new file mode 100644 index 0000000..6fed780 --- /dev/null +++ b/taehui-fe/src/assets/language/ko.json @@ -0,0 +1,72 @@ +{ + "alreadyAvatarID": "이미 가입된 아이디입니다.", + "assistForum": "매뉴얼", + "autoEssay": "자동 저장", + "autoEssays": "자동 저장 목록", + "autoLogIn": "자동 로그인", + "avatarCipher": "비밀번호", + "avatarCipherModified": "수정할 비밀번호", + "avatarCipherTest": "비밀번호 확인", + "avatarID": "아이디", + "avatarIntro": "자기소개", + "avatarName": "닉네임", + "comment": "덧글", + "commentary": "방명록", + "commentCount": "덧글 {commentCount} 개", + "dateForum": "업데이트 내역", + "doModifiedAvatar": "비밀번호가 수정되어 다시 로그인하세요", + "doModifyAvatar": "정보 수정", + "doModifyComment": "덧글 수정", + "doModifyCommentary": "방명록 수정", + "doModifyEssay": "게시글 수정", + "essay": "게시글", + "essayBefore": "이전 게시글", + "essayLater": "다음 게시글", + "failedValidateCipher": "올바르지 않은 비밀번호입니다.", + "failedValidation": "입력이 올바르지 않습니다.", + "fax": "이메일", + "fileUpload": "파일 업로드", + "fileUploading": "업로드하는 중입니다.", + "forums": "모든 게시판", + "hit00": "방문자 통계", + "hit01": "어제 방문자 {hitBefore} 명", + "hit02": "오늘 방문자 {hit} 명", + "hit03": "방문자 수는 2022-11-07 부터 집계됩니다.", + "hitCount": "조회수 {hitCount} 회", + "hitFileCount": "{hit} 회 다운로드", + "latestAvatarsView0": "가입한 회원", + "latestAvatarsView1": "방문한 회원", + "latestCommentsView": "작성된 덧글", + "latestEssaysView": "작성된 게시글", + "notLoggedIn": "로그아웃", + "notLoggedInText": "{avatarName}님 감사합니다.", + "onWant": "검색", + "postComment": "덧글 쓰기", + "postCommentary": "방명록 쓰기", + "postedAutoEssay": "게시글이 자동으로 저장됩니다.", + "postEssay": "게시글 쓰기", + "quit": "나가기", + "qwilightForum": "Qwilight 게시판", + "setAutoEssayQuestion": "자동 저장된 게시글을 불러올까요? 작성중인 글은 사라집니다.", + "loggedInText": "{avatarName}님 환영합니다.", + "logIn": "로그인", + "signUp": "회원 가입", + "softwareForum": "소프트웨어", + "ppt": "개발자 프로필", + "main": "홈으로", + "main00": "안녕하세요", + "main01": "Taehui가 운영하는 불로그입니다.", + "main02": "제가 만든 소프트웨어의 제공과 운영을 담당합니다.", + "main03": "이 사이트는 아직 개발 중입니다.", + "text": "본문", + "textTag": "글자", + "title": "제목", + "viewEditedEssay": "미리 보기", + "wantView": "검색 결과", + "wipeComment": "덧글 삭제", + "wipeCommentary": "방명록 삭제", + "wipeCommentQuestion": "덧글을 삭제할까요?", + "wipeEssay": "게시글 삭제", + "wipeEssayQuestion": "게시글을 삭제할까요?", + "wrongAvatar": "올바르지 않은 계정입니다." +} diff --git a/taehui-fe/src/avatar/AvatarView.tsx b/taehui-fe/src/avatar/AvatarView.tsx index 5dd77bd..93b3e28 100644 --- a/taehui-fe/src/avatar/AvatarView.tsx +++ b/taehui-fe/src/avatar/AvatarView.tsx @@ -1,34 +1,34 @@ +import usePostGetTotem from "@/avatar/usePostGetTotem"; +import useWipeTotem from "@/avatar/useWipeTotem"; +import AvatarTitle from "@/components/AvatarTitle"; +import { AvatarViewLoading } from "@/components/Loading"; + +import { useAvatarStore } from "@/store/Stores"; +import CryptoJS from "crypto-js"; import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; +import Link from "next/link"; import { useState } from "react"; import { Button, Col, Input, Row } from "reactstrap"; -import { Link } from "react-router-dom"; -import { useTranslation } from "react-i18next"; -import CryptoJS from "crypto-js"; -import { useTo } from "taehui-ts/fe-utility"; - -import { useAvatarStore } from "src/Stores"; -import AvatarTitle from "src/AvatarTitle"; -import { AvatarViewLoading } from "src/Loading"; -import usePostGetTotem from "src/avatar/usePostGetTotem"; -import useWipeTotem from "src/avatar/useWipeTotem"; +import { useTo } from "taehui-ts/fe-utilities"; export default observer( ({ isSessionLoading }: { isSessionLoading: boolean }) => { - const { t } = useTranslation(); + const t = useTranslations(); const { totem, taehuiAvatarID, taehuiAvatarName } = useAvatarStore(); const [avatarID, setAvatarID] = useState(""); const [avatarCipher, setAvatarCipher] = useState(""); - const [autoSignIn, setAutoSignIn] = useState(false); + const [autoLogIn, setAutoLogIn] = useState(false); const to = useTo(); const { mutateAsync: postGetTotem } = usePostGetTotem(); - const onSignIn = async () => { + const onLogIn = async () => { await postGetTotem({ avatarID, avatarCipher }); - if (autoSignIn) { + if (autoLogIn) { window.localStorage.setItem("avatarID", avatarID); window.localStorage.setItem( "avatarCipher", @@ -38,7 +38,7 @@ ).toString(), ); } - window.localStorage.setItem("autoSignIn", autoSignIn.toString()); + window.localStorage.setItem("autoLogIn", autoLogIn.toString()); }; const { mutateAsync: wipeTotem } = useWipeTotem(); @@ -59,12 +59,12 @@ await wipeTotem({ totem }); window.localStorage.removeItem("avatarID"); window.localStorage.removeItem("avatarCipher"); - window.localStorage.removeItem("autoSignIn"); + window.localStorage.removeItem("autoLogIn"); setAvatarCipher(""); - setAutoSignIn(false); + setAutoLogIn(false); }} > - {t("notSignedIn")} + {t("notLoggedIn")} @@ -106,28 +106,28 @@ }} onKeyDown={async ({ key }) => { if (key === "Enter") { - await onSignIn(); + await onLogIn(); } }} /> - - + diff --git a/taehui-fe/src/avatar/ModifyAvatarView.tsx b/taehui-fe/src/avatar/ModifyAvatarView.tsx index b373c9d..0d6b282 100644 --- a/taehui-fe/src/avatar/ModifyAvatarView.tsx +++ b/taehui-fe/src/avatar/ModifyAvatarView.tsx @@ -1,21 +1,21 @@ +import usePostDrawing from "@/avatar/usePostDrawing"; +import usePutAvatar from "@/avatar/usePutAvatar"; +import withTotem from "@/hoc/withTotem"; +import { useAvatarStore } from "@/store/Stores"; import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; +import Image from "next/image"; import { useMemo, useState } from "react"; -import { useTranslation } from "react-i18next"; import ReactTextareaAutosize from "react-textarea-autosize"; import { toast } from "react-toastify"; import { Button, Col, Input, Row } from "reactstrap"; -import { useTo } from "taehui-ts/fe-utility"; - -import { useAvatarStore } from "src/Stores"; -import usePutAvatar from "src/avatar/usePutAvatar"; -import usePostDrawing from "src/avatar/usePostDrawing"; -import withTotem from "src/withTotem"; +import { useTo } from "taehui-ts/fe-utilities"; export default withTotem( observer(() => { const { taehuiAvatarID, taehuiAvatarName, taehuiFax, taehuiAvatarIntro } = useAvatarStore(); - const { t } = useTranslation(); + const t = useTranslations(); const [avatarCipher, setAvatarCipher] = useState(""); const [avatarCipherModified, setAvatarCipherModified] = useState(""); @@ -33,9 +33,11 @@ return ( - { const inputElement = document.createElement("input"); diff --git a/taehui-fe/src/avatar/SignUpView.tsx b/taehui-fe/src/avatar/SignUpView.tsx index 2bc9f16..4358905 100644 --- a/taehui-fe/src/avatar/SignUpView.tsx +++ b/taehui-fe/src/avatar/SignUpView.tsx @@ -1,16 +1,15 @@ +import usePostAvatar from "@/avatar/usePostAvatar"; +import { useAvatarStore } from "@/store/Stores"; import { observer } from "mobx-react-lite"; +import { useTranslations } from "next-intl"; import { useLayoutEffect, useMemo, useState } from "react"; -import { useTranslation } from "react-i18next"; -import { Button, Col, Input, Row } from "reactstrap"; -import { useTo } from "taehui-ts/fe-utility"; import { toast } from "react-toastify"; - -import { useAvatarStore } from "src/Stores"; -import usePostAvatar from "src/avatar/usePostAvatar"; +import { Button, Col, Input, Row } from "reactstrap"; +import { useTo } from "taehui-ts/fe-utilities"; export default observer(() => { const { totem } = useAvatarStore(); - const { t } = useTranslation(); + const t = useTranslations(); const [avatarID, setAvatarID] = useState(""); const [avatarCipher, setAvatarCipher] = useState(""); diff --git a/taehui-fe/src/avatar/setAvatarStore.ts b/taehui-fe/src/avatar/setAvatarStore.ts index a18264c..84daf5f 100644 --- a/taehui-fe/src/avatar/setAvatarStore.ts +++ b/taehui-fe/src/avatar/setAvatarStore.ts @@ -1,7 +1,6 @@ +import { wwwAPI } from "@/utilities/wwwAPI"; import { getMillis } from "taehui-ts/date"; -import { wwwAXIOS } from "src/Www"; - export default function setAvatarStore() { return { totem: "", @@ -53,7 +52,7 @@ async loadTotem() { const totem = window.sessionStorage.getItem("totem"); if (totem) { - const { status, data } = await wwwAXIOS.patch("/avatar/totem", null, { + const { status, data } = await wwwAPI.patch("/avatar/totem", null, { headers: { millis: getMillis(), totem }, }); if (status === 201) { diff --git a/taehui-fe/src/avatar/useAutoLogIn.ts b/taehui-fe/src/avatar/useAutoLogIn.ts new file mode 100644 index 0000000..ae715cd --- /dev/null +++ b/taehui-fe/src/avatar/useAutoLogIn.ts @@ -0,0 +1,19 @@ +import usePostGetTotem from "@/avatar/usePostGetTotem"; +import CryptoJS from "crypto-js"; +import { useCallback } from "react"; + +export default function useAutoLogIn() { + const { mutateAsync: postGetTotem } = usePostGetTotem(); + + return useCallback(async () => { + if (window.localStorage.getItem("autoLogIn") === "true") { + await postGetTotem({ + avatarID: window.localStorage.getItem("avatarID") ?? "", + avatarCipher: CryptoJS.AES.decrypt( + window.localStorage.getItem("avatarCipher") ?? "", + "591A6F91-2A27-4A88-88FA-0FEB7CB5FD94", + ).toString(CryptoJS.enc.Utf8), + }); + } + }, [postGetTotem]); +} diff --git a/taehui-fe/src/avatar/useAutoSignIn.ts b/taehui-fe/src/avatar/useAutoSignIn.ts deleted file mode 100644 index 65a3496..0000000 --- a/taehui-fe/src/avatar/useAutoSignIn.ts +++ /dev/null @@ -1,20 +0,0 @@ -import CryptoJS from "crypto-js"; - -import usePostGetTotem from "src/avatar/usePostGetTotem"; -import { useCallback } from "react"; - -export default function useAutoSignIn() { - const { mutateAsync: postGetTotem } = usePostGetTotem(); - - return useCallback(async () => { - if (window.localStorage.getItem("autoSignIn") === "true") { - await postGetTotem({ - avatarID: window.localStorage.getItem("avatarID") ?? "", - avatarCipher: CryptoJS.AES.decrypt( - window.localStorage.getItem("avatarCipher") ?? "", - "591A6F91-2A27-4A88-88FA-0FEB7CB5FD94", - ).toString(CryptoJS.enc.Utf8), - }); - } - }, [postGetTotem]); -} diff --git a/taehui-fe/src/avatar/usePostAvatar.ts b/taehui-fe/src/avatar/usePostAvatar.ts index bd74a9b..69d1700 100644 --- a/taehui-fe/src/avatar/usePostAvatar.ts +++ b/taehui-fe/src/avatar/usePostAvatar.ts @@ -1,13 +1,12 @@ +import usePostGetTotem from "@/avatar/usePostGetTotem"; +import { isClientFault, wwwAPI } from "@/utilities/wwwAPI"; import { useMutation } from "@tanstack/react-query"; -import { useTranslation } from "react-i18next"; +import { useTranslations } from "next-intl"; import { toast } from "react-toastify"; import { getMillis } from "taehui-ts/date"; -import { isClientFault, wwwAXIOS } from "src/Www"; -import usePostGetTotem from "src/avatar/usePostGetTotem"; - export default function usePostAvatar() { - const { t } = useTranslation(); + const t = useTranslations(); const { mutateAsync: postGetTotem } = usePostGetTotem(); @@ -23,7 +22,7 @@ avatarCipher: string; fax: string; }) => { - await wwwAXIOS.post( + await wwwAPI.post( "/avatar", { avatarID, diff --git a/taehui-fe/src/avatar/usePostDrawing.ts b/taehui-fe/src/avatar/usePostDrawing.ts index 67c12e3..7c0b245 100644 --- a/taehui-fe/src/avatar/usePostDrawing.ts +++ b/taehui-fe/src/avatar/usePostDrawing.ts @@ -1,9 +1,8 @@ +import { useAvatarStore } from "@/store/Stores"; +import { wwwAPI } from "@/utilities/wwwAPI"; import { useMutation } from "@tanstack/react-query"; import { getMillis } from "taehui-ts/date"; -import { wwwAXIOS } from "src/Www"; -import { useAvatarStore } from "src/Stores"; - export default function usePostDrawing() { const { totem } = useAvatarStore(); @@ -11,7 +10,7 @@ mutationFn: async ({ file }: { file: File }) => { const form = new FormData(); form.append("data", file); - await wwwAXIOS.post("/avatar/drawing", form, { + await wwwAPI.post("/avatar/drawing", form, { headers: { millis: getMillis(), totem }, }); }, diff --git a/taehui-fe/src/avatar/usePostGetTotem.ts b/taehui-fe/src/avatar/usePostGetTotem.ts index 27e5081..4fb079d 100644 --- a/taehui-fe/src/avatar/usePostGetTotem.ts +++ b/taehui-fe/src/avatar/usePostGetTotem.ts @@ -1,17 +1,14 @@ +import { useAvatarStore } from "@/store/Stores"; +import { isClientFault, wwwAPI } from "@/utilities/wwwAPI"; import { useMutation } from "@tanstack/react-query"; -import { useTranslation } from "react-i18next"; +import { useTranslations } from "next-intl"; import { toast } from "react-toastify"; import { getMillis } from "taehui-ts/date"; -import { isClientFault, wwwAXIOS } from "src/Www"; -import { useAvatarStore } from "src/Stores"; -import { sprintf } from "sprintf-js"; -import { isAxiosError } from "axios"; - export default function usePostGetTotem() { const { setSession, saveTotem } = useAvatarStore(); - const { t } = useTranslation(); + const t = useTranslations(); return useMutation({ mutationFn: async ({ @@ -21,7 +18,7 @@ avatarID: string; avatarCipher: string; }) => { - const { data } = await wwwAXIOS.post( + const { data } = await wwwAPI.post( "/avatar/getTotem", { avatarID, @@ -38,7 +35,7 @@ onSuccess: (data) => { setSession(data); saveTotem(); - toast.success(sprintf(t("signedInText"), data.avatarName)); + toast.success(t("loggedInText", { avatarName: data.avatarName })); }, onError: (e) => { if (isClientFault(e)) { diff --git a/taehui-fe/src/avatar/usePutAvatar.ts b/taehui-fe/src/avatar/usePutAvatar.ts index 1f31051..288ec40 100644 --- a/taehui-fe/src/avatar/usePutAvatar.ts +++ b/taehui-fe/src/avatar/usePutAvatar.ts @@ -1,16 +1,14 @@ +import { useAvatarStore } from "@/store/Stores"; +import { isClientFault, wwwAPI } from "@/utilities/wwwAPI"; import { useMutation } from "@tanstack/react-query"; -import { useTranslation } from "react-i18next"; -import Swal from "sweetalert2"; +import { useTranslations } from "next-intl"; import { toast } from "react-toastify"; +import Swal from "sweetalert2"; import { getMillis } from "taehui-ts/date"; -import { useTo } from "taehui-ts/fe-utility"; - -import { isClientFault, wwwAXIOS } from "src/Www"; -import { useAvatarStore } from "src/Stores"; -import { isAxiosError } from "axios"; +import { useTo } from "taehui-ts/fe-utilities"; export default function usePutAvatar() { - const { t } = useTranslation(); + const t = useTranslations(); const { totem, setSession, saveTotem } = useAvatarStore(); @@ -30,7 +28,7 @@ fax: string; avatarIntro: string; }) => { - const { data } = await wwwAXIOS.put( + const { data } = await wwwAPI.put( "/avatar", { avatarCipher, diff --git a/taehui-fe/src/avatar/useWipeTotem.ts b/taehui-fe/src/avatar/useWipeTotem.ts index 63a00d1..e6d2141 100644 --- a/taehui-fe/src/avatar/useWipeTotem.ts +++ b/taehui-fe/src/avatar/useWipeTotem.ts @@ -1,20 +1,18 @@ +import { useAvatarStore } from "@/store/Stores"; +import { wwwAPI } from "@/utilities/wwwAPI"; import { useMutation } from "@tanstack/react-query"; -import { useTranslation } from "react-i18next"; +import { useTranslations } from "next-intl"; import { toast } from "react-toastify"; import { getMillis } from "taehui-ts/date"; -import { sprintf } from "sprintf-js"; - -import { wwwAXIOS } from "src/Www"; -import { useAvatarStore } from "src/Stores"; export default function useWipeTotem() { const { taehuiAvatarName, setSession, saveTotem } = useAvatarStore(); - const { t } = useTranslation(); + const t = useTranslations(); return useMutation({ mutationFn: async ({ totem }: { totem: string }) => { - const { data } = await wwwAXIOS.delete("/avatar/totem", { + const { data } = await wwwAPI.delete("/avatar/totem", { headers: { millis: getMillis(), totem, @@ -23,7 +21,7 @@ return data; }, onSuccess: async () => { - toast.success(sprintf(t("notSignedInText"), taehuiAvatarName)); + toast.success(t("notLoggedInText", { avatarName: taehuiAvatarName })); setSession({ totem: "", avatarID: "", diff --git a/taehui-fe/src/commentary/CommentaryItem.tsx b/taehui-fe/src/commentary/CommentaryItem.tsx deleted file mode 100644 index c740448..0000000 --- a/taehui-fe/src/commentary/CommentaryItem.tsx +++ /dev/null @@ -1,107 +0,0 @@ -import { useState } from "react"; -import { useTranslation } from "react-i18next"; -import ReactTextareaAutosize from "react-textarea-autosize"; -import { toast } from "react-toastify"; -import { Button, Col, Collapse, Input, ListGroupItem, Row } from "reactstrap"; -import { getDatetime } from "taehui-ts/date"; - -import { GetCommentaryAPI } from "src/wwwAPI"; -import useWipeCommentary from "src/commentary/useWipeCommentary"; -import usePutCommentary from "src/commentary/usePutCommentary"; - -const CommentaryItem = ({ - commentary: { commentaryID, avatarName, text, date }, -}: { - commentary: GetCommentaryAPI[number]; -}) => { - const { t } = useTranslation(); - - const [isModifyOpened, setModifyOpened] = useState(false); - const [avatarCipher, setAvatarCipher] = useState(""); - const [textInput, setTextInput] = useState(""); - - const { mutateAsync: wipeCommentary } = useWipeCommentary(); - const { mutateAsync: putCommentary } = usePutCommentary(); - - return ( - - - - {avatarName} - - { - setModifyOpened(true); - }} - > - {isModifyOpened ? ( - { - setTextInput(value); - }} - /> - ) : ( - {text} - )} - - - {getDatetime(date)} - - - - - - { - setAvatarCipher(value); - }} - /> - - - - - - - - - - - ); -}; - -export default CommentaryItem; diff --git a/taehui-fe/src/commentary/CommentaryView.tsx b/taehui-fe/src/commentary/CommentaryView.tsx deleted file mode 100644 index 74adeba..0000000 --- a/taehui-fe/src/commentary/CommentaryView.tsx +++ /dev/null @@ -1,98 +0,0 @@ -import { useState } from "react"; -import { Button, Col, Input, ListGroup, Row } from "reactstrap"; -import { useTranslation } from "react-i18next"; -import { toast } from "react-toastify"; -import ReactTextareaAutosize from "react-textarea-autosize"; - -import CommentaryItem from "src/commentary/CommentaryItem"; -import { CommentaryViewLoading } from "src/Loading"; -import useGetCommentary from "src/commentary/useGetCommentary"; -import usePostCommentary from "src/commentary/usePostCommentary"; - -const CommentaryView = () => { - const { t } = useTranslation(); - - const [avatarName, setAvatarName] = useState(""); - const [avatarCipher, setAvatarCipher] = useState(""); - const [textInput, setTextInput] = useState(""); - - const { data: commentary, isFetched: isCommentaryLoaded } = - useGetCommentary(); - const { mutateAsync: postCommentary } = usePostCommentary(); - - return ( - <> - - - { - setAvatarName(value); - }} - /> - - - { - setAvatarCipher(value); - }} - /> - - - - - { - setTextInput(value); - }} - /> - - - - - - {isCommentaryLoaded ? ( - - - - {commentary.map((commentary) => ( - - ))} - - - - ) : ( - - )} - - ); -}; - -export default CommentaryView; diff --git a/taehui-fe/src/commentary/useGetCommentary.ts b/taehui-fe/src/commentary/useGetCommentary.ts deleted file mode 100644 index 651012c..0000000 --- a/taehui-fe/src/commentary/useGetCommentary.ts +++ /dev/null @@ -1,15 +0,0 @@ -import { useQuery } from "@tanstack/react-query"; - -import { wwwAXIOS } from "src/Www"; -import { GetCommentaryAPI } from "src/wwwAPI"; - -export default function useGetCommentary() { - return useQuery({ - queryKey: ["commentary"], - queryFn: async () => { - const { data } = await wwwAXIOS.get("/commentary"); - return data; - }, - initialData: [], - }); -} diff --git a/taehui-fe/src/commentary/usePostCommentary.ts b/taehui-fe/src/commentary/usePostCommentary.ts deleted file mode 100644 index 2137aa0..0000000 --- a/taehui-fe/src/commentary/usePostCommentary.ts +++ /dev/null @@ -1,28 +0,0 @@ -import { useMutation, useQueryClient } from "@tanstack/react-query"; - -import { wwwAXIOS } from "src/Www"; - -export default function usePostCommentary() { - const queryClient = useQueryClient(); - - return useMutation({ - mutationFn: async ({ - avatarName, - avatarCipher, - text, - }: { - avatarName: string; - avatarCipher: string; - text: string; - }) => { - await wwwAXIOS.post("/commentary", { - avatarName, - avatarCipher, - text, - }); - }, - onSuccess: async () => { - await queryClient.invalidateQueries({ queryKey: ["commentary"] }); - }, - }); -} diff --git a/taehui-fe/src/commentary/usePutCommentary.ts b/taehui-fe/src/commentary/usePutCommentary.ts deleted file mode 100644 index 40e9c7e..0000000 --- a/taehui-fe/src/commentary/usePutCommentary.ts +++ /dev/null @@ -1,37 +0,0 @@ -import { useMutation, useQueryClient } from "@tanstack/react-query"; - -import { isClientFault, wwwAXIOS } from "src/Www"; -import { toast } from "react-toastify"; -import { useTranslation } from "react-i18next"; - -export default function usePutCommentary() { - const queryClient = useQueryClient(); - - const { t } = useTranslation(); - - return useMutation({ - mutationFn: async ({ - commentaryID, - avatarCipher, - text, - }: { - commentaryID: number; - avatarCipher: string; - text: string; - }) => { - await wwwAXIOS.put("/commentary", { - commentaryID, - avatarCipher, - text, - }); - }, - onSuccess: async () => { - await queryClient.invalidateQueries({ queryKey: ["commentary"] }); - }, - onError: (e) => { - if (isClientFault(e)) { - toast.error(t("failedValidateCipher")); - } - }, - }); -} diff --git a/taehui-fe/src/commentary/useWipeCommentary.ts b/taehui-fe/src/commentary/useWipeCommentary.ts deleted file mode 100644 index df17250..0000000 --- a/taehui-fe/src/commentary/useWipeCommentary.ts +++ /dev/null @@ -1,37 +0,0 @@ -import { useMutation, useQueryClient } from "@tanstack/react-query"; -import { toast } from "react-toastify"; -import { useTranslation } from "react-i18next"; - -import { isClientFault, wwwAXIOS } from "src/Www"; -import { GetCommentaryAPI } from "src/wwwAPI"; - -export default function useWipeCommentary() { - const queryClient = useQueryClient(); - - const { t } = useTranslation(); - - return useMutation({ - mutationFn: async ({ - commentaryID, - avatarCipher, - }: { - commentaryID: number; - avatarCipher: string; - }) => { - await wwwAXIOS.delete("/commentary", { - params: { - commentaryID, - avatarCipher, - }, - }); - }, - onSuccess: async () => { - await queryClient.invalidateQueries({ queryKey: ["commentary"] }); - }, - onError: (e) => { - if (isClientFault(e)) { - toast.error(t("failedValidateCipher")); - } - }, - }); -} diff --git a/taehui-fe/src/components/AvatarTitle.tsx b/taehui-fe/src/components/AvatarTitle.tsx new file mode 100644 index 0000000..c9d6ccd --- /dev/null +++ b/taehui-fe/src/components/AvatarTitle.tsx @@ -0,0 +1,40 @@ +import Image from "next/image"; +import { ReactNode } from "react"; +import { Col } from "reactstrap"; + +const AvatarTitle = ({ + avatarID, + avatarName, + children, +}: { + avatarID: string; + avatarName: string; + children: ReactNode; +}) => { + return ( + <> + { + e.stopPropagation(); + }} + > + + + + {avatarName} +
+ {children} + + + ); +}; + +export default AvatarTitle; diff --git a/taehui-fe/src/components/Loading.tsx b/taehui-fe/src/components/Loading.tsx new file mode 100644 index 0000000..fe05ba0 --- /dev/null +++ b/taehui-fe/src/components/Loading.tsx @@ -0,0 +1,86 @@ +import AvatarTitle from "@/components/AvatarTitle"; +import { useTranslations } from "next-intl"; +import { Col, ListGroupItem, Row } from "reactstrap"; + +export const HitViewLoading = () => { + const t = useTranslations(); + + return ( + + Loading... +
+ Loading... +
+ {t("hit03")} +
+ ); +}; + +export const LatestEssaysViewLoading = ({ + loadingCount, +}: { + loadingCount: number; +}) => { + return [...Array(loadingCount).keys()].map((i) => ( + + + + Loading... + + + + )); +}; + +export const LatestCommentsViewLoading = ({ + loadingCount, +}: { + loadingCount: number; +}) => { + return [...Array(loadingCount).keys()].map((i) => ( + + + + Loading... + + + + )); +}; + +export const LatestAvatarViewLoading = ({ + loadingCounts, +}: { + loadingCounts: number[]; +}) => + [...Array(loadingCounts[0]).keys()].map((i) => ( + + {[...Array(loadingCounts[1]).keys()].map((i) => ( + + Loading... + + ))} + + )); + +export const AvatarViewLoading = () => { + return ( + + + Loading... + + + ); +}; + +export const AutoEssayViewLoading = () => { + return ( + + + + Loading... + + + + ); +}; diff --git a/taehui-fe/src/components/LoadingLayer.tsx b/taehui-fe/src/components/LoadingLayer.tsx new file mode 100644 index 0000000..6c7bf9f --- /dev/null +++ b/taehui-fe/src/components/LoadingLayer.tsx @@ -0,0 +1,10 @@ +import { ReactNode } from "react"; +import { Col, Row } from "reactstrap"; + +export default function LoadingLayer({ children }: { children: ReactNode }) { + return ( + + {children} + + ); +} diff --git a/taehui-fe/src/components/TaehuiView.tsx b/taehui-fe/src/components/TaehuiView.tsx new file mode 100644 index 0000000..d538c18 --- /dev/null +++ b/taehui-fe/src/components/TaehuiView.tsx @@ -0,0 +1,126 @@ +"use client"; + +import useSession from "@/app/[language]/query/useSession"; +import vcs from "@/assets/vcs.png"; +import AvatarView from "@/avatar/AvatarView"; +import withQueryClient from "@/hoc/withQueryClient"; +import { useTaehuiStore } from "@/store/Stores"; +import { useTranslations } from "next-intl"; +import Image from "next/image"; +import Link from "next/link"; +import { ReactNode, useEffect, useMemo, useRef } from "react"; +import { ToastContainer } from "react-toastify"; +import { Button, Col, Container, Navbar, NavbarBrand, Row } from "reactstrap"; +import { useIsPath } from "taehui-ts/fe-utilities"; + +export default withQueryClient(function TaehuiView({ + children, +}: { + children: ReactNode; +}) { + const t = useTranslations(); + + const { setTitleViewHeight, setAvatarViewHeight } = useTaehuiStore(); + + const titleView = useRef(null); + const avatarView = useRef(null); + + const isSessionLoading = useSession(); + + const isPath = useIsPath(); + + const isAvatarViewVisible = useMemo( + () => !isPath("/avatar") && !isPath("/commentary"), + [isPath], + ); + + useEffect(() => { + setTitleViewHeight(titleView.current?.clientHeight ?? 0); + setAvatarViewHeight(avatarView.current?.clientHeight ?? 0); + }, [setAvatarViewHeight, setTitleViewHeight]); + + const getColor = (route: string, equals = false) => + isPath(route, equals) ? "primary" : "secondary"; + + return ( + <> +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+ + {children} + {isAvatarViewVisible && ( +
+
+ +
+ )} +
+ + + + ); +}); diff --git a/taehui-fe/src/forum/AutoEssayTitleView.tsx b/taehui-fe/src/forum/AutoEssayTitleView.tsx deleted file mode 100644 index 7c7fb79..0000000 --- a/taehui-fe/src/forum/AutoEssayTitleView.tsx +++ /dev/null @@ -1,54 +0,0 @@ -import { observer } from "mobx-react-lite"; -import { useTranslation } from "react-i18next"; -import { Col, ListGroupItem, Row } from "reactstrap"; -import Swal from "sweetalert2"; -import { getDatetime } from "taehui-ts/date"; - -import { useForumStore } from "src/Stores"; -import { GetAutoEssayAPI } from "src/wwwAPI"; -import useWipeAutoEssay from "src/forum/useWipeAutoEssay"; - -const AutoEssayTitleView = observer<{ autoEssay: GetAutoEssayAPI[0] }>( - ({ autoEssay: { autoEssayID, title, text, date } }) => { - const { mutateAsync: wipeAutoEssay } = useWipeAutoEssay(); - - const { setTitle, setText, setAutoEssayID } = useForumStore(); - const { t } = useTranslation(); - - return ( - { - const { isConfirmed, isDenied } = await Swal.fire({ - title: t("autoEssay"), - text: t("setAutoEssayQuestion"), - icon: "question", - showDenyButton: true, - denyButtonText: t("wipeEssay"), - }); - - if (isConfirmed) { - setTitle(title); - setText(text); - setAutoEssayID(autoEssayID); - } - - if (isDenied) { - await wipeAutoEssay({ autoEssayID }); - } - }} - > - - - {title} - - - {getDatetime(date)} - - - - ); - }, -); - -export default AutoEssayTitleView; diff --git a/taehui-fe/src/forum/CommentItem.tsx b/taehui-fe/src/forum/CommentItem.tsx deleted file mode 100644 index c2e9316..0000000 --- a/taehui-fe/src/forum/CommentItem.tsx +++ /dev/null @@ -1,165 +0,0 @@ -import { useMemo, useState } from "react"; -import { observer } from "mobx-react-lite"; -import { useParams } from "react-router-dom"; -import ReactTextareaAutosize from "react-textarea-autosize"; -import Swal from "sweetalert2"; -import { Button, Col, Collapse, Row } from "reactstrap"; -import { useTranslation } from "react-i18next"; -import { getDatetime } from "taehui-ts/date"; -import { toast } from "react-toastify"; - -import { useAvatarStore } from "src/Stores"; -import AvatarTitle from "src/AvatarTitle"; -import useWipeComment from "src/forum/useWipeComment"; -import usePutComment from "src/forum/usePutComment"; -import usePostComment from "src/forum/usePostComment"; - -export default observer( - ({ - commentID, - text, - avatarID, - avatarName, - date, - level, - }: { - commentID: number; - text: string; - date: string; - avatarID: string; - avatarName: string; - level: number; - }) => { - const { t } = useTranslation(); - const { totem, taehuiAvatarID, taehuiAvatarName, isSU } = useAvatarStore(); - - type CommentItemParams = { essayID: string }; - const { essayID } = useParams() as CommentItemParams; - - const [textInput, setTextInput] = useState(""); - const [targetTextInput, setTargetTextInput] = useState(""); - const [isTargetOpened, setTargetOpened] = useState(false); - - const isAllowModify = useMemo( - () => isSU || taehuiAvatarID === avatarID, - [isSU, avatarID, taehuiAvatarID], - ); - - const { mutateAsync: wipeComment } = useWipeComment(); - const { mutateAsync: putComment } = usePutComment(); - const { mutateAsync: postComment } = usePostComment(); - - return ( -
- - -
{ - if (totem && !isTargetOpened) { - setTargetOpened(true); - } - }} - > - {isTargetOpened && isAllowModify ? ( - - - { - setTextInput(value); - }} - /> - - - - - - - - - ) : ( - {text} - )} -
-
- - {getDatetime(date)} - -
- - - - - - { - setTargetTextInput(value); - }} - /> - - - - - - - - -
- ); - }, -); diff --git a/taehui-fe/src/forum/CommentTitleView.tsx b/taehui-fe/src/forum/CommentTitleView.tsx deleted file mode 100644 index 0dccc65..0000000 --- a/taehui-fe/src/forum/CommentTitleView.tsx +++ /dev/null @@ -1,39 +0,0 @@ -import { Col, ListGroupItem, Row } from "reactstrap"; -import { useTo } from "taehui-ts/fe-utility"; -import { getDatetime } from "taehui-ts/date"; - -import AvatarTitle from "src/AvatarTitle"; -import { GetLatestCommentAPI } from "src/wwwAPI"; - -const CommentTitleView = ({ - forumID, - essayID, - comment: { avatarID, avatarName, date, text }, -}: { - forumID: string; - essayID: number; - comment: GetLatestCommentAPI[number]; -}) => { - const to = useTo(); - - return ( - { - to(`/forum/${forumID}/${essayID}`); - }} - > - - - {text} - - - {getDatetime(date)} - - - - ); -}; - -export default CommentTitleView; diff --git a/taehui-fe/src/forum/CommentView.tsx b/taehui-fe/src/forum/CommentView.tsx deleted file mode 100644 index 5537372..0000000 --- a/taehui-fe/src/forum/CommentView.tsx +++ /dev/null @@ -1,109 +0,0 @@ -import { ReactNode, useMemo, useState } from "react"; -import { observer } from "mobx-react-lite"; -import { useParams } from "react-router-dom"; -import { toast } from "react-toastify"; -import { Badge, Button, Col, Row } from "reactstrap"; -import { useTranslation } from "react-i18next"; -import ReactTextareaAutosize from "react-textarea-autosize"; -import { sprintf } from "sprintf-js"; - -import { useAvatarStore } from "src/Stores"; -import CommentItem from "src/forum/CommentItem"; -import AvatarTitle from "src/AvatarTitle"; -import { GetCommentAPI } from "src/wwwAPI"; -import useGetComment from "src/forum/useGetComment"; -import usePostComment from "src/forum/usePostComment"; - -export default observer(() => { - const { t } = useTranslation(); - const { taehuiAvatarID, taehuiAvatarName, taehuiLevel } = useAvatarStore(); - const [textInput, setTextInput] = useState(""); - - type CommentViewParams = { essayID: string }; - const { essayID } = useParams() as CommentViewParams; - - const { data: comment } = useGetComment(essayID); - const { mutateAsync: postComment } = usePostComment(); - - const commentComponents = useMemo(() => { - const commentComponents: ReactNode[] = []; - - const setCommentComponents = - (level: number) => - ({ - commentID, - avatarID, - avatarName, - date, - text, - comments, - }: GetCommentAPI[number]) => { - commentComponents.push( - , - ); - - comments.forEach(setCommentComponents(level + 1)); - }; - - comment.forEach((comment) => { - setCommentComponents(0)(comment); - }); - - return commentComponents; - }, [comment]); - - return ( - <> - - - {sprintf(t("commentCount"), commentComponents.length)} - - - {commentComponents} - {taehuiLevel >= 1 && ( - - - - - { - setTextInput(value); - }} - /> - - - - - - - - )} - - ); -}); diff --git a/taehui-fe/src/forum/EssayTitleView.tsx b/taehui-fe/src/forum/EssayTitleView.tsx deleted file mode 100644 index bbc4600..0000000 --- a/taehui-fe/src/forum/EssayTitleView.tsx +++ /dev/null @@ -1,45 +0,0 @@ -import { Col, ListGroupItem, Row } from "reactstrap"; -import { sprintf } from "sprintf-js"; -import { useTranslation } from "react-i18next"; -import { useTo } from "taehui-ts/fe-utility"; -import { getDatetime } from "taehui-ts/date"; - -import AvatarTitle from "src/AvatarTitle"; -import { EssayAPIEssay } from "src/wwwAPI"; - -const EssayTitleView = ({ - forumID, - forumTitle, - essay: { essayID, title, avatarID, avatarName, date, commentCount, hitCount }, -}: { - forumID?: string; - forumTitle?: string; - essay: EssayAPIEssay; -}) => { - const { t } = useTranslation(); - const to = useTo(); - - return ( - { - to(`/forum/${forumID}/${essayID}`); - }} - > - - - - {forumTitle && `[${forumTitle}]`} {title} [{commentCount}] - - - - {getDatetime(date)} -
- {sprintf(t("hitCount"), hitCount)} - -
-
- ); -}; - -export default EssayTitleView; diff --git a/taehui-fe/src/forum/EssayView.tsx b/taehui-fe/src/forum/EssayView.tsx deleted file mode 100644 index ba79040..0000000 --- a/taehui-fe/src/forum/EssayView.tsx +++ /dev/null @@ -1,126 +0,0 @@ -import { useParams } from "react-router-dom"; -import { Button, Col, Row } from "reactstrap"; -import { useTranslation } from "react-i18next"; -import { observer } from "mobx-react-lite"; -import { useTo } from "taehui-ts/fe-utility"; -import Swal from "sweetalert2"; - -import { useAvatarStore } from "src/Stores"; -import TextView from "src/forum/TextView"; -import CommentView from "src/forum/CommentView"; -import EssayTitleView from "src/forum/EssayTitleView"; -import { EssayViewLoading } from "src/Loading"; -import useGetEssay from "src/forum/useGetEssay"; -import useWipeEssay from "src/forum/useWipeEssay"; - -export default observer(() => { - const { t } = useTranslation(); - - const { taehuiAvatarID, isSU } = useAvatarStore(); - - type EssayViewParams = { forumID: string; essayID: string }; - const { forumID, essayID } = useParams() as EssayViewParams; - - const to = useTo(); - - const { mutateAsync: wipeEssay } = useWipeEssay(); - - const { - data: { - forumTitle, - title, - text, - avatarID, - avatarName, - date, - hitCount, - essayLater, - essayBefore, - }, - isFetched: isEssayLoaded, - } = useGetEssay(essayID); - - const onWipeEssay = async () => { - if ( - ( - await Swal.fire({ - title: "Taehui", - text: t("wipeEssayQuestion"), - icon: "question", - showDenyButton: true, - }) - ).isConfirmed - ) { - await wipeEssay({ essayID }); - to(`/forum/${forumID}`); - } - }; - - const onQuit = () => { - to(`/forum/${forumID}`); - }; - - if (!isEssayLoaded) { - return ; - } - - const isAllowModify = isSU || taehuiAvatarID === avatarID; - - return ( - <> - - {isAllowModify && ( - <> - - - - - - - - )} - - - - -
- -
- {essayLater && ( - - )} - {essayBefore && ( - - )} -
- - - ); -}); diff --git a/taehui-fe/src/forum/ForumItem.tsx b/taehui-fe/src/forum/ForumItem.tsx deleted file mode 100644 index cd3408a..0000000 --- a/taehui-fe/src/forum/ForumItem.tsx +++ /dev/null @@ -1,32 +0,0 @@ -import { Link } from "react-router-dom"; -import { Badge, ListGroup, ListGroupItemHeading } from "reactstrap"; - -import EssayTitleView from "src/forum/EssayTitleView"; -import { EssayAPIEssay } from "src/wwwAPI"; - -const ForumItem = ({ - forum: { forumID, title, essays }, -}: { - forum: { - forumID: string; - title: string; - essays: EssayAPIEssay[]; - }; -}) => { - return ( - - - - {title} - - - {essays.map((essay) => { - return ( - - ); - })} - - ); -}; - -export default ForumItem; diff --git a/taehui-fe/src/forum/ForumView.tsx b/taehui-fe/src/forum/ForumView.tsx deleted file mode 100644 index 7acf942..0000000 --- a/taehui-fe/src/forum/ForumView.tsx +++ /dev/null @@ -1,96 +0,0 @@ -import { useEffect } from "react"; -import { Link, useParams } from "react-router-dom"; -import { - Badge, - Button, - Col, - ListGroup, - ListGroupItemHeading, - Row, -} from "reactstrap"; -import { observer } from "mobx-react-lite"; -import { useTranslation } from "react-i18next"; -import { useIntParam, useTo } from "taehui-ts/fe-utility"; - -import EssayTitleView from "src/forum/EssayTitleView"; -import PositionInput from "src/forum/PositionInput"; -import { useAvatarStore, useForumStore } from "src/Stores"; -import { ForumViewLoading } from "src/Loading"; -import useGetForum from "src/forum/useGetForum"; - -export default observer(() => { - const { taehuiLevel } = useAvatarStore(); - const { viewUnit, setLastPage } = useForumStore(); - const { t } = useTranslation(); - - type ForumViewParams = { - forumID: string; - }; - const { forumID } = useParams() as ForumViewParams; - const { param: page } = useIntParam("page", 1); - - const to = useTo(); - - const { - data: { title, essays, essayCount, level }, - isFetched: isForumLoaded, - } = useGetForum(forumID, page, viewUnit); - - useEffect(() => { - if (isForumLoaded) { - setLastPage(Math.ceil(essayCount / viewUnit)); - } - }, [essayCount, isForumLoaded, setLastPage, viewUnit]); - - return ( - <> - - - - - {title} - - {isForumLoaded ? ( - essays.map((essay) => ( - - )) - ) : ( - - )} - - - - - - - - - - {taehuiLevel >= level && ( - - - - - - )} - = level ? "auto" : undefined} - > - - - - - ); -}); diff --git a/taehui-fe/src/forum/PositionInput.tsx b/taehui-fe/src/forum/PositionInput.tsx deleted file mode 100644 index 5bea7be..0000000 --- a/taehui-fe/src/forum/PositionInput.tsx +++ /dev/null @@ -1,79 +0,0 @@ -import { useMemo } from "react"; -import { observer } from "mobx-react-lite"; -import { Pagination, PaginationItem, PaginationLink } from "reactstrap"; -import { useIntParam } from "taehui-ts/fe-utility"; - -import { useForumStore } from "src/Stores"; - -export default observer(() => { - const { pageUnit, lastPage } = useForumStore(); - - const { param: page, setParam: setPage } = useIntParam("page", 1); - - const targetPages = useMemo(() => { - const targetPages = []; - for ( - let i = 1 + Math.floor((page - 1) / pageUnit) * pageUnit; - i <= - Math.min( - lastPage, - Math.floor((page - 1) / pageUnit) * pageUnit + pageUnit, - ); - ++i - ) { - targetPages.push(i); - } - return targetPages; - }, [lastPage, page, pageUnit]); - - const isLowestPage = useMemo(() => page === 1, [page]); - const isHighestPage = useMemo(() => page === lastPage, [lastPage, page]); - - return ( - - - { - setPage(1); - }} - /> - - - { - setPage(page - 1); - }} - /> - - {targetPages.map((targetPage) => ( - - { - setPage(targetPage); - }} - > - {targetPage} - - - ))} - - { - setPage(page + 1); - }} - /> - - - { - setPage(lastPage); - }} - /> - - - ); -}); diff --git a/taehui-fe/src/forum/PostEssayView.tsx b/taehui-fe/src/forum/PostEssayView.tsx deleted file mode 100644 index 0717e97..0000000 --- a/taehui-fe/src/forum/PostEssayView.tsx +++ /dev/null @@ -1,401 +0,0 @@ -import { useEffect, useLayoutEffect, useRef, useState } from "react"; -import { useParams } from "react-router-dom"; -import { - Button, - Col, - Collapse, - Input, - ListGroup, - Modal, - ModalBody, - Row, - TabContent, - TabPane, -} from "reactstrap"; -import { toast } from "react-toastify"; -import { observer } from "mobx-react-lite"; -import { useTranslation } from "react-i18next"; -import { useTo, useWindowArea } from "taehui-ts/fe-utility"; - -import { useAvatarStore, useForumStore, useTaehuiStore } from "src/Stores"; -import TextView from "src/forum/TextView"; -import AutoEssayTitleView from "src/forum//AutoEssayTitleView"; -import { AutoEssayViewLoading } from "src/Loading"; -import useGetAutoEssay from "src/forum/useGetAutoEssay"; -import usePostAutoEssay from "src/forum/usePostAutoEssay"; -import usePutAutoEssay from "src/forum/usePutAutoEssay"; -import withTotem from "src/withTotem"; -import usePutEssay from "src/forum/usePutEssay"; -import usePostFile from "src/forum/usePostFile"; -import useGetEssay from "src/forum/useGetEssay"; -import usePostEssay from "src/forum/usePostEssay"; - -export default withTotem( - observer(() => { - const { - isTitleTextFilled, - title, - text, - setTitle, - setText, - autoEssayID, - setAutoEssayID, - } = useForumStore(); - const { titleViewHeight, avatarViewHeight } = useTaehuiStore(); - const { taehuiAvatarID, taehuiAvatarName } = useAvatarStore(); - - const { t } = useTranslation(); - const [isEdit, setEdit] = useState(true); - const [testText, setTestText] = useState(""); - const [textViewHeight, setTextViewHeight] = useState(100); - const [isAutoEssayOpened, setAutoEssayOpened] = useState(false); - - type PostEssayViewParams = { - forumID: string; - essayID?: string; - }; - const { forumID, essayID } = - useParams() as PostEssayViewParams; - - const { isFetched: isAutoEssayLoaded, data: autoEssay } = useGetAutoEssay( - forumID, - isAutoEssayOpened, - ); - - const editView = useRef(null); - const textView = useRef(null); - const inputView = useRef(null); - - const { mutateAsync: postAutoEssay } = usePostAutoEssay(); - const { mutateAsync: putAutoEssay } = usePutAutoEssay(); - const { mutateAsync: putEssay } = usePutEssay(); - const { isPending, mutateAsync: postFile } = usePostFile(); - const { mutateAsync: postEssay } = usePostEssay(); - - const { - data: essay, - data: { forumTitle }, - isFetched: isEssayLoaded, - } = useGetEssay(essayID); - - useEffect(() => { - if (isEssayLoaded) { - setTitle(essay.title); - setText(essay.text); - } - }, [essay, isEssayLoaded, setText, setTitle]); - - const { windowHeight } = useWindowArea(); - - const to = useTo(); - - const setTag = (tag: string) => { - const { current } = textView; - if (current) { - const { selectionStart, selectionEnd } = current; - const t = text.substring(selectionStart, selectionEnd); - const tag0 = "<" + tag + ">"; - const tag1 = ""; - if (t.startsWith(tag0) || t.endsWith(tag1)) { - setText( - text.substring(0, selectionStart) + - text.substring( - selectionStart + tag0.length, - selectionStart + t.length - tag1.length, - ) + - text.substring(selectionEnd), - ); - setTimeout(() => { - current.selectionStart = selectionStart; - current.selectionEnd = selectionEnd - tag0.length - tag1.length; - current.focus(); - }, 0); - } else { - setText( - text.substring(0, selectionStart) + - tag0 + - text.substring(selectionStart, selectionEnd) + - tag1 + - text.substring(selectionEnd), - ); - setTimeout(() => { - current.selectionStart = selectionStart; - current.selectionEnd = selectionEnd + tag0.length + tag1.length; - current.focus(); - }, 0); - } - } - }; - - useEffect(() => { - setTextViewHeight( - windowHeight - - titleViewHeight - - avatarViewHeight - - (editView.current?.clientHeight ?? 0) - - (inputView.current?.clientHeight ?? 0), - ); - }, [avatarViewHeight, titleViewHeight, windowHeight]); - - useEffect(() => { - if (!essayID) { - setTitle(""); - setText(""); - } - }, [essayID, setText, setTitle]); - - useEffect(() => { - const postAutoEssaysID = setInterval(async () => { - if (isTitleTextFilled) { - if (typeof autoEssayID === "number") { - await putAutoEssay({ autoEssayID, title, text }); - } else { - const { autoEssayID } = await postAutoEssay({ - forumID, - title, - text, - }); - setAutoEssayID(autoEssayID); - } - } - }, 60000); - - return () => { - clearInterval(postAutoEssaysID); - }; - }, [ - autoEssayID, - forumID, - isTitleTextFilled, - postAutoEssay, - putAutoEssay, - setAutoEssayID, - t, - text, - title, - ]); - - useLayoutEffect(() => { - if (!isEdit) { - setTestText(text); - } - }, [isEdit, text]); - - return ( - <> - {isEdit && ( -
- - - { - setTitle(value); - }} - /> - - - - - - - - - - - - - - {isAutoEssayLoaded ? ( - - {autoEssay.map((autoEssay) => ( - - ))} - - ) : ( - - )} - - - -
- )} - - - - - { - setText(value); - }} - innerRef={textView} - style={{ height: textViewHeight }} - /> - - - - - - - -
- - - - - - - - - - - - - - - - - - - {essayID ? ( - - - - ) : ( - - - - )} - - - - -
- - - {t("fileUploading")} - - - - ); - }), -); diff --git a/taehui-fe/src/forum/TextView.module.scss b/taehui-fe/src/forum/TextView.module.scss deleted file mode 100644 index f097979..0000000 --- a/taehui-fe/src/forum/TextView.module.scss +++ /dev/null @@ -1,22 +0,0 @@ -@mixin essay() { - border: thin black solid; - max-width: 100%; -} - -img { - &.essay { - @include essay(); - } -} - -audio { - &.essay { - @include essay(); - } -} - -video { - &.essay { - @include essay(); - } -} diff --git a/taehui-fe/src/forum/TextView.tsx b/taehui-fe/src/forum/TextView.tsx deleted file mode 100644 index c01b3d6..0000000 --- a/taehui-fe/src/forum/TextView.tsx +++ /dev/null @@ -1,99 +0,0 @@ -import { useEffect, useMemo, useState } from "react"; -import { Badge, Col, Row } from "reactstrap"; -import { sanitize } from "dompurify"; -import { useTranslation } from "react-i18next"; -import { sprintf } from "sprintf-js"; -import { getDatetime } from "taehui-ts/date"; - -import { getHitTexts, tag } from "src/Utility"; -import AvatarTitle from "src/AvatarTitle"; - -import scss from "src/forum/TextView.module.scss"; -import useGetHit from "src/forum/useGetHit"; - -const TextView = ({ - forumTitle, - title, - text, - avatarID, - avatarName, - date, - hitCount, -}: { - forumTitle: string; - title: string; - text: string; - avatarID: string; - avatarName: string; - date?: string; - hitCount?: number; -}) => { - const hitTexts = useMemo(() => getHitTexts(text), [text]); - const [textHTMLContents, setTextHTMLContents] = useState(""); - - const { t } = useTranslation(); - - const { data: hit, isFetched: isHitLoaded } = useGetHit(hitTexts); - - useEffect(() => { - setTextHTMLContents( - sanitize(tag(t, text, {}, scss.essay), { - ADD_ATTR: ["target"], - }), - ); - }, [t, text]); - - useEffect(() => { - if (isHitLoaded) { - setTextHTMLContents( - sanitize( - tag( - t, - text, - Object.fromEntries(hitTexts.map((hitText, i) => [hitText, hit[i]])), - scss.essay, - ), - { - ADD_ATTR: ["target"], - }, - ), - ); - } - }, [hit, hitTexts, isHitLoaded, t, text]); - - return ( - <> - - - {forumTitle} - - - - - {title} - - - {typeof hitCount === "number" && ( - <> - {getDatetime(date)} -
- {sprintf(t("hitCount"), hitCount)} - - )} - -
- - - - - - - ); -}; - -export default TextView; diff --git a/taehui-fe/src/forum/setForumStore.ts b/taehui-fe/src/forum/setForumStore.ts deleted file mode 100644 index cefc759..0000000 --- a/taehui-fe/src/forum/setForumStore.ts +++ /dev/null @@ -1,36 +0,0 @@ -export default function setForumStore() { - return { - title: "", - text: "", - autoEssayID: undefined as number | undefined, - - lastPage: 0, - pageUnit: 10, - viewUnit: 10, - level: 0, - - setTitle(title: string) { - this.title = title; - }, - - setText(text: string) { - this.text = text; - }, - - setAutoEssayID(autoEssayID?: number) { - this.autoEssayID = autoEssayID; - }, - - setLastPage(lastPage: number) { - this.lastPage = lastPage; - }, - - setLevel(level: number) { - this.level = level; - }, - - get isTitleTextFilled() { - return this.title && this.text; - }, - }; -} diff --git a/taehui-fe/src/forum/useGetAutoEssay.ts b/taehui-fe/src/forum/useGetAutoEssay.ts deleted file mode 100644 index 554be93..0000000 --- a/taehui-fe/src/forum/useGetAutoEssay.ts +++ /dev/null @@ -1,30 +0,0 @@ -import { useQuery } from "@tanstack/react-query"; -import { wwwAXIOS } from "src/Www"; -import { GetAutoEssayAPI } from "src/wwwAPI"; -import { getMillis } from "taehui-ts/date"; -import { useAvatarStore } from "src/Stores"; - -export default function useGetAutoEssay( - forumID: string, - isAutoEssayOpened: boolean, -) { - const { totem } = useAvatarStore(); - - return useQuery({ - enabled: isAutoEssayOpened, - queryKey: ["autoEssay", forumID, totem], - queryFn: async () => { - const { data } = await wwwAXIOS.get( - `/autoEssay/${forumID}`, - { - headers: { - millis: getMillis(), - totem, - }, - }, - ); - return data; - }, - initialData: [], - }); -} diff --git a/taehui-fe/src/forum/useGetComment.ts b/taehui-fe/src/forum/useGetComment.ts deleted file mode 100644 index 1c82b16..0000000 --- a/taehui-fe/src/forum/useGetComment.ts +++ /dev/null @@ -1,14 +0,0 @@ -import { useQuery } from "@tanstack/react-query"; -import { wwwAXIOS } from "src/Www"; -import { GetCommentAPI } from "src/wwwAPI"; - -export default function useGetComment(essayID: string) { - return useQuery({ - queryKey: ["comment", essayID], - queryFn: async () => { - const { data } = await wwwAXIOS.get(`/comment/${essayID}`); - return data; - }, - initialData: [], - }); -} diff --git a/taehui-fe/src/forum/useGetEssay.ts b/taehui-fe/src/forum/useGetEssay.ts deleted file mode 100644 index 27932a7..0000000 --- a/taehui-fe/src/forum/useGetEssay.ts +++ /dev/null @@ -1,38 +0,0 @@ -import { useQuery } from "@tanstack/react-query"; -import { wwwAXIOS } from "src/Www"; -import { EssayAPIEssay, GetEssayAPI } from "src/wwwAPI"; -import { getLanguage } from "taehui-ts/language"; - -export default function useGetEssay(essayID?: string) { - return useQuery<{ - forumTitle: string; - title: string; - text: string; - date: string; - avatarID: string; - avatarName: string; - hitCount: number; - essayBefore?: EssayAPIEssay; - essayLater?: EssayAPIEssay; - }>({ - enabled: !!essayID, - queryKey: ["essay", essayID], - queryFn: async () => { - const { data } = await wwwAXIOS.get(`/essay/${essayID}`, { - params: { language: getLanguage() }, - }); - return data; - }, - initialData: { - forumTitle: "", - title: "", - text: "", - date: "", - avatarID: "", - avatarName: "", - hitCount: 0, - essayBefore: undefined, - essayLater: undefined, - }, - }); -} diff --git a/taehui-fe/src/forum/useGetForum.ts b/taehui-fe/src/forum/useGetForum.ts deleted file mode 100644 index db4f08f..0000000 --- a/taehui-fe/src/forum/useGetForum.ts +++ /dev/null @@ -1,33 +0,0 @@ -import { useQuery } from "@tanstack/react-query"; -import { wwwAXIOS } from "src/Www"; -import { GetForumAPI } from "src/wwwAPI"; -import { getLanguage } from "taehui-ts/language"; - -export default function useGetForum( - forumID: string, - page: number, - viewUnit: number, -) { - const language = getLanguage(); - - return useQuery({ - queryKey: ["forum", forumID, page, viewUnit, language], - queryFn: async () => { - const { data } = await wwwAXIOS.get(`/forum/${forumID}`, { - params: { - page, - viewUnit, - language, - }, - }); - return data; - }, - initialData: { - title: "", - text: "", - essays: [], - essayCount: 0, - level: 0, - }, - }); -} diff --git a/taehui-fe/src/forum/useGetHit.ts b/taehui-fe/src/forum/useGetHit.ts deleted file mode 100644 index 9d509cf..0000000 --- a/taehui-fe/src/forum/useGetHit.ts +++ /dev/null @@ -1,25 +0,0 @@ -import { useQuery } from "@tanstack/react-query"; -import { wwwAXIOS } from "src/Www"; - -export default function useGetHit(hitTexts: string[]) { - return useQuery({ - queryKey: ["hit", hitTexts], - queryFn: async () => { - return ( - await Promise.allSettled( - hitTexts.map(async (hitText) => - wwwAXIOS.get(`/file/${hitText}/hit`), - ), - ) - ).map((value) => { - switch (value.status) { - case "fulfilled": - return value.value.data; - default: - return 0; - } - }); - }, - initialData: [], - }); -} diff --git a/taehui-fe/src/forum/usePostAutoEssay.ts b/taehui-fe/src/forum/usePostAutoEssay.ts deleted file mode 100644 index d0d6787..0000000 --- a/taehui-fe/src/forum/usePostAutoEssay.ts +++ /dev/null @@ -1,49 +0,0 @@ -import { useMutation, useQueryClient } from "@tanstack/react-query"; -import { wwwAXIOS } from "src/Www"; -import { getMillis } from "taehui-ts/date"; -import { toast } from "react-toastify"; -import { useTranslation } from "react-i18next"; - -import { useAvatarStore } from "src/Stores"; - -export default function usePostAutoEssay() { - const { totem } = useAvatarStore(); - - const { t } = useTranslation(); - - const queryClient = useQueryClient(); - - return useMutation({ - mutationFn: async ({ - forumID, - title, - text, - }: { - forumID: string; - title: string; - text: string; - }) => { - const { - data: { autoEssayID }, - } = await wwwAXIOS.post( - `/autoEssay/${forumID}`, - { - title, - text, - }, - { - headers: { - millis: getMillis(), - totem, - }, - }, - ); - - return autoEssayID; - }, - onSuccess: async (data) => { - await queryClient.invalidateQueries({ queryKey: ["autoEssay"] }); - toast.success(t("postedAutoEssay")); - }, - }); -} diff --git a/taehui-fe/src/forum/usePostComment.ts b/taehui-fe/src/forum/usePostComment.ts deleted file mode 100644 index feae741..0000000 --- a/taehui-fe/src/forum/usePostComment.ts +++ /dev/null @@ -1,37 +0,0 @@ -import { useMutation, useQueryClient } from "@tanstack/react-query"; -import { wwwAXIOS } from "src/Www"; -import { getMillis } from "taehui-ts/date"; - -import { useAvatarStore } from "src/Stores"; - -export default function usePostComment() { - const { totem } = useAvatarStore(); - - const queryClient = useQueryClient(); - - return useMutation({ - mutationFn: async ({ - essayID, - targetCommentID, - text, - }: { - essayID: string; - targetCommentID: number; - text: string; - }) => { - await wwwAXIOS.post( - `/comment/${essayID}`, - { targetCommentID, text }, - { - headers: { - millis: getMillis(), - totem, - }, - }, - ); - }, - onSuccess: async (data) => { - await queryClient.invalidateQueries({ queryKey: ["comment"] }); - }, - }); -} diff --git a/taehui-fe/src/forum/usePostEssay.ts b/taehui-fe/src/forum/usePostEssay.ts deleted file mode 100644 index 5b55cb3..0000000 --- a/taehui-fe/src/forum/usePostEssay.ts +++ /dev/null @@ -1,40 +0,0 @@ -import { useMutation, useQueryClient } from "@tanstack/react-query"; -import { wwwAXIOS } from "src/Www"; -import { getMillis } from "taehui-ts/date"; - -import { useAvatarStore } from "src/Stores"; - -export default function usePostEssay() { - const { totem } = useAvatarStore(); - - const queryClient = useQueryClient(); - - return useMutation({ - mutationFn: async ({ - forumID, - title, - text, - }: { - forumID: string; - title: string; - text: string; - }) => { - await wwwAXIOS.post( - `/essay/${forumID}`, - { - title, - text, - }, - { - headers: { - millis: getMillis(), - totem, - }, - }, - ); - }, - onSuccess: async (data) => { - await queryClient.invalidateQueries({ queryKey: ["essay"] }); - }, - }); -} diff --git a/taehui-fe/src/forum/usePostFile.ts b/taehui-fe/src/forum/usePostFile.ts deleted file mode 100644 index ce66905..0000000 --- a/taehui-fe/src/forum/usePostFile.ts +++ /dev/null @@ -1,51 +0,0 @@ -import { useMutation } from "@tanstack/react-query"; -import { wwwAXIOS } from "src/Www"; -import { getMillis } from "taehui-ts/date"; - -import { useAvatarStore } from "src/Stores"; - -export default function usePostFile() { - const { totem } = useAvatarStore(); - - return useMutation({ - mutationFn: async ({ - file, - textView, - }: { - file: File; - textView: HTMLTextAreaElement; - }) => { - const form = new FormData(); - form.append("data", file); - const { - status, - data: { fileName }, - } = await wwwAXIOS.post("/file", form, { - headers: { - millis: getMillis(), - totem, - }, - }); - if (status === 201) { - const { selectionStart, value } = textView; - const textBefore = value.substring(0, selectionStart); - const textLater = value.substring(selectionStart, value.length); - if (fileName.match(/^.*\.(bmp|gif|jpeg|jpg|png|webp)$/i)) { - return `${textBefore}${textLater}`; - } else if ( - fileName.match( - /^.*\.(aif|aiff|asf|flac|m4a|mid|midi|mp2|mp3|ogg|opus|raw|wav|wma)$/i, - ) - ) { - return `${textBefore}${textLater}`; - } else if ( - fileName.match(/^.*\.(avi|flv|m1v|mkv|mov|mp4|mpeg|mpg|webm|wmv)$/i) - ) { - return `${textBefore}${textLater}`; - } else { - return `${textBefore}${file.name}${textLater}`; - } - } - }, - }); -} diff --git a/taehui-fe/src/forum/usePutAutoEssay.ts b/taehui-fe/src/forum/usePutAutoEssay.ts deleted file mode 100644 index 327b9d7..0000000 --- a/taehui-fe/src/forum/usePutAutoEssay.ts +++ /dev/null @@ -1,45 +0,0 @@ -import { useMutation, useQueryClient } from "@tanstack/react-query"; -import { wwwAXIOS } from "src/Www"; -import { getMillis } from "taehui-ts/date"; -import { useTranslation } from "react-i18next"; - -import { useAvatarStore } from "src/Stores"; -import { toast } from "react-toastify"; - -export default function usePutAutoEssay() { - const { totem } = useAvatarStore(); - - const { t } = useTranslation(); - - const queryClient = useQueryClient(); - - return useMutation({ - mutationFn: async ({ - autoEssayID, - title, - text, - }: { - autoEssayID: number; - title: string; - text: string; - }) => { - await wwwAXIOS.put( - `/autoEssay/${autoEssayID}`, - { - title, - text, - }, - { - headers: { - millis: getMillis(), - totem, - }, - }, - ); - }, - onSuccess: async () => { - await queryClient.invalidateQueries({ queryKey: ["autoEssay"] }); - toast.success(t("postedAutoEssay")); - }, - }); -} diff --git a/taehui-fe/src/forum/usePutComment.ts b/taehui-fe/src/forum/usePutComment.ts deleted file mode 100644 index 580d08e..0000000 --- a/taehui-fe/src/forum/usePutComment.ts +++ /dev/null @@ -1,35 +0,0 @@ -import { useMutation, useQueryClient } from "@tanstack/react-query"; -import { wwwAXIOS } from "src/Www"; -import { getMillis } from "taehui-ts/date"; - -import { useAvatarStore } from "src/Stores"; - -export default function usePutComment() { - const { totem } = useAvatarStore(); - - const queryClient = useQueryClient(); - - return useMutation({ - mutationFn: async ({ - commentID, - text, - }: { - commentID: number; - text: string; - }) => { - await wwwAXIOS.put( - `/comment/${commentID}`, - { text }, - { - headers: { - millis: getMillis(), - totem, - }, - }, - ); - }, - onSuccess: async () => { - await queryClient.invalidateQueries({ queryKey: ["comment"] }); - }, - }); -} diff --git a/taehui-fe/src/forum/usePutEssay.ts b/taehui-fe/src/forum/usePutEssay.ts deleted file mode 100644 index f1d1413..0000000 --- a/taehui-fe/src/forum/usePutEssay.ts +++ /dev/null @@ -1,41 +0,0 @@ -import { useMutation, useQueryClient } from "@tanstack/react-query"; -import { wwwAXIOS } from "src/Www"; -import { getMillis } from "taehui-ts/date"; - -import { useAvatarStore } from "src/Stores"; - -export default function usePutEssay() { - const { totem } = useAvatarStore(); - - const queryClient = useQueryClient(); - - return useMutation({ - mutationFn: async ({ - essayID, - title, - text, - }: { - essayID: string; - title: string; - text: string; - }) => { - await wwwAXIOS.put( - `/essay/${essayID}`, - { - title, - text, - }, - { - headers: { - millis: getMillis(), - totem, - }, - }, - ); - }, - onSuccess: async (data, { essayID }) => { - await queryClient.invalidateQueries({ queryKey: ["forum"] }); - await queryClient.invalidateQueries({ queryKey: ["essay"] }); - }, - }); -} diff --git a/taehui-fe/src/forum/useWipeAutoEssay.ts b/taehui-fe/src/forum/useWipeAutoEssay.ts deleted file mode 100644 index 50aa234..0000000 --- a/taehui-fe/src/forum/useWipeAutoEssay.ts +++ /dev/null @@ -1,22 +0,0 @@ -import { useMutation, useQueryClient } from "@tanstack/react-query"; -import { getMillis } from "taehui-ts/date"; - -import { wwwAXIOS } from "src/Www"; -import { useAvatarStore, useForumStore } from "src/Stores"; - -export default function useWipeAutoEssay() { - const { totem } = useAvatarStore(); - - const queryClient = useQueryClient(); - - return useMutation({ - mutationFn: async ({ autoEssayID }: { autoEssayID: number }) => { - await wwwAXIOS.delete(`/autoEssay/${autoEssayID}`, { - headers: { millis: getMillis(), totem }, - }); - }, - onSuccess: async () => { - await queryClient.invalidateQueries({ queryKey: ["autoEssay"] }); - }, - }); -} diff --git a/taehui-fe/src/forum/useWipeComment.ts b/taehui-fe/src/forum/useWipeComment.ts deleted file mode 100644 index 1a0266d..0000000 --- a/taehui-fe/src/forum/useWipeComment.ts +++ /dev/null @@ -1,37 +0,0 @@ -import { useMutation, useQueryClient } from "@tanstack/react-query"; -import { toast } from "react-toastify"; -import { useTranslation } from "react-i18next"; -import { getMillis } from "taehui-ts/date"; - -import { isClientFault, wwwAXIOS } from "src/Www"; - -export default function useWipeComment() { - const queryClient = useQueryClient(); - - const { t } = useTranslation(); - - return useMutation({ - mutationFn: async ({ - commentID, - totem, - }: { - commentID: number; - totem: string; - }) => { - await wwwAXIOS.delete(`/comment/${commentID}`, { - headers: { - millis: getMillis(), - totem, - }, - }); - }, - onSuccess: async () => { - await queryClient.invalidateQueries({ queryKey: ["comment"] }); - }, - onError: (e) => { - if (isClientFault(e)) { - toast.error(t("failedValidateCipher")); - } - }, - }); -} diff --git a/taehui-fe/src/forum/useWipeEssay.ts b/taehui-fe/src/forum/useWipeEssay.ts deleted file mode 100644 index 21c6d26..0000000 --- a/taehui-fe/src/forum/useWipeEssay.ts +++ /dev/null @@ -1,25 +0,0 @@ -import { useMutation, useQueryClient } from "@tanstack/react-query"; -import { getMillis } from "taehui-ts/date"; - -import { wwwAXIOS } from "src/Www"; -import { useAvatarStore } from "src/Stores"; - -export default function useWipeEssay() { - const { totem } = useAvatarStore(); - - const queryClient = useQueryClient(); - - return useMutation({ - mutationFn: async ({ essayID }: { essayID: string }) => { - await wwwAXIOS.delete(`/essay/${essayID}`, { - headers: { - millis: getMillis(), - totem, - }, - }); - }, - onSuccess: async () => { - await queryClient.invalidateQueries({ queryKey: ["forum"] }); - }, - }); -} diff --git a/taehui-fe/src/forums/ForumsView.tsx b/taehui-fe/src/forums/ForumsView.tsx deleted file mode 100644 index fda808c..0000000 --- a/taehui-fe/src/forums/ForumsView.tsx +++ /dev/null @@ -1,36 +0,0 @@ -import { Col, Row } from "reactstrap"; -import { useParams } from "react-router-dom"; -import { useWindowArea } from "taehui-ts/fe-utility"; - -import ForumItem from "src/forum/ForumItem"; -import { ForumsViewLoading } from "src/Loading"; -import useGetForums from "src/forums/useGetForums"; - -const ForumsView = () => { - const line = useWindowArea().windowLength < 992 ? 1 : 2; - - type ForumsViewParams = { forumGroup: string }; - const { forumGroup } = useParams() as ForumsViewParams; - - const { data: forums, isFetched: isForumsLoaded } = useGetForums(forumGroup); - - if (!isForumsLoaded) { - return ; - } - - return ( - <> - {[...Array(Math.ceil(forums.length / line)).keys()].map((i) => ( - - {forums.slice(line * i, line * i + line).map((forum) => ( - - - - ))} - - ))} - - ); -}; - -export default ForumsView; diff --git a/taehui-fe/src/forums/useGetForums.ts b/taehui-fe/src/forums/useGetForums.ts deleted file mode 100644 index 34f0691..0000000 --- a/taehui-fe/src/forums/useGetForums.ts +++ /dev/null @@ -1,21 +0,0 @@ -import { useQuery } from "@tanstack/react-query"; -import { getLanguage } from "taehui-ts/language"; - -import { wwwAXIOS } from "src/Www"; -import { GetForumsAPI } from "src/wwwAPI"; - -export default function useGetForums(forumGroup: string) { - return useQuery({ - queryKey: ["forums", forumGroup], - queryFn: async () => { - const { data } = await wwwAXIOS.get( - forumGroup ? `/forums/${forumGroup}` : "/forums", - { - params: { language: getLanguage() }, - }, - ); - return data; - }, - initialData: [], - }); -} diff --git a/taehui-fe/src/hoc/withQueryClient.tsx b/taehui-fe/src/hoc/withQueryClient.tsx new file mode 100644 index 0000000..f4a7744 --- /dev/null +++ b/taehui-fe/src/hoc/withQueryClient.tsx @@ -0,0 +1,14 @@ +import { QueryClient, QueryClientProvider } from "@tanstack/react-query"; +import type { FC } from "react"; + +const queryClient = new QueryClient(); + +export default function withQueryClient(Component: FC) { + return (props: T) => { + return ( + + + + ); + }; +} diff --git a/taehui-fe/src/hoc/withTotem.tsx b/taehui-fe/src/hoc/withTotem.tsx new file mode 100644 index 0000000..53ecf81 --- /dev/null +++ b/taehui-fe/src/hoc/withTotem.tsx @@ -0,0 +1,16 @@ +import { useAvatarStore } from "@/store/Stores"; +import { observer } from "mobx-react-lite"; + +import type { FC } from "react"; + +export default function withTotem(Component: FC) { + return observer((props: T) => { + const { totem } = useAvatarStore(); + + if (!totem) { + return null; + } + + return ; + }); +} diff --git a/taehui-fe/src/i18n.ts b/taehui-fe/src/i18n.ts new file mode 100644 index 0000000..c156e6e --- /dev/null +++ b/taehui-fe/src/i18n.ts @@ -0,0 +1,14 @@ +import { getRequestConfig } from "next-intl/server"; +import { notFound } from "next/navigation"; + +const locales = ["en", "ko"]; + +export default getRequestConfig(async ({ locale }) => { + if (!locales.includes(locale)) { + notFound(); + } + + return { + messages: (await import(`@/assets/language/${locale}.json`)).default, + }; +}); diff --git a/taehui-fe/src/index.scss b/taehui-fe/src/index.scss deleted file mode 100644 index a06de8b..0000000 --- a/taehui-fe/src/index.scss +++ /dev/null @@ -1,82 +0,0 @@ -* { - margin: 0; - font-family: - "Century Gothic", - -apple-system, - BlinkMacSystemFont, - "Segoe UI", - "Roboto", - "Oxygen", - "Ubuntu", - "Cantarell", - "Fira Sans", - "Droid Sans", - "Helvetica Neue", - sans-serif; - -webkit-font-smoothing: antialiased; - -moz-osx-font-smoothing: grayscale; - - &.route { - cursor: pointer; - } -} - -@mixin default() { - font-size: 0.75rem; -} - -body { - background: url("assets/hexellence.png"); -} - -button { - &.btn { - @include default(); - } -} - -input[type="search"], -input[type="submit"], -input[type="text"], -input[type="email"], -input[type="password"] { - @include default(); -} - -button { - &.page-link { - @include default(); - } - - &.dropdown-item { - @include default(); - } -} - -textarea { - &.form-control { - @include default(); - } -} - -img { - &.avatar { - width: 3rem; - height: 3rem; - border: thin black solid; - border-radius: 50%; - } -} - -span { - @include default(); - - &.badge { - @include default(); - font-weight: normal; - } - - &.ln { - white-space: break-spaces; - } -} diff --git a/taehui-fe/src/index.tsx b/taehui-fe/src/index.tsx deleted file mode 100644 index 5ba5323..0000000 --- a/taehui-fe/src/index.tsx +++ /dev/null @@ -1,40 +0,0 @@ -import { createRoot } from "react-dom/client"; -import { BrowserRouter } from "react-router-dom"; -import { initReactI18next } from "react-i18next"; -import i18n from "i18next"; -import { getLanguage } from "taehui-ts/language"; -import { QueryClient, QueryClientProvider } from "@tanstack/react-query"; - -import { Stores } from "src/Stores"; -import TaehuiView from "src/taehui/TaehuiView"; - -import Language from "src/Language.json"; - -import "bootstrap/dist/css/bootstrap.min.css"; -import "react-contexify/dist/ReactContexify.css"; -import "react-toastify/dist/ReactToastify.css"; -import "src/index.scss"; - -const root = document.getElementById("root"); -if (root) { - (async () => { - await i18n.use(initReactI18next).init({ - resources: Language, - lng: "ko-KR", - }); - - await i18n.changeLanguage(getLanguage()); - - const queryClient = new QueryClient(); - - createRoot(root).render( - - - - - - - , - ); - })(); -} diff --git a/taehui-fe/src/middleware.ts b/taehui-fe/src/middleware.ts new file mode 100644 index 0000000..69dc475 --- /dev/null +++ b/taehui-fe/src/middleware.ts @@ -0,0 +1,12 @@ +import createMiddleware from "next-intl/middleware"; + +const locales = ["en", "ko"]; + +export default createMiddleware({ + locales, + defaultLocale: locales[0], +}); + +export const config = { + matcher: ["/((?!www|api|_next|.*\\..*).*)"], +}; diff --git a/taehui-fe/src/react-app-env.d.ts b/taehui-fe/src/react-app-env.d.ts deleted file mode 100644 index 6431bc5..0000000 --- a/taehui-fe/src/react-app-env.d.ts +++ /dev/null @@ -1 +0,0 @@ -/// diff --git a/taehui-fe/src/setupProxy.js b/taehui-fe/src/setupProxy.js deleted file mode 100644 index ab526b4..0000000 --- a/taehui-fe/src/setupProxy.js +++ /dev/null @@ -1,11 +0,0 @@ -const { createProxyMiddleware } = require("http-proxy-middleware"); - -module.exports = function (app) { - app.use( - createProxyMiddleware("/www", { - target: process.env.API ?? "https://taehui.ddns.net", - changeOrigin: true, - }), - ); -}; - diff --git a/taehui-fe/src/store/Stores.tsx b/taehui-fe/src/store/Stores.tsx new file mode 100644 index 0000000..ee8a3f5 --- /dev/null +++ b/taehui-fe/src/store/Stores.tsx @@ -0,0 +1,39 @@ +"use client"; + +import setForumStore from "@/app/[language]/forum/store/setForumStore"; +import setWantStore from "@/app/[language]/want/store/setWantStore"; +import setAvatarStore from "@/avatar/setAvatarStore"; +import setTaehuiStore from "@/store/setTaehuiStore"; +import { useLocalObservable } from "mobx-react-lite"; +import { createContext, FC, PropsWithChildren, useContext } from "react"; + +type MainStore = { + taehuiStore: ReturnType; + wantStore: ReturnType; + avatarStore: ReturnType; + forumStore: ReturnType; +}; + +const mainStore = createContext({} as MainStore); +const { Provider } = mainStore; + +export const Stores: FC = ({ children }) => ( + + {children} + +); + +export const useTaehuiStore = () => useContext(mainStore).taehuiStore; + +export const useWantStore = () => useContext(mainStore).wantStore; + +export const useAvatarStore = () => useContext(mainStore).avatarStore; + +export const useForumStore = () => useContext(mainStore).forumStore; diff --git a/taehui-fe/src/store/setTaehuiStore.ts b/taehui-fe/src/store/setTaehuiStore.ts new file mode 100644 index 0000000..ac86534 --- /dev/null +++ b/taehui-fe/src/store/setTaehuiStore.ts @@ -0,0 +1,14 @@ +export default function setTaehuiStore() { + return { + titleViewHeight: 0, + avatarViewHeight: 0, + + setTitleViewHeight(titleViewHeight: number) { + this.titleViewHeight = titleViewHeight; + }, + + setAvatarViewHeight(avatarViewHeight: number) { + this.avatarViewHeight = avatarViewHeight; + }, + }; +} diff --git a/taehui-fe/src/taehui/HitView.tsx b/taehui-fe/src/taehui/HitView.tsx deleted file mode 100644 index 0ccd216..0000000 --- a/taehui-fe/src/taehui/HitView.tsx +++ /dev/null @@ -1,43 +0,0 @@ -import { useEffect } from "react"; -import { useTranslation } from "react-i18next"; -import { sprintf } from "sprintf-js"; - -import { HitViewLoading } from "src/Loading"; -import useGetHit from "src/taehui/useGetHit"; -import usePostHit from "src/taehui/usePostHit"; - -const HitView = () => { - const { t } = useTranslation(); - - const { - data: [hitBefore, hit], - isFetched: isHitLoaded, - } = useGetHit(); - - const { mutateAsync: postHit } = usePostHit(); - - useEffect(() => { - (async () => { - await postHit(); - })(); - }, [postHit]); - - return ( - <> -
{t("hit00")}
- {isHitLoaded ? ( - - {sprintf(t("hit01"), hitBefore)} -
- {sprintf(t("hit02"), hit)} -
- {t("hit03")} -
- ) : ( - - )} - - ); -}; - -export default HitView; diff --git a/taehui-fe/src/taehui/LatestAvatarsView.tsx b/taehui-fe/src/taehui/LatestAvatarsView.tsx deleted file mode 100644 index 967a205..0000000 --- a/taehui-fe/src/taehui/LatestAvatarsView.tsx +++ /dev/null @@ -1,41 +0,0 @@ -import { Col, Row } from "reactstrap"; -import { useTranslation } from "react-i18next"; -import { getDatetime } from "taehui-ts/date"; - -import { LatestAvatarViewLoading } from "src/Loading"; -import AvatarTitle from "src/AvatarTitle"; -import useGetLatestAvatar from "src/taehui/useGetLatestAvatar"; - -const LatestAvatarsView = () => { - const { t } = useTranslation(); - - const { data: latestAvatar, isFetched: isLatestAvatarLoaded } = - useGetLatestAvatar(); - - return ( - - {latestAvatar.map((latestAvatar, i) => { - return ( - -
{t(`latestAvatarsView${i}`)}
- {isLatestAvatarLoaded ? ( - latestAvatar.map(({ avatarID, avatarName, date }) => { - return ( - - - {getDatetime(date)} - - - ); - }) - ) : ( - - )} - - ); - })} -
- ); -}; - -export default LatestAvatarsView; diff --git a/taehui-fe/src/taehui/LatestCommentsView.tsx b/taehui-fe/src/taehui/LatestCommentsView.tsx deleted file mode 100644 index ef90ba2..0000000 --- a/taehui-fe/src/taehui/LatestCommentsView.tsx +++ /dev/null @@ -1,37 +0,0 @@ -import { useTranslation } from "react-i18next"; -import { ListGroup, ListGroupItemHeading } from "reactstrap"; - -import { LatestCommentsViewLoading } from "src/Loading"; -import CommentTitleView from "src/forum/CommentTitleView"; -import useGetLatestComment from "src/taehui/useGetLatestComment"; - -const LatestCommentsView = () => { - const { t } = useTranslation(); - - const { data: latestComment, isFetched: isLatestCommentLoaded } = - useGetLatestComment(); - - return ( - <> - - {t("latestCommentsView")} - {isLatestCommentLoaded ? ( - latestComment.map((latestComment) => { - return ( - - ); - }) - ) : ( - - )} - - - ); -}; - -export default LatestCommentsView; diff --git a/taehui-fe/src/taehui/LatestEssaysView.tsx b/taehui-fe/src/taehui/LatestEssaysView.tsx deleted file mode 100644 index 88c0271..0000000 --- a/taehui-fe/src/taehui/LatestEssaysView.tsx +++ /dev/null @@ -1,37 +0,0 @@ -import { useTranslation } from "react-i18next"; -import { ListGroup, ListGroupItemHeading } from "reactstrap"; - -import { LatestEssaysViewLoading } from "src/Loading"; -import EssayTitleView from "src/forum/EssayTitleView"; -import useGetLatestEssay from "src/taehui/useGetLatestEssay"; - -const LatestEssaysView = () => { - const { t } = useTranslation(); - - const { data: latestEssay, isFetched: isLatestEssayLoaded } = - useGetLatestEssay(); - - return ( - <> - - {t("latestEssaysView")} - {isLatestEssayLoaded ? ( - latestEssay.map((latestEssay) => { - return ( - - ); - }) - ) : ( - - )} - - - ); -}; - -export default LatestEssaysView; diff --git a/taehui-fe/src/taehui/TaehuiInfoView.tsx b/taehui-fe/src/taehui/TaehuiInfoView.tsx deleted file mode 100644 index 6020108..0000000 --- a/taehui-fe/src/taehui/TaehuiInfoView.tsx +++ /dev/null @@ -1,158 +0,0 @@ -const TaehuiInfoView = () => { - return ( - <> - - 이름: 박태희 -
- 생년월일: 1994년 12월 21일 -
- 메일 주소:{" "} - taehui@taehui.ddns.net -
-
직장
-
    -
  • - (주) 네이버파이낸셜{" "} - 프론트엔드 개발자 (2020년 3월 12일 ~) -
    - 경기도 성남시 분당구 정자일로 95 1784 -
  • -
  • - (주) 네이버 2020 신입 프론트엔드 - 2020 신입 프론트엔드 개발자 (2020년 1월 2일 ~ 2020년 3월 11일) -
    - 경기도 성남시 분당구 불정로 6 NAVER -
  • -
-
-
거주지
-
    -
  • 경기도 성남시 분당구 (2020년)
  • -
  • 세종특별자치시 (2018년 ~ 2020년)
  • -
  • 대전광역시 유성구 (1994년 ~ 2018년)
  • -
-
-
경력
- -
-
학력
- -
-
군 복무
-
    -
  • - 대전시립박물관{" "} - 사회복무요원 (2015년 3월 9일 ~ 2017년 3월 8일) -
    - 대전광역시 유성구 도안대로 398 -
  • -
  • - - {`"판, 세상을 담다"`} - {" "} - 골패점 개발자 (2015년 4월 30일 ~ 2015년 8월 30일) -
    - 대전광역시 유성구 도안대로 398 -
  • -
-
-
자격증
- -
-
공모전
- -
- - ); -}; - -export default TaehuiInfoView; diff --git a/taehui-fe/src/taehui/TaehuiIntroView.tsx b/taehui-fe/src/taehui/TaehuiIntroView.tsx deleted file mode 100644 index cc1390b..0000000 --- a/taehui-fe/src/taehui/TaehuiIntroView.tsx +++ /dev/null @@ -1,36 +0,0 @@ -import { useTranslation } from "react-i18next"; - -import HitView from "src/taehui/HitView"; -import LatestEssaysView from "src/taehui/LatestEssaysView"; -import LatestCommentsView from "src/taehui/LatestCommentsView"; -import LatestAvatarsView from "src/taehui/LatestAvatarsView"; -import WantInput from "src/want/WantInput"; - -const TaehuiIntroView = () => { - const { t } = useTranslation(); - - return ( - <> - -
-
{t("taehuiIntro00")}
- - {t("taehuiIntro01")} -
- {t("taehuiIntro02")} -
- {t("taehuiIntro03")} -
-
- -
- -
- -
- - - ); -}; - -export default TaehuiIntroView; diff --git a/taehui-fe/src/taehui/TaehuiView.module.scss b/taehui-fe/src/taehui/TaehuiView.module.scss deleted file mode 100644 index 95ea8d1..0000000 --- a/taehui-fe/src/taehui/TaehuiView.module.scss +++ /dev/null @@ -1,9 +0,0 @@ -img { - &.taehui { - height: 3rem; - } - - &.vcs { - height: 1rem; - } -} diff --git a/taehui-fe/src/taehui/TaehuiView.tsx b/taehui-fe/src/taehui/TaehuiView.tsx deleted file mode 100644 index 69bcdcf..0000000 --- a/taehui-fe/src/taehui/TaehuiView.tsx +++ /dev/null @@ -1,207 +0,0 @@ -import { lazy, Suspense, useEffect, useMemo, useRef } from "react"; -import { Link, Route, Routes, useLocation } from "react-router-dom"; -import { Button, Col, Container, Navbar, NavbarBrand, Row } from "reactstrap"; -import { useTranslation } from "react-i18next"; -import { ToastContainer } from "react-toastify"; - -import SignUpView from "src/avatar/SignUpView"; -import ModifyAvatarView from "src/avatar/ModifyAvatarView"; -import CommentaryView from "src/commentary/CommentaryView"; -import TaehuiIntroView from "src/taehui/TaehuiIntroView"; -import TaehuiInfoView from "src/taehui/TaehuiInfoView"; -import useSession from "src/taehui/useSession"; - -import scss from "src/taehui/TaehuiView.module.scss"; -import { - AvatarViewLoading, - EssayViewLoading, - ForumsViewLoading, - ForumViewLoading, - WantViewLoading, -} from "src/Loading"; - -import vcs from "src/assets/vcs.png"; - -import { useTaehuiStore } from "src/Stores"; - -const AvatarView = lazy(() => import("src/avatar/AvatarView")); -const ForumsView = lazy(() => import("src/forums/ForumsView")); -const ForumView = lazy(() => import("src/forum/ForumView")); -const EssayView = lazy(() => import("src/forum/EssayView")); -const PostEssayView = lazy(() => import("src/forum/PostEssayView")); -const WantView = lazy(() => import("src/want/WantView")); - -const TaehuiView = () => { - const { t } = useTranslation(); - - const { setTitleViewHeight, setAvatarViewHeight } = useTaehuiStore(); - - const titleView = useRef(null); - const avatarView = useRef(null); - - const isSessionLoading = useSession(); - - const { pathname } = useLocation(); - - const isAvatarViewVisible = useMemo( - () => - !pathname.startsWith("/avatar") && !pathname.startsWith("/commentary"), - [pathname], - ); - - useEffect(() => { - setTitleViewHeight(titleView.current?.clientHeight ?? 0); - setAvatarViewHeight(avatarView.current?.clientHeight ?? 0); - }, [setAvatarViewHeight, setTitleViewHeight]); - - const getColor = (route: string) => - pathname === route ? "primary" : "secondary"; - - const getTo = (pathname: string) => ({ - ...window.location, - pathname, - search: "", - }); - - return ( - <> -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
- - - } /> - } /> - } /> - } /> - }> - - - } - /> - }> - - - } - /> - }> - - - } - /> - - - - } - /> - }> - - - } - /> - - - - } - /> - } /> - - {isAvatarViewVisible && ( -
-
- }> - - -
- )} -
- - - - ); -}; - -export default TaehuiView; diff --git a/taehui-fe/src/taehui/setTaehuiStore.ts b/taehui-fe/src/taehui/setTaehuiStore.ts deleted file mode 100644 index 62037c5..0000000 --- a/taehui-fe/src/taehui/setTaehuiStore.ts +++ /dev/null @@ -1,24 +0,0 @@ -export default function setTaehuiStore() { - return { - wantInput: "", - wantVariety: "essay", - titleViewHeight: 0, - avatarViewHeight: 0, - - setWantInput(wantInput: string) { - this.wantInput = wantInput; - }, - - setWantVariety(wantVariety: string) { - this.wantVariety = wantVariety; - }, - - setTitleViewHeight(titleViewHeight: number) { - this.titleViewHeight = titleViewHeight; - }, - - setAvatarViewHeight(avatarViewHeight: number) { - this.avatarViewHeight = avatarViewHeight; - }, - }; -} diff --git a/taehui-fe/src/taehui/useGetHit.ts b/taehui-fe/src/taehui/useGetHit.ts deleted file mode 100644 index be1aa41..0000000 --- a/taehui-fe/src/taehui/useGetHit.ts +++ /dev/null @@ -1,14 +0,0 @@ -import { useQuery } from "@tanstack/react-query"; - -import { wwwAXIOS } from "src/Www"; - -export default function useGetHit() { - return useQuery({ - queryKey: ["hit"], - queryFn: async () => { - const { data } = await wwwAXIOS.get("/hit"); - return data; - }, - initialData: [], - }); -} diff --git a/taehui-fe/src/taehui/useGetLatestAvatar.ts b/taehui-fe/src/taehui/useGetLatestAvatar.ts deleted file mode 100644 index c9f9d54..0000000 --- a/taehui-fe/src/taehui/useGetLatestAvatar.ts +++ /dev/null @@ -1,15 +0,0 @@ -import { useQuery } from "@tanstack/react-query"; - -import { wwwAXIOS } from "src/Www"; -import { GetLatestAvatarAPI } from "src/wwwAPI"; - -export default function useGetLatestAvatar() { - return useQuery({ - queryKey: ["latestAvatar"], - queryFn: async () => { - const { data } = await wwwAXIOS.get("/avatar/latest"); - return data; - }, - initialData: [], - }); -} diff --git a/taehui-fe/src/taehui/useGetLatestComment.ts b/taehui-fe/src/taehui/useGetLatestComment.ts deleted file mode 100644 index 3ad0c32..0000000 --- a/taehui-fe/src/taehui/useGetLatestComment.ts +++ /dev/null @@ -1,16 +0,0 @@ -import { useQuery } from "@tanstack/react-query"; - -import { wwwAXIOS } from "src/Www"; -import { GetLatestCommentAPI } from "src/wwwAPI"; - -export default function useGetLatestComment() { - return useQuery({ - queryKey: ["latestComment"], - queryFn: async () => { - const { data } = - await wwwAXIOS.get("/comment/latest"); - return data; - }, - initialData: [], - }); -} diff --git a/taehui-fe/src/taehui/useGetLatestEssay.ts b/taehui-fe/src/taehui/useGetLatestEssay.ts deleted file mode 100644 index d271111..0000000 --- a/taehui-fe/src/taehui/useGetLatestEssay.ts +++ /dev/null @@ -1,19 +0,0 @@ -import { useQuery } from "@tanstack/react-query"; -import { getLanguage } from "taehui-ts/language"; - -import { wwwAXIOS } from "src/Www"; -import { GetLatestEssayAPI } from "src/wwwAPI"; - -export default function useGetLatestEssay() { - const language = getLanguage(); - return useQuery({ - queryKey: ["latestEssay"], - queryFn: async () => { - const { data } = await wwwAXIOS.get("/essay/latest", { - params: { language }, - }); - return data; - }, - initialData: [], - }); -} diff --git a/taehui-fe/src/taehui/usePostHit.ts b/taehui-fe/src/taehui/usePostHit.ts deleted file mode 100644 index 29c78a0..0000000 --- a/taehui-fe/src/taehui/usePostHit.ts +++ /dev/null @@ -1,22 +0,0 @@ -import { useMutation, useQueryClient } from "@tanstack/react-query"; -import { getMillis } from "taehui-ts/date"; - -import { wwwAXIOS } from "src/Www"; - -export default function usePostHit() { - const queryClient = useQueryClient(); - - return useMutation({ - mutationFn: async () => { - const { data } = await wwwAXIOS.post("/hit", null, { - headers: { - millis: getMillis(), - }, - }); - return data; - }, - onSuccess: async () => { - await queryClient.invalidateQueries({ queryKey: ["hit"] }); - }, - }); -} diff --git a/taehui-fe/src/taehui/useSession.ts b/taehui-fe/src/taehui/useSession.ts deleted file mode 100644 index 19a0923..0000000 --- a/taehui-fe/src/taehui/useSession.ts +++ /dev/null @@ -1,30 +0,0 @@ -import { useEffect, useState } from "react"; - -import { useAvatarStore } from "src/Stores"; -import useAutoSignIn from "src/avatar/useAutoSignIn"; - -const useSession = () => { - const { loadTotem, totem } = useAvatarStore(); - const [isLoading, setLoading] = useState(true); - - const autoSignIn = useAutoSignIn(); - - useEffect(() => { - (async () => { - await loadTotem(); - setLoading(false); - })(); - }, [loadTotem]); - - useEffect(() => { - (async () => { - if (!isLoading && !totem) { - await autoSignIn(); - } - })(); - }, [autoSignIn, isLoading, totem]); - - return isLoading; -}; - -export default useSession; diff --git a/taehui-fe/src/type/wwwAPI.d.ts b/taehui-fe/src/type/wwwAPI.d.ts new file mode 100644 index 0000000..5327724 --- /dev/null +++ b/taehui-fe/src/type/wwwAPI.d.ts @@ -0,0 +1,110 @@ +export type GetCommentaryAPI = { + commentaryID: number; + avatarName: string; + text: string; + date: string; +}[]; + +export type GetEssayAPI = { + forumTitle: string; + title: string; + text: string; + date: string; + avatarID: string; + avatarName: string; + hitCount: number; + essayBefore: EssayAPIEssay; + essayLater: EssayAPIEssay; +}; + +export type EssayAPIEssay = { + essayID: number; + avatarID: string; + avatarName: string; + date: string; + title: string; + commentCount: number; + hitCount: number; + essayBefore?: Essay; + essayLater?: Essay; +}; + +export type GetCommentAPI = { + commentID: number; + date: string; + avatarID: string; + avatarName: string; + text: string; + comments: GetCommentAPI[number][]; +}[]; + +export type GetForumAPI = { + title: string; + text: string; + essays: EssayAPIEssay[]; + essayCount: number; + level: number; +}; + +export type GetAutoEssayAPI = { + autoEssayID: number; + date: string; + title: string; + text: string; +}[]; + +export type GetForumsAPI = { + forumID: string; + title: string; + essays: EssayAPIEssay[]; +}[]; + +export type GetLatestAvatarAPI = { + avatarID: string; + avatarName: string; + date: string; +}[][]; + +export type GetLatestCommentAPI = { + commentID: number; + date: string; + avatarID: string; + avatarName: string; + text: string; + forumID: string; + essayID: number; +}[]; + +export type GetLatestEssayAPI = { + essayID: number; + avatarID: string; + avatarName: string; + date: string; + title: string; + commentCount: number; + hitCount: number; + forumTitle?: string; + forumID?: string; +}[]; + +export type GetWantAPIEssay = { + essayID: number; + avatarID: string; + avatarName: string; + date: string; + title: string; + commentCount: number; + hitCount: number; + forumTitle?: string; + forumID?: string; +}; + +export type GetWantAPIComment = { + commentID: number; + date: string; + avatarID: string; + avatarName: string; + text: string; + forumID: string; + essayID: number; +}; diff --git a/taehui-fe/src/utilities/Utility.ts b/taehui-fe/src/utilities/Utility.ts new file mode 100644 index 0000000..0fa4542 --- /dev/null +++ b/taehui-fe/src/utilities/Utility.ts @@ -0,0 +1,52 @@ +import { useTranslations } from "next-intl"; + +export const getHitTexts = (text: string) => { + const pathBefore = window.location.href.substring( + 0, + window.location.href.lastIndexOf("/"), + ); + const textHtml = new DOMParser().parseFromString(text, "text/html"); + return Array.from(textHtml.getElementsByTagName("a")) + .filter(({ href }) => href.startsWith(pathBefore)) + .map(({ href }) => href.substring(href.lastIndexOf("/") + 1)); +}; + +export const tag = ( + t: ReturnType>, + text: string, + hits: { [fileName: string]: number }, + tagClass: string, +) => { + const textHtml = new DOMParser().parseFromString(text, "text/html"); + Array.from(textHtml.getElementsByTagName("img")).forEach((tag) => { + const src = tag.getAttribute("src"); + if (src?.includes("/") === false) { + tag.src = `/www/file/${src}`; + tag.className = tagClass; + } + }); + Array.from(textHtml.getElementsByTagName("audio")).forEach((tag) => { + const src = tag.getAttribute("src"); + if (src?.includes("/") === false) { + tag.src = `/www/file/${src}`; + tag.className = tagClass; + } + }); + Array.from(textHtml.getElementsByTagName("video")).forEach((tag) => { + const src = tag.getAttribute("src"); + if (src?.includes("/") === false) { + tag.src = `/www/file/${src}`; + tag.className = tagClass; + } + }); + Array.from(textHtml.getElementsByTagName("a")).forEach((tag) => { + const href = tag.getAttribute("href"); + if (href?.includes("/") === false) { + tag.href = `/www/file/${href}`; + if (hits[href] >= 0) { + tag.innerHTML += ` (${t("hitFileCount", { hit: hits[href] })})`; + } + } + }); + return textHtml.body.innerHTML; +}; diff --git a/taehui-fe/src/utilities/wwwAPI.ts b/taehui-fe/src/utilities/wwwAPI.ts new file mode 100644 index 0000000..01912b3 --- /dev/null +++ b/taehui-fe/src/utilities/wwwAPI.ts @@ -0,0 +1,29 @@ +import axios, { AxiosError, isAxiosError } from "axios"; +import { toast } from "react-toastify"; + +export const wwwAPI = axios.create({ + baseURL: "/www", +}); + +wwwAPI.interceptors.response.use( + (value) => value, + (e: AxiosError) => { + switch (e.response?.status) { + case 401: + toast.error("Unauthorized"); + window.sessionStorage.removeItem("totem"); + break; + case 413: + toast.error("Payload Too Large"); + break; + case 502: + toast.error("Bad Gateway"); + break; + } + + throw e; + }, +); + +export const isClientFault = (e: Error) => + isAxiosError(e) && e.response?.status === 403; diff --git a/taehui-fe/src/want/WantInput.tsx b/taehui-fe/src/want/WantInput.tsx deleted file mode 100644 index dd40adc..0000000 --- a/taehui-fe/src/want/WantInput.tsx +++ /dev/null @@ -1,84 +0,0 @@ -import { ChangeEventHandler, KeyboardEventHandler, useState } from "react"; -import { useTranslation } from "react-i18next"; -import { - Button, - Col, - Dropdown, - DropdownItem, - DropdownMenu, - DropdownToggle, - Input, - Row, -} from "reactstrap"; -import { observer } from "mobx-react-lite"; -import { useTo } from "taehui-ts/fe-utility"; - -import { useTaehuiStore } from "src/Stores"; - -export default observer(() => { - const { wantInput, setWantInput, wantVariety, setWantVariety } = - useTaehuiStore(); - - const [isWantVarietyOpened, setWantVarietyOpened] = useState(false); - - const { t } = useTranslation(); - - const to = useTo(); - - const onWant = () => { - if (wantInput) { - to(`/want/${wantVariety}/${encodeURIComponent(wantInput)}`); - } - }; - - const onInput: ChangeEventHandler = ({ - target: { value }, - }) => { - setWantInput(value); - }; - - const onInputLower: KeyboardEventHandler = ({ key }) => { - if (key === "Enter") { - onWant(); - } - }; - - const onCloseWantVariety = () => { - setWantVarietyOpened(!isWantVarietyOpened); - }; - - const onInputWantVariety = (wantVariety: "essay" | "comment") => () => { - setWantVariety(wantVariety); - }; - - return ( - - - - {t(wantVariety)} - - - {t("essay")} - - - {t("comment")} - - - - - - - - - - - - ); -}); diff --git a/taehui-fe/src/want/WantView.tsx b/taehui-fe/src/want/WantView.tsx deleted file mode 100644 index a28d61b..0000000 --- a/taehui-fe/src/want/WantView.tsx +++ /dev/null @@ -1,80 +0,0 @@ -import { useTranslation } from "react-i18next"; -import { useParams } from "react-router-dom"; -import { Col, ListGroup, ListGroupItemHeading, Row } from "reactstrap"; -import InfiniteScroll from "react-infinite-scroll-component"; - -import { WantViewLoading } from "src/Loading"; -import EssayTitleView from "src/forum/EssayTitleView"; -import WantInput from "src/want/WantInput"; -import CommentTitleView from "src/forum/CommentTitleView"; -import { GetWantAPIComment, GetWantAPIEssay } from "src/wwwAPI"; -import useGetWant from "src/want/useGetWant"; - -const WantView = () => { - const { t } = useTranslation(); - - type WantViewParams = { - wantVariety: "essay" | "comment"; - wantInput: string; - }; - const { wantVariety, wantInput } = - useParams() as WantViewParams; - - const { - fetchNextPage, - hasNextPage, - data: { pages }, - isFetched: isWantLoaded, - } = useGetWant(wantVariety, wantInput); - - return ( - <> - -
- {isWantLoaded ? ( - - - - {t("wantView")} - fetchNextPage()} - hasMore={hasNextPage} - loader={null} - > - {wantVariety === "essay" && - (pages as GetWantAPIEssay[]).flatMap((wantedEssayTitle) => { - return ( - - ); - })} - {wantVariety === "comment" && - (pages as GetWantAPIComment[]).flatMap( - (wantedCommentTitle) => { - return ( - - ); - }, - )} - - - - - ) : ( - - )} - - ); -}; - -export default WantView; diff --git a/taehui-fe/src/want/useGetWant.ts b/taehui-fe/src/want/useGetWant.ts deleted file mode 100644 index 6dbeab0..0000000 --- a/taehui-fe/src/want/useGetWant.ts +++ /dev/null @@ -1,31 +0,0 @@ -import { useInfiniteQuery } from "@tanstack/react-query"; - -import { wwwAXIOS } from "src/Www"; -import { GetWantAPIComment, GetWantAPIEssay } from "src/wwwAPI"; - -export default function useGetWant( - wantVariety: "essay" | "comment", - wantInput: string, -) { - return useInfiniteQuery({ - queryKey: ["want", wantVariety, wantInput], - queryFn: async ({ pageParam }) => { - const { data } = await wwwAXIOS.get< - (GetWantAPIEssay | GetWantAPIComment)[] - >(`/want/${wantVariety}/${wantInput}/${pageParam}`); - return data; - }, - initialPageParam: 1, - initialData: { - pages: [], - pageParams: [1], - }, - getNextPageParam: (lastPage, allPages, lastPageParam) => { - return !lastPage || lastPage.length > 0 ? lastPageParam + 1 : undefined; - }, - select: (data) => ({ - pages: data.pages.flatMap((page) => page), - pageParams: data.pageParams, - }), - }); -} diff --git a/taehui-fe/src/withTotem.tsx b/taehui-fe/src/withTotem.tsx deleted file mode 100644 index cf2e760..0000000 --- a/taehui-fe/src/withTotem.tsx +++ /dev/null @@ -1,17 +0,0 @@ -import { observer } from "mobx-react-lite"; - -import { useAvatarStore } from "src/Stores"; - -import type { FC } from "react"; - -export default function withTotem(Component: FC) { - return observer((props: T) => { - const { totem } = useAvatarStore(); - - if (!totem) { - return null; - } - - return ; - }); -} diff --git a/taehui-fe/src/wwwAPI.d.ts b/taehui-fe/src/wwwAPI.d.ts deleted file mode 100644 index 5327724..0000000 --- a/taehui-fe/src/wwwAPI.d.ts +++ /dev/null @@ -1,110 +0,0 @@ -export type GetCommentaryAPI = { - commentaryID: number; - avatarName: string; - text: string; - date: string; -}[]; - -export type GetEssayAPI = { - forumTitle: string; - title: string; - text: string; - date: string; - avatarID: string; - avatarName: string; - hitCount: number; - essayBefore: EssayAPIEssay; - essayLater: EssayAPIEssay; -}; - -export type EssayAPIEssay = { - essayID: number; - avatarID: string; - avatarName: string; - date: string; - title: string; - commentCount: number; - hitCount: number; - essayBefore?: Essay; - essayLater?: Essay; -}; - -export type GetCommentAPI = { - commentID: number; - date: string; - avatarID: string; - avatarName: string; - text: string; - comments: GetCommentAPI[number][]; -}[]; - -export type GetForumAPI = { - title: string; - text: string; - essays: EssayAPIEssay[]; - essayCount: number; - level: number; -}; - -export type GetAutoEssayAPI = { - autoEssayID: number; - date: string; - title: string; - text: string; -}[]; - -export type GetForumsAPI = { - forumID: string; - title: string; - essays: EssayAPIEssay[]; -}[]; - -export type GetLatestAvatarAPI = { - avatarID: string; - avatarName: string; - date: string; -}[][]; - -export type GetLatestCommentAPI = { - commentID: number; - date: string; - avatarID: string; - avatarName: string; - text: string; - forumID: string; - essayID: number; -}[]; - -export type GetLatestEssayAPI = { - essayID: number; - avatarID: string; - avatarName: string; - date: string; - title: string; - commentCount: number; - hitCount: number; - forumTitle?: string; - forumID?: string; -}[]; - -export type GetWantAPIEssay = { - essayID: number; - avatarID: string; - avatarName: string; - date: string; - title: string; - commentCount: number; - hitCount: number; - forumTitle?: string; - forumID?: string; -}; - -export type GetWantAPIComment = { - commentID: number; - date: string; - avatarID: string; - avatarName: string; - text: string; - forumID: string; - essayID: number; -}; diff --git a/taehui-fe/tsconfig.json b/taehui-fe/tsconfig.json index a2fa134..002d44f 100644 --- a/taehui-fe/tsconfig.json +++ b/taehui-fe/tsconfig.json @@ -4,17 +4,24 @@ "lib": ["dom", "dom.iterable", "esnext"], "allowJs": true, "skipLibCheck": true, - "esModuleInterop": true, - "allowSyntheticDefaultImports": true, "strict": true, - "forceConsistentCasingInFileNames": true, - "noFallthroughCasesInSwitch": true, + "noEmit": true, + "esModuleInterop": true, "module": "esnext", - "moduleResolution": "node", + "moduleResolution": "bundler", "resolveJsonModule": true, "isolatedModules": true, - "noEmit": true, - "jsx": "react-jsx", - "baseUrl": "." - } + "jsx": "preserve", + "incremental": true, + "plugins": [ + { + "name": "next" + } + ], + "paths": { + "@/*": ["./src/*"] + } + }, + "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts"], + "exclude": ["node_modules"], } diff --git a/taehui-ts/package.json b/taehui-ts/package.json index f69e86e..d14245e 100644 --- a/taehui-ts/package.json +++ b/taehui-ts/package.json @@ -4,7 +4,7 @@ "private": true, "exports": { "./date": "./build/date.js", - "./fe-utility": "./build/fe-utility.js", + "./fe-utilities": "./build/fe-utilities.js", "./language": "./build/language.js" }, "typesVersions": { @@ -12,8 +12,8 @@ "date": [ "./build/date.d.ts" ], - "fe-utility": [ - "./build/fe-utility.d.ts" + "fe-utilities": [ + "./build/fe-utilities.d.ts" ], "language": [ "./build/language.d.ts" diff --git a/taehui-ts/rollup.config.mjs b/taehui-ts/rollup.config.mjs index f4756f2..307454e 100644 --- a/taehui-ts/rollup.config.mjs +++ b/taehui-ts/rollup.config.mjs @@ -3,7 +3,7 @@ export default defineConfig({ external: ["dayjs", "next", "next-intl", "qs", "react"], - input: ["src/date.ts", "src/language.ts", "src/fe-utility.ts"], + input: ["src/date.ts", "src/language.ts", "src/fe-utilities.ts"], plugins: [ typescript({ compilerOptions: { diff --git a/taehui-ts/src/fe-utilities.ts b/taehui-ts/src/fe-utilities.ts new file mode 100644 index 0000000..ea39158 --- /dev/null +++ b/taehui-ts/src/fe-utilities.ts @@ -0,0 +1,105 @@ +import { useLocale } from "next-intl"; +import { + useParams, + usePathname, + useRouter, + useSearchParams, +} from "next/navigation"; +import { parse, stringify } from "qs"; +import { useCallback, useEffect, useState } from "react"; +import urlcat from "urlcat"; + +export function useWindowArea() { + const [windowLength, setWindowLength] = useState( + typeof window === "object" ? window.innerWidth : 0, + ); + const [windowHeight, setWindowHeight] = useState( + typeof window === "object" ? window.innerHeight : 0, + ); + + useEffect(() => { + const onModified = () => { + setWindowLength(window.innerWidth); + setWindowHeight(window.innerHeight); + }; + + window.addEventListener("resize", onModified); + + return () => { + window.removeEventListener("resize", onModified); + }; + }, []); + + return { windowLength, windowHeight }; +} + +export function useTo() { + const { push } = useRouter(); + + return useCallback( + (pathname: string, search = "") => push(urlcat(pathname, parse(search))), + [push], + ); +} + +export function useParam(text: string, defaultValue: string) { + const to = useTo(); + const searchParams = useSearchParams(); + const param = searchParams.get(text) ?? defaultValue; + + const pathname = usePathname(); + + return { + param, + setParam: useCallback( + (param: string) => { + to(pathname, stringify({ ...searchParams.entries(), [text]: param })); + }, + [pathname, searchParams, text, to], + ), + }; +} + +export function useIntParam(text: string, defaultValue: number) { + const { param, setParam } = useParam(text, defaultValue.toString()); + + return { + param: Number(param), + setParam: useCallback( + (param: number) => { + setParam(param.toString()); + }, + [setParam], + ), + }; +} + +export function useWant(route: string) { + const to = useTo(); + const { want = [""] } = useParams<{ want: string[] }>(); + + return { + want: want[0], + setWant: useCallback( + (want: string) => { + to(route + "/" + want); + }, + [to, route], + ), + }; +} + +export function useIsPath() { + const pathname = usePathname(); + const locale = useLocale(); + + return useCallback( + (route: string, equals = false) => { + const routeLanguage = `/${locale}${route}`; + return equals + ? pathname === routeLanguage + : pathname.startsWith(routeLanguage); + }, + [locale, pathname], + ); +} diff --git a/taehui-ts/src/fe-utility.ts b/taehui-ts/src/fe-utility.ts deleted file mode 100644 index 49e9c6a..0000000 --- a/taehui-ts/src/fe-utility.ts +++ /dev/null @@ -1,100 +0,0 @@ -import { useLocale } from "next-intl"; -import { - useParams, - usePathname, - useRouter, - useSearchParams, -} from "next/navigation"; -import { parse, stringify } from "qs"; -import { useCallback, useEffect, useState } from "react"; -import urlcat from "urlcat"; - -export function useWindowArea() { - const [windowLength, setWindowLength] = useState( - typeof window === "object" ? window.innerWidth : 0, - ); - const [windowHeight, setWindowHeight] = useState( - typeof window === "object" ? window.innerHeight : 0, - ); - - useEffect(() => { - const onModified = () => { - setWindowLength(window.innerWidth); - setWindowHeight(window.innerHeight); - }; - - window.addEventListener("resize", onModified); - - return () => { - window.removeEventListener("resize", onModified); - }; - }, []); - - return { windowLength, windowHeight }; -} - -export function useTo() { - const { push } = useRouter(); - - return useCallback( - (pathname: string, search = "") => push(urlcat(pathname, parse(search))), - [push], - ); -} - -export function useParam(text: string, defaultValue: string) { - const to = useTo(); - const searchParams = useSearchParams(); - const param = searchParams.get(text) ?? defaultValue; - - const pathname = usePathname(); - - return { - param, - setParam: useCallback( - (param: string) => { - to(pathname, stringify({ ...searchParams.entries(), [text]: param })); - }, - [pathname, searchParams, text, to], - ), - }; -} - -export function useIntParam(text: string, defaultValue: number) { - const { param, setParam } = useParam(text, defaultValue.toString()); - - return { - param: Number(param), - setParam: useCallback( - (param: number) => { - setParam(param.toString()); - }, - [setParam], - ), - }; -} - -export function useWant(route: string) { - const to = useTo(); - const { want = [] } = useParams(); - - return { - want: want[0] ?? "", - setWant: useCallback( - (want: string) => { - to(route + "/" + want); - }, - [to, route], - ), - }; -} - -export function useIsPath() { - const pathname = usePathname(); - const locale = useLocale(); - - return useCallback( - (route: string) => pathname.startsWith(`/${locale}${route}`), - [locale, pathname], - ); -} diff --git a/taehui-ts/tsconfig.json b/taehui-ts/tsconfig.json index 98a07d0..939fdc1 100644 --- a/taehui-ts/tsconfig.json +++ b/taehui-ts/tsconfig.json @@ -26,13 +26,13 @@ /* Modules */ "module": "Node16", /* Specify what module code is generated. */ - // "rootDir": "./", /* Specify the root folder within your source files. */ + // "rootDir": "./", /* Specify the main folder within your source files. */ "moduleResolution": "Node16", /* Specify how TypeScript looks up a file from a given module specifier. */ // "baseUrl": "./", /* Specify the base directory to resolve non-relative module names. */ // "paths": {}, /* Specify a set of entries that re-map imports to additional lookup locations. */ // "rootDirs": [], /* Allow multiple folders to be treated as one when resolving modules. */ - // "typeRoots": [], /* Specify multiple folders that act like './node_modules/@types'. */ - // "types": [], /* Specify type package names to be included without being referenced in a source file. */ + // "typeRoots": [], /* Specify multiple folders that act like './node_modules/@type'. */ + // "type": [], /* Specify type package names to be included without being referenced in a source file. */ // "allowUmdGlobalAccess": true, /* Allow accessing UMD globals from modules. */ // "moduleSuffixes": [], /* List of file name suffixes to search when resolving a module. */ // "allowImportingTsExtensions": true, /* Allow imports to include TypeScript file extensions. Requires '--moduleResolution bundler' and either '--noEmit' or '--emitDeclarationOnly' to be set. */ @@ -59,9 +59,9 @@ // "removeComments": true, /* Disable emitting comments. */ // "noEmit": true, /* Disable emitting files from a compilation. */ // "importHelpers": true, /* Allow importing helper functions from tslib once per project, instead of including them per-file. */ - // "importsNotUsedAsValues": "remove", /* Specify emit/checking behavior for imports that are only used for types. */ + // "importsNotUsedAsValues": "remove", /* Specify emit/checking behavior for imports that are only used for type. */ // "downlevelIteration": true, /* Emit more compliant, but verbose and less performant JavaScript for iteration. */ - // "sourceRoot": "", /* Specify the root path for debuggers to find the reference source code. */ + // "sourceRoot": "", /* Specify the main path for debuggers to find the reference source code. */ // "mapRoot": "", /* Specify the location where debugger should locate map files instead of generated locations. */ // "inlineSources": true, /* Include source code in the sourcemaps inside the emitted JavaScript. */ // "emitBOM": true, /* Emit a UTF-8 Byte Order Mark (BOM) in the beginning of output files. */ @@ -93,7 +93,7 @@ // "alwaysStrict": true, /* Ensure 'use strict' is always emitted. */ // "noUnusedLocals": true, /* Enable error reporting when local variables aren't read. */ // "noUnusedParameters": true, /* Raise an error when a function parameter isn't read. */ - // "exactOptionalPropertyTypes": true, /* Interpret optional property types as written, rather than adding 'undefined'. */ + // "exactOptionalPropertyTypes": true, /* Interpret optional property type as written, rather than adding 'undefined'. */ // "noImplicitReturns": true, /* Enable error reporting for codepaths that do not explicitly return in a function. */ // "noFallthroughCasesInSwitch": true, /* Enable error reporting for fallthrough cases in switch statements. */ // "noUncheckedIndexedAccess": true, /* Add 'undefined' to a type when accessed using an index. */ diff --git a/taehui-www/ecosystem.config.js b/taehui-www/ecosystem.config.js index fd87433..ce082ee 100644 --- a/taehui-www/ecosystem.config.js +++ b/taehui-www/ecosystem.config.js @@ -1,7 +1,7 @@ module.exports = { apps: [ { - name: "taehui", + name: "root", script: ".", instances: "max", exec_mode: "cluster", diff --git a/taehui-www/tsconfig.json b/taehui-www/tsconfig.json index fd92ab7..74ab1dc 100644 --- a/taehui-www/tsconfig.json +++ b/taehui-www/tsconfig.json @@ -26,13 +26,13 @@ /* Modules */ "module": "commonjs", /* Specify what module code is generated. */ - // "rootDir": "./", /* Specify the root folder within your source files. */ + // "rootDir": "./", /* Specify the main folder within your source files. */ // "moduleResolution": "node10", /* Specify how TypeScript looks up a file from a given module specifier. */ // "baseUrl": "./", /* Specify the base directory to resolve non-relative module names. */ // "paths": {}, /* Specify a set of entries that re-map imports to additional lookup locations. */ // "rootDirs": [], /* Allow multiple folders to be treated as one when resolving modules. */ - // "typeRoots": [], /* Specify multiple folders that act like './node_modules/@types'. */ - // "types": [], /* Specify type package names to be included without being referenced in a source file. */ + // "typeRoots": [], /* Specify multiple folders that act like './node_modules/@type'. */ + // "type": [], /* Specify type package names to be included without being referenced in a source file. */ // "allowUmdGlobalAccess": true, /* Allow accessing UMD globals from modules. */ // "moduleSuffixes": [], /* List of file name suffixes to search when resolving a module. */ // "allowImportingTsExtensions": true, /* Allow imports to include TypeScript file extensions. Requires '--moduleResolution bundler' and either '--noEmit' or '--emitDeclarationOnly' to be set. */ @@ -59,9 +59,9 @@ // "removeComments": true, /* Disable emitting comments. */ // "noEmit": true, /* Disable emitting files from a compilation. */ // "importHelpers": true, /* Allow importing helper functions from tslib once per project, instead of including them per-file. */ - // "importsNotUsedAsValues": "remove", /* Specify emit/checking behavior for imports that are only used for types. */ + // "importsNotUsedAsValues": "remove", /* Specify emit/checking behavior for imports that are only used for type. */ // "downlevelIteration": true, /* Emit more compliant, but verbose and less performant JavaScript for iteration. */ - // "sourceRoot": "", /* Specify the root path for debuggers to find the reference source code. */ + // "sourceRoot": "", /* Specify the main path for debuggers to find the reference source code. */ // "mapRoot": "", /* Specify the location where debugger should locate map files instead of generated locations. */ // "inlineSources": true, /* Include source code in the sourcemaps inside the emitted JavaScript. */ // "emitBOM": true, /* Emit a UTF-8 Byte Order Mark (BOM) in the beginning of output files. */ @@ -93,7 +93,7 @@ // "alwaysStrict": true, /* Ensure 'use strict' is always emitted. */ // "noUnusedLocals": true, /* Enable error reporting when local variables aren't read. */ // "noUnusedParameters": true, /* Raise an error when a function parameter isn't read. */ - // "exactOptionalPropertyTypes": true, /* Interpret optional property types as written, rather than adding 'undefined'. */ + // "exactOptionalPropertyTypes": true, /* Interpret optional property type as written, rather than adding 'undefined'. */ // "noImplicitReturns": true, /* Enable error reporting for codepaths that do not explicitly return in a function. */ // "noFallthroughCasesInSwitch": true, /* Enable error reporting for fallthrough cases in switch statements. */ // "noUncheckedIndexedAccess": true, /* Add 'undefined' to a type when accessed using an index. */ diff --git a/turbo.json b/turbo.json index e70f635..394d90b 100644 --- a/turbo.json +++ b/turbo.json @@ -1,7 +1,7 @@ { "$schema": "https://turbo.build/schema.json", "pipeline": { - "start": { + "dev": { "dependsOn": [ "build:taehui-ts" ] @@ -16,7 +16,7 @@ "^build" ], "outputs": [ - "build/**" + ".next/**" ] }, "deploy": {