diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 4a92bce..63470e5 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -50,7 +50,7 @@ importers: version: 9.29.0 '@feature-sliced/eslint-config': specifier: ^0.1.1 - version: 0.1.1(eslint-plugin-boundaries@5.0.1(@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1))(eslint-plugin-import@2.32.0) + version: 0.1.1(eslint-plugin-boundaries@5.0.1(@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1))(eslint-plugin-import@2.32.0) '@types/node': specifier: ^24.0.3 version: 24.0.3 @@ -65,13 +65,13 @@ importers: version: 5.3.3 '@typescript-eslint/eslint-plugin': specifier: ^8.34.1 - version: 8.34.1(@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3) + version: 8.35.0(@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3) '@typescript-eslint/parser': specifier: ^8.34.1 - version: 8.34.1(eslint@8.57.1)(typescript@5.8.3) + version: 8.35.0(eslint@8.57.1)(typescript@5.8.3) '@vitejs/plugin-react': specifier: ^4.4.1 - version: 4.5.2(vite@6.3.5(@types/node@24.0.3)(jiti@2.4.2)(tsx@4.20.3)(yaml@2.8.0)) + version: 4.6.0(vite@6.3.5(@types/node@24.0.3)(jiti@2.4.2)(tsx@4.20.3)(yaml@2.8.0)) eslint: specifier: ^8.57.1 version: 8.57.1 @@ -83,10 +83,10 @@ importers: version: 4.4.3(eslint-plugin-import@2.32.0)(eslint@8.57.1) eslint-plugin-boundaries: specifier: ^5.0.1 - version: 5.0.1(@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1) + version: 5.0.1(@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1) eslint-plugin-import: specifier: ^2.32.0 - version: 2.32.0(@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1) + version: 2.32.0(@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1) eslint-plugin-jsx-a11y: specifier: ^6.10.2 version: 6.10.2(eslint@8.57.1) @@ -113,7 +113,7 @@ importers: version: 1.2.1 prettier: specifier: ^3.5.3 - version: 3.5.3 + version: 3.6.0 tsx: specifier: ^4.20.3 version: 4.20.3 @@ -122,7 +122,7 @@ importers: version: 5.8.3 typescript-eslint: specifier: ^8.30.1 - version: 8.34.1(eslint@8.57.1)(typescript@5.8.3) + version: 8.35.0(eslint@8.57.1)(typescript@5.8.3) vite: specifier: ^6.3.5 version: 6.3.5(@types/node@24.0.3)(jiti@2.4.2)(tsx@4.20.3)(yaml@2.8.0) @@ -915,8 +915,8 @@ packages: '@protobufjs/utf8@1.1.0': resolution: {integrity: sha512-Vvn3zZrhQZkkBE8LSuW3em98c0FwgO4nxzv6OdSxPKJIEKY2bGbHn+mhGIPerzI4twdxaP8/0+06HBpwf345Lw==} - '@rolldown/pluginutils@1.0.0-beta.11': - resolution: {integrity: sha512-L/gAA/hyCSuzTF1ftlzUSI/IKr2POHsv1Dd78GfqkR83KMNuswWD61JxGV2L7nRwBBBSDr6R1gCkdTmoN7W4ag==} + '@rolldown/pluginutils@1.0.0-beta.19': + resolution: {integrity: sha512-3FL3mnMbPu0muGOCaKAhhFEYmqv9eTfPSJRJmANrCwtgK8VuxpsZDGK+m0LYAGoyO8+0j5uRe4PeyPDK1yA/hA==} '@rollup/rollup-android-arm-eabi@4.44.0': resolution: {integrity: sha512-xEiEE5oDW6tK4jXCAyliuntGR+amEMO7HLtdSshVuhFnKTYoeYMyXQK7pLouAJJj5KHdwdn87bfHAR2nSdNAUA==} @@ -1084,63 +1084,63 @@ packages: '@types/react@19.1.8': resolution: {integrity: sha512-AwAfQ2Wa5bCx9WP8nZL2uMZWod7J7/JSplxbTmBQ5ms6QpqNYm672H0Vu9ZVKVngQ+ii4R/byguVEUZQyeg44g==} - '@typescript-eslint/eslint-plugin@8.34.1': - resolution: {integrity: sha512-STXcN6ebF6li4PxwNeFnqF8/2BNDvBupf2OPx2yWNzr6mKNGF7q49VM00Pz5FaomJyqvbXpY6PhO+T9w139YEQ==} + '@typescript-eslint/eslint-plugin@8.35.0': + resolution: {integrity: sha512-ijItUYaiWuce0N1SoSMrEd0b6b6lYkYt99pqCPfybd+HKVXtEvYhICfLdwp42MhiI5mp0oq7PKEL+g1cNiz/Eg==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - '@typescript-eslint/parser': ^8.34.1 + '@typescript-eslint/parser': ^8.35.0 eslint: ^8.57.0 || ^9.0.0 typescript: '>=4.8.4 <5.9.0' - '@typescript-eslint/parser@8.34.1': - resolution: {integrity: sha512-4O3idHxhyzjClSMJ0a29AcoK0+YwnEqzI6oz3vlRf3xw0zbzt15MzXwItOlnr5nIth6zlY2RENLsOPvhyrKAQA==} + '@typescript-eslint/parser@8.35.0': + resolution: {integrity: sha512-6sMvZePQrnZH2/cJkwRpkT7DxoAWh+g6+GFRK6bV3YQo7ogi3SX5rgF6099r5Q53Ma5qeT7LGmOmuIutF4t3lA==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 typescript: '>=4.8.4 <5.9.0' - '@typescript-eslint/project-service@8.34.1': - resolution: {integrity: sha512-nuHlOmFZfuRwLJKDGQOVc0xnQrAmuq1Mj/ISou5044y1ajGNp2BNliIqp7F2LPQ5sForz8lempMFCovfeS1XoA==} + '@typescript-eslint/project-service@8.35.0': + resolution: {integrity: sha512-41xatqRwWZuhUMF/aZm2fcUsOFKNcG28xqRSS6ZVr9BVJtGExosLAm5A1OxTjRMagx8nJqva+P5zNIGt8RIgbQ==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: typescript: '>=4.8.4 <5.9.0' - '@typescript-eslint/scope-manager@8.34.1': - resolution: {integrity: sha512-beu6o6QY4hJAgL1E8RaXNC071G4Kso2MGmJskCFQhRhg8VOH/FDbC8soP8NHN7e/Hdphwp8G8cE6OBzC8o41ZA==} + '@typescript-eslint/scope-manager@8.35.0': + resolution: {integrity: sha512-+AgL5+mcoLxl1vGjwNfiWq5fLDZM1TmTPYs2UkyHfFhgERxBbqHlNjRzhThJqz+ktBqTChRYY6zwbMwy0591AA==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - '@typescript-eslint/tsconfig-utils@8.34.1': - resolution: {integrity: sha512-K4Sjdo4/xF9NEeA2khOb7Y5nY6NSXBnod87uniVYW9kHP+hNlDV8trUSFeynA2uxWam4gIWgWoygPrv9VMWrYg==} + '@typescript-eslint/tsconfig-utils@8.35.0': + resolution: {integrity: sha512-04k/7247kZzFraweuEirmvUj+W3bJLI9fX6fbo1Qm2YykuBvEhRTPl8tcxlYO8kZZW+HIXfkZNoasVb8EV4jpA==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: typescript: '>=4.8.4 <5.9.0' - '@typescript-eslint/type-utils@8.34.1': - resolution: {integrity: sha512-Tv7tCCr6e5m8hP4+xFugcrwTOucB8lshffJ6zf1mF1TbU67R+ntCc6DzLNKM+s/uzDyv8gLq7tufaAhIBYeV8g==} + '@typescript-eslint/type-utils@8.35.0': + resolution: {integrity: sha512-ceNNttjfmSEoM9PW87bWLDEIaLAyR+E6BoYJQ5PfaDau37UGca9Nyq3lBk8Bw2ad0AKvYabz6wxc7DMTO2jnNA==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 typescript: '>=4.8.4 <5.9.0' - '@typescript-eslint/types@8.34.1': - resolution: {integrity: sha512-rjLVbmE7HR18kDsjNIZQHxmv9RZwlgzavryL5Lnj2ujIRTeXlKtILHgRNmQ3j4daw7zd+mQgy+uyt6Zo6I0IGA==} + '@typescript-eslint/types@8.35.0': + resolution: {integrity: sha512-0mYH3emanku0vHw2aRLNGqe7EXh9WHEhi7kZzscrMDf6IIRUQ5Jk4wp1QrledE/36KtdZrVfKnE32eZCf/vaVQ==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - '@typescript-eslint/typescript-estree@8.34.1': - resolution: {integrity: sha512-rjCNqqYPuMUF5ODD+hWBNmOitjBWghkGKJg6hiCHzUvXRy6rK22Jd3rwbP2Xi+R7oYVvIKhokHVhH41BxPV5mA==} + '@typescript-eslint/typescript-estree@8.35.0': + resolution: {integrity: sha512-F+BhnaBemgu1Qf8oHrxyw14wq6vbL8xwWKKMwTMwYIRmFFY/1n/9T/jpbobZL8vp7QyEUcC6xGrnAO4ua8Kp7w==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: typescript: '>=4.8.4 <5.9.0' - '@typescript-eslint/utils@8.34.1': - resolution: {integrity: sha512-mqOwUdZ3KjtGk7xJJnLbHxTuWVn3GO2WZZuM+Slhkun4+qthLdXx32C8xIXbO1kfCECb3jIs3eoxK3eryk7aoQ==} + '@typescript-eslint/utils@8.35.0': + resolution: {integrity: sha512-nqoMu7WWM7ki5tPgLVsmPM8CkqtoPUG6xXGeefM5t4x3XumOEKMoUZPdi+7F+/EotukN4R9OWdmDxN80fqoZeg==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 typescript: '>=4.8.4 <5.9.0' - '@typescript-eslint/visitor-keys@8.34.1': - resolution: {integrity: sha512-xoh5rJ+tgsRKoXnkBPFRLZ7rjKM0AfVbC68UZ/ECXoDbfggb9RbEySN359acY1vS3qZ0jVTVWzbtfapwm5ztxw==} + '@typescript-eslint/visitor-keys@8.35.0': + resolution: {integrity: sha512-zTh2+1Y8ZpmeQaQVIc/ZZxsx8UzgKJyNg1PTvjzC7WMhPSVS8bfDX34k1SrwOf016qd5RU3az2UxUNue3IfQ5g==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} '@ungap/structured-clone@1.3.0': @@ -1241,8 +1241,8 @@ packages: cpu: [x64] os: [win32] - '@vitejs/plugin-react@4.5.2': - resolution: {integrity: sha512-QNVT3/Lxx99nMQWJWF7K4N6apUEuT0KlZA3mx/mVaoGj3smm/8rc8ezz15J1pcbcjDK0V15rpHetVfya08r76Q==} + '@vitejs/plugin-react@4.6.0': + resolution: {integrity: sha512-5Kgff+m8e2PB+9j51eGHEpn5kUzRKH2Ry0qGoe8ItJg7pqnkPrYPkDQZGgGmTa0EGarHrkjLvOdU3b1fzI8otQ==} engines: {node: ^14.18.0 || >=16.0.0} peerDependencies: vite: ^4.2.0 || ^5.0.0 || ^6.0.0 || ^7.0.0-beta.0 @@ -1550,8 +1550,8 @@ packages: resolution: {integrity: sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==} engines: {node: '>= 0.4'} - electron-to-chromium@1.5.171: - resolution: {integrity: sha512-scWpzXEJEMrGJa4Y6m/tVotb0WuvNmasv3wWVzUAeCgKU0ToFOhUW6Z+xWnRQANMYGxN4ngJXIThgBJOqzVPCQ==} + electron-to-chromium@1.5.172: + resolution: {integrity: sha512-fnKW9dGgmBfsebbYognQSv0CGGLFH1a5iV9EDYTBwmAQn+whbzHbLFlC+3XbHc8xaNtpO0etm8LOcRXs1qMRkQ==} emoji-regex@10.4.0: resolution: {integrity: sha512-EC+0oUMY1Rqm4O6LLrgjtYDvcVYTy7chDnM4Q7030tP4Kwj3u/pR6gP9ygnp2CJMK5Gq+9Q2oqmrFJAz01DXjw==} @@ -2445,8 +2445,8 @@ packages: resolution: {integrity: sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==} engines: {node: '>= 0.8.0'} - prettier@3.5.3: - resolution: {integrity: sha512-QQtaxnoDJeAkDvDKWCLiwIXkTgRhwYDEQCghU9Z6q03iyek/rxRh/2lC3HB7P8sWT2xC/y5JDctPLBIGzHKbhw==} + prettier@3.6.0: + resolution: {integrity: sha512-ujSB9uXHJKzM/2GBuE0hBOUgC77CN3Bnpqa+g80bkv3T3A93wL/xlzDATHhnhkzifz/UE2SNOvmbTz5hSkDlHw==} engines: {node: '>=14'} hasBin: true @@ -2788,8 +2788,8 @@ packages: resolution: {integrity: sha512-3KS2b+kL7fsuk/eJZ7EQdnEmQoaho/r6KUef7hxvltNA5DR8NAUM+8wJMbJyZ4G9/7i3v5zPBIMN5aybAh2/Jg==} engines: {node: '>= 0.4'} - typescript-eslint@8.34.1: - resolution: {integrity: sha512-XjS+b6Vg9oT1BaIUfkW3M3LvqZE++rbzAMEHuccCfO/YkP43ha6w3jTEMilQxMF92nVOYCcdjv1ZUhAa1D/0ow==} + typescript-eslint@8.35.0: + resolution: {integrity: sha512-uEnz70b7kBz6eg/j0Czy6K5NivaYopgxRjsnAJ2Fx5oTLo3wefTHIbL7AkQr1+7tJCRVpTs/wiM8JR/11Loq9A==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 @@ -3392,10 +3392,10 @@ snapshots: '@eslint/js@9.29.0': {} - '@feature-sliced/eslint-config@0.1.1(eslint-plugin-boundaries@5.0.1(@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1))(eslint-plugin-import@2.32.0)': + '@feature-sliced/eslint-config@0.1.1(eslint-plugin-boundaries@5.0.1(@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1))(eslint-plugin-import@2.32.0)': dependencies: - eslint-plugin-boundaries: 5.0.1(@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1) - eslint-plugin-import: 2.32.0(@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1) + eslint-plugin-boundaries: 5.0.1(@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1) + eslint-plugin-import: 2.32.0(@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1) '@firebase/ai@1.4.0(@firebase/app-types@0.9.3)(@firebase/app@0.13.1)': dependencies: @@ -3887,7 +3887,7 @@ snapshots: '@protobufjs/utf8@1.1.0': {} - '@rolldown/pluginutils@1.0.0-beta.11': {} + '@rolldown/pluginutils@1.0.0-beta.19': {} '@rollup/rollup-android-arm-eabi@4.44.0': optional: true @@ -4025,14 +4025,14 @@ snapshots: dependencies: csstype: 3.1.3 - '@typescript-eslint/eslint-plugin@8.34.1(@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3)': + '@typescript-eslint/eslint-plugin@8.35.0(@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3)': dependencies: '@eslint-community/regexpp': 4.12.1 - '@typescript-eslint/parser': 8.34.1(eslint@8.57.1)(typescript@5.8.3) - '@typescript-eslint/scope-manager': 8.34.1 - '@typescript-eslint/type-utils': 8.34.1(eslint@8.57.1)(typescript@5.8.3) - '@typescript-eslint/utils': 8.34.1(eslint@8.57.1)(typescript@5.8.3) - '@typescript-eslint/visitor-keys': 8.34.1 + '@typescript-eslint/parser': 8.35.0(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/scope-manager': 8.35.0 + '@typescript-eslint/type-utils': 8.35.0(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/utils': 8.35.0(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/visitor-keys': 8.35.0 eslint: 8.57.1 graphemer: 1.4.0 ignore: 7.0.5 @@ -4042,40 +4042,40 @@ snapshots: transitivePeerDependencies: - supports-color - '@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3)': + '@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3)': dependencies: - '@typescript-eslint/scope-manager': 8.34.1 - '@typescript-eslint/types': 8.34.1 - '@typescript-eslint/typescript-estree': 8.34.1(typescript@5.8.3) - '@typescript-eslint/visitor-keys': 8.34.1 + '@typescript-eslint/scope-manager': 8.35.0 + '@typescript-eslint/types': 8.35.0 + '@typescript-eslint/typescript-estree': 8.35.0(typescript@5.8.3) + '@typescript-eslint/visitor-keys': 8.35.0 debug: 4.4.1 eslint: 8.57.1 typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/project-service@8.34.1(typescript@5.8.3)': + '@typescript-eslint/project-service@8.35.0(typescript@5.8.3)': dependencies: - '@typescript-eslint/tsconfig-utils': 8.34.1(typescript@5.8.3) - '@typescript-eslint/types': 8.34.1 + '@typescript-eslint/tsconfig-utils': 8.35.0(typescript@5.8.3) + '@typescript-eslint/types': 8.35.0 debug: 4.4.1 typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/scope-manager@8.34.1': + '@typescript-eslint/scope-manager@8.35.0': dependencies: - '@typescript-eslint/types': 8.34.1 - '@typescript-eslint/visitor-keys': 8.34.1 + '@typescript-eslint/types': 8.35.0 + '@typescript-eslint/visitor-keys': 8.35.0 - '@typescript-eslint/tsconfig-utils@8.34.1(typescript@5.8.3)': + '@typescript-eslint/tsconfig-utils@8.35.0(typescript@5.8.3)': dependencies: typescript: 5.8.3 - '@typescript-eslint/type-utils@8.34.1(eslint@8.57.1)(typescript@5.8.3)': + '@typescript-eslint/type-utils@8.35.0(eslint@8.57.1)(typescript@5.8.3)': dependencies: - '@typescript-eslint/typescript-estree': 8.34.1(typescript@5.8.3) - '@typescript-eslint/utils': 8.34.1(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/typescript-estree': 8.35.0(typescript@5.8.3) + '@typescript-eslint/utils': 8.35.0(eslint@8.57.1)(typescript@5.8.3) debug: 4.4.1 eslint: 8.57.1 ts-api-utils: 2.1.0(typescript@5.8.3) @@ -4083,14 +4083,14 @@ snapshots: transitivePeerDependencies: - supports-color - '@typescript-eslint/types@8.34.1': {} + '@typescript-eslint/types@8.35.0': {} - '@typescript-eslint/typescript-estree@8.34.1(typescript@5.8.3)': + '@typescript-eslint/typescript-estree@8.35.0(typescript@5.8.3)': dependencies: - '@typescript-eslint/project-service': 8.34.1(typescript@5.8.3) - '@typescript-eslint/tsconfig-utils': 8.34.1(typescript@5.8.3) - '@typescript-eslint/types': 8.34.1 - '@typescript-eslint/visitor-keys': 8.34.1 + '@typescript-eslint/project-service': 8.35.0(typescript@5.8.3) + '@typescript-eslint/tsconfig-utils': 8.35.0(typescript@5.8.3) + '@typescript-eslint/types': 8.35.0 + '@typescript-eslint/visitor-keys': 8.35.0 debug: 4.4.1 fast-glob: 3.3.3 is-glob: 4.0.3 @@ -4101,20 +4101,20 @@ snapshots: transitivePeerDependencies: - supports-color - '@typescript-eslint/utils@8.34.1(eslint@8.57.1)(typescript@5.8.3)': + '@typescript-eslint/utils@8.35.0(eslint@8.57.1)(typescript@5.8.3)': dependencies: '@eslint-community/eslint-utils': 4.7.0(eslint@8.57.1) - '@typescript-eslint/scope-manager': 8.34.1 - '@typescript-eslint/types': 8.34.1 - '@typescript-eslint/typescript-estree': 8.34.1(typescript@5.8.3) + '@typescript-eslint/scope-manager': 8.35.0 + '@typescript-eslint/types': 8.35.0 + '@typescript-eslint/typescript-estree': 8.35.0(typescript@5.8.3) eslint: 8.57.1 typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/visitor-keys@8.34.1': + '@typescript-eslint/visitor-keys@8.35.0': dependencies: - '@typescript-eslint/types': 8.34.1 + '@typescript-eslint/types': 8.35.0 eslint-visitor-keys: 4.2.1 '@ungap/structured-clone@1.3.0': {} @@ -4178,12 +4178,12 @@ snapshots: '@unrs/resolver-binding-win32-x64-msvc@1.9.1': optional: true - '@vitejs/plugin-react@4.5.2(vite@6.3.5(@types/node@24.0.3)(jiti@2.4.2)(tsx@4.20.3)(yaml@2.8.0))': + '@vitejs/plugin-react@4.6.0(vite@6.3.5(@types/node@24.0.3)(jiti@2.4.2)(tsx@4.20.3)(yaml@2.8.0))': dependencies: '@babel/core': 7.27.4 '@babel/plugin-transform-react-jsx-self': 7.27.1(@babel/core@7.27.4) '@babel/plugin-transform-react-jsx-source': 7.27.1(@babel/core@7.27.4) - '@rolldown/pluginutils': 1.0.0-beta.11 + '@rolldown/pluginutils': 1.0.0-beta.19 '@types/babel__core': 7.20.5 react-refresh: 0.17.0 vite: 6.3.5(@types/node@24.0.3)(jiti@2.4.2)(tsx@4.20.3)(yaml@2.8.0) @@ -4338,7 +4338,7 @@ snapshots: browserslist@4.25.0: dependencies: caniuse-lite: 1.0.30001724 - electron-to-chromium: 1.5.171 + electron-to-chromium: 1.5.172 node-releases: 2.0.19 update-browserslist-db: 1.1.3(browserslist@4.25.0) @@ -4524,7 +4524,7 @@ snapshots: es-errors: 1.3.0 gopd: 1.2.0 - electron-to-chromium@1.5.171: {} + electron-to-chromium@1.5.172: {} emoji-regex@10.4.0: {} @@ -4703,38 +4703,38 @@ snapshots: tinyglobby: 0.2.14 unrs-resolver: 1.9.1 optionalDependencies: - eslint-plugin-import: 2.32.0(@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1) + eslint-plugin-import: 2.32.0(@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1) transitivePeerDependencies: - supports-color - eslint-module-utils@2.12.0(@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1): + eslint-module-utils@2.12.0(@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1): dependencies: debug: 3.2.7 optionalDependencies: - '@typescript-eslint/parser': 8.34.1(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/parser': 8.35.0(eslint@8.57.1)(typescript@5.8.3) eslint: 8.57.1 eslint-import-resolver-node: 0.3.9 eslint-import-resolver-typescript: 4.4.3(eslint-plugin-import@2.32.0)(eslint@8.57.1) transitivePeerDependencies: - supports-color - eslint-module-utils@2.12.1(@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1): + eslint-module-utils@2.12.1(@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1): dependencies: debug: 3.2.7 optionalDependencies: - '@typescript-eslint/parser': 8.34.1(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/parser': 8.35.0(eslint@8.57.1)(typescript@5.8.3) eslint: 8.57.1 eslint-import-resolver-node: 0.3.9 eslint-import-resolver-typescript: 4.4.3(eslint-plugin-import@2.32.0)(eslint@8.57.1) transitivePeerDependencies: - supports-color - eslint-plugin-boundaries@5.0.1(@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1): + eslint-plugin-boundaries@5.0.1(@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1): dependencies: chalk: 4.1.2 eslint: 8.57.1 eslint-import-resolver-node: 0.3.9 - eslint-module-utils: 2.12.0(@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1) + eslint-module-utils: 2.12.0(@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1) micromatch: 4.0.8 transitivePeerDependencies: - '@typescript-eslint/parser' @@ -4742,7 +4742,7 @@ snapshots: - eslint-import-resolver-webpack - supports-color - eslint-plugin-import@2.32.0(@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1): + eslint-plugin-import@2.32.0(@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1): dependencies: '@rtsao/scc': 1.1.0 array-includes: 3.1.9 @@ -4753,7 +4753,7 @@ snapshots: doctrine: 2.1.0 eslint: 8.57.1 eslint-import-resolver-node: 0.3.9 - eslint-module-utils: 2.12.1(@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1) + eslint-module-utils: 2.12.1(@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3))(eslint-import-resolver-node@0.3.9)(eslint-import-resolver-typescript@4.4.3)(eslint@8.57.1) hasown: 2.0.2 is-core-module: 2.16.1 is-glob: 4.0.3 @@ -4765,7 +4765,7 @@ snapshots: string.prototype.trimend: 1.0.9 tsconfig-paths: 3.15.0 optionalDependencies: - '@typescript-eslint/parser': 8.34.1(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/parser': 8.35.0(eslint@8.57.1)(typescript@5.8.3) transitivePeerDependencies: - eslint-import-resolver-typescript - eslint-import-resolver-webpack @@ -5567,7 +5567,7 @@ snapshots: prelude-ls@1.2.1: {} - prettier@3.5.3: {} + prettier@3.6.0: {} prop-types@15.8.1: dependencies: @@ -5985,11 +5985,11 @@ snapshots: possible-typed-array-names: 1.1.0 reflect.getprototypeof: 1.0.10 - typescript-eslint@8.34.1(eslint@8.57.1)(typescript@5.8.3): + typescript-eslint@8.35.0(eslint@8.57.1)(typescript@5.8.3): dependencies: - '@typescript-eslint/eslint-plugin': 8.34.1(@typescript-eslint/parser@8.34.1(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3) - '@typescript-eslint/parser': 8.34.1(eslint@8.57.1)(typescript@5.8.3) - '@typescript-eslint/utils': 8.34.1(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/eslint-plugin': 8.35.0(@typescript-eslint/parser@8.35.0(eslint@8.57.1)(typescript@5.8.3))(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/parser': 8.35.0(eslint@8.57.1)(typescript@5.8.3) + '@typescript-eslint/utils': 8.35.0(eslint@8.57.1)(typescript@5.8.3) eslint: 8.57.1 typescript: 5.8.3 transitivePeerDependencies: diff --git a/src/features/auth/hooks/useGithubLogin.ts b/src/features/auth/hooks/useGithubLogin.ts new file mode 100644 index 0000000..1109506 --- /dev/null +++ b/src/features/auth/hooks/useGithubLogin.ts @@ -0,0 +1,53 @@ +import { signInWithPopup, fetchSignInMethodsForEmail } from "firebase/auth"; +import { useNavigate } from "react-router-dom"; + +import { auth, githubProvider } from "@shared/firebase/firebase"; + +// ✅ 반환 타입 명시 +const useGithubLogin = (): { githubLogin: () => Promise } => { + const navigate = useNavigate(); + + // ✅ 함수 타입 명시 + const githubLogin = async (): Promise => { + try { + const result = await signInWithPopup(auth, githubProvider); + const user = result.user; + + console.log("GitHub 로그인 성공: ", user); + navigate("/"); + } catch (error: any) { + console.error("GitHub 로그인 실패: ", error); + + if (error.code === "auth/account-exists-with-different-credential") { + const email = error.customData?.email; + + if (email) { + const methods = await fetchSignInMethodsForEmail(auth, email); + console.warn("이미 가입된 로그인 방법:", methods); + + if (methods.length > 0) { + if (methods.includes("google.com")) { + alert( + "이미 Google 계정으로 가입된 이메일입니다. Google 로그인을 이용해주세요." + ); + } else { + alert(`이미 가입된 로그인 방법: ${methods.join(", ")}`); + } + } else { + alert( + "이미 다른 로그인 방법으로 가입된 이메일입니다. 다른 로그인 방법을 사용해주세요." + ); + } + } else { + alert( + "이미 다른 로그인 방법으로 가입된 계정입니다. 이메일 정보를 가져올 수 없습니다." + ); + } + } + } + }; + + return { githubLogin }; +}; + +export { useGithubLogin }; diff --git a/src/features/auth/hooks/useGoogleLogin.ts b/src/features/auth/hooks/useGoogleLogin.ts new file mode 100644 index 0000000..89f3e55 --- /dev/null +++ b/src/features/auth/hooks/useGoogleLogin.ts @@ -0,0 +1,24 @@ +import { signInWithPopup } from "firebase/auth"; +import { useNavigate } from "react-router-dom"; + +import { auth, googleProvider } from "@shared/firebase/firebase"; + +const useGoogleLogin = (): { googleLogin: () => Promise } => { + const navigate = useNavigate(); + + const googleLogin = async (): Promise => { + try { + const result = await signInWithPopup(auth, googleProvider); + const user = result.user; + + console.log("Google 로그인 성공: ", user); + navigate("/"); + } catch (error) { + console.error("Google 로그인 실패: ", error); + } + }; + + return { googleLogin }; +}; + +export { useGoogleLogin }; diff --git a/src/features/auth/ui/LoginForm.tsx b/src/features/auth/ui/LoginForm.tsx new file mode 100644 index 0000000..ed8f917 --- /dev/null +++ b/src/features/auth/ui/LoginForm.tsx @@ -0,0 +1,36 @@ +import { Divider } from "@mui/material"; +import type { JSX } from "react"; + +import { useGithubLogin } from "@features/auth/hooks/useGithubLogin"; +import { useGoogleLogin } from "@features/auth/hooks/useGoogleLogin"; +import { LoginTitle } from "@features/auth/ui/LoginTitle"; +import { SignupGuide } from "@features/auth/ui/SignupGuide"; +import { SocialLoginButton } from "@features/auth/ui/SocialLoginButton"; + +const LoginForm = (): JSX.Element => { + const { googleLogin } = useGoogleLogin(); + const { githubLogin } = useGithubLogin(); + + return ( + <> + + + + + + 또는 + + + + ); +}; + +export { LoginForm }; diff --git a/src/features/auth/ui/LoginTitle.tsx b/src/features/auth/ui/LoginTitle.tsx new file mode 100644 index 0000000..37566c1 --- /dev/null +++ b/src/features/auth/ui/LoginTitle.tsx @@ -0,0 +1,17 @@ +import { Typography } from "@mui/material"; +import type { JSX } from "react"; + +const LoginTitle = (): JSX.Element => { + return ( + <> + + 로그인 + + + 소셜 계정으로 간편하게 시작하세요 ✨ + + + ); +}; + +export { LoginTitle }; diff --git a/src/features/auth/ui/SignupGuide.tsx b/src/features/auth/ui/SignupGuide.tsx new file mode 100644 index 0000000..cac6b88 --- /dev/null +++ b/src/features/auth/ui/SignupGuide.tsx @@ -0,0 +1,19 @@ +import { Typography } from "@mui/material"; +import type { JSX } from "react"; + +const SignupGuide = (): JSX.Element => { + return ( + + 계정이 없으신가요?{" "} + + 회원가입하기 → + + + ); +}; + +export { SignupGuide }; diff --git a/src/features/auth/ui/SocialLoginButton.tsx b/src/features/auth/ui/SocialLoginButton.tsx new file mode 100644 index 0000000..e10047a --- /dev/null +++ b/src/features/auth/ui/SocialLoginButton.tsx @@ -0,0 +1,36 @@ +import { Button, styled } from "@mui/material"; +import type { JSX } from "react"; + +interface SocialLoginButtonProps { + label: string; + logo: string; + onClick: () => void; +} + +const SocialButton = styled(Button)({ + width: "100%", + marginBottom: "16px", + textTransform: "none", + display: "flex", + alignItems: "center", + justifyContent: "center", +}); + +const SocialLoginButton = ({ + label, + logo, + onClick, +}: SocialLoginButtonProps): JSX.Element => { + return ( + + Social Logo + {label} + + ); +}; + +export { SocialLoginButton }; diff --git a/src/pages/home/ui/HomePage.tsx b/src/pages/home/ui/HomePage.tsx index 58bf6ea..e24b775 100644 --- a/src/pages/home/ui/HomePage.tsx +++ b/src/pages/home/ui/HomePage.tsx @@ -1,6 +1,8 @@ import type { JSX } from "react"; const HomePage = (): JSX.Element => { + console.log("API_KEY: ", import.meta.env.VITE_API_KEY); + return (

홈 페이지

diff --git a/src/pages/login/ui/LoginPage.tsx b/src/pages/login/ui/LoginPage.tsx index d02ddde..019dc5e 100644 --- a/src/pages/login/ui/LoginPage.tsx +++ b/src/pages/login/ui/LoginPage.tsx @@ -1,7 +1,43 @@ +import { Box, Typography, styled } from "@mui/material"; import type { JSX } from "react"; +import { LoginForm } from "@features/auth/ui/LoginForm"; + +const PageWrapper = styled(Box)({ + display: "flex", + flexDirection: "column", + justifyContent: "center", + alignItems: "center", + minHeight: "100vh", + backgroundColor: "#f5f7fb", +}); + +const LoginBox = styled(Box)({ + width: "100%", + maxWidth: "400px", + padding: "32px", + borderRadius: "12px", + backgroundColor: "#fff", + boxShadow: "0 4px 12px rgba(0, 0, 0, 0.1)", + textAlign: "center", +}); + const LoginPage = (): JSX.Element => { - return
LoginPagesad
; + console.log("API_KEY: ", import.meta.env.VITE_API_KEY); + return ( + + + ⚡ 프로젝트 잼 + + + 함께 만들어가는 사이드 프로젝트 + + + + + + + ); }; export default LoginPage; diff --git a/src/shared/firebase/firebase.ts b/src/shared/firebase/firebase.ts index 43f490f..7c0896c 100644 --- a/src/shared/firebase/firebase.ts +++ b/src/shared/firebase/firebase.ts @@ -1,5 +1,6 @@ -import { initializeApp, type FirebaseApp } from "firebase/app"; -import { Firestore, getFirestore } from "firebase/firestore/lite"; +import { initializeApp } from "firebase/app"; +import { getAuth, GoogleAuthProvider, GithubAuthProvider } from "firebase/auth"; +import { getFirestore } from "firebase/firestore/lite"; const firebaseConfig = { apiKey: import.meta.env.VITE_API_KEY, @@ -11,5 +12,10 @@ const firebaseConfig = { measurementId: import.meta.env.VITE_MEASUREMENT_ID, }; -const app: FirebaseApp = initializeApp(firebaseConfig); -export const db: Firestore = getFirestore(app); +const app = initializeApp(firebaseConfig); + +export const auth = getAuth(app); +export const googleProvider = new GoogleAuthProvider(); +export const githubProvider = new GithubAuthProvider(); + +export const db = getFirestore(app);