From 3b1a5ea41f8c22517d03ec2fa8be5c3792c87e48 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Mon, 25 Sep 2023 14:07:02 +0900 Subject: [PATCH 01/55] =?UTF-8?q?feat:=20typescript=20=EA=B8=B0=EC=B4=88?= =?UTF-8?q?=EC=84=B8=ED=8C=85?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- package-lock.json | 243 +++++++++++++++++++++++++++++++++++- package.json | 7 ++ src/App.js | 25 ---- src/App.test.js | 6 +- src/App.tsx | 12 ++ src/{index.js => index.tsx} | 4 +- src/logo.svg | 1 - src/style/GlobalStyle.tsx | 8 ++ tsconfig.json | 26 ++++ 9 files changed, 298 insertions(+), 34 deletions(-) delete mode 100644 src/App.js create mode 100644 src/App.tsx rename src/{index.js => index.tsx} (73%) delete mode 100644 src/logo.svg create mode 100644 src/style/GlobalStyle.tsx create mode 100644 tsconfig.json diff --git a/package-lock.json b/package-lock.json index 82a715f..8209405 100644 --- a/package-lock.json +++ b/package-lock.json @@ -11,9 +11,16 @@ "@testing-library/jest-dom": "^5.17.0", "@testing-library/react": "^13.4.0", "@testing-library/user-event": "^13.5.0", + "@types/jest": "^29.5.5", + "@types/node": "^20.6.5", + "@types/react": "^18.2.22", + "@types/react-dom": "^18.2.7", "react": "^18.2.0", "react-dom": "^18.2.0", "react-scripts": "5.0.1", + "styled-components": "^6.0.8", + "styled-reset": "^4.5.1", + "typescript": "^4.9.5", "web-vitals": "^2.1.4" } }, @@ -53,6 +60,78 @@ "node": ">=6.0.0" } }, + "node_modules/@babel/cli": { + "version": "7.22.15", + "resolved": "https://registry.npmjs.org/@babel/cli/-/cli-7.22.15.tgz", + "integrity": "sha512-prtg5f6zCERIaECeTZzd2fMtVjlfjhUcO+fBLQ6DXXdq5FljN+excVitJ2nogsusdf31LeqkjAfXZ7Xq+HmN8g==", + "dependencies": { + "@jridgewell/trace-mapping": "^0.3.17", + "commander": "^4.0.1", + "convert-source-map": "^1.1.0", + "fs-readdir-recursive": "^1.1.0", + "glob": "^7.2.0", + "make-dir": "^2.1.0", + "slash": "^2.0.0" + }, + "bin": { + "babel": "bin/babel.js", + "babel-external-helpers": "bin/babel-external-helpers.js" + }, + "engines": { + "node": ">=6.9.0" + }, + "optionalDependencies": { + "@nicolo-ribaudo/chokidar-2": "2.1.8-no-fsevents.3", + "chokidar": "^3.4.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/cli/node_modules/commander": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/commander/-/commander-4.1.1.tgz", + "integrity": "sha512-NOKm8xhkzAjzFx8B2v5OAHT+u5pRQc2UCa2Vq9jYL/31o2wi9mxBA7LIFs3sV5VSC49z6pEhfbMULvShKj26WA==", + "engines": { + "node": ">= 6" + } + }, + "node_modules/@babel/cli/node_modules/make-dir": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-2.1.0.tgz", + "integrity": "sha512-LS9X+dc8KLxXCb8dni79fLIIUA5VyZoyjSMCwTluaXA0o27cCK0bhXkpgw+sTXVpPy/lSO57ilRixqk0vDmtRA==", + "dependencies": { + "pify": "^4.0.1", + "semver": "^5.6.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/@babel/cli/node_modules/pify": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/pify/-/pify-4.0.1.tgz", + "integrity": "sha512-uB80kBFb/tfd68bVleG9T5GGsGPjJrLAUpR5PZIrhBnIaRTQRjqdJSsIKkOP6OAIFbj7GOrcudc5pNjZ+geV2g==", + "engines": { + "node": ">=6" + } + }, + "node_modules/@babel/cli/node_modules/semver": { + "version": "5.7.2", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.2.tgz", + "integrity": "sha512-cBznnQ9KjJqU67B52RMC65CMarK2600WFnbkcaiwWq3xy/5haFJlshgnpjovMVJ+Hff49d8GEn0b87C5pDQ10g==", + "bin": { + "semver": "bin/semver" + } + }, + "node_modules/@babel/cli/node_modules/slash": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/slash/-/slash-2.0.0.tgz", + "integrity": "sha512-ZYKh3Wh2z1PpEXWr0MpSBZ0V6mZHAQfYevttO11c51CaWjGTaadiKZ+wVt1PbMlDV5qhMFslpZCemhwOK7C89A==", + "engines": { + "node": ">=6" + } + }, "node_modules/@babel/code-frame": { "version": "7.22.13", "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.22.13.tgz", @@ -530,6 +609,20 @@ "@babel/core": "^7.13.0" } }, + "node_modules/@babel/plugin-external-helpers": { + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/plugin-external-helpers/-/plugin-external-helpers-7.22.5.tgz", + "integrity": "sha512-ngnNEWxmykPk82mH4ajZT0qTztr3Je6hrMuKAslZVM8G1YZTENJSYwrIGtt6KOtznug3exmAtF4so/nPqJuA4A==", + "dependencies": { + "@babel/helper-plugin-utils": "^7.22.5" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, "node_modules/@babel/plugin-proposal-class-properties": { "version": "7.18.6", "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-class-properties/-/plugin-proposal-class-properties-7.18.6.tgz", @@ -596,6 +689,25 @@ "@babel/core": "^7.0.0-0" } }, + "node_modules/@babel/plugin-proposal-object-rest-spread": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-object-rest-spread/-/plugin-proposal-object-rest-spread-7.20.7.tgz", + "integrity": "sha512-d2S98yCiLxDVmBmE8UjGcfPvNEUbA1U5q5WxaWFUGRzJSVAZqm5W6MbPct0jxnegUZ0niLeNX+IOzEs7wYg9Dg==", + "deprecated": "This proposal has been merged to the ECMAScript standard and thus this plugin is no longer maintained. Please use @babel/plugin-transform-object-rest-spread instead.", + "dependencies": { + "@babel/compat-data": "^7.20.5", + "@babel/helper-compilation-targets": "^7.20.7", + "@babel/helper-plugin-utils": "^7.20.2", + "@babel/plugin-syntax-object-rest-spread": "^7.8.3", + "@babel/plugin-transform-parameters": "^7.20.7" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, "node_modules/@babel/plugin-proposal-optional-chaining": { "version": "7.21.0", "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-optional-chaining/-/plugin-proposal-optional-chaining-7.21.0.tgz", @@ -2270,6 +2382,24 @@ "postcss-selector-parser": "^6.0.10" } }, + "node_modules/@emotion/is-prop-valid": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/@emotion/is-prop-valid/-/is-prop-valid-1.2.1.tgz", + "integrity": "sha512-61Mf7Ufx4aDxx1xlDeOm8aFFigGHE4z+0sKCa+IHCeZKiyP9RLD0Mmx7m8b9/Cf37f7NAvQOOJAbQQGVr5uERw==", + "dependencies": { + "@emotion/memoize": "^0.8.1" + } + }, + "node_modules/@emotion/memoize": { + "version": "0.8.1", + "resolved": "https://registry.npmjs.org/@emotion/memoize/-/memoize-0.8.1.tgz", + "integrity": "sha512-W2P2c/VRW1/1tLox0mVUalvnWXxavmv/Oum2aPsRcoDJuob75FC3Y8FbpfLwUegRcxINtGUMPq0tFCvYNTBXNA==" + }, + "node_modules/@emotion/unitless": { + "version": "0.8.1", + "resolved": "https://registry.npmjs.org/@emotion/unitless/-/unitless-0.8.1.tgz", + "integrity": "sha512-KOEGMu6dmJZtpadb476IsZBclKvILjopjUii3V+7MnXIQCYh8W3NgNcgwo21n9LXZX6EDIKvqfjYxXebDwxKmQ==" + }, "node_modules/@eslint-community/eslint-utils": { "version": "4.4.0", "resolved": "https://registry.npmjs.org/@eslint-community/eslint-utils/-/eslint-utils-4.4.0.tgz", @@ -3132,6 +3262,12 @@ "resolved": "https://registry.npmjs.org/@leichtgewicht/ip-codec/-/ip-codec-2.0.4.tgz", "integrity": "sha512-Hcv+nVC0kZnQ3tD9GVu5xSMR4VVYOteQIr/hwFPVEvPdlXqgGEuRjiheChHgdM+JyqdgNcmzZOX/tnl0JOiI7A==" }, + "node_modules/@nicolo-ribaudo/chokidar-2": { + "version": "2.1.8-no-fsevents.3", + "resolved": "https://registry.npmjs.org/@nicolo-ribaudo/chokidar-2/-/chokidar-2-2.1.8-no-fsevents.3.tgz", + "integrity": "sha512-s88O1aVtXftvp5bCPB7WnmXc5IwOZZ7YPuwNPt+GtOOXpPvad1LfbmjYv+qII7zP6RU2QGnqve27dnLycEnyEQ==", + "optional": true + }, "node_modules/@nicolo-ribaudo/eslint-scope-5-internals": { "version": "5.1.1-v1", "resolved": "https://registry.npmjs.org/@nicolo-ribaudo/eslint-scope-5-internals/-/eslint-scope-5-internals-5.1.1-v1.tgz", @@ -4297,9 +4433,9 @@ "integrity": "sha512-YATxVxgRqNH6nHEIsvg6k2Boc1JHI9ZbH5iWFFv/MTkchz3b1ieGDa5T0a9RznNdI0KhVbdbWSN+KWWrQZRxTw==" }, "node_modules/@types/node": { - "version": "20.6.4", - "resolved": "https://registry.npmjs.org/@types/node/-/node-20.6.4.tgz", - "integrity": "sha512-nU6d9MPY0NBUMiE/nXd2IIoC4OLvsLpwAjheoAeuzgvDZA1Cb10QYg+91AF6zQiKWRN5i1m07x6sMe0niBznoQ==" + "version": "20.6.5", + "resolved": "https://registry.npmjs.org/@types/node/-/node-20.6.5.tgz", + "integrity": "sha512-2qGq5LAOTh9izcc0+F+dToFigBWiK1phKPt7rNhOqJSr35y8rlIBjDwGtFSgAI6MGIhjwOVNSQZVdJsZJ2uR1w==" }, "node_modules/@types/parse-json": { "version": "4.0.0", @@ -4412,6 +4548,11 @@ "resolved": "https://registry.npmjs.org/@types/stack-utils/-/stack-utils-2.0.1.tgz", "integrity": "sha512-Hl219/BT5fLAaz6NDkSuhzasy49dwQS/DSdu4MdggFB8zcXv7vflBI3xp7FEmkmdDkBUI2bPUNeMttp2knYdxw==" }, + "node_modules/@types/stylis": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/@types/stylis/-/stylis-4.2.0.tgz", + "integrity": "sha512-n4sx2bqL0mW1tvDf/loQ+aMX7GQD3lc3fkCMC55VFNDu/vBOabO+LTIeXKM14xK0ppk5TUGcWRjiSpIlUpghKw==" + }, "node_modules/@types/testing-library__jest-dom": { "version": "5.14.9", "resolved": "https://registry.npmjs.org/@types/testing-library__jest-dom/-/testing-library__jest-dom-5.14.9.tgz", @@ -5826,6 +5967,14 @@ "node": ">= 6" } }, + "node_modules/camelize": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/camelize/-/camelize-1.0.1.tgz", + "integrity": "sha512-dU+Tx2fsypxTgtLoE36npi3UqcjSSMNYfkqgmoEhtZrraP5VWq0K7FkWVTYa8eMPtnU/G2txVsfdCJTn9uzpuQ==", + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/caniuse-api": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/caniuse-api/-/caniuse-api-3.0.0.tgz", @@ -6261,6 +6410,14 @@ "postcss": "^8.4" } }, + "node_modules/css-color-keywords": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/css-color-keywords/-/css-color-keywords-1.0.0.tgz", + "integrity": "sha512-FyyrDHZKEjXDpNJYvVsV960FiqQyXc/LlYmsxl2BcdMb2WPx0OGRVgTg55rPSyLSNMqP52R9r8geSp7apN3Ofg==", + "engines": { + "node": ">=4" + } + }, "node_modules/css-declaration-sorter": { "version": "6.4.1", "resolved": "https://registry.npmjs.org/css-declaration-sorter/-/css-declaration-sorter-6.4.1.tgz", @@ -6442,6 +6599,16 @@ "resolved": "https://registry.npmjs.org/css-select-base-adapter/-/css-select-base-adapter-0.1.1.tgz", "integrity": "sha512-jQVeeRG70QI08vSTwf1jHxp74JoZsr2XSgETae8/xC8ovSnL2WF87GTLO86Sbwdt2lK4Umg4HnnwMO4YF3Ce7w==" }, + "node_modules/css-to-react-native": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/css-to-react-native/-/css-to-react-native-3.2.0.tgz", + "integrity": "sha512-e8RKaLXMOFii+02mOlqwjbD00KSEKqblnpO9e++1aXS1fPQOpS1YoqdVHBqPjHNoxeF2mimzVqawm2KCbEdtHQ==", + "dependencies": { + "camelize": "^1.0.0", + "css-color-keywords": "^1.0.0", + "postcss-value-parser": "^4.0.2" + } + }, "node_modules/css-tree": { "version": "1.0.0-alpha.37", "resolved": "https://registry.npmjs.org/css-tree/-/css-tree-1.0.0-alpha.37.tgz", @@ -8549,6 +8716,11 @@ "resolved": "https://registry.npmjs.org/fs-monkey/-/fs-monkey-1.0.4.tgz", "integrity": "sha512-INM/fWAxMICjttnD0DX1rBvinKskj5G1w+oy/pnm9u/tSlnBrzFonJMcalKJ30P8RRsPzKcCG7Q8l0jx5Fh9YQ==" }, + "node_modules/fs-readdir-recursive": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/fs-readdir-recursive/-/fs-readdir-recursive-1.1.0.tgz", + "integrity": "sha512-GNanXlVr2pf02+sPN40XN8HG+ePaNcvM0q5mZBd668Obwb0yD5GiUbZOFgwn8kGMY6I3mdyDJzieUy3PTYyTRA==" + }, "node_modules/fs.realpath": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", @@ -15513,6 +15685,11 @@ "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==" }, + "node_modules/shallowequal": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/shallowequal/-/shallowequal-1.1.0.tgz", + "integrity": "sha512-y0m1JoUZSlPAjXVtPPW70aZWfIL/dSP7AFkRnniLCrK/8MDKog3TySTBmckD+RObVxH0v4Tox67+F14PdED2oQ==" + }, "node_modules/shebang-command": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", @@ -16009,6 +16186,60 @@ "webpack": "^5.0.0" } }, + "node_modules/styled-components": { + "version": "6.0.8", + "resolved": "https://registry.npmjs.org/styled-components/-/styled-components-6.0.8.tgz", + "integrity": "sha512-AwI02MTWZwqjzfXgR5QcbmcSn5xVjY4N2TLjSuYnmuBGF3y7GicHz3ysbpUq2EMJP5M8/Nc22vcmF3V3WNZDFA==", + "dependencies": { + "@babel/cli": "^7.21.0", + "@babel/core": "^7.21.0", + "@babel/helper-module-imports": "^7.18.6", + "@babel/plugin-external-helpers": "^7.18.6", + "@babel/plugin-proposal-class-properties": "^7.18.6", + "@babel/plugin-proposal-object-rest-spread": "^7.20.7", + "@babel/preset-env": "^7.20.2", + "@babel/preset-react": "^7.18.6", + "@babel/preset-typescript": "^7.21.0", + "@babel/traverse": "^7.21.2", + "@emotion/is-prop-valid": "^1.2.1", + "@emotion/unitless": "^0.8.0", + "@types/stylis": "^4.0.2", + "css-to-react-native": "^3.2.0", + "csstype": "^3.1.2", + "postcss": "^8.4.23", + "shallowequal": "^1.1.0", + "stylis": "^4.3.0", + "tslib": "^2.5.0" + }, + "engines": { + "node": ">= 16" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/styled-components" + }, + "peerDependencies": { + "babel-plugin-styled-components": ">= 2", + "react": ">= 16.8.0", + "react-dom": ">= 16.8.0" + }, + "peerDependenciesMeta": { + "babel-plugin-styled-components": { + "optional": true + } + } + }, + "node_modules/styled-reset": { + "version": "4.5.1", + "resolved": "https://registry.npmjs.org/styled-reset/-/styled-reset-4.5.1.tgz", + "integrity": "sha512-6EvFWZRwaFRFxiPYMwmnzOe33rDkw5r9jIU0eEi49bkt6VSrvjeMp2ZOw/YFbw5SVs81llIY+5fzHtR2/VBZfQ==", + "engines": { + "node": ">=18.0.0" + }, + "peerDependencies": { + "styled-components": ">=4.0.0 || >=5.0.0 || >=6.0.0" + } + }, "node_modules/stylehacks": { "version": "5.1.1", "resolved": "https://registry.npmjs.org/stylehacks/-/stylehacks-5.1.1.tgz", @@ -16024,6 +16255,11 @@ "postcss": "^8.2.15" } }, + "node_modules/stylis": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/stylis/-/stylis-4.3.0.tgz", + "integrity": "sha512-E87pIogpwUsUwXw7dNyU4QDjdgVMy52m+XEOPEKUn161cCzWjjhPSQhByfd1CcNvrOLnXQ6OnnZDwnJrz/Z4YQ==" + }, "node_modules/sucrase": { "version": "3.34.0", "resolved": "https://registry.npmjs.org/sucrase/-/sucrase-3.34.0.tgz", @@ -16656,7 +16892,6 @@ "version": "4.9.5", "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.9.5.tgz", "integrity": "sha512-1FXk9E2Hm+QzZQ7z+McJiHL4NW1F2EzMu9Nq9i3zAaGqibafqYwCVU6WyWAuyQRRzOlxou8xZSyXLEN8oKj24g==", - "peer": true, "bin": { "tsc": "bin/tsc", "tsserver": "bin/tsserver" diff --git a/package.json b/package.json index 49b3308..7e5911b 100644 --- a/package.json +++ b/package.json @@ -6,9 +6,16 @@ "@testing-library/jest-dom": "^5.17.0", "@testing-library/react": "^13.4.0", "@testing-library/user-event": "^13.5.0", + "@types/jest": "^29.5.5", + "@types/node": "^20.6.5", + "@types/react": "^18.2.22", + "@types/react-dom": "^18.2.7", "react": "^18.2.0", "react-dom": "^18.2.0", "react-scripts": "5.0.1", + "styled-components": "^6.0.8", + "styled-reset": "^4.5.1", + "typescript": "^4.9.5", "web-vitals": "^2.1.4" }, "scripts": { diff --git a/src/App.js b/src/App.js deleted file mode 100644 index 3784575..0000000 --- a/src/App.js +++ /dev/null @@ -1,25 +0,0 @@ -import logo from './logo.svg'; -import './App.css'; - -function App() { - return ( -
-
- logo -

- Edit src/App.js and save to reload. -

- - Learn React - -
-
- ); -} - -export default App; diff --git a/src/App.test.js b/src/App.test.js index 1f03afe..9382b9a 100644 --- a/src/App.test.js +++ b/src/App.test.js @@ -1,7 +1,7 @@ -import { render, screen } from '@testing-library/react'; -import App from './App'; +import { render, screen } from "@testing-library/react"; +import App from "./App"; -test('renders learn react link', () => { +test("renders learn react link", () => { render(); const linkElement = screen.getByText(/learn react/i); expect(linkElement).toBeInTheDocument(); diff --git a/src/App.tsx b/src/App.tsx new file mode 100644 index 0000000..7c91b29 --- /dev/null +++ b/src/App.tsx @@ -0,0 +1,12 @@ +import './App.css'; +import GlobalStyle from "./style/GlobalStyle"; +function App() { + return ( + <> + + <>hello + + ); +} + +export default App; diff --git a/src/index.js b/src/index.tsx similarity index 73% rename from src/index.js rename to src/index.tsx index d563c0f..6703a8e 100644 --- a/src/index.js +++ b/src/index.tsx @@ -4,7 +4,9 @@ import './index.css'; import App from './App'; import reportWebVitals from './reportWebVitals'; -const root = ReactDOM.createRoot(document.getElementById('root')); +const rootElement = document.getElementById('root'); +if (!rootElement) throw new Error('Failed to find the root element'); +const root = ReactDOM.createRoot(rootElement); root.render( diff --git a/src/logo.svg b/src/logo.svg deleted file mode 100644 index 9dfc1c0..0000000 --- a/src/logo.svg +++ /dev/null @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/src/style/GlobalStyle.tsx b/src/style/GlobalStyle.tsx new file mode 100644 index 0000000..7c86ddf --- /dev/null +++ b/src/style/GlobalStyle.tsx @@ -0,0 +1,8 @@ +import {createGlobalStyle} from "styled-components"; +import reset from "styled-reset"; + +const GlobalStyle = createGlobalStyle` + ${reset} +`; + +export default GlobalStyle; \ No newline at end of file diff --git a/tsconfig.json b/tsconfig.json new file mode 100644 index 0000000..74caf0d --- /dev/null +++ b/tsconfig.json @@ -0,0 +1,26 @@ +{ + "compilerOptions": { + "target": "es5", + "lib": [ + "dom", + "dom.iterable", + "esnext" + ], + "allowJs": true, + "skipLibCheck": true, + "esModuleInterop": true, + "allowSyntheticDefaultImports": true, + "strict": true, + "forceConsistentCasingInFileNames": true, + "noFallthroughCasesInSwitch": true, + "module": "esnext", + "moduleResolution": "node", + "resolveJsonModule": true, + "isolatedModules": true, + "noEmit": true, + "jsx": "react-jsx" + }, + "include": [ + "src" + ] +} \ No newline at end of file From 689891ffe62f404b39329b4d6316cc34780d0474 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Mon, 25 Sep 2023 14:49:22 +0900 Subject: [PATCH 02/55] =?UTF-8?q?style:=20color.css=20=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/style/color.css | 12 ++++++++++++ 1 file changed, 12 insertions(+) create mode 100644 src/style/color.css diff --git a/src/style/color.css b/src/style/color.css new file mode 100644 index 0000000..82c871a --- /dev/null +++ b/src/style/color.css @@ -0,0 +1,12 @@ +:root{ + --black : #1A1A1A; /*주로 배경색*/ + --gray-1 : #2E2E2E; + --gray-2 : #484848; + --gray-3 : #555555;/*비강조, 두루두루*/ + --gray-4 : #7E7E7E; /*비강조, 주로 텍스트*/ + --gray-5 :#A7A7A7; + --gray-6 :#D5D5D5;/*강조, 주로 아이콘*/ + --gray-7 :#F2F2F2;/*강조, 주로 텍스트*/ + --white : #FFFFFF; + --green : #22FF60;/*포인트*/ +} \ No newline at end of file From 252da7ae00eb7a8c3b00ef356655da73ee9a670d Mon Sep 17 00:00:00 2001 From: leekyuho Date: Mon, 25 Sep 2023 20:42:48 +0900 Subject: [PATCH 03/55] =?UTF-8?q?feat:=20status=20bar=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/App.css | 38 ------------------ src/App.test.js | 8 ---- src/App.tsx | 6 ++- src/assets/Iphone/Battery.svg | 7 ++++ src/assets/Iphone/Clock.svg | 4 ++ src/assets/Iphone/Signal.svg | 5 +++ src/assets/Iphone/WifiConnection.svg | 5 +++ src/components/organisms/StatusBar.tsx | 54 ++++++++++++++++++++++++++ src/custom.d.ts | 6 +++ src/index.css | 13 ------- src/index.tsx | 9 +---- src/pages/ChattingPage.tsx | 9 +++++ src/reportWebVitals.js | 13 ------- src/setupTests.js | 5 --- src/style/GlobalStyle.tsx | 17 +++++++- tsconfig.json | 2 +- 16 files changed, 113 insertions(+), 88 deletions(-) delete mode 100644 src/App.css delete mode 100644 src/App.test.js create mode 100644 src/assets/Iphone/Battery.svg create mode 100644 src/assets/Iphone/Clock.svg create mode 100644 src/assets/Iphone/Signal.svg create mode 100644 src/assets/Iphone/WifiConnection.svg create mode 100644 src/components/organisms/StatusBar.tsx create mode 100644 src/custom.d.ts delete mode 100644 src/index.css create mode 100644 src/pages/ChattingPage.tsx delete mode 100644 src/reportWebVitals.js delete mode 100644 src/setupTests.js diff --git a/src/App.css b/src/App.css deleted file mode 100644 index 74b5e05..0000000 --- a/src/App.css +++ /dev/null @@ -1,38 +0,0 @@ -.App { - text-align: center; -} - -.App-logo { - height: 40vmin; - pointer-events: none; -} - -@media (prefers-reduced-motion: no-preference) { - .App-logo { - animation: App-logo-spin infinite 20s linear; - } -} - -.App-header { - background-color: #282c34; - min-height: 100vh; - display: flex; - flex-direction: column; - align-items: center; - justify-content: center; - font-size: calc(10px + 2vmin); - color: white; -} - -.App-link { - color: #61dafb; -} - -@keyframes App-logo-spin { - from { - transform: rotate(0deg); - } - to { - transform: rotate(360deg); - } -} diff --git a/src/App.test.js b/src/App.test.js deleted file mode 100644 index 9382b9a..0000000 --- a/src/App.test.js +++ /dev/null @@ -1,8 +0,0 @@ -import { render, screen } from "@testing-library/react"; -import App from "./App"; - -test("renders learn react link", () => { - render(); - const linkElement = screen.getByText(/learn react/i); - expect(linkElement).toBeInTheDocument(); -}); diff --git a/src/App.tsx b/src/App.tsx index 7c91b29..3c7cdce 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -1,10 +1,12 @@ -import './App.css'; import GlobalStyle from "./style/GlobalStyle"; +import ChattingPage from "./pages/ChattingPage" +import "./style/color.css"; function App() { return ( <> - <>hello + {/* 나중에 라우트 추가 */} + ); } diff --git a/src/assets/Iphone/Battery.svg b/src/assets/Iphone/Battery.svg new file mode 100644 index 0000000..268d73a --- /dev/null +++ b/src/assets/Iphone/Battery.svg @@ -0,0 +1,7 @@ + + + + + + + diff --git a/src/assets/Iphone/Clock.svg b/src/assets/Iphone/Clock.svg new file mode 100644 index 0000000..498c55d --- /dev/null +++ b/src/assets/Iphone/Clock.svg @@ -0,0 +1,4 @@ + + + + diff --git a/src/assets/Iphone/Signal.svg b/src/assets/Iphone/Signal.svg new file mode 100644 index 0000000..ad585c3 --- /dev/null +++ b/src/assets/Iphone/Signal.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/src/assets/Iphone/WifiConnection.svg b/src/assets/Iphone/WifiConnection.svg new file mode 100644 index 0000000..ba76072 --- /dev/null +++ b/src/assets/Iphone/WifiConnection.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/src/components/organisms/StatusBar.tsx b/src/components/organisms/StatusBar.tsx new file mode 100644 index 0000000..81b15a5 --- /dev/null +++ b/src/components/organisms/StatusBar.tsx @@ -0,0 +1,54 @@ +import { ReactComponent as Battery } from "../../assets/Iphone/Battery.svg"; +import { ReactComponent as Clock } from "../../assets/Iphone/Clock.svg"; +import { ReactComponent as Signal } from "../../assets/Iphone/Signal.svg"; +import { ReactComponent as WifiConnection } from "../../assets/Iphone/WifiConnection.svg"; +import styled from "styled-components"; +function StatusBar(){ + return( + + + + + + + + + ); +} +const StatusBarWrapper = styled.div` + width: 23.4375rem; + height: 2.9375rem; + position : relative; +`; + +const StyledClock = styled(Clock)` + position : absolute; + width: 4.125rem; + height: 1.4375rem; + padding: 0.8125rem 0 0.6875rem 1.375rem; + right: 17.9375rem; +`; +//indicator wrap +const Indicators = styled.div` + position : absolute; + display: inline-flex; + align-items: center; + gap: 0.40625rem; + left: 17.4375rem; + right: 1.16875rem; + top: 1.4375rem; + bottom: 0.6875rem; +`; +const StyledSignal = styled(Signal)` + width: 1.2481875rem; + height: 0.75rem; +`; +const StyledWifi = styled(WifiConnection)` + width: 1.0625rem; + height: 0.78125rem; +`; +const StyledBattery = styled(Battery)` + width: 1.708125rem; + height: 0.8125rem; +`; +export default StatusBar; diff --git a/src/custom.d.ts b/src/custom.d.ts new file mode 100644 index 0000000..436ba68 --- /dev/null +++ b/src/custom.d.ts @@ -0,0 +1,6 @@ +declare module '*.svg' { + import React = require('react'); + export const ReactComponent: React.FC>; + const src: string; + export default src; +} \ No newline at end of file diff --git a/src/index.css b/src/index.css deleted file mode 100644 index ec2585e..0000000 --- a/src/index.css +++ /dev/null @@ -1,13 +0,0 @@ -body { - margin: 0; - font-family: -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; -} - -code { - font-family: source-code-pro, Menlo, Monaco, Consolas, 'Courier New', - monospace; -} diff --git a/src/index.tsx b/src/index.tsx index 6703a8e..3cb455e 100644 --- a/src/index.tsx +++ b/src/index.tsx @@ -1,8 +1,8 @@ import React from 'react'; import ReactDOM from 'react-dom/client'; -import './index.css'; + import App from './App'; -import reportWebVitals from './reportWebVitals'; + const rootElement = document.getElementById('root'); if (!rootElement) throw new Error('Failed to find the root element'); @@ -12,8 +12,3 @@ root.render( ); - -// If you want to start measuring performance in your app, pass a function -// to log results (for example: reportWebVitals(console.log)) -// or send to an analytics endpoint. Learn more: https://bit.ly/CRA-vitals -reportWebVitals(); diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx new file mode 100644 index 0000000..b716919 --- /dev/null +++ b/src/pages/ChattingPage.tsx @@ -0,0 +1,9 @@ +import StatusBar from "../components/organisms/StatusBar"; +function ChattingPage(){ + return( +
+ +
+ ); +} +export default ChattingPage; \ No newline at end of file diff --git a/src/reportWebVitals.js b/src/reportWebVitals.js deleted file mode 100644 index 5253d3a..0000000 --- a/src/reportWebVitals.js +++ /dev/null @@ -1,13 +0,0 @@ -const reportWebVitals = onPerfEntry => { - if (onPerfEntry && onPerfEntry instanceof Function) { - import('web-vitals').then(({ getCLS, getFID, getFCP, getLCP, getTTFB }) => { - getCLS(onPerfEntry); - getFID(onPerfEntry); - getFCP(onPerfEntry); - getLCP(onPerfEntry); - getTTFB(onPerfEntry); - }); - } -}; - -export default reportWebVitals; diff --git a/src/setupTests.js b/src/setupTests.js deleted file mode 100644 index 8f2609b..0000000 --- a/src/setupTests.js +++ /dev/null @@ -1,5 +0,0 @@ -// jest-dom adds custom jest matchers for asserting on DOM nodes. -// allows you to do things like: -// expect(element).toHaveTextContent(/react/i) -// learn more: https://github.com/testing-library/jest-dom -import '@testing-library/jest-dom'; diff --git a/src/style/GlobalStyle.tsx b/src/style/GlobalStyle.tsx index 7c86ddf..8a142a3 100644 --- a/src/style/GlobalStyle.tsx +++ b/src/style/GlobalStyle.tsx @@ -1,8 +1,23 @@ import {createGlobalStyle} from "styled-components"; import reset from "styled-reset"; - +import "./color.css"; const GlobalStyle = createGlobalStyle` ${reset} + html,body{ + height:100%; + } + body{ + background-color : var(--white); + display:flex; + justify-content: center; + align-items: center; + } + .pageWrapper{ + width: 23.4375rem; + height: 50.75rem; + border-radius: 1.25rem; + background-color : var(--black); + } `; export default GlobalStyle; \ No newline at end of file diff --git a/tsconfig.json b/tsconfig.json index 74caf0d..28aa7d5 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -21,6 +21,6 @@ "jsx": "react-jsx" }, "include": [ - "src" + "src","src/custom.d.ts" ] } \ No newline at end of file From 4177d469e6f444d7667db2e443fbc2d3d5880d69 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Mon, 25 Sep 2023 21:33:28 +0900 Subject: [PATCH 04/55] =?UTF-8?q?style:=20GlobalStyle.js=20wrapper=20?= =?UTF-8?q?=EB=B6=84=EB=A6=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/App.tsx | 10 ++++- src/assets/Iphone/HomeBar.svg | 3 ++ src/components/HomeIndicator.tsx | 19 +++++++++ src/components/StatusBar.tsx | 54 ++++++++++++++++++++++++++ src/components/organisms/StatusBar.tsx | 54 -------------------------- src/pages/ChattingPage.tsx | 4 +- src/style/GlobalStyle.tsx | 6 ++- 7 files changed, 91 insertions(+), 59 deletions(-) create mode 100644 src/assets/Iphone/HomeBar.svg create mode 100644 src/components/HomeIndicator.tsx create mode 100644 src/components/StatusBar.tsx delete mode 100644 src/components/organisms/StatusBar.tsx diff --git a/src/App.tsx b/src/App.tsx index 3c7cdce..ffd5e85 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -1,12 +1,18 @@ import GlobalStyle from "./style/GlobalStyle"; import ChattingPage from "./pages/ChattingPage" +import StatusBar from "./components/StatusBar"; +import HomeIndicator from "./components/HomeIndicator"; import "./style/color.css"; function App() { return ( <> - {/* 나중에 라우트 추가 */} - +
+ + {/* 나중에 라우터 추가 or Router.js*/} + + +
); } diff --git a/src/assets/Iphone/HomeBar.svg b/src/assets/Iphone/HomeBar.svg new file mode 100644 index 0000000..ce4d360 --- /dev/null +++ b/src/assets/Iphone/HomeBar.svg @@ -0,0 +1,3 @@ + + + diff --git a/src/components/HomeIndicator.tsx b/src/components/HomeIndicator.tsx new file mode 100644 index 0000000..b4989d5 --- /dev/null +++ b/src/components/HomeIndicator.tsx @@ -0,0 +1,19 @@ +import { ReactComponent as HomeBar } from "../assets/Iphone/HomeBar.svg"; +import styled from "styled-components"; +function HomeIndicator(){ + return( + + + + ); +} +const HomeBarWrapper = styled.div` + width: 23.4375rem; + height: 2.125rem; +`; +const StyledHomeBar = styled(HomeBar)` + width: 8.375rem; + height: 0.3125rem; + padding: 1.3125rem 7.5rem 0.5rem 7.5625rem; +`; +export default HomeIndicator; diff --git a/src/components/StatusBar.tsx b/src/components/StatusBar.tsx new file mode 100644 index 0000000..485220b --- /dev/null +++ b/src/components/StatusBar.tsx @@ -0,0 +1,54 @@ +import { ReactComponent as Battery } from "../assets/Iphone/Battery.svg"; +import { ReactComponent as Clock } from "../assets/Iphone/Clock.svg"; +import { ReactComponent as Signal } from "../assets/Iphone/Signal.svg"; +import { ReactComponent as WifiConnection } from "../assets/Iphone/WifiConnection.svg"; +import styled from "styled-components"; +function StatusBar() { + return ( + + + + + + + + + ); +} +const StatusBarWrapper = styled.div` + width: 23.4375rem; + height: 2.9375rem; + position: relative; +`; + +const StyledClock = styled(Clock)` + position: absolute; + width: 4.125rem; + height: 1.4375rem; + padding: 0.8125rem 0 0.6875rem 1.375rem; + right: 17.9375rem; +`; +//indicator wrap +const Indicators = styled.div` + position: absolute; + display: inline-flex; + align-items: center; + gap: 0.40625rem; + left: 17.4375rem; + right: 1.16875rem; + top: 1.4375rem; + bottom: 0.6875rem; +`; +const StyledSignal = styled(Signal)` + width: 1.2481875rem; + height: 0.75rem; +`; +const StyledWifi = styled(WifiConnection)` + width: 1.0625rem; + height: 0.78125rem; +`; +const StyledBattery = styled(Battery)` + width: 1.708125rem; + height: 0.8125rem; +`; +export default StatusBar; diff --git a/src/components/organisms/StatusBar.tsx b/src/components/organisms/StatusBar.tsx deleted file mode 100644 index 81b15a5..0000000 --- a/src/components/organisms/StatusBar.tsx +++ /dev/null @@ -1,54 +0,0 @@ -import { ReactComponent as Battery } from "../../assets/Iphone/Battery.svg"; -import { ReactComponent as Clock } from "../../assets/Iphone/Clock.svg"; -import { ReactComponent as Signal } from "../../assets/Iphone/Signal.svg"; -import { ReactComponent as WifiConnection } from "../../assets/Iphone/WifiConnection.svg"; -import styled from "styled-components"; -function StatusBar(){ - return( - - - - - - - - - ); -} -const StatusBarWrapper = styled.div` - width: 23.4375rem; - height: 2.9375rem; - position : relative; -`; - -const StyledClock = styled(Clock)` - position : absolute; - width: 4.125rem; - height: 1.4375rem; - padding: 0.8125rem 0 0.6875rem 1.375rem; - right: 17.9375rem; -`; -//indicator wrap -const Indicators = styled.div` - position : absolute; - display: inline-flex; - align-items: center; - gap: 0.40625rem; - left: 17.4375rem; - right: 1.16875rem; - top: 1.4375rem; - bottom: 0.6875rem; -`; -const StyledSignal = styled(Signal)` - width: 1.2481875rem; - height: 0.75rem; -`; -const StyledWifi = styled(WifiConnection)` - width: 1.0625rem; - height: 0.78125rem; -`; -const StyledBattery = styled(Battery)` - width: 1.708125rem; - height: 0.8125rem; -`; -export default StatusBar; diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index b716919..f6cc4fe 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -1,8 +1,8 @@ -import StatusBar from "../components/organisms/StatusBar"; +import StatusBar from "../components/StatusBar"; +import HomeIndicator from "../components/HomeIndicator"; function ChattingPage(){ return(
-
); } diff --git a/src/style/GlobalStyle.tsx b/src/style/GlobalStyle.tsx index 8a142a3..e811463 100644 --- a/src/style/GlobalStyle.tsx +++ b/src/style/GlobalStyle.tsx @@ -12,12 +12,16 @@ const GlobalStyle = createGlobalStyle` justify-content: center; align-items: center; } - .pageWrapper{ + .mainWrapper{ width: 23.4375rem; height: 50.75rem; border-radius: 1.25rem; background-color : var(--black); } + .pageWrapper{ /*pageWrapper는 header footer 제외 높이*/ + width: 23.4375rem; + height: 45.6875rem; + } `; export default GlobalStyle; \ No newline at end of file From 4fe28644533c6d2345f74b25eda7bd57810b9547 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Tue, 26 Sep 2023 04:21:57 +0900 Subject: [PATCH 05/55] =?UTF-8?q?feat:=20chatting=20=ED=99=94=EB=A9=B4=20?= =?UTF-8?q?=ED=94=84=EB=A1=9C=ED=95=84=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/assets/Icons/Back.svg | 3 ++ src/assets/Icons/Call.svg | 3 ++ src/assets/Icons/Freinds.svg | 8 ++++ src/assets/Icons/More.svg | 5 +++ src/components/ChattingProfile.tsx | 70 ++++++++++++++++++++++++++++++ src/pages/ChattingPage.tsx | 11 ++++- src/style/GlobalStyle.tsx | 5 +++ src/style/font.tsx | 48 ++++++++++++++++++++ 8 files changed, 151 insertions(+), 2 deletions(-) create mode 100644 src/assets/Icons/Back.svg create mode 100644 src/assets/Icons/Call.svg create mode 100644 src/assets/Icons/Freinds.svg create mode 100644 src/assets/Icons/More.svg create mode 100644 src/components/ChattingProfile.tsx create mode 100644 src/style/font.tsx diff --git a/src/assets/Icons/Back.svg b/src/assets/Icons/Back.svg new file mode 100644 index 0000000..f0fc13a --- /dev/null +++ b/src/assets/Icons/Back.svg @@ -0,0 +1,3 @@ + + + \ No newline at end of file diff --git a/src/assets/Icons/Call.svg b/src/assets/Icons/Call.svg new file mode 100644 index 0000000..77c289d --- /dev/null +++ b/src/assets/Icons/Call.svg @@ -0,0 +1,3 @@ + + + \ No newline at end of file diff --git a/src/assets/Icons/Freinds.svg b/src/assets/Icons/Freinds.svg new file mode 100644 index 0000000..844fed5 --- /dev/null +++ b/src/assets/Icons/Freinds.svg @@ -0,0 +1,8 @@ + + + + + + + + \ No newline at end of file diff --git a/src/assets/Icons/More.svg b/src/assets/Icons/More.svg new file mode 100644 index 0000000..7c155b4 --- /dev/null +++ b/src/assets/Icons/More.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/src/components/ChattingProfile.tsx b/src/components/ChattingProfile.tsx new file mode 100644 index 0000000..34c8a09 --- /dev/null +++ b/src/components/ChattingProfile.tsx @@ -0,0 +1,70 @@ +import { ReactComponent as Back } from "../assets/Icons/Back.svg"; +import { ReactComponent as Call } from "../assets/Icons/Call.svg"; +import { ReactComponent as Friends } from "../assets/Icons/Freinds.svg"; +import { ReactComponent as More } from "../assets/Icons/More.svg"; +import { Heading2, Caption1 } from "../style/font"; +import "../style/color.css"; +import styled from "styled-components"; +function ChattingProfile(){ + return( + + + + + + + + 신현재 + 근무 중 + + 삼성전자/HR/부장 + + + ); +} +const ChattingProfileWrapper = styled.div` + position:relative; + width: 22.1875rem; + height: 3rem; + padding: 0.5rem 0.625rem; +`; +const StyledBack = styled(Back)` + position:absolute; + width: 0.625rem; + height: 1.25rem; + padding: 0.25rem 0.625rem; + left: 0.625rem; + top: 1.19rem; +`; +const StyledFriends = styled(Friends)` + position:absolute; + width: 3rem; + height: 3rem; + left: 3.56rem; + top: 0.5rem; +`; +const StyledCall = styled(Call)` + position:absolute; + width: 1.125rem; + height: 1.125rem; + padding: 0.3125rem; + right: 3.375rem; + top: 1.125rem; +`; +const StyledMore = styled(More)` + position:absolute; + right: 0.625rem; + top: 1.125rem; +`; +const UserInfoWrapper = styled.div` + position:absolute; + left:7.06rem; + display:flex; + flex-direction:column; + align-items: flex-start; /*왼쪽으로 정렬*/ +`; +const UserWrapper = styled.div` + display:flex; + gap : 0.31rem; +`; +export default ChattingProfile; \ No newline at end of file diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index f6cc4fe..41cb52f 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -1,9 +1,16 @@ -import StatusBar from "../components/StatusBar"; -import HomeIndicator from "../components/HomeIndicator"; +import ChattingProfile from "../components/ChattingProfile"; +import styled from "styled-components"; function ChattingPage(){ return(
+ + +
); } +const Divider = styled.hr` + border: 0.0625rem solid var(--gray-3); + margin : 0 0 0.3125rem 0; +`; export default ChattingPage; \ No newline at end of file diff --git a/src/style/GlobalStyle.tsx b/src/style/GlobalStyle.tsx index e811463..45f5edc 100644 --- a/src/style/GlobalStyle.tsx +++ b/src/style/GlobalStyle.tsx @@ -3,6 +3,10 @@ import reset from "styled-reset"; import "./color.css"; const GlobalStyle = createGlobalStyle` ${reset} + @font-face { + font-family: 'Pretendard-Regular'; + src: url('https://cdn.jsdelivr.net/gh/Project-Noonnu/noonfonts_2107@1.1/Pretendard-Regular.woff') format('woff'); + } html,body{ height:100%; } @@ -11,6 +15,7 @@ const GlobalStyle = createGlobalStyle` display:flex; justify-content: center; align-items: center; + font-family: 'Pretendard-Regular'; } .mainWrapper{ width: 23.4375rem; diff --git a/src/style/font.tsx b/src/style/font.tsx new file mode 100644 index 0000000..8edc5ad --- /dev/null +++ b/src/style/font.tsx @@ -0,0 +1,48 @@ +import styled from 'styled-components'; +import "../style/color.css"; +export const Heading1 =styled.div` + color: ${props => props.color || 'var(--white)'}; + font-size: 1.5rem; + font-style: normal; + font-weight: 700; + line-height: 1.375rem; /* 91.667% */ + letter-spacing: -0.0255rem; +`; +export const Heading2 =styled.div` + color: ${props => props.color || 'var(--white)'}; + font-size: 1.375rem; + font-style: normal; + font-weight: 700; + line-height: 1.375rem; /* 100% */ + letter-spacing: -0.0255rem; +`; +export const Body1 =styled.div` + color: ${props => props.color || 'var(--white)'}; + font-size: 1.125rem; + font-style: normal; + font-weight: 700; + line-height: 1.375rem; /* 122.222% */ + letter-spacing: -0.0255rem; +`; +export const Body2 =styled.div` + color: ${props => props.color || 'var(--white)'}; + font-size: 1.125rem; + font-style: normal; + font-weight: 500; + line-height: 1.5rem; /* 133.333% */ + letter-spacing: -0.0255rem; +`; +export const Caption1 =styled.div` + color: ${props => props.color || 'var(--white)'}; + font-size: 0.875rem; + font-style: normal; + font-weight: 500; + line-height: 1.375rem; /* 157.143% */ +`; +export const Caption2 =styled.div` + color: ${props => props.color || 'var(--white)'}; + font-size: 0.875rem; + font-style: normal; + font-weight: 300; + line-height: 1.375rem; /* 157.143% */ +`; \ No newline at end of file From e4b058ef144aa47cb3204c77140cccbd37fc786d Mon Sep 17 00:00:00 2001 From: leekyuho Date: Tue, 26 Sep 2023 21:19:40 +0900 Subject: [PATCH 06/55] =?UTF-8?q?feat:=20=EB=A9=94=EC=84=B8=EC=A7=80=20?= =?UTF-8?q?=EC=9E=85=EB=A0=A5=EC=B0=BD=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- package-lock.json | 18 +++++++ package.json | 3 ++ src/assets/Icons/Chat.svg | 4 ++ src/assets/Icons/Plus.svg | 3 ++ src/assets/Icons/Send.svg | 3 ++ src/components/ChattingEmpty.tsx | 0 src/components/ChattingInput.tsx | 89 ++++++++++++++++++++++++++++++++ src/data/userData.json | 52 +++++++++++++++++++ src/pages/ChattingPage.tsx | 3 ++ src/style/GlobalStyle.tsx | 6 +++ 10 files changed, 181 insertions(+) create mode 100644 src/assets/Icons/Chat.svg create mode 100644 src/assets/Icons/Plus.svg create mode 100644 src/assets/Icons/Send.svg create mode 100644 src/components/ChattingEmpty.tsx create mode 100644 src/components/ChattingInput.tsx create mode 100644 src/data/userData.json diff --git a/package-lock.json b/package-lock.json index 8209405..deaa894 100644 --- a/package-lock.json +++ b/package-lock.json @@ -22,6 +22,9 @@ "styled-reset": "^4.5.1", "typescript": "^4.9.5", "web-vitals": "^2.1.4" + }, + "devDependencies": { + "prettier": "3.0.3" } }, "node_modules/@aashutoshrathi/word-wrap": { @@ -14458,6 +14461,21 @@ "node": ">= 0.8.0" } }, + "node_modules/prettier": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/prettier/-/prettier-3.0.3.tgz", + "integrity": "sha512-L/4pUDMxcNa8R/EthV08Zt42WBO4h1rarVtK0K+QJG0X187OLo7l699jWw0GKuwzkPQ//jMFA/8Xm6Fh3J/DAg==", + "dev": true, + "bin": { + "prettier": "bin/prettier.cjs" + }, + "engines": { + "node": ">=14" + }, + "funding": { + "url": "https://github.com/prettier/prettier?sponsor=1" + } + }, "node_modules/pretty-bytes": { "version": "5.6.0", "resolved": "https://registry.npmjs.org/pretty-bytes/-/pretty-bytes-5.6.0.tgz", diff --git a/package.json b/package.json index 7e5911b..a4ef344 100644 --- a/package.json +++ b/package.json @@ -41,5 +41,8 @@ "last 1 firefox version", "last 1 safari version" ] + }, + "devDependencies": { + "prettier": "3.0.3" } } diff --git a/src/assets/Icons/Chat.svg b/src/assets/Icons/Chat.svg new file mode 100644 index 0000000..7165415 --- /dev/null +++ b/src/assets/Icons/Chat.svg @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/src/assets/Icons/Plus.svg b/src/assets/Icons/Plus.svg new file mode 100644 index 0000000..374636f --- /dev/null +++ b/src/assets/Icons/Plus.svg @@ -0,0 +1,3 @@ + + + \ No newline at end of file diff --git a/src/assets/Icons/Send.svg b/src/assets/Icons/Send.svg new file mode 100644 index 0000000..3e51197 --- /dev/null +++ b/src/assets/Icons/Send.svg @@ -0,0 +1,3 @@ + + + \ No newline at end of file diff --git a/src/components/ChattingEmpty.tsx b/src/components/ChattingEmpty.tsx new file mode 100644 index 0000000..e69de29 diff --git a/src/components/ChattingInput.tsx b/src/components/ChattingInput.tsx new file mode 100644 index 0000000..050366c --- /dev/null +++ b/src/components/ChattingInput.tsx @@ -0,0 +1,89 @@ +import { useState } from "react"; +import { ReactComponent as Plus } from "../assets/Icons/Plus.svg"; +import { ReactComponent as Send } from "../assets/Icons/Send.svg"; +import styled from "styled-components"; +import { Body2, Caption1 } from "../style/font"; +function ChattingInput(){ + const [typeMessage, setTypeMessage] = useState("메세지를 입력하세요"); + const[input,setInput] = useState(""); + //메세지창에 메세지 없을 때만 placeholder 출력 + const handleFocus = ()=>{ + setTypeMessage(""); + } + const handleBlur = ()=>{ + if(input.trim() === ""){ + setTypeMessage("메세지를 입력하세요"); + } + } + const handleSubmit = (e:any)=>{ + e.preventDefault(); + setInput(""); + } + const handleOnChange = (e:any)=>{ + setInput(e.target.value); + } + return( + + + + + + {typeMessage} + + + ); +} +const ChattingInputWrapper = styled.div` + width: 23.4375rem; + height: 3.69rem; + position: relative; + position: absolute; + top : 42rem; + .placeHolder{ + pointer-events: none; /*input이 묻히기 때문에 제외*/ + position : absolute; + top: 1.56rem; + left: 4.38rem; + } +`; +const StyledPlus = styled(Plus)` + position: absolute; + width: 1.25rem; + height: 1.25rem; + padding: 0.25rem; + left : 1rem; + top : 1.44rem; +`; +const StyledSend = styled(Send)` + position: absolute; + width: 1.1875rem; + height: 1.1875rem; + padding: 0.28125rem; + top:1.47rem; + right : 0.97rem; +`; +const StyledForm = styled.form` + .message-input{ + border : none; + position: absolute; + background-color : var(--gray-1); + top:0.94rem; + left:3.12rem; + width: 17.25rem; + height: 2.75rem; + border-radius: 6.25rem; + text-indent : 1.25rem; + font-family : 'Pretendard-Regular';/*globalstyle 왜 적용안되는지?*/ + color: var(--gray-7); + font-size: 1.125rem; + font-style: normal; + font-weight: 500; + line-height: 1.5rem; /* 133.333% */ + letter-spacing: -0.0255rem; + } +`; +export default ChattingInput; diff --git a/src/data/userData.json b/src/data/userData.json new file mode 100644 index 0000000..c22cf0c --- /dev/null +++ b/src/data/userData.json @@ -0,0 +1,52 @@ +{ + "users": [ + { + "id": 0, + "name": "신현재", + "profileImage": "", + "company":"삼성전자", + "department": "HR", + "rank":"부장" + }, + { + "id": 1, + "name": "신낸재", + "profileImage": "", + "company":"카카오뱅크", + "department": "프로덕트팀", + "rank":"팀장" + }, + { + "id": 2, + "name": "현재", + "profileImage": "", + "company":"하나은행", + "department": "영업1팀", + "rank":"차장" + }, + { + "id": 3, + "name": "나는낸재", + "profileImage": "", + "company":"제일기획", + "department": "기획2팀", + "rank":"팀장" + }, + { + "id": 4, + "name": "Hyunjae Shin", + "profileImage": "", + "company":"삼성전자", + "department": "글로벌사업부", + "rank":"부장" + }, + { + "id": 5, + "name": "신현재다", + "profileImage": "", + "company":"삼성전자", + "department": "DX", + "rank":"부장" + } + ] + } \ No newline at end of file diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index 41cb52f..bbb45b3 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -1,3 +1,4 @@ +import ChattingInput from "../components/ChattingInput"; import ChattingProfile from "../components/ChattingProfile"; import styled from "styled-components"; function ChattingPage(){ @@ -6,6 +7,8 @@ function ChattingPage(){ + {/* default, 말하면 생기기 state로 true false 관리 */} + ); } diff --git a/src/style/GlobalStyle.tsx b/src/style/GlobalStyle.tsx index 45f5edc..4c10842 100644 --- a/src/style/GlobalStyle.tsx +++ b/src/style/GlobalStyle.tsx @@ -6,6 +6,8 @@ const GlobalStyle = createGlobalStyle` @font-face { font-family: 'Pretendard-Regular'; src: url('https://cdn.jsdelivr.net/gh/Project-Noonnu/noonfonts_2107@1.1/Pretendard-Regular.woff') format('woff'); + font-weight: 400; + font-style: normal; } html,body{ height:100%; @@ -17,6 +19,9 @@ const GlobalStyle = createGlobalStyle` align-items: center; font-family: 'Pretendard-Regular'; } + input{ + outline: none; + } .mainWrapper{ width: 23.4375rem; height: 50.75rem; @@ -26,6 +31,7 @@ const GlobalStyle = createGlobalStyle` .pageWrapper{ /*pageWrapper는 header footer 제외 높이*/ width: 23.4375rem; height: 45.6875rem; + position : relative; } `; From f2c52632c94d30ca84ca204c451a36bcfa18bbd7 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Tue, 26 Sep 2023 21:43:50 +0900 Subject: [PATCH 07/55] =?UTF-8?q?feat:=20=EC=B1=84=ED=8C=85=20=EB=B9=88?= =?UTF-8?q?=ED=99=94=EB=A9=B4=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/ChattingEmpty.tsx | 41 ++++++++++++++++++++++++++++++++ src/pages/ChattingPage.tsx | 2 ++ 2 files changed, 43 insertions(+) diff --git a/src/components/ChattingEmpty.tsx b/src/components/ChattingEmpty.tsx index e69de29..5d2d166 100644 --- a/src/components/ChattingEmpty.tsx +++ b/src/components/ChattingEmpty.tsx @@ -0,0 +1,41 @@ +import { ReactComponent as Chat } from "../assets/Icons/Chat.svg"; +import styled from "styled-components"; +import { Body2 } from "../style/font"; +function ChattingEmpty(){ + return( + + + + 상대방과 대화를
+ 시작해보세요 +
+
+ ); +} +const ChattingEmptyWrapper = styled.div` + width: 23.4375rem; + height: 37.69rem; + position : relative; + overflow-y: scroll; + scrollbar-width: none; /* Firefox */ + -ms-overflow-style: none; /* Internet Explorer/Edge */ + &::-webkit-scrollbar { + display: none; /* Chrome, Safari*/ + } + .defaultChat{ + position : absolute; + text-align: center; + left: 8.25rem; + top: 17.935rem; + } +`; +const StyledChat = styled(Chat)` + position : absolute; + width: 1.9375rem; + height: 1.9375rem; + left : 10.75rem; + top :15.315rem; +`; +export default ChattingEmpty; diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index bbb45b3..aeba8d1 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -1,3 +1,4 @@ +import ChattingEmpty from "../components/ChattingEmpty"; import ChattingInput from "../components/ChattingInput"; import ChattingProfile from "../components/ChattingProfile"; import styled from "styled-components"; @@ -8,6 +9,7 @@ function ChattingPage(){ {/* default, 말하면 생기기 state로 true false 관리 */} + ); From 59cd26103e3e8543518fcc11c4dfeb4a7547036c Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 27 Sep 2023 03:12:57 +0900 Subject: [PATCH 08/55] =?UTF-8?q?feat:=20=EC=B1=84=ED=8C=85=20component=20?= =?UTF-8?q?=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/App.tsx | 10 +++--- src/components/ChatBubble.tsx | 53 ++++++++++++++++++++++++++++++ src/components/ChattingEmpty.tsx | 9 ++--- src/components/ChattingFull.tsx | 29 ++++++++++++++++ src/components/ChattingInput.tsx | 9 ++--- src/components/ChattingProfile.tsx | 8 ++--- src/components/HomeIndicator.tsx | 2 +- src/components/StatusBar.tsx | 8 ++--- src/pages/ChattingPage.tsx | 6 ++-- src/style/GlobalStyle.tsx | 5 +-- 10 files changed, 108 insertions(+), 31 deletions(-) create mode 100644 src/components/ChatBubble.tsx create mode 100644 src/components/ChattingFull.tsx diff --git a/src/App.tsx b/src/App.tsx index ffd5e85..c2f683f 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -8,11 +8,11 @@ function App() { <>
- - {/* 나중에 라우터 추가 or Router.js*/} - - -
+ + {/* 나중에 라우터 추가 or Router.js*/} + + + ); } diff --git a/src/components/ChatBubble.tsx b/src/components/ChatBubble.tsx new file mode 100644 index 0000000..741068c --- /dev/null +++ b/src/components/ChatBubble.tsx @@ -0,0 +1,53 @@ +import styled from "styled-components"; +import "../style/color.css"; +import { Body2 ,Caption2} from "../style/font"; +interface ChatBubbleProps{ + isUser:boolean; + content:string; +} +interface IsUserProps{ + isUser:boolean; +} +function ChatBubble(props: ChatBubbleProps){ + return( + +
+ 10:24 + + {props.content} + + +
+
+ ); +} +const ChatContainer = styled.div` + display: flex; + flex-direction : column; + align-items: ${props => (props.isUser ? "flex-end" : "flex-start")}; + .chatWrapper{ + display:flex; + flex-direction : ${props => (props.isUser ? "row" : "row-reverse")}; + align-items: flex-end; + gap : 0.3125rem; + } + .writeTime{ + margin-bottom : 0.625rem; + } +`; +const ChatBox = styled.div` + display: inline-block; + background-color : ${props => (props.isUser ? "var(--green)" : "var(--gray-1)")}; + max-width : 16.8125rem; + width: fit-content; + border-radius: 6.25rem; + margin : ${props => (props.isUser ? "0.625rem 1.25rem 0.625rem 0" : "0.625rem 0 0.625rem 1.25rem")}; +`; +const ChatText = styled(Body2)` + color : ${props => (props.isUser ? "var(--gray-1)" : "var(--gray-7)")}; + padding: 0.625rem 1.25rem; +`; + +export default ChatBubble; \ No newline at end of file diff --git a/src/components/ChattingEmpty.tsx b/src/components/ChattingEmpty.tsx index 5d2d166..0a28248 100644 --- a/src/components/ChattingEmpty.tsx +++ b/src/components/ChattingEmpty.tsx @@ -1,4 +1,5 @@ -import { ReactComponent as Chat } from "../assets/Icons/Chat.svg"; +import { ReactComponent as Chat } from "../assets/icons/Chat.svg"; +import ChatBubble from "./ChatBubble"; import styled from "styled-components"; import { Body2 } from "../style/font"; function ChattingEmpty(){ @@ -18,12 +19,6 @@ const ChattingEmptyWrapper = styled.div` width: 23.4375rem; height: 37.69rem; position : relative; - overflow-y: scroll; - scrollbar-width: none; /* Firefox */ - -ms-overflow-style: none; /* Internet Explorer/Edge */ - &::-webkit-scrollbar { - display: none; /* Chrome, Safari*/ - } .defaultChat{ position : absolute; text-align: center; diff --git a/src/components/ChattingFull.tsx b/src/components/ChattingFull.tsx new file mode 100644 index 0000000..a3b380b --- /dev/null +++ b/src/components/ChattingFull.tsx @@ -0,0 +1,29 @@ +import styled from "styled-components"; +import "../style/color.css"; +import { Body2 ,Caption2} from "../style/font"; +import { useState } from "react"; +import ChatBubble from "./ChatBubble"; + +function ChattingFull(){ + const temp1 = true; + const temp2 = false; + return( + + + + + ); +} +const ChattingFullWrapper = styled.div` + display : flex; + flex-direction : column; + width: 23.4375rem; + height: 37.69rem; + overflow-y: scroll; + scrollbar-width: none; /* Firefox */ + -ms-overflow-style: none; /* Internet Explorer/Edge */ + &::-webkit-scrollbar { + display: none; /* Chrome, Safari*/ + } +`; +export default ChattingFull; diff --git a/src/components/ChattingInput.tsx b/src/components/ChattingInput.tsx index 050366c..75dacea 100644 --- a/src/components/ChattingInput.tsx +++ b/src/components/ChattingInput.tsx @@ -1,6 +1,6 @@ import { useState } from "react"; -import { ReactComponent as Plus } from "../assets/Icons/Plus.svg"; -import { ReactComponent as Send } from "../assets/Icons/Send.svg"; +import { ReactComponent as Plus } from "../assets/icons/Plus.svg"; +import { ReactComponent as Send } from "../assets/icons/Send.svg"; import styled from "styled-components"; import { Body2, Caption1 } from "../style/font"; function ChattingInput(){ @@ -73,10 +73,11 @@ const StyledForm = styled.form` background-color : var(--gray-1); top:0.94rem; left:3.12rem; - width: 17.25rem; + width: 14.75rem; height: 2.75rem; border-radius: 6.25rem; - text-indent : 1.25rem; + padding-left:1.25rem; + padding-right:1.25rem; font-family : 'Pretendard-Regular';/*globalstyle 왜 적용안되는지?*/ color: var(--gray-7); font-size: 1.125rem; diff --git a/src/components/ChattingProfile.tsx b/src/components/ChattingProfile.tsx index 34c8a09..8af2935 100644 --- a/src/components/ChattingProfile.tsx +++ b/src/components/ChattingProfile.tsx @@ -1,7 +1,7 @@ -import { ReactComponent as Back } from "../assets/Icons/Back.svg"; -import { ReactComponent as Call } from "../assets/Icons/Call.svg"; -import { ReactComponent as Friends } from "../assets/Icons/Freinds.svg"; -import { ReactComponent as More } from "../assets/Icons/More.svg"; +import { ReactComponent as Back } from "../assets/icons/Back.svg"; +import { ReactComponent as Call } from "../assets/icons/Call.svg"; +import { ReactComponent as Friends } from "../assets/icons/Freinds.svg"; +import { ReactComponent as More } from "../assets/icons/More.svg"; import { Heading2, Caption1 } from "../style/font"; import "../style/color.css"; import styled from "styled-components"; diff --git a/src/components/HomeIndicator.tsx b/src/components/HomeIndicator.tsx index b4989d5..d84f998 100644 --- a/src/components/HomeIndicator.tsx +++ b/src/components/HomeIndicator.tsx @@ -1,4 +1,4 @@ -import { ReactComponent as HomeBar } from "../assets/Iphone/HomeBar.svg"; +import { ReactComponent as HomeBar } from "../assets/iphone/HomeBar.svg"; import styled from "styled-components"; function HomeIndicator(){ return( diff --git a/src/components/StatusBar.tsx b/src/components/StatusBar.tsx index 485220b..5bc8b32 100644 --- a/src/components/StatusBar.tsx +++ b/src/components/StatusBar.tsx @@ -1,7 +1,7 @@ -import { ReactComponent as Battery } from "../assets/Iphone/Battery.svg"; -import { ReactComponent as Clock } from "../assets/Iphone/Clock.svg"; -import { ReactComponent as Signal } from "../assets/Iphone/Signal.svg"; -import { ReactComponent as WifiConnection } from "../assets/Iphone/WifiConnection.svg"; +import { ReactComponent as Battery } from "../assets/iphone/Battery.svg"; +import { ReactComponent as Clock } from "../assets/iphone/Clock.svg"; +import { ReactComponent as Signal } from "../assets/iphone/Signal.svg"; +import { ReactComponent as WifiConnection } from "../assets/iphone/WifiConnection.svg"; import styled from "styled-components"; function StatusBar() { return ( diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index aeba8d1..0706342 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -1,4 +1,5 @@ import ChattingEmpty from "../components/ChattingEmpty"; +import ChattingFull from "../components/ChattingFull"; import ChattingInput from "../components/ChattingInput"; import ChattingProfile from "../components/ChattingProfile"; import styled from "styled-components"; @@ -8,8 +9,9 @@ function ChattingPage(){ - {/* default, 말하면 생기기 state로 true false 관리 */} - + {/* 대화내용 있고 없음으로 예외처리 */} + + {/* */} ); diff --git a/src/style/GlobalStyle.tsx b/src/style/GlobalStyle.tsx index 4c10842..85f26f1 100644 --- a/src/style/GlobalStyle.tsx +++ b/src/style/GlobalStyle.tsx @@ -6,13 +6,10 @@ const GlobalStyle = createGlobalStyle` @font-face { font-family: 'Pretendard-Regular'; src: url('https://cdn.jsdelivr.net/gh/Project-Noonnu/noonfonts_2107@1.1/Pretendard-Regular.woff') format('woff'); - font-weight: 400; - font-style: normal; } + html,body{ height:100%; - } - body{ background-color : var(--white); display:flex; justify-content: center; From 5023ee5df0b502574ea6c3bb994cb856b2059e3d Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 27 Sep 2023 17:44:44 +0900 Subject: [PATCH 09/55] =?UTF-8?q?chore:=20json=20data=20=ED=8C=8C=EC=9D=BC?= =?UTF-8?q?=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/data/chatData.json | 36 +++++++++++++++ src/data/userData.json | 102 ++++++++++++++++++++--------------------- 2 files changed, 87 insertions(+), 51 deletions(-) create mode 100644 src/data/chatData.json diff --git a/src/data/chatData.json b/src/data/chatData.json new file mode 100644 index 0000000..2f0ecfc --- /dev/null +++ b/src/data/chatData.json @@ -0,0 +1,36 @@ +{ + "chattings": [ + { + "chatRoomId": 0, + "userList": [0,3], + "chatList":[ + { + "chatId":0, + "userId":0, + "message" :"에어팟을 끼고 일해도 힘듭니다" + }, + { + "chatId":1, + "userId":3, + "message" :"앗 그렇군뇽" + } + ] + }, + { + "chatRommId": 1, + "userList": [0,2], + "chatList":[ + { + "chatId":0, + "userId":0, + "message" :"배고파요" + }, + { + "chatId":1, + "userId":2, + "message" :"네" + } + ] + } + ] +} \ No newline at end of file diff --git a/src/data/userData.json b/src/data/userData.json index c22cf0c..2f76b47 100644 --- a/src/data/userData.json +++ b/src/data/userData.json @@ -1,52 +1,52 @@ { - "users": [ - { - "id": 0, - "name": "신현재", - "profileImage": "", - "company":"삼성전자", - "department": "HR", - "rank":"부장" - }, - { - "id": 1, - "name": "신낸재", - "profileImage": "", - "company":"카카오뱅크", - "department": "프로덕트팀", - "rank":"팀장" - }, - { - "id": 2, - "name": "현재", - "profileImage": "", - "company":"하나은행", - "department": "영업1팀", - "rank":"차장" - }, - { - "id": 3, - "name": "나는낸재", - "profileImage": "", - "company":"제일기획", - "department": "기획2팀", - "rank":"팀장" - }, - { - "id": 4, - "name": "Hyunjae Shin", - "profileImage": "", - "company":"삼성전자", - "department": "글로벌사업부", - "rank":"부장" - }, - { - "id": 5, - "name": "신현재다", - "profileImage": "", - "company":"삼성전자", - "department": "DX", - "rank":"부장" - } - ] - } \ No newline at end of file + "users": [ + { + "userId": 0, + "name": "신현재", + "profileImage": "", + "company":"삼성전자", + "department": "HR", + "rank":"부장" + }, + { + "userId": 1, + "name": "신낸재", + "profileImage": "", + "company":"카카오뱅크", + "department": "프로덕트팀", + "rank":"팀장" + }, + { + "userId": 2, + "name": "현재", + "profileImage": "", + "company":"하나은행", + "department": "영업1팀", + "rank":"차장" + }, + { + "userId": 3, + "name": "나는낸재", + "profileImage": "", + "company":"제일기획", + "department": "기획2팀", + "rank":"팀장" + }, + { + "userId": 4, + "name": "Hyunjae Shin", + "profileImage": "", + "company":"삼성전자", + "department": "글로벌사업부", + "rank":"부장" + }, + { + "userId": 5, + "name": "신현재다", + "profileImage": "", + "company":"삼성전자", + "department": "DX", + "rank":"부장" + } + ] +} \ No newline at end of file From a58dc137dbedf36661bfc153a747b5cadf82d306 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Thu, 28 Sep 2023 01:10:17 +0900 Subject: [PATCH 10/55] =?UTF-8?q?feat:=20recoil=EC=9D=84=20=ED=86=B5?= =?UTF-8?q?=ED=95=9C=20json=20chat=20=EB=8D=B0=EC=9D=B4=ED=84=B0=20=20?= =?UTF-8?q?=EC=B6=9C=EB=A0=A5=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- package-lock.json | 25 +++++++++++++++++++++++++ package.json | 1 + src/components/ChatBubble.tsx | 19 +++++++++---------- src/components/ChattingEmpty.tsx | 1 + src/components/ChattingFull.tsx | 26 ++++++++++++++++++++------ src/data/chatData.json | 2 +- src/index.tsx | 6 ++++-- src/pages/ChattingPage.tsx | 4 ++-- src/recoil/state.ts | 20 ++++++++++++++++++++ 9 files changed, 83 insertions(+), 21 deletions(-) create mode 100644 src/recoil/state.ts diff --git a/package-lock.json b/package-lock.json index deaa894..8edf0d4 100644 --- a/package-lock.json +++ b/package-lock.json @@ -18,6 +18,7 @@ "react": "^18.2.0", "react-dom": "^18.2.0", "react-scripts": "5.0.1", + "recoil": "^0.7.7", "styled-components": "^6.0.8", "styled-reset": "^4.5.1", "typescript": "^4.9.5", @@ -8987,6 +8988,11 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/hamt_plus": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/hamt_plus/-/hamt_plus-1.0.2.tgz", + "integrity": "sha512-t2JXKaehnMb9paaYA7J0BX8QQAY8lwfQ9Gjf4pg/mk4krt+cmwmU652HOoWonf+7+EQV97ARPMhhVgU1ra2GhA==" + }, "node_modules/handle-thing": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/handle-thing/-/handle-thing-2.0.1.tgz", @@ -14980,6 +14986,25 @@ "node": ">=8.10.0" } }, + "node_modules/recoil": { + "version": "0.7.7", + "resolved": "https://registry.npmjs.org/recoil/-/recoil-0.7.7.tgz", + "integrity": "sha512-8Og5KPQW9LwC577Vc7Ug2P0vQshkv1y3zG3tSSkWMqkWSwHmE+by06L8JtnGocjW6gcCvfwB3YtrJG6/tWivNQ==", + "dependencies": { + "hamt_plus": "1.0.2" + }, + "peerDependencies": { + "react": ">=16.13.1" + }, + "peerDependenciesMeta": { + "react-dom": { + "optional": true + }, + "react-native": { + "optional": true + } + } + }, "node_modules/recursive-readdir": { "version": "2.2.3", "resolved": "https://registry.npmjs.org/recursive-readdir/-/recursive-readdir-2.2.3.tgz", diff --git a/package.json b/package.json index a4ef344..44bb48e 100644 --- a/package.json +++ b/package.json @@ -13,6 +13,7 @@ "react": "^18.2.0", "react-dom": "^18.2.0", "react-scripts": "5.0.1", + "recoil": "^0.7.7", "styled-components": "^6.0.8", "styled-reset": "^4.5.1", "typescript": "^4.9.5", diff --git a/src/components/ChatBubble.tsx b/src/components/ChatBubble.tsx index 741068c..79e3590 100644 --- a/src/components/ChatBubble.tsx +++ b/src/components/ChatBubble.tsx @@ -3,27 +3,26 @@ import "../style/color.css"; import { Body2 ,Caption2} from "../style/font"; interface ChatBubbleProps{ isUser:boolean; - content:string; -} -interface IsUserProps{ - isUser:boolean; + message :string; } + function ChatBubble(props: ChatBubbleProps){ return( - +
10:24 - {props.content} + {props.message}
-
+ ); } -const ChatContainer = styled.div` +//user 쪽 채팅과 상대방쪽 채팅 props로 구분 +const ChatBubbleContainer = styled.div<{isUser:boolean}>` display: flex; flex-direction : column; align-items: ${props => (props.isUser ? "flex-end" : "flex-start")}; @@ -37,7 +36,7 @@ const ChatContainer = styled.div` margin-bottom : 0.625rem; } `; -const ChatBox = styled.div` +const ChatBox = styled.div<{isUser:boolean}>` display: inline-block; background-color : ${props => (props.isUser ? "var(--green)" : "var(--gray-1)")}; max-width : 16.8125rem; @@ -45,7 +44,7 @@ const ChatBox = styled.div` border-radius: 6.25rem; margin : ${props => (props.isUser ? "0.625rem 1.25rem 0.625rem 0" : "0.625rem 0 0.625rem 1.25rem")}; `; -const ChatText = styled(Body2)` +const ChatText = styled(Body2)<{isUser:boolean}>` color : ${props => (props.isUser ? "var(--gray-1)" : "var(--gray-7)")}; padding: 0.625rem 1.25rem; `; diff --git a/src/components/ChattingEmpty.tsx b/src/components/ChattingEmpty.tsx index 0a28248..6487c74 100644 --- a/src/components/ChattingEmpty.tsx +++ b/src/components/ChattingEmpty.tsx @@ -2,6 +2,7 @@ import { ReactComponent as Chat } from "../assets/icons/Chat.svg"; import ChatBubble from "./ChatBubble"; import styled from "styled-components"; import { Body2 } from "../style/font"; + function ChattingEmpty(){ return( diff --git a/src/components/ChattingFull.tsx b/src/components/ChattingFull.tsx index a3b380b..b780976 100644 --- a/src/components/ChattingFull.tsx +++ b/src/components/ChattingFull.tsx @@ -3,14 +3,28 @@ import "../style/color.css"; import { Body2 ,Caption2} from "../style/font"; import { useState } from "react"; import ChatBubble from "./ChatBubble"; - -function ChattingFull(){ - const temp1 = true; - const temp2 = false; +import { useRecoilState, useRecoilValue } from "recoil"; +import { chatRoomListState, currentUserState } from "../recoil/state"; +interface ChattingProps{ + chatRoomId : number; + isUser:boolean; +} +function ChattingFull(props:ChattingProps){ + //모든 채팅방 정보 + const chatRoomList = useRecoilValue(chatRoomListState); + const initializedChat = chatRoomList[props.chatRoomId].chatList; + //현재 채팅방 chat list + const [chatList, setChatList] = useState(initializedChat); + //현재 user id, chat의 userId와 같을 경우 true 넘김 + const currentUser = useRecoilValue(currentUserState); return( - - + { + chatList.map((value, index)=>{ + return( + + )}) + } ); } diff --git a/src/data/chatData.json b/src/data/chatData.json index 2f0ecfc..67b8f8b 100644 --- a/src/data/chatData.json +++ b/src/data/chatData.json @@ -17,7 +17,7 @@ ] }, { - "chatRommId": 1, + "chatRoomId": 1, "userList": [0,2], "chatList":[ { diff --git a/src/index.tsx b/src/index.tsx index 3cb455e..2bcae0f 100644 --- a/src/index.tsx +++ b/src/index.tsx @@ -1,6 +1,6 @@ import React from 'react'; import ReactDOM from 'react-dom/client'; - +import { RecoilRoot } from 'recoil'; import App from './App'; @@ -9,6 +9,8 @@ if (!rootElement) throw new Error('Failed to find the root element'); const root = ReactDOM.createRoot(rootElement); root.render( - + + + ); diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index 0706342..83ece28 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -9,8 +9,8 @@ function ChattingPage(){ - {/* 대화내용 있고 없음으로 예외처리 */} - + {/* 대화내용 있고 없음으로 예외처리 isUser 여기서 넘겨야함*/} + {/* */} diff --git a/src/recoil/state.ts b/src/recoil/state.ts new file mode 100644 index 0000000..a4b3431 --- /dev/null +++ b/src/recoil/state.ts @@ -0,0 +1,20 @@ +import {atom, selector, selectorFamily} from 'recoil'; +import userData from '../data/userData.json'; +import chatData from '../data/chatData.json'; +//현재 user,나머지 user list, chattingRoom list +export const currentUserState = atom({ + key : 'currentUserState', + default: userData.users[0], +}); + +export const friendsState = atom({ + key : 'friendsState', + default : userData.users.slice(1), +}); + +export const chatRoomListState = atom({ + key : 'chatRoomListState', + default : chatData.chattings, +}); + + From e616c6e8cb231e9d2b6502339ac0a3fd6133a905 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Thu, 28 Sep 2023 16:23:03 +0900 Subject: [PATCH 11/55] =?UTF-8?q?feat:=20=EC=B1=84=ED=8C=85=EC=B0=BD=20?= =?UTF-8?q?=EB=92=A4=EC=A7=91=ED=9E=88=EA=B8=B0=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/App.tsx | 4 ++-- src/components/ChatBubble.tsx | 24 +++++++++---------- src/components/ChattingFull.tsx | 12 ++++++---- src/components/ChattingProfile.tsx | 14 +++++++---- src/data/chatData.json | 7 +++++- src/data/userData.json | 18 ++++++++++----- src/pages/ChattingPage.tsx | 37 +++++++++++++++++++++++++----- src/recoil/state.ts | 19 +++++++++++---- 8 files changed, 96 insertions(+), 39 deletions(-) diff --git a/src/App.tsx b/src/App.tsx index c2f683f..76e73f7 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -9,8 +9,8 @@ function App() {
- {/* 나중에 라우터 추가 or Router.js*/} - + {/* 나중에 라우터 추가 or Router.js / 그리고 chatting room 여러개*/} +
diff --git a/src/components/ChatBubble.tsx b/src/components/ChatBubble.tsx index 79e3590..74c34a1 100644 --- a/src/components/ChatBubble.tsx +++ b/src/components/ChatBubble.tsx @@ -2,19 +2,19 @@ import styled from "styled-components"; import "../style/color.css"; import { Body2 ,Caption2} from "../style/font"; interface ChatBubbleProps{ - isUser:boolean; + isMyChat:boolean; message :string; } function ChatBubble(props: ChatBubbleProps){ return( - +
10:24 - - {props.message} + + {props.message}
@@ -22,13 +22,13 @@ function ChatBubble(props: ChatBubbleProps){ ); } //user 쪽 채팅과 상대방쪽 채팅 props로 구분 -const ChatBubbleContainer = styled.div<{isUser:boolean}>` +const ChatBubbleContainer = styled.div<{isMyChat:boolean}>` display: flex; flex-direction : column; - align-items: ${props => (props.isUser ? "flex-end" : "flex-start")}; + align-items: ${props => (props.isMyChat ? "flex-end" : "flex-start")}; .chatWrapper{ display:flex; - flex-direction : ${props => (props.isUser ? "row" : "row-reverse")}; + flex-direction : ${props => (props.isMyChat ? "row" : "row-reverse")}; align-items: flex-end; gap : 0.3125rem; } @@ -36,16 +36,16 @@ const ChatBubbleContainer = styled.div<{isUser:boolean}>` margin-bottom : 0.625rem; } `; -const ChatBox = styled.div<{isUser:boolean}>` +const ChatBox = styled.div<{isMyChat:boolean}>` display: inline-block; - background-color : ${props => (props.isUser ? "var(--green)" : "var(--gray-1)")}; + background-color : ${props => (props.isMyChat ? "var(--green)" : "var(--gray-1)")}; max-width : 16.8125rem; width: fit-content; border-radius: 6.25rem; - margin : ${props => (props.isUser ? "0.625rem 1.25rem 0.625rem 0" : "0.625rem 0 0.625rem 1.25rem")}; + margin : ${props => (props.isMyChat ? "0.625rem 1.25rem 0.625rem 0" : "0.625rem 0 0.625rem 1.25rem")}; `; -const ChatText = styled(Body2)<{isUser:boolean}>` - color : ${props => (props.isUser ? "var(--gray-1)" : "var(--gray-7)")}; +const ChatText = styled(Body2)<{isMyChat:boolean}>` + color : ${props => (props.isMyChat ? "var(--gray-1)" : "var(--gray-7)")}; padding: 0.625rem 1.25rem; `; diff --git a/src/components/ChattingFull.tsx b/src/components/ChattingFull.tsx index b780976..cbe34da 100644 --- a/src/components/ChattingFull.tsx +++ b/src/components/ChattingFull.tsx @@ -4,7 +4,7 @@ import { Body2 ,Caption2} from "../style/font"; import { useState } from "react"; import ChatBubble from "./ChatBubble"; import { useRecoilState, useRecoilValue } from "recoil"; -import { chatRoomListState, currentUserState } from "../recoil/state"; +import { chatRoomListState, loginUserState ,nowUserIdState} from "../recoil/state"; interface ChattingProps{ chatRoomId : number; isUser:boolean; @@ -15,14 +15,18 @@ function ChattingFull(props:ChattingProps){ const initializedChat = chatRoomList[props.chatRoomId].chatList; //현재 채팅방 chat list const [chatList, setChatList] = useState(initializedChat); - //현재 user id, chat의 userId와 같을 경우 true 넘김 - const currentUser = useRecoilValue(currentUserState); + //현재 사용중인 user의 id + const nowUser = useRecoilValue(nowUserIdState); return( { chatList.map((value, index)=>{ return( - + )}) } diff --git a/src/components/ChattingProfile.tsx b/src/components/ChattingProfile.tsx index 8af2935..9e4f007 100644 --- a/src/components/ChattingProfile.tsx +++ b/src/components/ChattingProfile.tsx @@ -4,8 +4,14 @@ import { ReactComponent as Friends } from "../assets/icons/Freinds.svg"; import { ReactComponent as More } from "../assets/icons/More.svg"; import { Heading2, Caption1 } from "../style/font"; import "../style/color.css"; +import { usersState } from "../recoil/state"; +import { useRecoilValue } from "recoil"; import styled from "styled-components"; -function ChattingProfile(){ +interface ChattingProfileProps{ + userId:number; +} +function ChattingProfile(props:ChattingProfileProps){ + const users = useRecoilValue(usersState); return( @@ -14,10 +20,10 @@ function ChattingProfile(){ - 신현재 - 근무 중 + {users[props.userId].name} + {users[props.userId].isWorking} - 삼성전자/HR/부장 + {users[props.userId].company}/{users[props.userId].department}/{users[props.userId].rank} ); diff --git a/src/data/chatData.json b/src/data/chatData.json index 67b8f8b..59facd2 100644 --- a/src/data/chatData.json +++ b/src/data/chatData.json @@ -12,7 +12,7 @@ { "chatId":1, "userId":3, - "message" :"앗 그렇군뇽" + "message" :"앗 그렇군뇽 그냥 하세요" } ] }, @@ -31,6 +31,11 @@ "message" :"네" } ] + }, + { + "chatRoomId": 2, + "userList": [0,4], + "chatList":[] } ] } \ No newline at end of file diff --git a/src/data/userData.json b/src/data/userData.json index 2f76b47..3847485 100644 --- a/src/data/userData.json +++ b/src/data/userData.json @@ -6,7 +6,8 @@ "profileImage": "", "company":"삼성전자", "department": "HR", - "rank":"부장" + "rank":"부장", + "isWorking":"근무 중" }, { "userId": 1, @@ -14,7 +15,8 @@ "profileImage": "", "company":"카카오뱅크", "department": "프로덕트팀", - "rank":"팀장" + "rank":"팀장", + "isWorking":"퇴근" }, { "userId": 2, @@ -22,7 +24,8 @@ "profileImage": "", "company":"하나은행", "department": "영업1팀", - "rank":"차장" + "rank":"차장", + "isWorking":"퇴근" }, { "userId": 3, @@ -30,7 +33,8 @@ "profileImage": "", "company":"제일기획", "department": "기획2팀", - "rank":"팀장" + "rank":"팀장", + "isWorking":"퇴근" }, { "userId": 4, @@ -38,7 +42,8 @@ "profileImage": "", "company":"삼성전자", "department": "글로벌사업부", - "rank":"부장" + "rank":"부장", + "isWorking":"근무 중" }, { "userId": 5, @@ -46,7 +51,8 @@ "profileImage": "", "company":"삼성전자", "department": "DX", - "rank":"부장" + "rank":"부장", + "isWorking":"근무 중" } ] } \ No newline at end of file diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index 83ece28..d190ea8 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -3,15 +3,40 @@ import ChattingFull from "../components/ChattingFull"; import ChattingInput from "../components/ChattingInput"; import ChattingProfile from "../components/ChattingProfile"; import styled from "styled-components"; -function ChattingPage(){ +import {useState} from "react"; +import { useRecoilState, useRecoilValue } from "recoil"; +import { chatRoomListState, nowUserIdState } from "../recoil/state"; +interface ChattingPageProps{ + chatRoomId:number; +} +function ChattingPage(props:ChattingPageProps){ + //chatting 전체 리스트 + const chatRoomList = useRecoilValue(chatRoomListState); + //채팅방 사용자 2명 + const roomUsers = chatRoomList[props.chatRoomId].userList; + //user switch 상태 + const [switchUser,setSwitchUser] = useState(0); + //list 길이 체크해서 빈 채팅방 or 채팅있는 채팅방 + const chatList = chatRoomList[props.chatRoomId].chatList; + //현재 사용중인 user의 id(login user 아님) + const [nowUserId, setNowUserId] = useRecoilState(nowUserIdState); + //0,1로 switch 하면서 채팅방 userlist의 0,1인덱스의 user로 전환 + const handleUserSwitch = ()=>{ + if(switchUser === 0){ + setSwitchUser(1); + } + else if(switchUser === 1){ + setSwitchUser(0); + } + setNowUserId(roomUsers[switchUser]); + }; return(
- - +
+ +
- {/* 대화내용 있고 없음으로 예외처리 isUser 여기서 넘겨야함*/} - - {/* */} + {chatList.length !== 0 ? : }
); diff --git a/src/recoil/state.ts b/src/recoil/state.ts index a4b3431..93014a4 100644 --- a/src/recoil/state.ts +++ b/src/recoil/state.ts @@ -1,16 +1,27 @@ import {atom, selector, selectorFamily} from 'recoil'; import userData from '../data/userData.json'; import chatData from '../data/chatData.json'; -//현재 user,나머지 user list, chattingRoom list -export const currentUserState = atom({ - key : 'currentUserState', +//현재 login한 user,나머지 user list, chattingRoom list +export const loginUserState = atom({ + key : 'loginUserState', default: userData.users[0], }); - +//초기 사용 user는 0번 고정 +export const nowUserIdState = atom({ + key : 'nowUserIdState', + default : userData.users[0].userId, +}); +//user제외 나머지 friends export const friendsState = atom({ key : 'friendsState', default : userData.users.slice(1), }); +//총 user데이터 +export const usersState = atom({ + key : 'usersState', + default : userData.users, +}); + export const chatRoomListState = atom({ key : 'chatRoomListState', From b7eacd3ebe7afd82a21bbbbaf4ae78eea01d8404 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Fri, 29 Sep 2023 00:58:58 +0900 Subject: [PATCH 12/55] =?UTF-8?q?feat:=20=EC=B1=84=ED=8C=85=20=EA=B8=B0?= =?UTF-8?q?=EB=8A=A5=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/ChatBubble.tsx | 9 +++- src/components/ChattingFull.tsx | 74 ++++++++++++++++++++++-------- src/components/ChattingInput.tsx | 41 +++++++++++++++-- src/components/ChattingProfile.tsx | 1 + src/data/chatData.json | 12 +++-- src/pages/ChattingPage.tsx | 5 +- src/recoil/state.ts | 11 +++-- src/style/color.css | 24 +++++----- 8 files changed, 132 insertions(+), 45 deletions(-) diff --git a/src/components/ChatBubble.tsx b/src/components/ChatBubble.tsx index 74c34a1..d697ae7 100644 --- a/src/components/ChatBubble.tsx +++ b/src/components/ChatBubble.tsx @@ -4,15 +4,20 @@ import { Body2 ,Caption2} from "../style/font"; interface ChatBubbleProps{ isMyChat:boolean; message :string; + chatDate : string; } - function ChatBubble(props: ChatBubbleProps){ + const date = new Date(props.chatDate); + const hours = date.getHours(); + const minutes = date.getMinutes(); + const isAM = hours < 12 ? true : false; + const hours12 = hours < 13 ? hours : hours-12; return(
10:24 + color="var(--gray-4)">{isAM ? "오전" : "오후"} {hours12}:{minutes<10 ? "0"+minutes : minutes} {props.message} diff --git a/src/components/ChattingFull.tsx b/src/components/ChattingFull.tsx index cbe34da..9bf2474 100644 --- a/src/components/ChattingFull.tsx +++ b/src/components/ChattingFull.tsx @@ -1,47 +1,85 @@ import styled from "styled-components"; import "../style/color.css"; -import { Body2 ,Caption2} from "../style/font"; -import { useState } from "react"; +import {Caption1} from "../style/font"; +import React, { useEffect, useRef} from "react"; import ChatBubble from "./ChatBubble"; -import { useRecoilState, useRecoilValue } from "recoil"; -import { chatRoomListState, loginUserState ,nowUserIdState} from "../recoil/state"; +import { useRecoilValue } from "recoil"; +import { chatListByIdState, nowUserIdState} from "../recoil/state"; interface ChattingProps{ chatRoomId : number; isUser:boolean; } +const dayList = ["일","월", "화","수", "목","금", "토"]; function ChattingFull(props:ChattingProps){ - //모든 채팅방 정보 - const chatRoomList = useRecoilValue(chatRoomListState); - const initializedChat = chatRoomList[props.chatRoomId].chatList; - //현재 채팅방 chat list - const [chatList, setChatList] = useState(initializedChat); + // //현재 채팅방 chat list + const chatList = useRecoilValue(chatListByIdState(props.chatRoomId)); //현재 사용중인 user의 id const nowUser = useRecoilValue(nowUserIdState); + + //chat 추가 되면 scroll 밑으로 + const scrollRef = useRef(null); + useEffect(()=>{ + if(scrollRef.current){ + scrollRef.current.scrollTop = scrollRef.current.scrollHeight; + } + + },[chatList]); return( - + { chatList.map((value, index)=>{ + //여기서 변화체크 + let dateChange:boolean = false; + const nowChatDate =new Date(chatList[index].date); + if(index === 0 ){ + dateChange=true; + } + else{ + const lastChatDate =new Date(chatList[index-1].date); + if(lastChatDate.getDate() !== nowChatDate.getDate()){ + dateChange=true; + } + else{ + dateChange=false; + } + } return( - - )}) + <> + + {dateChange? + {nowChatDate.getFullYear()}년 {nowChatDate.getMonth()+1}월 {nowChatDate.getDate()}일 ({dayList[nowChatDate.getDay()]}) + :null} + + + + ) + }) } ); -} +}; const ChattingFullWrapper = styled.div` display : flex; flex-direction : column; width: 23.4375rem; height: 37.69rem; - overflow-y: scroll; + overflow-y: auto; scrollbar-width: none; /* Firefox */ -ms-overflow-style: none; /* Internet Explorer/Edge */ &::-webkit-scrollbar { display: none; /* Chrome, Safari*/ } `; +const DateCaption = styled.div` + display:flex; + justify-content : center; + align-items : center; + .dateBox{ + padding: 0.9375rem 0; + } +`; export default ChattingFull; diff --git a/src/components/ChattingInput.tsx b/src/components/ChattingInput.tsx index 75dacea..ca88dfb 100644 --- a/src/components/ChattingInput.tsx +++ b/src/components/ChattingInput.tsx @@ -3,9 +3,25 @@ import { ReactComponent as Plus } from "../assets/icons/Plus.svg"; import { ReactComponent as Send } from "../assets/icons/Send.svg"; import styled from "styled-components"; import { Body2, Caption1 } from "../style/font"; -function ChattingInput(){ +import { chatListByIdState, chatRoomListState, nowUserIdState } from "../recoil/state"; +import { useRecoilState, useRecoilValue } from "recoil"; +interface ChattingInputProps{ + chatRoomId : number; +} +interface ChatInfo{ + chatId:number; + userId:number; + message:string; + date:string; +} +function ChattingInput(props : ChattingInputProps){ const [typeMessage, setTypeMessage] = useState("메세지를 입력하세요"); - const[input,setInput] = useState(""); + const [input,setInput] = useState(""); + //현재 사용 user ID + const nowUser = useRecoilValue(nowUserIdState); + //모든 채팅방 list + const [chatRoomList,setChatRoomList] = useRecoilState(chatRoomListState); + const [chatList, setChatList] = useRecoilState(chatListByIdState(props.chatRoomId)); //메세지창에 메세지 없을 때만 placeholder 출력 const handleFocus = ()=>{ setTypeMessage(""); @@ -17,7 +33,18 @@ function ChattingInput(){ } const handleSubmit = (e:any)=>{ e.preventDefault(); - setInput(""); + if(input.trim() !== ""){ + const chatInstance:ChatInfo = { + chatId:chatRoomList[props.chatRoomId].chatList.length,//현재 chatlength+1 + userId:nowUser, + message: input, + date: String(new Date()) + } + const copy = [...chatList]; + copy.push(chatInstance); + setChatList(copy); + setInput(""); + } } const handleOnChange = (e:any)=>{ setInput(e.target.value); @@ -29,11 +56,12 @@ function ChattingInput(){ {typeMessage} - + ); } @@ -65,6 +93,11 @@ const StyledSend = styled(Send)` padding: 0.28125rem; top:1.47rem; right : 0.97rem; + cursor : pointer; + &:hover{ + color : #FFFFFF; + filter : brightness(300%); + } `; const StyledForm = styled.form` .message-input{ diff --git a/src/components/ChattingProfile.tsx b/src/components/ChattingProfile.tsx index 9e4f007..3409d25 100644 --- a/src/components/ChattingProfile.tsx +++ b/src/components/ChattingProfile.tsx @@ -65,6 +65,7 @@ const StyledMore = styled(More)` const UserInfoWrapper = styled.div` position:absolute; left:7.06rem; + padding-top:0.2rem; display:flex; flex-direction:column; align-items: flex-start; /*왼쪽으로 정렬*/ diff --git a/src/data/chatData.json b/src/data/chatData.json index 59facd2..3a66d68 100644 --- a/src/data/chatData.json +++ b/src/data/chatData.json @@ -7,12 +7,14 @@ { "chatId":0, "userId":0, - "message" :"에어팟을 끼고 일해도 힘듭니다" + "message" :"에어팟을 끼고 일해도 힘듭니다", + "date": "Thu Sep 28 2023 09:41:56 GMT+0900 (한국 표준시)" }, { "chatId":1, "userId":3, - "message" :"앗 그렇군뇽 그냥 하세요" + "message" :"앗 그렇군뇽 그냥 하세요", + "date": "Thu Sep 28 2023 10:31:42 GMT+0900 (한국 표준시)" } ] }, @@ -23,12 +25,14 @@ { "chatId":0, "userId":0, - "message" :"배고파요" + "message" :"배고파요", + "date": "Fri May 5 2023 16:18:14 GMT+0900 (한국 표준시)" }, { "chatId":1, "userId":2, - "message" :"네" + "message" :"네", + "date": "Fri May 5 2023 16:18:14 GMT+0900 (한국 표준시)" } ] }, diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index d190ea8..5668c1e 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -37,12 +37,13 @@ function ChattingPage(props:ChattingPageProps){
{chatList.length !== 0 ? : } - + ); } const Divider = styled.hr` border: 0.0625rem solid var(--gray-3); - margin : 0 0 0.3125rem 0; + margin : 0; + `; export default ChattingPage; \ No newline at end of file diff --git a/src/recoil/state.ts b/src/recoil/state.ts index 93014a4..fdaa0ca 100644 --- a/src/recoil/state.ts +++ b/src/recoil/state.ts @@ -1,4 +1,4 @@ -import {atom, selector, selectorFamily} from 'recoil'; +import {atom, atomFamily, selector, selectorFamily} from 'recoil'; import userData from '../data/userData.json'; import chatData from '../data/chatData.json'; //현재 login한 user,나머지 user list, chattingRoom list @@ -22,10 +22,15 @@ export const usersState = atom({ default : userData.users, }); - export const chatRoomListState = atom({ key : 'chatRoomListState', default : chatData.chattings, }); - +export const chatListByIdState = atomFamily({ + key: 'chatListByIdState', + default: (chatRoomId: number) => { + const chatRoom = chatData.chattings.find(room => room.chatRoomId === chatRoomId); + return chatRoom ? chatRoom.chatList : []; + }, + }); diff --git a/src/style/color.css b/src/style/color.css index 82c871a..043a9ce 100644 --- a/src/style/color.css +++ b/src/style/color.css @@ -1,12 +1,12 @@ -:root{ - --black : #1A1A1A; /*주로 배경색*/ - --gray-1 : #2E2E2E; - --gray-2 : #484848; - --gray-3 : #555555;/*비강조, 두루두루*/ - --gray-4 : #7E7E7E; /*비강조, 주로 텍스트*/ - --gray-5 :#A7A7A7; - --gray-6 :#D5D5D5;/*강조, 주로 아이콘*/ - --gray-7 :#F2F2F2;/*강조, 주로 텍스트*/ - --white : #FFFFFF; - --green : #22FF60;/*포인트*/ -} \ No newline at end of file +:root { + --black: #1a1a1a; /*주로 배경색*/ + --gray-1: #2e2e2e; + --gray-2: #484848; + --gray-3: #555555; /*비강조, 두루두루*/ + --gray-4: #7e7e7e; /*비강조, 주로 텍스트*/ + --gray-5: #a7a7a7; + --gray-6: #d5d5d5; /*강조, 주로 아이콘*/ + --gray-7: #f2f2f2; /*강조, 주로 텍스트*/ + --white: #ffffff; + --green: #22ff60; /*포인트*/ +} From b97b4708cf35c30327d59ed96c26a5bbb4c3acc9 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Fri, 29 Sep 2023 12:51:12 +0900 Subject: [PATCH 13/55] =?UTF-8?q?feat:=20localstorage=20=EC=A0=80=EC=9E=A5?= =?UTF-8?q?=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- public/favicon.ico | Bin 3870 -> 1150 bytes src/components/ChattingFull.tsx | 5 +++-- src/components/ChattingInput.tsx | 2 +- src/pages/ChattingPage.tsx | 20 ++++++++++++++++---- src/recoil/state.ts | 2 +- 5 files changed, 21 insertions(+), 8 deletions(-) diff --git a/public/favicon.ico b/public/favicon.ico index a11777cc471a4344702741ab1c8a588998b1311a..7537528f36b737dba52d4740d6c4cfa910bfaf58 100644 GIT binary patch literal 1150 zcmds%Pb-8`6vmITvzb!Xla-xMzz1OE8(2>Ar!=t|ij`t9)F?Hj#6n6|ifmCL3$d^v zc4K2|l+FA+=f38xncSJO>T7MsG9m}FNS z#`3#!O&LzvZbF5Z5T~Ghjd5Lnt-bN_%sr1!$;JMi223%WJjJpcdz literal 3870 zcma);c{J4h9>;%nil|2-o+rCuEF-(I%-F}ijC~o(k~HKAkr0)!FCj~d>`RtpD?8b; zXOC1OD!V*IsqUwzbMF1)-gEDD=A573Z-&G7^LoAC9|WO7Xc0Cx1g^Zu0u_SjAPB3vGa^W|sj)80f#V0@M_CAZTIO(t--xg= z!sii`1giyH7EKL_+Wi0ab<)&E_0KD!3Rp2^HNB*K2@PHCs4PWSA32*-^7d{9nH2_E zmC{C*N*)(vEF1_aMamw2A{ZH5aIDqiabnFdJ|y0%aS|64E$`s2ccV~3lR!u<){eS` z#^Mx6o(iP1Ix%4dv`t@!&Za-K@mTm#vadc{0aWDV*_%EiGK7qMC_(`exc>-$Gb9~W!w_^{*pYRm~G zBN{nA;cm^w$VWg1O^^<6vY`1XCD|s_zv*g*5&V#wv&s#h$xlUilPe4U@I&UXZbL z0)%9Uj&@yd03n;!7do+bfixH^FeZ-Ema}s;DQX2gY+7g0s(9;`8GyvPY1*vxiF&|w z>!vA~GA<~JUqH}d;DfBSi^IT*#lrzXl$fNpq0_T1tA+`A$1?(gLb?e#0>UELvljtQ zK+*74m0jn&)5yk8mLBv;=@}c{t0ztT<v;Avck$S6D`Z)^c0(jiwKhQsn|LDRY&w(Fmi91I7H6S;b0XM{e zXp0~(T@k_r-!jkLwd1_Vre^v$G4|kh4}=Gi?$AaJ)3I+^m|Zyj#*?Kp@w(lQdJZf4 z#|IJW5z+S^e9@(6hW6N~{pj8|NO*>1)E=%?nNUAkmv~OY&ZV;m-%?pQ_11)hAr0oAwILrlsGawpxx4D43J&K=n+p3WLnlDsQ$b(9+4 z?mO^hmV^F8MV{4Lx>(Q=aHhQ1){0d*(e&s%G=i5rq3;t{JC zmgbn5Nkl)t@fPH$v;af26lyhH!k+#}_&aBK4baYPbZy$5aFx4}ka&qxl z$=Rh$W;U)>-=S-0=?7FH9dUAd2(q#4TCAHky!$^~;Dz^j|8_wuKc*YzfdAht@Q&ror?91Dm!N03=4=O!a)I*0q~p0g$Fm$pmr$ zb;wD;STDIi$@M%y1>p&_>%?UP($15gou_ue1u0!4(%81;qcIW8NyxFEvXpiJ|H4wz z*mFT(qVx1FKufG11hByuX%lPk4t#WZ{>8ka2efjY`~;AL6vWyQKpJun2nRiZYDij$ zP>4jQXPaP$UC$yIVgGa)jDV;F0l^n(V=HMRB5)20V7&r$jmk{UUIe zVjKroK}JAbD>B`2cwNQ&GDLx8{pg`7hbA~grk|W6LgiZ`8y`{Iq0i>t!3p2}MS6S+ zO_ruKyAElt)rdS>CtF7j{&6rP-#c=7evGMt7B6`7HG|-(WL`bDUAjyn+k$mx$CH;q2Dz4x;cPP$hW=`pFfLO)!jaCL@V2+F)So3}vg|%O*^T1j>C2lx zsURO-zIJC$^$g2byVbRIo^w>UxK}74^TqUiRR#7s_X$e)$6iYG1(PcW7un-va-S&u zHk9-6Zn&>T==A)lM^D~bk{&rFzCi35>UR!ZjQkdSiNX*-;l4z9j*7|q`TBl~Au`5& z+c)*8?#-tgUR$Zd%Q3bs96w6k7q@#tUn`5rj+r@_sAVVLqco|6O{ILX&U-&-cbVa3 zY?ngHR@%l{;`ri%H*0EhBWrGjv!LE4db?HEWb5mu*t@{kv|XwK8?npOshmzf=vZA@ zVSN9sL~!sn?r(AK)Q7Jk2(|M67Uy3I{eRy z_l&Y@A>;vjkWN5I2xvFFTLX0i+`{qz7C_@bo`ZUzDugfq4+>a3?1v%)O+YTd6@Ul7 zAfLfm=nhZ`)P~&v90$&UcF+yXm9sq!qCx3^9gzIcO|Y(js^Fj)Rvq>nQAHI92ap=P z10A4@prk+AGWCb`2)dQYFuR$|H6iDE8p}9a?#nV2}LBCoCf(Xi2@szia7#gY>b|l!-U`c}@ zLdhvQjc!BdLJvYvzzzngnw51yRYCqh4}$oRCy-z|v3Hc*d|?^Wj=l~18*E~*cR_kU z{XsxM1i{V*4GujHQ3DBpl2w4FgFR48Nma@HPgnyKoIEY-MqmMeY=I<%oG~l!f<+FN z1ZY^;10j4M4#HYXP zw5eJpA_y(>uLQ~OucgxDLuf}fVs272FaMxhn4xnDGIyLXnw>Xsd^J8XhcWIwIoQ9} z%FoSJTAGW(SRGwJwb=@pY7r$uQRK3Zd~XbxU)ts!4XsJrCycrWSI?e!IqwqIR8+Jh zlRjZ`UO1I!BtJR_2~7AbkbSm%XQqxEPkz6BTGWx8e}nQ=w7bZ|eVP4?*Tb!$(R)iC z9)&%bS*u(lXqzitAN)Oo=&Ytn>%Hzjc<5liuPi>zC_nw;Z0AE3Y$Jao_Q90R-gl~5 z_xAb2J%eArrC1CN4G$}-zVvCqF1;H;abAu6G*+PDHSYFx@Tdbfox*uEd3}BUyYY-l zTfEsOqsi#f9^FoLO;ChK<554qkri&Av~SIM*{fEYRE?vH7pTAOmu2pz3X?Wn*!ROX ztd54huAk&mFBemMooL33RV-*1f0Q3_(7hl$<#*|WF9P!;r;4_+X~k~uKEqdzZ$5Al zV63XN@)j$FN#cCD;ek1R#l zv%pGrhB~KWgoCj%GT?%{@@o(AJGt*PG#l3i>lhmb_twKH^EYvacVY-6bsCl5*^~L0 zonm@lk2UvvTKr2RS%}T>^~EYqdL1q4nD%0n&Xqr^cK^`J5W;lRRB^R-O8b&HENO||mo0xaD+S=I8RTlIfVgqN@SXDr2&-)we--K7w= zJVU8?Z+7k9dy;s;^gDkQa`0nz6N{T?(A&Iz)2!DEecLyRa&FI!id#5Z7B*O2=PsR0 zEvc|8{NS^)!d)MDX(97Xw}m&kEO@5jqRaDZ!+%`wYOI<23q|&js`&o4xvjP7D_xv@ z5hEwpsp{HezI9!~6O{~)lLR@oF7?J7i>1|5a~UuoN=q&6N}EJPV_GD`&M*v8Y`^2j zKII*d_@Fi$+i*YEW+Hbzn{iQk~yP z>7N{S4)r*!NwQ`(qcN#8SRQsNK6>{)X12nbF`*7#ecO7I)Q$uZsV+xS4E7aUn+U(K baj7?x%VD!5Cxk2YbYLNVeiXvvpMCWYo=by@ diff --git a/src/components/ChattingFull.tsx b/src/components/ChattingFull.tsx index 9bf2474..b9e21d1 100644 --- a/src/components/ChattingFull.tsx +++ b/src/components/ChattingFull.tsx @@ -15,14 +15,15 @@ function ChattingFull(props:ChattingProps){ const chatList = useRecoilValue(chatListByIdState(props.chatRoomId)); //현재 사용중인 user의 id const nowUser = useRecoilValue(nowUserIdState); - + //chat 추가 되면 scroll 밑으로 const scrollRef = useRef(null); + //chat 추가되면 scroll 내리고, localstorage 저장 useEffect(()=>{ if(scrollRef.current){ scrollRef.current.scrollTop = scrollRef.current.scrollHeight; } - + localStorage.setItem("chat"+String(props.chatRoomId),JSON.stringify(chatList)); },[chatList]); return( diff --git a/src/components/ChattingInput.tsx b/src/components/ChattingInput.tsx index ca88dfb..07387bb 100644 --- a/src/components/ChattingInput.tsx +++ b/src/components/ChattingInput.tsx @@ -35,7 +35,7 @@ function ChattingInput(props : ChattingInputProps){ e.preventDefault(); if(input.trim() !== ""){ const chatInstance:ChatInfo = { - chatId:chatRoomList[props.chatRoomId].chatList.length,//현재 chatlength+1 + chatId:chatList.length,//현재 chatlength+1 userId:nowUser, message: input, date: String(new Date()) diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index 5668c1e..5c5c855 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -3,15 +3,17 @@ import ChattingFull from "../components/ChattingFull"; import ChattingInput from "../components/ChattingInput"; import ChattingProfile from "../components/ChattingProfile"; import styled from "styled-components"; -import {useState} from "react"; +import {useState, useEffect} from "react"; import { useRecoilState, useRecoilValue } from "recoil"; -import { chatRoomListState, nowUserIdState } from "../recoil/state"; +import { chatListByIdState, chatRoomListState, nowUserIdState } from "../recoil/state"; interface ChattingPageProps{ chatRoomId:number; } function ChattingPage(props:ChattingPageProps){ //chatting 전체 리스트 const chatRoomList = useRecoilValue(chatRoomListState); + //해당 채팅방 chatting list + const [chatListById, setChatListById] = useRecoilState(chatListByIdState(props.chatRoomId)); //채팅방 사용자 2명 const roomUsers = chatRoomList[props.chatRoomId].userList; //user switch 상태 @@ -20,6 +22,17 @@ function ChattingPage(props:ChattingPageProps){ const chatList = chatRoomList[props.chatRoomId].chatList; //현재 사용중인 user의 id(login user 아님) const [nowUserId, setNowUserId] = useRecoilState(nowUserIdState); + //localstorage에 없으면 json 파일 저장, 있으면 chatList 불러옴 + const initializeChat = localStorage.getItem("chat"+String(props.chatRoomId)); + useEffect(()=>{ + if(initializeChat===null){ + localStorage.setItem("chat"+String(props.chatRoomId),JSON.stringify(chatListById)); + } + else{ + setChatListById(JSON.parse(initializeChat)); + } + },[]) + //0,1로 switch 하면서 채팅방 userlist의 0,1인덱스의 user로 전환 const handleUserSwitch = ()=>{ if(switchUser === 0){ @@ -43,7 +56,6 @@ function ChattingPage(props:ChattingPageProps){ } const Divider = styled.hr` border: 0.0625rem solid var(--gray-3); - margin : 0; - + margin : 0; `; export default ChattingPage; \ No newline at end of file diff --git a/src/recoil/state.ts b/src/recoil/state.ts index fdaa0ca..bd14cf2 100644 --- a/src/recoil/state.ts +++ b/src/recoil/state.ts @@ -33,4 +33,4 @@ export const chatListByIdState = atomFamily({ const chatRoom = chatData.chattings.find(room => room.chatRoomId === chatRoomId); return chatRoom ? chatRoom.chatList : []; }, - }); +}); From 5512ac52dda1940ec14eb7445c1518643248ea6d Mon Sep 17 00:00:00 2001 From: leekyuho Date: Fri, 29 Sep 2023 15:10:57 +0900 Subject: [PATCH 14/55] =?UTF-8?q?chore:=20app=20=EB=AA=85=20=EB=B3=80?= =?UTF-8?q?=EA=B2=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- public/index.html | 4 ++-- src/components/ChattingFull.tsx | 3 +-- 2 files changed, 3 insertions(+), 4 deletions(-) diff --git a/public/index.html b/public/index.html index aa069f2..74da10b 100644 --- a/public/index.html +++ b/public/index.html @@ -1,4 +1,4 @@ - + @@ -24,7 +24,7 @@ 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`. --> - React App + Chat diff --git a/src/components/ChattingFull.tsx b/src/components/ChattingFull.tsx index b9e21d1..cc10305 100644 --- a/src/components/ChattingFull.tsx +++ b/src/components/ChattingFull.tsx @@ -15,7 +15,6 @@ function ChattingFull(props:ChattingProps){ const chatList = useRecoilValue(chatListByIdState(props.chatRoomId)); //현재 사용중인 user의 id const nowUser = useRecoilValue(nowUserIdState); - //chat 추가 되면 scroll 밑으로 const scrollRef = useRef(null); //chat 추가되면 scroll 내리고, localstorage 저장 @@ -29,7 +28,7 @@ function ChattingFull(props:ChattingProps){ { chatList.map((value, index)=>{ - //여기서 변화체크 + //하루넘어가면 날짜 출력 let dateChange:boolean = false; const nowChatDate =new Date(chatList[index].date); if(index === 0 ){ From 71f0a7fe223cf630da3953b60fbc5b39e62aae00 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Fri, 29 Sep 2023 16:25:41 +0900 Subject: [PATCH 15/55] =?UTF-8?q?fix:=20build=EC=8B=9C=20svg=20module=20?= =?UTF-8?q?=EB=B2=84=EA=B7=B8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/custom.d.ts => custom.d.ts | 0 src/components/ChattingEmpty.tsx | 1 - src/components/ChattingFull.tsx | 2 +- src/components/ChattingInput.tsx | 2 +- tsconfig.json | 3 +-- 5 files changed, 3 insertions(+), 5 deletions(-) rename src/custom.d.ts => custom.d.ts (100%) diff --git a/src/custom.d.ts b/custom.d.ts similarity index 100% rename from src/custom.d.ts rename to custom.d.ts diff --git a/src/components/ChattingEmpty.tsx b/src/components/ChattingEmpty.tsx index 6487c74..0a76add 100644 --- a/src/components/ChattingEmpty.tsx +++ b/src/components/ChattingEmpty.tsx @@ -1,5 +1,4 @@ import { ReactComponent as Chat } from "../assets/icons/Chat.svg"; -import ChatBubble from "./ChatBubble"; import styled from "styled-components"; import { Body2 } from "../style/font"; diff --git a/src/components/ChattingFull.tsx b/src/components/ChattingFull.tsx index cc10305..b59a67c 100644 --- a/src/components/ChattingFull.tsx +++ b/src/components/ChattingFull.tsx @@ -1,7 +1,7 @@ import styled from "styled-components"; import "../style/color.css"; import {Caption1} from "../style/font"; -import React, { useEffect, useRef} from "react"; +import { useEffect, useRef} from "react"; import ChatBubble from "./ChatBubble"; import { useRecoilValue } from "recoil"; import { chatListByIdState, nowUserIdState} from "../recoil/state"; diff --git a/src/components/ChattingInput.tsx b/src/components/ChattingInput.tsx index 07387bb..85672eb 100644 --- a/src/components/ChattingInput.tsx +++ b/src/components/ChattingInput.tsx @@ -2,7 +2,7 @@ import { useState } from "react"; import { ReactComponent as Plus } from "../assets/icons/Plus.svg"; import { ReactComponent as Send } from "../assets/icons/Send.svg"; import styled from "styled-components"; -import { Body2, Caption1 } from "../style/font"; +import { Body2 } from "../style/font"; import { chatListByIdState, chatRoomListState, nowUserIdState } from "../recoil/state"; import { useRecoilState, useRecoilValue } from "recoil"; interface ChattingInputProps{ diff --git a/tsconfig.json b/tsconfig.json index 28aa7d5..a71d860 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -21,6 +21,5 @@ "jsx": "react-jsx" }, "include": [ - "src","src/custom.d.ts" - ] + "src", "custom.d.ts" ] } \ No newline at end of file From 98e62b4f60999e8250ca648d92cc3e6165e1e9bb Mon Sep 17 00:00:00 2001 From: leekyuho Date: Fri, 29 Sep 2023 16:57:23 +0900 Subject: [PATCH 16/55] =?UTF-8?q?chore:=20custom.d.ts=20=ED=8F=B4=EB=8D=94?= =?UTF-8?q?=20=EC=9C=84=EC=B9=98=20=EB=B3=80=EA=B2=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- package-lock.json | 3897 ++++++++++++++------------------ package.json | 6 +- custom.d.ts => src/custom.d.ts | 0 tsconfig.json | 3 +- 4 files changed, 1705 insertions(+), 2201 deletions(-) rename custom.d.ts => src/custom.d.ts (100%) diff --git a/package-lock.json b/package-lock.json index 8edf0d4..9487c0a 100644 --- a/package-lock.json +++ b/package-lock.json @@ -12,9 +12,9 @@ "@testing-library/react": "^13.4.0", "@testing-library/user-event": "^13.5.0", "@types/jest": "^29.5.5", - "@types/node": "^20.6.5", - "@types/react": "^18.2.22", - "@types/react-dom": "^18.2.7", + "@types/node": "^20.7.1", + "@types/react": "^18.2.23", + "@types/react-dom": "^18.2.8", "react": "^18.2.0", "react-dom": "^18.2.0", "react-scripts": "5.0.1", @@ -65,13 +65,13 @@ } }, "node_modules/@babel/cli": { - "version": "7.22.15", - "resolved": "https://registry.npmjs.org/@babel/cli/-/cli-7.22.15.tgz", - "integrity": "sha512-prtg5f6zCERIaECeTZzd2fMtVjlfjhUcO+fBLQ6DXXdq5FljN+excVitJ2nogsusdf31LeqkjAfXZ7Xq+HmN8g==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/cli/-/cli-7.23.0.tgz", + "integrity": "sha512-17E1oSkGk2IwNILM4jtfAvgjt+ohmpfBky8aLerUfYZhiPNg7ca+CRCxZn8QDxwNhV/upsc2VHBCqGFIR+iBfA==", "dependencies": { "@jridgewell/trace-mapping": "^0.3.17", "commander": "^4.0.1", - "convert-source-map": "^1.1.0", + "convert-source-map": "^2.0.0", "fs-readdir-recursive": "^1.1.0", "glob": "^7.2.0", "make-dir": "^2.1.0", @@ -148,6 +148,70 @@ "node": ">=6.9.0" } }, + "node_modules/@babel/code-frame/node_modules/ansi-styles": { + "version": "3.2.1", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", + "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", + "dependencies": { + "color-convert": "^1.9.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/code-frame/node_modules/chalk": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", + "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", + "dependencies": { + "ansi-styles": "^3.2.1", + "escape-string-regexp": "^1.0.5", + "supports-color": "^5.3.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/code-frame/node_modules/color-convert": { + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz", + "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==", + "dependencies": { + "color-name": "1.1.3" + } + }, + "node_modules/@babel/code-frame/node_modules/color-name": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", + "integrity": "sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw==" + }, + "node_modules/@babel/code-frame/node_modules/escape-string-regexp": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", + "integrity": "sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==", + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/@babel/code-frame/node_modules/has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw==", + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/code-frame/node_modules/supports-color": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dependencies": { + "has-flag": "^3.0.0" + }, + "engines": { + "node": ">=4" + } + }, "node_modules/@babel/compat-data": { "version": "7.22.20", "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.22.20.tgz", @@ -157,21 +221,21 @@ } }, "node_modules/@babel/core": { - "version": "7.22.20", - "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.22.20.tgz", - "integrity": "sha512-Y6jd1ahLubuYweD/zJH+vvOY141v4f9igNQAQ+MBgq9JlHS2iTsZKn1aMsb3vGccZsXI16VzTBw52Xx0DWmtnA==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.23.0.tgz", + "integrity": "sha512-97z/ju/Jy1rZmDxybphrBuI+jtJjFVoz7Mr9yUQVVVi+DNZE333uFQeMOqcCIy1x3WYBIbWftUSLmbNXNT7qFQ==", "dependencies": { "@ampproject/remapping": "^2.2.0", "@babel/code-frame": "^7.22.13", - "@babel/generator": "^7.22.15", + "@babel/generator": "^7.23.0", "@babel/helper-compilation-targets": "^7.22.15", - "@babel/helper-module-transforms": "^7.22.20", - "@babel/helpers": "^7.22.15", - "@babel/parser": "^7.22.16", + "@babel/helper-module-transforms": "^7.23.0", + "@babel/helpers": "^7.23.0", + "@babel/parser": "^7.23.0", "@babel/template": "^7.22.15", - "@babel/traverse": "^7.22.20", - "@babel/types": "^7.22.19", - "convert-source-map": "^1.7.0", + "@babel/traverse": "^7.23.0", + "@babel/types": "^7.23.0", + "convert-source-map": "^2.0.0", "debug": "^4.1.0", "gensync": "^1.0.0-beta.2", "json5": "^2.2.3", @@ -227,11 +291,11 @@ } }, "node_modules/@babel/generator": { - "version": "7.22.15", - "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.22.15.tgz", - "integrity": "sha512-Zu9oWARBqeVOW0dZOjXc3JObrzuqothQ3y/n1kUtrjCoCPLkXUwMvOo/F/TCfoHMbWIFlWwpZtkZVb9ga4U2pA==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.23.0.tgz", + "integrity": "sha512-lN85QRR+5IbYrMWM6Y4pE/noaQtg4pNiqeNGX60eqOfo6gtEj6uw/JagelB8vVztSd7R6M5n1+PQkDbHbBRU4g==", "dependencies": { - "@babel/types": "^7.22.15", + "@babel/types": "^7.23.0", "@jridgewell/gen-mapping": "^0.3.2", "@jridgewell/trace-mapping": "^0.3.17", "jsesc": "^2.5.1" @@ -363,12 +427,12 @@ } }, "node_modules/@babel/helper-function-name": { - "version": "7.22.5", - "resolved": "https://registry.npmjs.org/@babel/helper-function-name/-/helper-function-name-7.22.5.tgz", - "integrity": "sha512-wtHSq6jMRE3uF2otvfuD3DIvVhOsSNshQl0Qrd7qC9oQJzHvOL4qQXlQn2916+CXGywIjpGuIkoyZRRxHPiNQQ==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/helper-function-name/-/helper-function-name-7.23.0.tgz", + "integrity": "sha512-OErEqsrxjZTJciZ4Oo+eoZqeW9UIiOcuYKRJA4ZAgV9myA+pOXhhmpfNCKjEH/auVfEYVFJ6y1Tc4r0eIApqiw==", "dependencies": { - "@babel/template": "^7.22.5", - "@babel/types": "^7.22.5" + "@babel/template": "^7.22.15", + "@babel/types": "^7.23.0" }, "engines": { "node": ">=6.9.0" @@ -386,11 +450,11 @@ } }, "node_modules/@babel/helper-member-expression-to-functions": { - "version": "7.22.15", - "resolved": "https://registry.npmjs.org/@babel/helper-member-expression-to-functions/-/helper-member-expression-to-functions-7.22.15.tgz", - "integrity": "sha512-qLNsZbgrNh0fDQBCPocSL8guki1hcPvltGDv/NxvUoABwFq7GkKSu1nRXeJkVZc+wJvne2E0RKQz+2SQrz6eAA==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/helper-member-expression-to-functions/-/helper-member-expression-to-functions-7.23.0.tgz", + "integrity": "sha512-6gfrPwh7OuT6gZyJZvd6WbTfrqAo7vm4xCzAXOusKqq/vWdKXphTpj5klHKNmRUU6/QRGlBsyU9mAIPaWHlqJA==", "dependencies": { - "@babel/types": "^7.22.15" + "@babel/types": "^7.23.0" }, "engines": { "node": ">=6.9.0" @@ -408,9 +472,9 @@ } }, "node_modules/@babel/helper-module-transforms": { - "version": "7.22.20", - "resolved": "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.22.20.tgz", - "integrity": "sha512-dLT7JVWIUUxKOs1UnJUBR3S70YK+pKX6AbJgB2vMIvEkZkrfJDbYDJesnPshtKV4LhDOR3Oc5YULeDizRek+5A==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.23.0.tgz", + "integrity": "sha512-WhDWw1tdrlT0gMgUJSlX0IQvoO1eN279zrAUbVB+KpV2c3Tylz8+GnKOLllCS6Z/iZQEyVYxhZVUdPTqs2YYPw==", "dependencies": { "@babel/helper-environment-visitor": "^7.22.20", "@babel/helper-module-imports": "^7.22.15", @@ -547,13 +611,13 @@ } }, "node_modules/@babel/helpers": { - "version": "7.22.15", - "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.22.15.tgz", - "integrity": "sha512-7pAjK0aSdxOwR+CcYAqgWOGy5dcfvzsTIfFTb2odQqW47MDfv14UaJDY6eng8ylM2EaeKXdxaSWESbkmaQHTmw==", + "version": "7.23.1", + "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.23.1.tgz", + "integrity": "sha512-chNpneuK18yW5Oxsr+t553UZzzAs3aZnFm4bxhebsNTeshrC95yA7l5yl7GBAG+JG1rF0F7zzD2EixK9mWSDoA==", "dependencies": { "@babel/template": "^7.22.15", - "@babel/traverse": "^7.22.15", - "@babel/types": "^7.22.15" + "@babel/traverse": "^7.23.0", + "@babel/types": "^7.23.0" }, "engines": { "node": ">=6.9.0" @@ -572,10 +636,74 @@ "node": ">=6.9.0" } }, + "node_modules/@babel/highlight/node_modules/ansi-styles": { + "version": "3.2.1", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", + "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", + "dependencies": { + "color-convert": "^1.9.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/highlight/node_modules/chalk": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", + "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", + "dependencies": { + "ansi-styles": "^3.2.1", + "escape-string-regexp": "^1.0.5", + "supports-color": "^5.3.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/highlight/node_modules/color-convert": { + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz", + "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==", + "dependencies": { + "color-name": "1.1.3" + } + }, + "node_modules/@babel/highlight/node_modules/color-name": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", + "integrity": "sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw==" + }, + "node_modules/@babel/highlight/node_modules/escape-string-regexp": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", + "integrity": "sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==", + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/@babel/highlight/node_modules/has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw==", + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/highlight/node_modules/supports-color": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dependencies": { + "has-flag": "^3.0.0" + }, + "engines": { + "node": ">=4" + } + }, "node_modules/@babel/parser": { - "version": "7.22.16", - "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.22.16.tgz", - "integrity": "sha512-+gPfKv8UWeKKeJTUxe59+OobVcrYHETCsORl61EmSkmgymguYk/X5bp7GuUIXaFsc6y++v8ZxPsLSSuujqDphA==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.23.0.tgz", + "integrity": "sha512-vvPKKdMemU85V9WE/l5wZEmImpCtLqbnTvqDS2U1fJ96KrxoW7KrXhNsNCblQlg8Ck4b85yxdTyelsMUgFUXiw==", "bin": { "parser": "bin/babel-parser.js" }, @@ -644,13 +772,13 @@ } }, "node_modules/@babel/plugin-proposal-decorators": { - "version": "7.22.15", - "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-decorators/-/plugin-proposal-decorators-7.22.15.tgz", - "integrity": "sha512-kc0VvbbUyKelvzcKOSyQUSVVXS5pT3UhRB0e3c9An86MvLqs+gx0dN4asllrDluqSa3m9YyooXKGOFVomnyFkg==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-decorators/-/plugin-proposal-decorators-7.23.0.tgz", + "integrity": "sha512-kYsT+f5ARWF6AdFmqoEEp+hpqxEB8vGmRWfw2aj78M2vTwS2uHW91EF58iFm1Z9U8Y/RrLu2XKJn46P9ca1b0w==", "dependencies": { "@babel/helper-create-class-features-plugin": "^7.22.15", "@babel/helper-plugin-utils": "^7.22.5", - "@babel/helper-replace-supers": "^7.22.9", + "@babel/helper-replace-supers": "^7.22.20", "@babel/helper-split-export-declaration": "^7.22.6", "@babel/plugin-syntax-decorators": "^7.22.10" }, @@ -1102,9 +1230,9 @@ } }, "node_modules/@babel/plugin-transform-block-scoping": { - "version": "7.22.15", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-block-scoping/-/plugin-transform-block-scoping-7.22.15.tgz", - "integrity": "sha512-G1czpdJBZCtngoK1sJgloLiOHUnkb/bLZwqVZD8kXmq0ZnVfTTWUcs9OWtp0mBtYJ+4LQY1fllqBkOIPhXmFmw==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-block-scoping/-/plugin-transform-block-scoping-7.23.0.tgz", + "integrity": "sha512-cOsrbmIOXmf+5YbL99/S49Y3j46k/T16b9ml8bm9lP6N9US5iQ2yBK7gpui1pg0V/WMcXdkfKbTb7HXq9u+v4g==", "dependencies": { "@babel/helper-plugin-utils": "^7.22.5" }, @@ -1184,9 +1312,9 @@ } }, "node_modules/@babel/plugin-transform-destructuring": { - "version": "7.22.15", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-destructuring/-/plugin-transform-destructuring-7.22.15.tgz", - "integrity": "sha512-HzG8sFl1ZVGTme74Nw+X01XsUTqERVQ6/RLHo3XjGRzm7XD6QTtfS3NJotVgCGy8BzkDqRjRBD8dAyJn5TuvSQ==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-destructuring/-/plugin-transform-destructuring-7.23.0.tgz", + "integrity": "sha512-vaMdgNXFkYrB+8lbgniSYWHsgqK5gjaMNcc84bMIOMRLH0L9AqYq3hwMdvnyqj1OPqea8UtjPEuS/DCenah1wg==", "dependencies": { "@babel/helper-plugin-utils": "^7.22.5" }, @@ -1375,11 +1503,11 @@ } }, "node_modules/@babel/plugin-transform-modules-amd": { - "version": "7.22.5", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-amd/-/plugin-transform-modules-amd-7.22.5.tgz", - "integrity": "sha512-R+PTfLTcYEmb1+kK7FNkhQ1gP4KgjpSO6HfH9+f8/yfp2Nt3ggBjiVpRwmwTlfqZLafYKJACy36yDXlEmI9HjQ==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-amd/-/plugin-transform-modules-amd-7.23.0.tgz", + "integrity": "sha512-xWT5gefv2HGSm4QHtgc1sYPbseOyf+FFDo2JbpE25GWl5BqTGO9IMwTYJRoIdjsF85GE+VegHxSCUt5EvoYTAw==", "dependencies": { - "@babel/helper-module-transforms": "^7.22.5", + "@babel/helper-module-transforms": "^7.23.0", "@babel/helper-plugin-utils": "^7.22.5" }, "engines": { @@ -1390,11 +1518,11 @@ } }, "node_modules/@babel/plugin-transform-modules-commonjs": { - "version": "7.22.15", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-commonjs/-/plugin-transform-modules-commonjs-7.22.15.tgz", - "integrity": "sha512-jWL4eh90w0HQOTKP2MoXXUpVxilxsB2Vl4ji69rSjS3EcZ/v4sBmn+A3NpepuJzBhOaEBbR7udonlHHn5DWidg==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-commonjs/-/plugin-transform-modules-commonjs-7.23.0.tgz", + "integrity": "sha512-32Xzss14/UVc7k9g775yMIvkVK8xwKE0DPdP5JTapr3+Z9w4tzeOuLNY6BXDQR6BdnzIlXnCGAzsk/ICHBLVWQ==", "dependencies": { - "@babel/helper-module-transforms": "^7.22.15", + "@babel/helper-module-transforms": "^7.23.0", "@babel/helper-plugin-utils": "^7.22.5", "@babel/helper-simple-access": "^7.22.5" }, @@ -1406,14 +1534,14 @@ } }, "node_modules/@babel/plugin-transform-modules-systemjs": { - "version": "7.22.11", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-systemjs/-/plugin-transform-modules-systemjs-7.22.11.tgz", - "integrity": "sha512-rIqHmHoMEOhI3VkVf5jQ15l539KrwhzqcBO6wdCNWPWc/JWt9ILNYNUssbRpeq0qWns8svuw8LnMNCvWBIJ8wA==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-systemjs/-/plugin-transform-modules-systemjs-7.23.0.tgz", + "integrity": "sha512-qBej6ctXZD2f+DhlOC9yO47yEYgUh5CZNz/aBoH4j/3NOlRfJXJbY7xDQCqQVf9KbrqGzIWER1f23doHGrIHFg==", "dependencies": { "@babel/helper-hoist-variables": "^7.22.5", - "@babel/helper-module-transforms": "^7.22.9", + "@babel/helper-module-transforms": "^7.23.0", "@babel/helper-plugin-utils": "^7.22.5", - "@babel/helper-validator-identifier": "^7.22.5" + "@babel/helper-validator-identifier": "^7.22.20" }, "engines": { "node": ">=6.9.0" @@ -1545,9 +1673,9 @@ } }, "node_modules/@babel/plugin-transform-optional-chaining": { - "version": "7.22.15", - "resolved": "https://registry.npmjs.org/@babel/plugin-transform-optional-chaining/-/plugin-transform-optional-chaining-7.22.15.tgz", - "integrity": "sha512-ngQ2tBhq5vvSJw2Q2Z9i7ealNkpDMU0rGWnHPKqRZO0tzZ5tlaoz4hDvhXioOoaE0X2vfNss1djwg0DXlfu30A==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-optional-chaining/-/plugin-transform-optional-chaining-7.23.0.tgz", + "integrity": "sha512-sBBGXbLJjxTzLBF5rFWaikMnOGOk/BmK6vVByIdEggZ7Vn6CvWXZyRkkLFK6WE0IF8jSliyOkUN6SScFgzCM0g==", "dependencies": { "@babel/helper-plugin-utils": "^7.22.5", "@babel/helper-skip-transparent-expression-wrappers": "^7.22.5", @@ -2032,14 +2160,14 @@ } }, "node_modules/@babel/preset-typescript": { - "version": "7.22.15", - "resolved": "https://registry.npmjs.org/@babel/preset-typescript/-/preset-typescript-7.22.15.tgz", - "integrity": "sha512-HblhNmh6yM+cU4VwbBRpxFhxsTdfS1zsvH9W+gEjD0ARV9+8B4sNfpI6GuhePti84nuvhiwKS539jKPFHskA9A==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/preset-typescript/-/preset-typescript-7.23.0.tgz", + "integrity": "sha512-6P6VVa/NM/VlAYj5s2Aq/gdVg8FSENCg3wlZ6Qau9AcPaoF5LbN1nyGlR9DTRIw9PpxI94e+ReydsJHcjwAweg==", "dependencies": { "@babel/helper-plugin-utils": "^7.22.5", "@babel/helper-validator-option": "^7.22.15", "@babel/plugin-syntax-jsx": "^7.22.5", - "@babel/plugin-transform-modules-commonjs": "^7.22.15", + "@babel/plugin-transform-modules-commonjs": "^7.23.0", "@babel/plugin-transform-typescript": "^7.22.15" }, "engines": { @@ -2055,9 +2183,9 @@ "integrity": "sha512-x/rqGMdzj+fWZvCOYForTghzbtqPDZ5gPwaoNGHdgDfF2QA/XZbCBp4Moo5scrkAMPhB7z26XM/AaHuIJdgauA==" }, "node_modules/@babel/runtime": { - "version": "7.22.15", - "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.22.15.tgz", - "integrity": "sha512-T0O+aa+4w0u06iNmapipJXMV4HoUir03hpx3/YqXXhu9xim3w+dVphjFWl1OH8NbZHw5Lbm9k45drDkgq2VNNA==", + "version": "7.23.1", + "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.23.1.tgz", + "integrity": "sha512-hC2v6p8ZSI/W0HUzh3V8C5g+NwSKzKPtJwSpTjwl0o297GP9+ZLQSkdvHz46CM3LqyoXxq+5G9komY+eSqSO0g==", "dependencies": { "regenerator-runtime": "^0.14.0" }, @@ -2079,18 +2207,18 @@ } }, "node_modules/@babel/traverse": { - "version": "7.22.20", - "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.22.20.tgz", - "integrity": "sha512-eU260mPZbU7mZ0N+X10pxXhQFMGTeLb9eFS0mxehS8HZp9o1uSnFeWQuG1UPrlxgA7QoUzFhOnilHDp0AXCyHw==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.23.0.tgz", + "integrity": "sha512-t/QaEvyIoIkwzpiZ7aoSKK8kObQYeF7T2v+dazAYCb8SXtp58zEVkWW7zAnju8FNKNdr4ScAOEDmMItbyOmEYw==", "dependencies": { "@babel/code-frame": "^7.22.13", - "@babel/generator": "^7.22.15", + "@babel/generator": "^7.23.0", "@babel/helper-environment-visitor": "^7.22.20", - "@babel/helper-function-name": "^7.22.5", + "@babel/helper-function-name": "^7.23.0", "@babel/helper-hoist-variables": "^7.22.5", "@babel/helper-split-export-declaration": "^7.22.6", - "@babel/parser": "^7.22.16", - "@babel/types": "^7.22.19", + "@babel/parser": "^7.23.0", + "@babel/types": "^7.23.0", "debug": "^4.1.0", "globals": "^11.1.0" }, @@ -2099,12 +2227,12 @@ } }, "node_modules/@babel/types": { - "version": "7.22.19", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.22.19.tgz", - "integrity": "sha512-P7LAw/LbojPzkgp5oznjE6tQEIWbp4PkkfrZDINTro9zgBRtI324/EYsiSI7lhPbpIQ+DCeR2NNmMWANGGfZsg==", + "version": "7.23.0", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.23.0.tgz", + "integrity": "sha512-0oIyUfKoI3mSqMvsxBdclDwxXKXAUA8v/apZbc+iSyARYou1o8ZGDxbUYyLFoW2arqS2jDGqJuZvv1d/io1axg==", "dependencies": { "@babel/helper-string-parser": "^7.22.5", - "@babel/helper-validator-identifier": "^7.22.19", + "@babel/helper-validator-identifier": "^7.22.20", "to-fast-properties": "^2.0.0" }, "engines": { @@ -2419,9 +2547,9 @@ } }, "node_modules/@eslint-community/regexpp": { - "version": "4.8.1", - "resolved": "https://registry.npmjs.org/@eslint-community/regexpp/-/regexpp-4.8.1.tgz", - "integrity": "sha512-PWiOzLIUAjN/w5K17PoF4n6sKBw0gqLHPhywmYHP4t1VFQQVYeb1yWsJwnMVEMl3tUHME7X/SJPZLmtG7XBDxQ==", + "version": "4.9.0", + "resolved": "https://registry.npmjs.org/@eslint-community/regexpp/-/regexpp-4.9.0.tgz", + "integrity": "sha512-zJmuCWj2VLBt4c25CfBIbMZLGLyhkvs7LznyVX5HfpzeocThgIj5XQK4L+g3U36mMcx8bPMhGyPpwCATamC4jQ==", "engines": { "node": "^12.0.0 || ^14.0.0 || >=16.0.0" } @@ -2622,68 +2750,62 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/@jest/console/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "node_modules/@jest/console/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", "dependencies": { - "color-convert": "^2.0.1" + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" }, "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/@jest/console/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "node_modules/@jest/console/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "@types/yargs-parser": "*" } }, - "node_modules/@jest/console/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/@jest/console/node_modules/jest-message-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-27.5.1.tgz", + "integrity": "sha512-rMyFe1+jnyAAf+NHwTclDz0eAaLkVDdKVHHBFWsBWHnnh5YeJMNWWsv7AbFYXfK3oTqvL7VTWkhNLu1jX24D+g==", "dependencies": { - "color-name": "~1.1.4" + "@babel/code-frame": "^7.12.13", + "@jest/types": "^27.5.1", + "@types/stack-utils": "^2.0.0", + "chalk": "^4.0.0", + "graceful-fs": "^4.2.9", + "micromatch": "^4.0.4", + "pretty-format": "^27.5.1", + "slash": "^3.0.0", + "stack-utils": "^2.0.3" }, "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@jest/console/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/@jest/console/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/@jest/console/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/@jest/console/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", "dependencies": { - "has-flag": "^4.0.0" + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" }, "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, "node_modules/@jest/core": { @@ -2732,68 +2854,62 @@ } } }, - "node_modules/@jest/core/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "node_modules/@jest/core/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", "dependencies": { - "color-convert": "^2.0.1" + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" }, "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/@jest/core/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "node_modules/@jest/core/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "@types/yargs-parser": "*" } }, - "node_modules/@jest/core/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/@jest/core/node_modules/jest-message-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-27.5.1.tgz", + "integrity": "sha512-rMyFe1+jnyAAf+NHwTclDz0eAaLkVDdKVHHBFWsBWHnnh5YeJMNWWsv7AbFYXfK3oTqvL7VTWkhNLu1jX24D+g==", "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@jest/core/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/@jest/core/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "@babel/code-frame": "^7.12.13", + "@jest/types": "^27.5.1", + "@types/stack-utils": "^2.0.0", + "chalk": "^4.0.0", + "graceful-fs": "^4.2.9", + "micromatch": "^4.0.4", + "pretty-format": "^27.5.1", + "slash": "^3.0.0", + "stack-utils": "^2.0.3" + }, "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/@jest/core/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/@jest/core/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", "dependencies": { - "has-flag": "^4.0.0" + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" }, "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, "node_modules/@jest/environment": { @@ -2810,6 +2926,29 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, + "node_modules/@jest/environment/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", + "dependencies": { + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/@jest/environment/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", + "dependencies": { + "@types/yargs-parser": "*" + } + }, "node_modules/@jest/expect-utils": { "version": "29.7.0", "resolved": "https://registry.npmjs.org/@jest/expect-utils/-/expect-utils-29.7.0.tgz", @@ -2821,14 +2960,6 @@ "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, - "node_modules/@jest/expect-utils/node_modules/jest-get-type": { - "version": "29.6.3", - "resolved": "https://registry.npmjs.org/jest-get-type/-/jest-get-type-29.6.3.tgz", - "integrity": "sha512-zrteXnqYxfQh7l5FHyL38jL39di8H8rHoecLH3JNxH3BwOrBsNeabdap5e0I23lD4HHI8W5VFBZqG4Eaq5LNcw==", - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, "node_modules/@jest/fake-timers": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/@jest/fake-timers/-/fake-timers-27.5.1.tgz", @@ -2845,6 +2976,64 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, + "node_modules/@jest/fake-timers/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", + "dependencies": { + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/@jest/fake-timers/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", + "dependencies": { + "@types/yargs-parser": "*" + } + }, + "node_modules/@jest/fake-timers/node_modules/jest-message-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-27.5.1.tgz", + "integrity": "sha512-rMyFe1+jnyAAf+NHwTclDz0eAaLkVDdKVHHBFWsBWHnnh5YeJMNWWsv7AbFYXfK3oTqvL7VTWkhNLu1jX24D+g==", + "dependencies": { + "@babel/code-frame": "^7.12.13", + "@jest/types": "^27.5.1", + "@types/stack-utils": "^2.0.0", + "chalk": "^4.0.0", + "graceful-fs": "^4.2.9", + "micromatch": "^4.0.4", + "pretty-format": "^27.5.1", + "slash": "^3.0.0", + "stack-utils": "^2.0.3" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/@jest/fake-timers/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", + "dependencies": { + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, "node_modules/@jest/globals": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/@jest/globals/-/globals-27.5.1.tgz", @@ -2858,6 +3047,106 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, + "node_modules/@jest/globals/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", + "dependencies": { + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/@jest/globals/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", + "dependencies": { + "@types/yargs-parser": "*" + } + }, + "node_modules/@jest/globals/node_modules/diff-sequences": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/diff-sequences/-/diff-sequences-27.5.1.tgz", + "integrity": "sha512-k1gCAXAsNgLwEL+Y8Wvl+M6oEFj5bgazfZULpS5CneoPPXRaCCW7dm+q21Ky2VEE5X+VeRDBVg1Pcvvsr4TtNQ==", + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/@jest/globals/node_modules/expect": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/expect/-/expect-27.5.1.tgz", + "integrity": "sha512-E1q5hSUG2AmYQwQJ041nvgpkODHQvB+RKlB4IYdru6uJsyFTRyZAP463M+1lINorwbqAmUggi6+WwkD8lCS/Dw==", + "dependencies": { + "@jest/types": "^27.5.1", + "jest-get-type": "^27.5.1", + "jest-matcher-utils": "^27.5.1", + "jest-message-util": "^27.5.1" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/@jest/globals/node_modules/jest-diff": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-diff/-/jest-diff-27.5.1.tgz", + "integrity": "sha512-m0NvkX55LDt9T4mctTEgnZk3fmEg3NRYutvMPWM/0iPnkFj2wIeF45O1718cMSOFO1vINkqmxqD8vE37uTEbqw==", + "dependencies": { + "chalk": "^4.0.0", + "diff-sequences": "^27.5.1", + "jest-get-type": "^27.5.1", + "pretty-format": "^27.5.1" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/@jest/globals/node_modules/jest-get-type": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-get-type/-/jest-get-type-27.5.1.tgz", + "integrity": "sha512-2KY95ksYSaK7DMBWQn6dQz3kqAf3BB64y2udeG+hv4KfSOb9qwcYQstTJc1KCbsix+wLZWZYN8t7nwX3GOBLRw==", + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/@jest/globals/node_modules/jest-matcher-utils": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-matcher-utils/-/jest-matcher-utils-27.5.1.tgz", + "integrity": "sha512-z2uTx/T6LBaCoNWNFWwChLBKYxTMcGBRjAt+2SbP929/Fflb9aa5LGma654Rz8z9HLxsrUaYzxE9T/EFIL/PAw==", + "dependencies": { + "chalk": "^4.0.0", + "jest-diff": "^27.5.1", + "jest-get-type": "^27.5.1", + "pretty-format": "^27.5.1" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/@jest/globals/node_modules/jest-message-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-27.5.1.tgz", + "integrity": "sha512-rMyFe1+jnyAAf+NHwTclDz0eAaLkVDdKVHHBFWsBWHnnh5YeJMNWWsv7AbFYXfK3oTqvL7VTWkhNLu1jX24D+g==", + "dependencies": { + "@babel/code-frame": "^7.12.13", + "@jest/types": "^27.5.1", + "@types/stack-utils": "^2.0.0", + "chalk": "^4.0.0", + "graceful-fs": "^4.2.9", + "micromatch": "^4.0.4", + "pretty-format": "^27.5.1", + "slash": "^3.0.0", + "stack-utils": "^2.0.3" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, "node_modules/@jest/reporters": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/@jest/reporters/-/reporters-27.5.1.tgz", @@ -2901,57 +3190,43 @@ } } }, - "node_modules/@jest/reporters/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "node_modules/@jest/reporters/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", "dependencies": { - "color-convert": "^2.0.1" + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" }, "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/@jest/reporters/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "node_modules/@jest/reporters/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "@types/yargs-parser": "*" } }, - "node_modules/@jest/reporters/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/@jest/reporters/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", "dependencies": { - "color-name": "~1.1.4" + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" }, "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@jest/reporters/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/@jest/reporters/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, "node_modules/@jest/reporters/node_modules/source-map": { @@ -2962,26 +3237,15 @@ "node": ">=0.10.0" } }, - "node_modules/@jest/reporters/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, "node_modules/@jest/schemas": { - "version": "28.1.3", - "resolved": "https://registry.npmjs.org/@jest/schemas/-/schemas-28.1.3.tgz", - "integrity": "sha512-/l/VWsdt/aBXgjshLWOFyFt3IVdYypu5y2Wn2rOO1un6nkqIn8SLXzgIMYXFyYsRWDyF5EthmKJMIdJvk08grg==", + "version": "29.6.3", + "resolved": "https://registry.npmjs.org/@jest/schemas/-/schemas-29.6.3.tgz", + "integrity": "sha512-mo5j5X+jIZmJQveBKeS/clAueipV7KgiX1vMgCxam1RNYiqE1w62n0/tJJnHtjW8ZHcQco5gY85jA3mi0L+nSA==", "dependencies": { - "@sinclair/typebox": "^0.24.1" + "@sinclair/typebox": "^0.27.8" }, "engines": { - "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, "node_modules/@jest/source-map": { @@ -3019,6 +3283,29 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, + "node_modules/@jest/test-result/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", + "dependencies": { + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/@jest/test-result/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", + "dependencies": { + "@types/yargs-parser": "*" + } + }, "node_modules/@jest/test-sequencer": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/@jest/test-sequencer/-/test-sequencer-27.5.1.tgz", @@ -3058,79 +3345,7 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/@jest/transform/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/@jest/transform/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/@jest/transform/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@jest/transform/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/@jest/transform/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" - } - }, - "node_modules/@jest/transform/node_modules/source-map": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/@jest/transform/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/@jest/types": { + "node_modules/@jest/transform/node_modules/@jest/types": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", @@ -3141,72 +3356,61 @@ "@types/yargs": "^16.0.0", "chalk": "^4.0.0" }, - "engines": { - "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" - } - }, - "node_modules/@jest/types/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/@jest/types/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "node_modules/@jest/transform/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "@types/yargs-parser": "*" } }, - "node_modules/@jest/types/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/@jest/transform/node_modules/convert-source-map": { + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.9.0.tgz", + "integrity": "sha512-ASFBup0Mz1uyiIjANan1jzLQami9z1PoYSZCiiYW2FczPbenXc45FZdBZLzOT+r6+iciuEModtmCti+hjaAk0A==" + }, + "node_modules/@jest/transform/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", "dependencies": { - "color-name": "~1.1.4" + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" }, "engines": { - "node": ">=7.0.0" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/@jest/types/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/@jest/types/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "node_modules/@jest/transform/node_modules/source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", "engines": { - "node": ">=8" + "node": ">=0.10.0" } }, - "node_modules/@jest/types/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/@jest/types": { + "version": "29.6.3", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-29.6.3.tgz", + "integrity": "sha512-u3UPsIilWKOM3F9CXtrG8LEJmNxwoCQC/XVj4IKYXvvpx7QIi/Kg1LI5uDmDpKlac62NUtX7eLjRh+jVZcLOzw==", "dependencies": { - "has-flag": "^4.0.0" + "@jest/schemas": "^29.6.3", + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^17.0.8", + "chalk": "^4.0.0" }, "engines": { - "node": ">=8" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, "node_modules/@jridgewell/gen-mapping": { @@ -3456,14 +3660,14 @@ "integrity": "sha512-EYNwp3bU+98cpU4lAWYYL7Zz+2gryWH1qbdDTidVd6hkiR6weksdbMadyXKXNPEkQFhXM+hVO9ZygomHXp+AIw==" }, "node_modules/@rushstack/eslint-patch": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/@rushstack/eslint-patch/-/eslint-patch-1.4.0.tgz", - "integrity": "sha512-cEjvTPU32OM9lUFegJagO0mRnIn+rbqrG89vV8/xLnLFX0DoR0r1oy5IlTga71Q7uT3Qus7qm7wgeiMT/+Irlg==" + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/@rushstack/eslint-patch/-/eslint-patch-1.5.0.tgz", + "integrity": "sha512-EF3948ckf3f5uPgYbQ6GhyA56Dmv8yg0+ir+BroRjwdxyZJsekhZzawOecC2rOTPCz173t7ZcR1HHZu0dZgOCw==" }, "node_modules/@sinclair/typebox": { - "version": "0.24.51", - "resolved": "https://registry.npmjs.org/@sinclair/typebox/-/typebox-0.24.51.tgz", - "integrity": "sha512-1P1OROm/rdubP5aFDSZQILU0vrLCJ4fvHt6EoqHEM+2D/G5MK3bIaymUKLit8Js9gbns5UyJnkP/TZROLw4tUA==" + "version": "0.27.8", + "resolved": "https://registry.npmjs.org/@sinclair/typebox/-/typebox-0.27.8.tgz", + "integrity": "sha512-+Fj43pSMwJs4KRrH/938Uf+uAELIgVBmQzg/q1YG10djyfA3TnrU8N8XzqCh/okZdszqBQTZf96idMfE5lnwTA==" }, "node_modules/@sinonjs/commons": { "version": "1.8.6", @@ -3718,85 +3922,6 @@ "node": ">=14" } }, - "node_modules/@testing-library/dom/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "peer": true, - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/@testing-library/dom/node_modules/aria-query": { - "version": "5.1.3", - "resolved": "https://registry.npmjs.org/aria-query/-/aria-query-5.1.3.tgz", - "integrity": "sha512-R5iJ5lkuHybztUfuOAznmboyjWq8O6sqNqtK7CLOqdydi54VNbORp49mb14KbWgG1QD3JFO9hJdZ+y4KutfdOQ==", - "peer": true, - "dependencies": { - "deep-equal": "^2.0.5" - } - }, - "node_modules/@testing-library/dom/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "peer": true, - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/@testing-library/dom/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "peer": true, - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@testing-library/dom/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", - "peer": true - }, - "node_modules/@testing-library/dom/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "peer": true, - "engines": { - "node": ">=8" - } - }, - "node_modules/@testing-library/dom/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "peer": true, - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, "node_modules/@testing-library/jest-dom": { "version": "5.17.0", "resolved": "https://registry.npmjs.org/@testing-library/jest-dom/-/jest-dom-5.17.0.tgz", @@ -3818,172 +3943,51 @@ "yarn": ">=1" } }, - "node_modules/@testing-library/jest-dom/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/@testing-library/jest-dom/node_modules/chalk": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-3.0.0.tgz", - "integrity": "sha512-4D3B6Wf41KOYRFdszmDqMCGq5VV/uMAB273JILmO+3jAlh8X4qDtdtgCR3fxtbLEMzSx22QdhnDcJvu2u1fVwg==", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/@testing-library/jest-dom/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@testing-library/jest-dom/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/@testing-library/jest-dom/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" - } - }, - "node_modules/@testing-library/jest-dom/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/@testing-library/react": { - "version": "13.4.0", - "resolved": "https://registry.npmjs.org/@testing-library/react/-/react-13.4.0.tgz", - "integrity": "sha512-sXOGON+WNTh3MLE9rve97ftaZukN3oNf2KjDy7YTx6hcTO2uuLHuCGynMDhFwGw/jYf4OJ2Qk0i4i79qMNNkyw==", - "dependencies": { - "@babel/runtime": "^7.12.5", - "@testing-library/dom": "^8.5.0", - "@types/react-dom": "^18.0.0" - }, - "engines": { - "node": ">=12" - }, - "peerDependencies": { - "react": "^18.0.0", - "react-dom": "^18.0.0" - } - }, - "node_modules/@testing-library/react/node_modules/@testing-library/dom": { - "version": "8.20.1", - "resolved": "https://registry.npmjs.org/@testing-library/dom/-/dom-8.20.1.tgz", - "integrity": "sha512-/DiOQ5xBxgdYRC8LNk7U+RWat0S3qRLeIw3ZIkMQ9kkVlRmwD/Eg8k8CqIpD6GW7u20JIUOfMKbxtiLutpjQ4g==", - "dependencies": { - "@babel/code-frame": "^7.10.4", - "@babel/runtime": "^7.12.5", - "@types/aria-query": "^5.0.1", - "aria-query": "5.1.3", - "chalk": "^4.1.0", - "dom-accessibility-api": "^0.5.9", - "lz-string": "^1.5.0", - "pretty-format": "^27.0.2" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/@testing-library/react/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/@testing-library/react/node_modules/aria-query": { - "version": "5.1.3", - "resolved": "https://registry.npmjs.org/aria-query/-/aria-query-5.1.3.tgz", - "integrity": "sha512-R5iJ5lkuHybztUfuOAznmboyjWq8O6sqNqtK7CLOqdydi54VNbORp49mb14KbWgG1QD3JFO9hJdZ+y4KutfdOQ==", - "dependencies": { - "deep-equal": "^2.0.5" - } - }, - "node_modules/@testing-library/react/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "node_modules/@testing-library/jest-dom/node_modules/chalk": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-3.0.0.tgz", + "integrity": "sha512-4D3B6Wf41KOYRFdszmDqMCGq5VV/uMAB273JILmO+3jAlh8X4qDtdtgCR3fxtbLEMzSx22QdhnDcJvu2u1fVwg==", "dependencies": { "ansi-styles": "^4.1.0", "supports-color": "^7.1.0" }, "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "node": ">=8" } }, - "node_modules/@testing-library/react/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/@testing-library/react": { + "version": "13.4.0", + "resolved": "https://registry.npmjs.org/@testing-library/react/-/react-13.4.0.tgz", + "integrity": "sha512-sXOGON+WNTh3MLE9rve97ftaZukN3oNf2KjDy7YTx6hcTO2uuLHuCGynMDhFwGw/jYf4OJ2Qk0i4i79qMNNkyw==", "dependencies": { - "color-name": "~1.1.4" + "@babel/runtime": "^7.12.5", + "@testing-library/dom": "^8.5.0", + "@types/react-dom": "^18.0.0" }, "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@testing-library/react/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/@testing-library/react/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" + "node": ">=12" + }, + "peerDependencies": { + "react": "^18.0.0", + "react-dom": "^18.0.0" } }, - "node_modules/@testing-library/react/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/@testing-library/react/node_modules/@testing-library/dom": { + "version": "8.20.1", + "resolved": "https://registry.npmjs.org/@testing-library/dom/-/dom-8.20.1.tgz", + "integrity": "sha512-/DiOQ5xBxgdYRC8LNk7U+RWat0S3qRLeIw3ZIkMQ9kkVlRmwD/Eg8k8CqIpD6GW7u20JIUOfMKbxtiLutpjQ4g==", "dependencies": { - "has-flag": "^4.0.0" + "@babel/code-frame": "^7.10.4", + "@babel/runtime": "^7.12.5", + "@types/aria-query": "^5.0.1", + "aria-query": "5.1.3", + "chalk": "^4.1.0", + "dom-accessibility-api": "^0.5.9", + "lz-string": "^1.5.0", + "pretty-format": "^27.0.2" }, "engines": { - "node": ">=8" + "node": ">=12" } }, "node_modules/@testing-library/user-event": { @@ -4170,17 +4174,17 @@ "integrity": "sha512-z/QT1XN4K4KYuslS23k62yDIDLwLFkzxOuMplDtObz0+y7VqJCaO2o+SPwHCvLFZh7xazvvoor2tA/hPz9ee7g==" }, "node_modules/@types/istanbul-lib-report": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/@types/istanbul-lib-report/-/istanbul-lib-report-3.0.0.tgz", - "integrity": "sha512-plGgXAPfVKFoYfa9NpYDAkseG+g6Jr294RqeqcqDixSbU34MZVJRi/P+7Y8GDpzkEwLaGZZOpKIEmeVZNtKsrg==", + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/@types/istanbul-lib-report/-/istanbul-lib-report-3.0.1.tgz", + "integrity": "sha512-gPQuzaPR5h/djlAv2apEG1HVOyj1IUs7GpfMZixU0/0KXT3pm64ylHuMUI1/Akh+sq/iikxg6Z2j+fcMDXaaTQ==", "dependencies": { "@types/istanbul-lib-coverage": "*" } }, "node_modules/@types/istanbul-reports": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/@types/istanbul-reports/-/istanbul-reports-3.0.1.tgz", - "integrity": "sha512-c3mAZEuK0lvBp8tmuL74XRKn1+y2dcwOUpH7x4WrF6gk1GIgiluDRgMYQtw2OFcBvAJWlt6ASU3tSqxp0Uu0Aw==", + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/@types/istanbul-reports/-/istanbul-reports-3.0.2.tgz", + "integrity": "sha512-kv43F9eb3Lhj+lr/Hn6OcLCs/sSM8bt+fIaP11rCYngfV6NVjzWXJ17owQtDQTL9tQ8WSLUrGsSJ6rJz0F1w1A==", "dependencies": { "@types/istanbul-lib-report": "*" } @@ -4194,191 +4198,15 @@ "pretty-format": "^29.0.0" } }, - "node_modules/@types/jest/node_modules/@jest/schemas": { - "version": "29.6.3", - "resolved": "https://registry.npmjs.org/@jest/schemas/-/schemas-29.6.3.tgz", - "integrity": "sha512-mo5j5X+jIZmJQveBKeS/clAueipV7KgiX1vMgCxam1RNYiqE1w62n0/tJJnHtjW8ZHcQco5gY85jA3mi0L+nSA==", - "dependencies": { - "@sinclair/typebox": "^0.27.8" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@types/jest/node_modules/@jest/types": { - "version": "29.6.3", - "resolved": "https://registry.npmjs.org/@jest/types/-/types-29.6.3.tgz", - "integrity": "sha512-u3UPsIilWKOM3F9CXtrG8LEJmNxwoCQC/XVj4IKYXvvpx7QIi/Kg1LI5uDmDpKlac62NUtX7eLjRh+jVZcLOzw==", - "dependencies": { - "@jest/schemas": "^29.6.3", - "@types/istanbul-lib-coverage": "^2.0.0", - "@types/istanbul-reports": "^3.0.0", - "@types/node": "*", - "@types/yargs": "^17.0.8", - "chalk": "^4.0.0" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@types/jest/node_modules/@sinclair/typebox": { - "version": "0.27.8", - "resolved": "https://registry.npmjs.org/@sinclair/typebox/-/typebox-0.27.8.tgz", - "integrity": "sha512-+Fj43pSMwJs4KRrH/938Uf+uAELIgVBmQzg/q1YG10djyfA3TnrU8N8XzqCh/okZdszqBQTZf96idMfE5lnwTA==" - }, - "node_modules/@types/jest/node_modules/@types/yargs": { - "version": "17.0.24", - "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-17.0.24.tgz", - "integrity": "sha512-6i0aC7jV6QzQB8ne1joVZ0eSFIstHsCrobmOtghM11yGlH0j43FKL2UhWdELkyps0zuf7qVTUVCCR+tgSlyLLw==", - "dependencies": { - "@types/yargs-parser": "*" - } - }, "node_modules/@types/jest/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/@types/jest/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", + "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", "engines": { "node": ">=10" }, "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/@types/jest/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@types/jest/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/@types/jest/node_modules/diff-sequences": { - "version": "29.6.3", - "resolved": "https://registry.npmjs.org/diff-sequences/-/diff-sequences-29.6.3.tgz", - "integrity": "sha512-EjePK1srD3P08o2j4f0ExnylqRs5B9tJjcp9t1krH2qRi8CCdsYfwe9JgSLurFBWwq4uOlipzfk5fHNvwFKr8Q==", - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@types/jest/node_modules/expect": { - "version": "29.7.0", - "resolved": "https://registry.npmjs.org/expect/-/expect-29.7.0.tgz", - "integrity": "sha512-2Zks0hf1VLFYI1kbh0I5jP3KHHyCHpkfyHBzsSXRFgl/Bg9mWYfMW8oD+PdMPlEwy5HNsR9JutYy6pMeOh61nw==", - "dependencies": { - "@jest/expect-utils": "^29.7.0", - "jest-get-type": "^29.6.3", - "jest-matcher-utils": "^29.7.0", - "jest-message-util": "^29.7.0", - "jest-util": "^29.7.0" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@types/jest/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" - } - }, - "node_modules/@types/jest/node_modules/jest-diff": { - "version": "29.7.0", - "resolved": "https://registry.npmjs.org/jest-diff/-/jest-diff-29.7.0.tgz", - "integrity": "sha512-LMIgiIrhigmPrs03JHpxUh2yISK3vLFPkAodPeo0+BuF7wA2FoQbkEg1u8gBYBThncu7e1oEDUfIXVuTqLRUjw==", - "dependencies": { - "chalk": "^4.0.0", - "diff-sequences": "^29.6.3", - "jest-get-type": "^29.6.3", - "pretty-format": "^29.7.0" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@types/jest/node_modules/jest-get-type": { - "version": "29.6.3", - "resolved": "https://registry.npmjs.org/jest-get-type/-/jest-get-type-29.6.3.tgz", - "integrity": "sha512-zrteXnqYxfQh7l5FHyL38jL39di8H8rHoecLH3JNxH3BwOrBsNeabdap5e0I23lD4HHI8W5VFBZqG4Eaq5LNcw==", - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@types/jest/node_modules/jest-matcher-utils": { - "version": "29.7.0", - "resolved": "https://registry.npmjs.org/jest-matcher-utils/-/jest-matcher-utils-29.7.0.tgz", - "integrity": "sha512-sBkD+Xi9DtcChsI3L3u0+N0opgPYnCRPtGcQYrgXmR+hmt/fYfWAL0xRXYU8eWOdfuLgBe0YCW3AFtnRLagq/g==", - "dependencies": { - "chalk": "^4.0.0", - "jest-diff": "^29.7.0", - "jest-get-type": "^29.6.3", - "pretty-format": "^29.7.0" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@types/jest/node_modules/jest-message-util": { - "version": "29.7.0", - "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-29.7.0.tgz", - "integrity": "sha512-GBEV4GRADeP+qtB2+6u61stea8mGcOT4mCtrYISZwfu9/ISHFJ/5zOMXYbpBE9RsS5+Gb63DW4FgmnKJ79Kf6w==", - "dependencies": { - "@babel/code-frame": "^7.12.13", - "@jest/types": "^29.6.3", - "@types/stack-utils": "^2.0.0", - "chalk": "^4.0.0", - "graceful-fs": "^4.2.9", - "micromatch": "^4.0.4", - "pretty-format": "^29.7.0", - "slash": "^3.0.0", - "stack-utils": "^2.0.3" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" - } - }, - "node_modules/@types/jest/node_modules/jest-util": { - "version": "29.7.0", - "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-29.7.0.tgz", - "integrity": "sha512-z6EbKajIpqGKU56y5KBUgy1dt1ihhQJgWzUlZHArA/+X2ad7Cb5iF+AK1EWVL/Bo7Rz9uurpqw6SiBCefUbCGA==", - "dependencies": { - "@jest/types": "^29.6.3", - "@types/node": "*", - "chalk": "^4.0.0", - "ci-info": "^3.2.0", - "graceful-fs": "^4.2.9", - "picomatch": "^2.2.3" - }, - "engines": { - "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + "url": "https://github.com/chalk/ansi-styles?sponsor=1" } }, "node_modules/@types/jest/node_modules/pretty-format": { @@ -4394,33 +4222,11 @@ "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, - "node_modules/@types/jest/node_modules/pretty-format/node_modules/ansi-styles": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", - "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/@types/jest/node_modules/react-is": { "version": "18.2.0", "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.2.0.tgz", "integrity": "sha512-xWGDIW6x921xtzPkhiULtthJHoJvBbF3q26fzloPCK0hsvxtPVelvftw3zjbHWSkR2km9Z+4uxbDDK/6Zw9B8w==" }, - "node_modules/@types/jest/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, "node_modules/@types/json-schema": { "version": "7.0.13", "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.13.tgz", @@ -4432,14 +4238,14 @@ "integrity": "sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ==" }, "node_modules/@types/mime": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/@types/mime/-/mime-1.3.2.tgz", - "integrity": "sha512-YATxVxgRqNH6nHEIsvg6k2Boc1JHI9ZbH5iWFFv/MTkchz3b1ieGDa5T0a9RznNdI0KhVbdbWSN+KWWrQZRxTw==" + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/@types/mime/-/mime-1.3.3.tgz", + "integrity": "sha512-Ys+/St+2VF4+xuY6+kDIXGxbNRO0mesVg0bbxEfB97Od1Vjpjx9KD1qxs64Gcb3CWPirk9Xe+PT4YiiHQ9T+eg==" }, "node_modules/@types/node": { - "version": "20.6.5", - "resolved": "https://registry.npmjs.org/@types/node/-/node-20.6.5.tgz", - "integrity": "sha512-2qGq5LAOTh9izcc0+F+dToFigBWiK1phKPt7rNhOqJSr35y8rlIBjDwGtFSgAI6MGIhjwOVNSQZVdJsZJ2uR1w==" + "version": "20.7.1", + "resolved": "https://registry.npmjs.org/@types/node/-/node-20.7.1.tgz", + "integrity": "sha512-LT+OIXpp2kj4E2S/p91BMe+VgGX2+lfO+XTpfXhh+bCk2LkQtHZSub8ewFBMGP5ClysPjTDFa4sMI8Q3n4T0wg==" }, "node_modules/@types/parse-json": { "version": "4.0.0", @@ -4467,14 +4273,14 @@ "integrity": "sha512-u95svzDlTysU5xecFNTgfFG5RUWu1A9P0VzgpcIiGZA9iraHOdSzcxMxQ55DyeRaGCSxQi7LxXDI4rzq/MYfdg==" }, "node_modules/@types/range-parser": { - "version": "1.2.4", - "resolved": "https://registry.npmjs.org/@types/range-parser/-/range-parser-1.2.4.tgz", - "integrity": "sha512-EEhsLsD6UsDM1yFhAvy0Cjr6VwmpMWqFBCb9w07wVugF7w9nfajxLuVmngTIpgS6svCnm6Vaw+MZhoDCKnOfsw==" + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/@types/range-parser/-/range-parser-1.2.5.tgz", + "integrity": "sha512-xrO9OoVPqFuYyR/loIHjnbvvyRZREYKLjxV4+dY6v3FQR3stQ9ZxIGkaclF7YhI9hfjpuTbu14hZEy94qKLtOA==" }, "node_modules/@types/react": { - "version": "18.2.22", - "resolved": "https://registry.npmjs.org/@types/react/-/react-18.2.22.tgz", - "integrity": "sha512-60fLTOLqzarLED2O3UQImc/lsNRgG0jE/a1mPW9KjMemY0LMITWEsbS4VvZ4p6rorEHd5YKxxmMKSDK505GHpA==", + "version": "18.2.23", + "resolved": "https://registry.npmjs.org/@types/react/-/react-18.2.23.tgz", + "integrity": "sha512-qHLW6n1q2+7KyBEYnrZpcsAmU/iiCh9WGCKgXvMxx89+TYdJWRjZohVIo9XTcoLhfX3+/hP0Pbulu3bCZQ9PSA==", "dependencies": { "@types/prop-types": "*", "@types/scheduler": "*", @@ -4482,9 +4288,9 @@ } }, "node_modules/@types/react-dom": { - "version": "18.2.7", - "resolved": "https://registry.npmjs.org/@types/react-dom/-/react-dom-18.2.7.tgz", - "integrity": "sha512-GRaAEriuT4zp9N4p1i8BDBYmEyfo+xQ3yHjJU4eiK5NDa1RmUZG+unZABUTK4/Ox/M+GaHwb6Ow8rUITrtjszA==", + "version": "18.2.8", + "resolved": "https://registry.npmjs.org/@types/react-dom/-/react-dom-18.2.8.tgz", + "integrity": "sha512-bAIvO5lN/U8sPGvs1Xm61rlRHHaq5rp5N3kp9C+NJ/Q41P8iqjkXSu0+/qu8POsjH9pNWb0OYabFez7taP7omw==", "dependencies": { "@types/react": "*" } @@ -4503,36 +4309,36 @@ "integrity": "sha512-wWKOClTTiizcZhXnPY4wikVAwmdYHp8q6DmC+EJUzAMsycb7HB32Kh9RN4+0gExjmPmZSAQjgURXIGATPegAvA==" }, "node_modules/@types/scheduler": { - "version": "0.16.3", - "resolved": "https://registry.npmjs.org/@types/scheduler/-/scheduler-0.16.3.tgz", - "integrity": "sha512-5cJ8CB4yAx7BH1oMvdU0Jh9lrEXyPkar6F9G/ERswkCuvP4KQZfZkSjcMbAICCpQTN4OuZn8tz0HiKv9TGZgrQ==" + "version": "0.16.4", + "resolved": "https://registry.npmjs.org/@types/scheduler/-/scheduler-0.16.4.tgz", + "integrity": "sha512-2L9ifAGl7wmXwP4v3pN4p2FLhD0O1qsJpvKmNin5VA8+UvNVb447UDaAEV6UdrkA+m/Xs58U1RFps44x6TFsVQ==" }, "node_modules/@types/semver": { - "version": "7.5.2", - "resolved": "https://registry.npmjs.org/@types/semver/-/semver-7.5.2.tgz", - "integrity": "sha512-7aqorHYgdNO4DM36stTiGO3DvKoex9TQRwsJU6vMaFGyqpBA1MNZkz+PG3gaNUPpTAOYhT1WR7M1JyA3fbS9Cw==" + "version": "7.5.3", + "resolved": "https://registry.npmjs.org/@types/semver/-/semver-7.5.3.tgz", + "integrity": "sha512-OxepLK9EuNEIPxWNME+C6WwbRAOOI2o2BaQEGzz5Lu2e4Z5eDnEo+/aVEDMIXywoJitJ7xWd641wrGLZdtwRyw==" }, "node_modules/@types/send": { - "version": "0.17.1", - "resolved": "https://registry.npmjs.org/@types/send/-/send-0.17.1.tgz", - "integrity": "sha512-Cwo8LE/0rnvX7kIIa3QHCkcuF21c05Ayb0ZfxPiv0W8VRiZiNW/WuRupHKpqqGVGf7SUA44QSOUKaEd9lIrd/Q==", + "version": "0.17.2", + "resolved": "https://registry.npmjs.org/@types/send/-/send-0.17.2.tgz", + "integrity": "sha512-aAG6yRf6r0wQ29bkS+x97BIs64ZLxeE/ARwyS6wrldMm3C1MdKwCcnnEwMC1slI8wuxJOpiUH9MioC0A0i+GJw==", "dependencies": { "@types/mime": "^1", "@types/node": "*" } }, "node_modules/@types/serve-index": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/@types/serve-index/-/serve-index-1.9.1.tgz", - "integrity": "sha512-d/Hs3nWDxNL2xAczmOVZNj92YZCS6RGxfBPjKzuu/XirCgXdpKEb88dYNbrYGint6IVWLNP+yonwVAuRC0T2Dg==", + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/@types/serve-index/-/serve-index-1.9.2.tgz", + "integrity": "sha512-asaEIoc6J+DbBKXtO7p2shWUpKacZOoMBEGBgPG91P8xhO53ohzHWGCs4ScZo5pQMf5ukQzVT9fhX1WzpHihig==", "dependencies": { "@types/express": "*" } }, "node_modules/@types/serve-static": { - "version": "1.15.2", - "resolved": "https://registry.npmjs.org/@types/serve-static/-/serve-static-1.15.2.tgz", - "integrity": "sha512-J2LqtvFYCzaj8pVYKw8klQXrLLk7TBZmQ4ShlcdkELFKGwGMfevMLneMMRkMgZxotOD9wg497LpC7O8PcvAmfw==", + "version": "1.15.3", + "resolved": "https://registry.npmjs.org/@types/serve-static/-/serve-static-1.15.3.tgz", + "integrity": "sha512-yVRvFsEMrv7s0lGhzrggJjNOSmZCdgCjw9xWrPr/kNNLp6FaDfMC1KaYl3TSJ0c58bECwNBMoQrZJ8hA8E1eFg==", "dependencies": { "@types/http-errors": "*", "@types/mime": "*", @@ -4540,9 +4346,9 @@ } }, "node_modules/@types/sockjs": { - "version": "0.3.33", - "resolved": "https://registry.npmjs.org/@types/sockjs/-/sockjs-0.3.33.tgz", - "integrity": "sha512-f0KEEe05NvUnat+boPTZ0dgaLZ4SfSouXUgv5noUiefG2ajgKjmETo9ZJyuqsl7dfl2aHlLJUiki6B4ZYldiiw==", + "version": "0.3.34", + "resolved": "https://registry.npmjs.org/@types/sockjs/-/sockjs-0.3.34.tgz", + "integrity": "sha512-R+n7qBFnm/6jinlteC9DBL5dGiDGjWAvjo4viUanpnc/dG1y7uDoacXPIQ/PQEg1fI912SMHIa014ZjRpvDw4g==", "dependencies": { "@types/node": "*" } @@ -4553,9 +4359,9 @@ "integrity": "sha512-Hl219/BT5fLAaz6NDkSuhzasy49dwQS/DSdu4MdggFB8zcXv7vflBI3xp7FEmkmdDkBUI2bPUNeMttp2knYdxw==" }, "node_modules/@types/stylis": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/@types/stylis/-/stylis-4.2.0.tgz", - "integrity": "sha512-n4sx2bqL0mW1tvDf/loQ+aMX7GQD3lc3fkCMC55VFNDu/vBOabO+LTIeXKM14xK0ppk5TUGcWRjiSpIlUpghKw==" + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/@types/stylis/-/stylis-4.2.1.tgz", + "integrity": "sha512-OSaMrXUKxVigGlKRrET39V2xdhzlztQ9Aqumn1WbCBKHOi9ry7jKSd7rkyj0GzmWaU960Rd+LpOFpLfx5bMQAg==" }, "node_modules/@types/testing-library__jest-dom": { "version": "5.14.9", @@ -4571,25 +4377,25 @@ "integrity": "sha512-IDaobHimLQhjwsQ/NMwRVfa/yL7L/wriQPMhw1ZJall0KX6E1oxk29XMDeilW5qTIg5aoiqf5Udy8U/51aNoQQ==" }, "node_modules/@types/ws": { - "version": "8.5.5", - "resolved": "https://registry.npmjs.org/@types/ws/-/ws-8.5.5.tgz", - "integrity": "sha512-lwhs8hktwxSjf9UaZ9tG5M03PGogvFaH8gUgLNbN9HKIg0dvv6q+gkSuJ8HN4/VbyxkuLzCjlN7GquQ0gUJfIg==", + "version": "8.5.6", + "resolved": "https://registry.npmjs.org/@types/ws/-/ws-8.5.6.tgz", + "integrity": "sha512-8B5EO9jLVCy+B58PLHvLDuOD8DRVMgQzq8d55SjLCOn9kqGyqOvy27exVaTio1q1nX5zLu8/6N0n2ThSxOM6tg==", "dependencies": { "@types/node": "*" } }, "node_modules/@types/yargs": { - "version": "16.0.5", - "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.5.tgz", - "integrity": "sha512-AxO/ADJOBFJScHbWhq2xAhlWP24rY4aCEG/NFaMvbT3X2MgRsLjhjQwsn0Zi5zn0LG9jUhCCZMeX9Dkuw6k+vQ==", + "version": "17.0.26", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-17.0.26.tgz", + "integrity": "sha512-Y3vDy2X6zw/ZCumcwLpdhM5L7jmyGpmBCTYMHDLqT2IKVMYRRLdv6ZakA+wxhra6Z/3bwhNbNl9bDGXaFU+6rw==", "dependencies": { "@types/yargs-parser": "*" } }, "node_modules/@types/yargs-parser": { - "version": "21.0.0", - "resolved": "https://registry.npmjs.org/@types/yargs-parser/-/yargs-parser-21.0.0.tgz", - "integrity": "sha512-iO9ZQHkZxHn4mSakYV0vFHAVDyEOIJQrV2uZ06HxEPcx+mt8swXoZHIbaaJ2crJYFfErySgktuTZ3BeLz+XmFA==" + "version": "21.0.1", + "resolved": "https://registry.npmjs.org/@types/yargs-parser/-/yargs-parser-21.0.1.tgz", + "integrity": "sha512-axdPBuLuEJt0c4yI5OZssC19K2Mq1uKdrfZBzuxLvaztgqUtFYZUNw7lETExPYJR9jdEoIg4mb7RQKRQzOkeGQ==" }, "node_modules/@typescript-eslint/eslint-plugin": { "version": "5.62.0", @@ -5146,14 +4952,17 @@ } }, "node_modules/ansi-styles": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", - "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", "dependencies": { - "color-convert": "^1.9.0" + "color-convert": "^2.0.1" }, "engines": { - "node": ">=4" + "node": ">=8" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" } }, "node_modules/any-promise": { @@ -5187,11 +4996,11 @@ } }, "node_modules/aria-query": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/aria-query/-/aria-query-5.3.0.tgz", - "integrity": "sha512-b0P0sZPKtyu8HkeRAfCq0IfURZK+SuwMjY1UXGBU27wpAiTwQAIlq56IbIO+ytk/JjS1fMR14ee5WBBfKi5J6A==", + "version": "5.1.3", + "resolved": "https://registry.npmjs.org/aria-query/-/aria-query-5.1.3.tgz", + "integrity": "sha512-R5iJ5lkuHybztUfuOAznmboyjWq8O6sqNqtK7CLOqdydi54VNbORp49mb14KbWgG1QD3JFO9hJdZ+y4KutfdOQ==", "dependencies": { - "dequal": "^2.0.3" + "deep-equal": "^2.0.5" } }, "node_modules/array-buffer-byte-length": { @@ -5459,68 +5268,27 @@ "@babel/core": "^7.8.0" } }, - "node_modules/babel-jest/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/babel-jest/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/babel-jest/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/babel-jest/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", "dependencies": { - "color-name": "~1.1.4" + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" }, "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/babel-jest/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/babel-jest/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/babel-jest/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/babel-jest/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" + "@types/yargs-parser": "*" } }, "node_modules/babel-loader": { @@ -5861,9 +5629,9 @@ "integrity": "sha512-9o5UecI3GhkpM6DrXr69PblIuWxPKk9Y0jHBRhdocZ2y7YECBFCsHm79Pr3OyR2AvjhDkabFJaDJMYRazHgsow==" }, "node_modules/browserslist": { - "version": "4.21.11", - "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.21.11.tgz", - "integrity": "sha512-xn1UXOKUz7DjdGlg9RrUr0GGiWzI97UQJnugHtH0OLDfJB7jMgoIkYvRIEO1l9EeEERVqeqLYOcFBW9ldjypbQ==", + "version": "4.22.1", + "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.22.1.tgz", + "integrity": "sha512-FEVc202+2iuClEhZhrWy6ZiAcRLvNMyYcxZ8raemul1DYVOVdFsbqckWLdsixQZCpJlwe77Z3UTalE7jsjnKfQ==", "funding": [ { "type": "opencollective", @@ -5879,8 +5647,8 @@ } ], "dependencies": { - "caniuse-lite": "^1.0.30001538", - "electron-to-chromium": "^1.4.526", + "caniuse-lite": "^1.0.30001541", + "electron-to-chromium": "^1.4.535", "node-releases": "^2.0.13", "update-browserslist-db": "^1.0.13" }, @@ -5991,9 +5759,9 @@ } }, "node_modules/caniuse-lite": { - "version": "1.0.30001538", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001538.tgz", - "integrity": "sha512-HWJnhnID+0YMtGlzcp3T9drmBJUVDchPJ08tpUGFLs9CYlwWPH2uLgpHn8fND5pCgXVtnGS3H4QR9XLMHVNkHw==", + "version": "1.0.30001541", + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001541.tgz", + "integrity": "sha512-bLOsqxDgTqUBkzxbNlSBt8annkDpQB9NdzdTbO2ooJ+eC/IQcvDspDc058g84ejCelF7vHUx57KIOjEecOHXaw==", "funding": [ { "type": "opencollective", @@ -6018,16 +5786,18 @@ } }, "node_modules/chalk": { - "version": "2.4.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", - "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", "dependencies": { - "ansi-styles": "^3.2.1", - "escape-string-regexp": "^1.0.5", - "supports-color": "^5.3.0" + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" }, "engines": { - "node": ">=4" + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" } }, "node_modules/char-regex": { @@ -6158,12 +5928,31 @@ "node": ">= 4.0" } }, - "node_modules/collect-v8-coverage": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/collect-v8-coverage/-/collect-v8-coverage-1.0.2.tgz", - "integrity": "sha512-lHl4d5/ONEbLlJvaJNtsF/Lz+WvB07u2ycqTYbdrq7UypDXailES4valYb2eWiJFxZlVmpGekfqoxQhzyFdT4Q==" + "node_modules/coa/node_modules/ansi-styles": { + "version": "3.2.1", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", + "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", + "dependencies": { + "color-convert": "^1.9.0" + }, + "engines": { + "node": ">=4" + } }, - "node_modules/color-convert": { + "node_modules/coa/node_modules/chalk": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", + "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", + "dependencies": { + "ansi-styles": "^3.2.1", + "escape-string-regexp": "^1.0.5", + "supports-color": "^5.3.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/coa/node_modules/color-convert": { "version": "1.9.3", "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz", "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==", @@ -6171,11 +5960,59 @@ "color-name": "1.1.3" } }, - "node_modules/color-name": { + "node_modules/coa/node_modules/color-name": { "version": "1.1.3", "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", "integrity": "sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw==" }, + "node_modules/coa/node_modules/escape-string-regexp": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", + "integrity": "sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==", + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/coa/node_modules/has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw==", + "engines": { + "node": ">=4" + } + }, + "node_modules/coa/node_modules/supports-color": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dependencies": { + "has-flag": "^3.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/collect-v8-coverage": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/collect-v8-coverage/-/collect-v8-coverage-1.0.2.tgz", + "integrity": "sha512-lHl4d5/ONEbLlJvaJNtsF/Lz+WvB07u2ycqTYbdrq7UypDXailES4valYb2eWiJFxZlVmpGekfqoxQhzyFdT4Q==" + }, + "node_modules/color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dependencies": { + "color-name": "~1.1.4" + }, + "engines": { + "node": ">=7.0.0" + } + }, + "node_modules/color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" + }, "node_modules/colord": { "version": "2.9.3", "resolved": "https://registry.npmjs.org/colord/-/colord-2.9.3.tgz", @@ -6307,9 +6144,9 @@ } }, "node_modules/convert-source-map": { - "version": "1.9.0", - "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.9.0.tgz", - "integrity": "sha512-ASFBup0Mz1uyiIjANan1jzLQami9z1PoYSZCiiYW2FczPbenXc45FZdBZLzOT+r6+iciuEModtmCti+hjaAk0A==" + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-2.0.0.tgz", + "integrity": "sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==" }, "node_modules/cookie": { "version": "0.5.0", @@ -7024,11 +6861,11 @@ "integrity": "sha512-gxtyfqMg7GKyhQmb056K7M3xszy/myH8w+B4RT+QXBQsvAOdc3XymqDDPHx1BgPgsdAA5SIifona89YtRATDzw==" }, "node_modules/diff-sequences": { - "version": "27.5.1", - "resolved": "https://registry.npmjs.org/diff-sequences/-/diff-sequences-27.5.1.tgz", - "integrity": "sha512-k1gCAXAsNgLwEL+Y8Wvl+M6oEFj5bgazfZULpS5CneoPPXRaCCW7dm+q21Ky2VEE5X+VeRDBVg1Pcvvsr4TtNQ==", + "version": "29.6.3", + "resolved": "https://registry.npmjs.org/diff-sequences/-/diff-sequences-29.6.3.tgz", + "integrity": "sha512-EjePK1srD3P08o2j4f0ExnylqRs5B9tJjcp9t1krH2qRi8CCdsYfwe9JgSLurFBWwq4uOlipzfk5fHNvwFKr8Q==", "engines": { - "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, "node_modules/dir-glob": { @@ -7204,9 +7041,9 @@ } }, "node_modules/electron-to-chromium": { - "version": "1.4.528", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.528.tgz", - "integrity": "sha512-UdREXMXzLkREF4jA8t89FQjA8WHI6ssP38PMY4/4KhXFQbtImnghh4GkCgrtiZwLKUKVD2iTVXvDVQjfomEQuA==" + "version": "1.4.536", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.536.tgz", + "integrity": "sha512-L4VgC/76m6y8WVCgnw5kJy/xs7hXrViCFdNKVG8Y7B2isfwrFryFyJzumh3ugxhd/oB1uEaEEvRdmeLrnd7OFA==" }, "node_modules/emittery": { "version": "0.8.1", @@ -7429,11 +7266,14 @@ "integrity": "sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==" }, "node_modules/escape-string-regexp": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", - "integrity": "sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==", + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", + "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", "engines": { - "node": ">=0.8.0" + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" } }, "node_modules/escodegen": { @@ -7886,14 +7726,6 @@ "ajv": "^8.8.2" } }, - "node_modules/eslint-webpack-plugin/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" - } - }, "node_modules/eslint-webpack-plugin/node_modules/jest-worker": { "version": "28.1.3", "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-28.1.3.tgz", @@ -7932,79 +7764,23 @@ }, "node_modules/eslint-webpack-plugin/node_modules/supports-color": { "version": "8.1.1", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", - "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/supports-color?sponsor=1" - } - }, - "node_modules/eslint/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/eslint/node_modules/argparse": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz", - "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==" - }, - "node_modules/eslint/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/eslint/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/eslint/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/eslint/node_modules/escape-string-regexp": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", - "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", + "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", + "dependencies": { + "has-flag": "^4.0.0" + }, "engines": { "node": ">=10" }, "funding": { - "url": "https://github.com/sponsors/sindresorhus" + "url": "https://github.com/chalk/supports-color?sponsor=1" } }, + "node_modules/eslint/node_modules/argparse": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz", + "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==" + }, "node_modules/eslint/node_modules/globals": { "version": "13.22.0", "resolved": "https://registry.npmjs.org/globals/-/globals-13.22.0.tgz", @@ -8019,14 +7795,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/eslint/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" - } - }, "node_modules/eslint/node_modules/js-yaml": { "version": "4.1.0", "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz", @@ -8038,17 +7806,6 @@ "js-yaml": "bin/js-yaml.js" } }, - "node_modules/eslint/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, "node_modules/eslint/node_modules/type-fest": { "version": "0.20.2", "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.20.2.tgz", @@ -8183,17 +7940,18 @@ } }, "node_modules/expect": { - "version": "27.5.1", - "resolved": "https://registry.npmjs.org/expect/-/expect-27.5.1.tgz", - "integrity": "sha512-E1q5hSUG2AmYQwQJ041nvgpkODHQvB+RKlB4IYdru6uJsyFTRyZAP463M+1lINorwbqAmUggi6+WwkD8lCS/Dw==", + "version": "29.7.0", + "resolved": "https://registry.npmjs.org/expect/-/expect-29.7.0.tgz", + "integrity": "sha512-2Zks0hf1VLFYI1kbh0I5jP3KHHyCHpkfyHBzsSXRFgl/Bg9mWYfMW8oD+PdMPlEwy5HNsR9JutYy6pMeOh61nw==", "dependencies": { - "@jest/types": "^27.5.1", - "jest-get-type": "^27.5.1", - "jest-matcher-utils": "^27.5.1", - "jest-message-util": "^27.5.1" + "@jest/expect-utils": "^29.7.0", + "jest-get-type": "^29.6.3", + "jest-matcher-utils": "^29.7.0", + "jest-message-util": "^29.7.0", + "jest-util": "^29.7.0" }, "engines": { - "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, "node_modules/express": { @@ -8543,51 +8301,6 @@ } } }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/fork-ts-checker-webpack-plugin/node_modules/cosmiconfig": { "version": "6.0.0", "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-6.0.0.tgz", @@ -8617,14 +8330,6 @@ "node": ">=10" } }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" - } - }, "node_modules/fork-ts-checker-webpack-plugin/node_modules/schema-utils": { "version": "2.7.0", "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-2.7.0.tgz", @@ -8642,17 +8347,6 @@ "url": "https://opencollective.com/webpack" } }, - "node_modules/fork-ts-checker-webpack-plugin/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, "node_modules/fork-ts-checker-webpack-plugin/node_modules/tapable": { "version": "1.1.3", "resolved": "https://registry.npmjs.org/tapable/-/tapable-1.1.3.tgz", @@ -8716,9 +8410,9 @@ } }, "node_modules/fs-monkey": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/fs-monkey/-/fs-monkey-1.0.4.tgz", - "integrity": "sha512-INM/fWAxMICjttnD0DX1rBvinKskj5G1w+oy/pnm9u/tSlnBrzFonJMcalKJ30P8RRsPzKcCG7Q8l0jx5Fh9YQ==" + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/fs-monkey/-/fs-monkey-1.0.5.tgz", + "integrity": "sha512-8uMbBjrhzW76TYgEV27Y5E//W2f/lTFmx78P2w19FZSxarhI/798APGQyuGCwmkNxgwGRhrLfvWyLBvNtuOmew==" }, "node_modules/fs-readdir-recursive": { "version": "1.1.0", @@ -9023,11 +8717,11 @@ } }, "node_modules/has-flag": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", - "integrity": "sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw==", + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", "engines": { - "node": ">=4" + "node": ">=8" } }, "node_modules/has-property-descriptors": { @@ -9949,14 +9643,6 @@ "node": ">=10" } }, - "node_modules/istanbul-lib-report/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" - } - }, "node_modules/istanbul-lib-report/node_modules/make-dir": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-4.0.0.tgz", @@ -9971,17 +9657,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/istanbul-lib-report/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, "node_modules/istanbul-lib-source-maps": { "version": "4.0.1", "resolved": "https://registry.npmjs.org/istanbul-lib-source-maps/-/istanbul-lib-source-maps-4.0.1.tgz", @@ -10044,70 +9719,6 @@ "node": ">=10" } }, - "node_modules/jake/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/jake/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/jake/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jake/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/jake/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" - } - }, - "node_modules/jake/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, "node_modules/jest": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest/-/jest-27.5.1.tgz", @@ -10145,6 +9756,29 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, + "node_modules/jest-changed-files/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", + "dependencies": { + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/jest-changed-files/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", + "dependencies": { + "@types/yargs-parser": "*" + } + }, "node_modules/jest-circus": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-circus/-/jest-circus-27.5.1.tgz", @@ -10174,68 +9808,120 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-circus/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, + "node_modules/jest-circus/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", + "dependencies": { + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/jest-circus/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", + "dependencies": { + "@types/yargs-parser": "*" + } + }, + "node_modules/jest-circus/node_modules/diff-sequences": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/diff-sequences/-/diff-sequences-27.5.1.tgz", + "integrity": "sha512-k1gCAXAsNgLwEL+Y8Wvl+M6oEFj5bgazfZULpS5CneoPPXRaCCW7dm+q21Ky2VEE5X+VeRDBVg1Pcvvsr4TtNQ==", + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/jest-circus/node_modules/expect": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/expect/-/expect-27.5.1.tgz", + "integrity": "sha512-E1q5hSUG2AmYQwQJ041nvgpkODHQvB+RKlB4IYdru6uJsyFTRyZAP463M+1lINorwbqAmUggi6+WwkD8lCS/Dw==", + "dependencies": { + "@jest/types": "^27.5.1", + "jest-get-type": "^27.5.1", + "jest-matcher-utils": "^27.5.1", + "jest-message-util": "^27.5.1" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/jest-circus/node_modules/jest-diff": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-diff/-/jest-diff-27.5.1.tgz", + "integrity": "sha512-m0NvkX55LDt9T4mctTEgnZk3fmEg3NRYutvMPWM/0iPnkFj2wIeF45O1718cMSOFO1vINkqmxqD8vE37uTEbqw==", + "dependencies": { + "chalk": "^4.0.0", + "diff-sequences": "^27.5.1", + "jest-get-type": "^27.5.1", + "pretty-format": "^27.5.1" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/jest-circus/node_modules/jest-get-type": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-get-type/-/jest-get-type-27.5.1.tgz", + "integrity": "sha512-2KY95ksYSaK7DMBWQn6dQz3kqAf3BB64y2udeG+hv4KfSOb9qwcYQstTJc1KCbsix+wLZWZYN8t7nwX3GOBLRw==", "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-circus/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "node_modules/jest-circus/node_modules/jest-matcher-utils": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-matcher-utils/-/jest-matcher-utils-27.5.1.tgz", + "integrity": "sha512-z2uTx/T6LBaCoNWNFWwChLBKYxTMcGBRjAt+2SbP929/Fflb9aa5LGma654Rz8z9HLxsrUaYzxE9T/EFIL/PAw==", "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" + "chalk": "^4.0.0", + "jest-diff": "^27.5.1", + "jest-get-type": "^27.5.1", + "pretty-format": "^27.5.1" }, "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-circus/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/jest-circus/node_modules/jest-message-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-27.5.1.tgz", + "integrity": "sha512-rMyFe1+jnyAAf+NHwTclDz0eAaLkVDdKVHHBFWsBWHnnh5YeJMNWWsv7AbFYXfK3oTqvL7VTWkhNLu1jX24D+g==", "dependencies": { - "color-name": "~1.1.4" + "@babel/code-frame": "^7.12.13", + "@jest/types": "^27.5.1", + "@types/stack-utils": "^2.0.0", + "chalk": "^4.0.0", + "graceful-fs": "^4.2.9", + "micromatch": "^4.0.4", + "pretty-format": "^27.5.1", + "slash": "^3.0.0", + "stack-utils": "^2.0.3" }, "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-circus/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/jest-circus/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-circus/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/jest-circus/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", "dependencies": { - "has-flag": "^4.0.0" + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" }, "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, "node_modules/jest-cli": { @@ -10271,68 +9957,43 @@ } } }, - "node_modules/jest-cli/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/jest-cli/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "node_modules/jest-cli/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" }, "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-cli/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/jest-cli/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-cli/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/jest-cli/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" + "@types/yargs-parser": "*" } }, - "node_modules/jest-cli/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/jest-cli/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", "dependencies": { - "has-flag": "^4.0.0" + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" }, "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, "node_modules/jest-config": { @@ -10377,148 +10038,96 @@ } } }, - "node_modules/jest-config/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/jest-config/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "node_modules/jest-config/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" }, "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-config/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/jest-config/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-config/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/jest-config/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" + "@types/yargs-parser": "*" } }, - "node_modules/jest-config/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dependencies": { - "has-flag": "^4.0.0" - }, + "node_modules/jest-config/node_modules/jest-get-type": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-get-type/-/jest-get-type-27.5.1.tgz", + "integrity": "sha512-2KY95ksYSaK7DMBWQn6dQz3kqAf3BB64y2udeG+hv4KfSOb9qwcYQstTJc1KCbsix+wLZWZYN8t7nwX3GOBLRw==", "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-diff": { + "node_modules/jest-config/node_modules/jest-util": { "version": "27.5.1", - "resolved": "https://registry.npmjs.org/jest-diff/-/jest-diff-27.5.1.tgz", - "integrity": "sha512-m0NvkX55LDt9T4mctTEgnZk3fmEg3NRYutvMPWM/0iPnkFj2wIeF45O1718cMSOFO1vINkqmxqD8vE37uTEbqw==", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", "dependencies": { + "@jest/types": "^27.5.1", + "@types/node": "*", "chalk": "^4.0.0", - "diff-sequences": "^27.5.1", - "jest-get-type": "^27.5.1", - "pretty-format": "^27.5.1" + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" }, "engines": { "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-diff/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/jest-diff/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/jest-diff/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/jest-diff": { + "version": "29.7.0", + "resolved": "https://registry.npmjs.org/jest-diff/-/jest-diff-29.7.0.tgz", + "integrity": "sha512-LMIgiIrhigmPrs03JHpxUh2yISK3vLFPkAodPeo0+BuF7wA2FoQbkEg1u8gBYBThncu7e1oEDUfIXVuTqLRUjw==", "dependencies": { - "color-name": "~1.1.4" + "chalk": "^4.0.0", + "diff-sequences": "^29.6.3", + "jest-get-type": "^29.6.3", + "pretty-format": "^29.7.0" }, "engines": { - "node": ">=7.0.0" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, - "node_modules/jest-diff/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/jest-diff/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "node_modules/jest-diff/node_modules/ansi-styles": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", + "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", "engines": { - "node": ">=8" + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" } }, - "node_modules/jest-diff/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/jest-diff/node_modules/pretty-format": { + "version": "29.7.0", + "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-29.7.0.tgz", + "integrity": "sha512-Pdlw/oPxN+aXdmM9R00JVC9WVFoCLTKJvDVLgmJ+qAffBMxsV85l/Lu7sNx4zSzPyoL2euImuEwHhOXdEgNFZQ==", "dependencies": { - "has-flag": "^4.0.0" + "@jest/schemas": "^29.6.3", + "ansi-styles": "^5.0.0", + "react-is": "^18.0.0" }, "engines": { - "node": ">=8" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, + "node_modules/jest-diff/node_modules/react-is": { + "version": "18.2.0", + "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.2.0.tgz", + "integrity": "sha512-xWGDIW6x921xtzPkhiULtthJHoJvBbF3q26fzloPCK0hsvxtPVelvftw3zjbHWSkR2km9Z+4uxbDDK/6Zw9B8w==" + }, "node_modules/jest-docblock": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-docblock/-/jest-docblock-27.5.1.tgz", @@ -10545,68 +10154,51 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-each/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/jest-each/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "node_modules/jest-each/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" }, "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-each/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/jest-each/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" + "@types/yargs-parser": "*" } }, - "node_modules/jest-each/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/jest-each/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "node_modules/jest-each/node_modules/jest-get-type": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-get-type/-/jest-get-type-27.5.1.tgz", + "integrity": "sha512-2KY95ksYSaK7DMBWQn6dQz3kqAf3BB64y2udeG+hv4KfSOb9qwcYQstTJc1KCbsix+wLZWZYN8t7nwX3GOBLRw==", "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-each/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/jest-each/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", "dependencies": { - "has-flag": "^4.0.0" + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" }, "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, "node_modules/jest-environment-jsdom": { @@ -10626,6 +10218,45 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, + "node_modules/jest-environment-jsdom/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", + "dependencies": { + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/jest-environment-jsdom/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", + "dependencies": { + "@types/yargs-parser": "*" + } + }, + "node_modules/jest-environment-jsdom/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", + "dependencies": { + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, "node_modules/jest-environment-node": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-environment-node/-/jest-environment-node-27.5.1.tgz", @@ -10642,14 +10273,53 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-get-type": { + "node_modules/jest-environment-node/node_modules/@jest/types": { "version": "27.5.1", - "resolved": "https://registry.npmjs.org/jest-get-type/-/jest-get-type-27.5.1.tgz", - "integrity": "sha512-2KY95ksYSaK7DMBWQn6dQz3kqAf3BB64y2udeG+hv4KfSOb9qwcYQstTJc1KCbsix+wLZWZYN8t7nwX3GOBLRw==", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", + "dependencies": { + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/jest-environment-node/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", + "dependencies": { + "@types/yargs-parser": "*" + } + }, + "node_modules/jest-environment-node/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", + "dependencies": { + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" + }, "engines": { "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, + "node_modules/jest-get-type": { + "version": "29.6.3", + "resolved": "https://registry.npmjs.org/jest-get-type/-/jest-get-type-29.6.3.tgz", + "integrity": "sha512-zrteXnqYxfQh7l5FHyL38jL39di8H8rHoecLH3JNxH3BwOrBsNeabdap5e0I23lD4HHI8W5VFBZqG4Eaq5LNcw==", + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, "node_modules/jest-haste-map": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-haste-map/-/jest-haste-map-27.5.1.tgz", @@ -10675,6 +10345,45 @@ "fsevents": "^2.3.2" } }, + "node_modules/jest-haste-map/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", + "dependencies": { + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/jest-haste-map/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", + "dependencies": { + "@types/yargs-parser": "*" + } + }, + "node_modules/jest-haste-map/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", + "dependencies": { + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, "node_modules/jest-jasmine2": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-jasmine2/-/jest-jasmine2-27.5.1.tgz", @@ -10702,75 +10411,58 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-jasmine2/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/jest-jasmine2/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "node_modules/jest-jasmine2/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" }, "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-jasmine2/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/jest-jasmine2/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" + "@types/yargs-parser": "*" } }, - "node_modules/jest-jasmine2/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/jest-jasmine2/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "node_modules/jest-jasmine2/node_modules/diff-sequences": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/diff-sequences/-/diff-sequences-27.5.1.tgz", + "integrity": "sha512-k1gCAXAsNgLwEL+Y8Wvl+M6oEFj5bgazfZULpS5CneoPPXRaCCW7dm+q21Ky2VEE5X+VeRDBVg1Pcvvsr4TtNQ==", "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-jasmine2/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/jest-jasmine2/node_modules/expect": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/expect/-/expect-27.5.1.tgz", + "integrity": "sha512-E1q5hSUG2AmYQwQJ041nvgpkODHQvB+RKlB4IYdru6uJsyFTRyZAP463M+1lINorwbqAmUggi6+WwkD8lCS/Dw==", "dependencies": { - "has-flag": "^4.0.0" + "@jest/types": "^27.5.1", + "jest-get-type": "^27.5.1", + "jest-matcher-utils": "^27.5.1", + "jest-message-util": "^27.5.1" }, "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-leak-detector": { + "node_modules/jest-jasmine2/node_modules/jest-diff": { "version": "27.5.1", - "resolved": "https://registry.npmjs.org/jest-leak-detector/-/jest-leak-detector-27.5.1.tgz", - "integrity": "sha512-POXfWAMvfU6WMUXftV4HolnJfnPOGEu10fscNCA76KBpRRhcMN2c8d3iT2pxQS3HLbA+5X4sOUPzYO2NUyIlHQ==", + "resolved": "https://registry.npmjs.org/jest-diff/-/jest-diff-27.5.1.tgz", + "integrity": "sha512-m0NvkX55LDt9T4mctTEgnZk3fmEg3NRYutvMPWM/0iPnkFj2wIeF45O1718cMSOFO1vINkqmxqD8vE37uTEbqw==", "dependencies": { + "chalk": "^4.0.0", + "diff-sequences": "^27.5.1", "jest-get-type": "^27.5.1", "pretty-format": "^27.5.1" }, @@ -10778,7 +10470,15 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-matcher-utils": { + "node_modules/jest-jasmine2/node_modules/jest-get-type": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-get-type/-/jest-get-type-27.5.1.tgz", + "integrity": "sha512-2KY95ksYSaK7DMBWQn6dQz3kqAf3BB64y2udeG+hv4KfSOb9qwcYQstTJc1KCbsix+wLZWZYN8t7nwX3GOBLRw==", + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/jest-jasmine2/node_modules/jest-matcher-utils": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-matcher-utils/-/jest-matcher-utils-27.5.1.tgz", "integrity": "sha512-z2uTx/T6LBaCoNWNFWwChLBKYxTMcGBRjAt+2SbP929/Fflb9aa5LGma654Rz8z9HLxsrUaYzxE9T/EFIL/PAw==", @@ -10792,152 +10492,151 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-matcher-utils/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "node_modules/jest-jasmine2/node_modules/jest-message-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-27.5.1.tgz", + "integrity": "sha512-rMyFe1+jnyAAf+NHwTclDz0eAaLkVDdKVHHBFWsBWHnnh5YeJMNWWsv7AbFYXfK3oTqvL7VTWkhNLu1jX24D+g==", "dependencies": { - "color-convert": "^2.0.1" + "@babel/code-frame": "^7.12.13", + "@jest/types": "^27.5.1", + "@types/stack-utils": "^2.0.0", + "chalk": "^4.0.0", + "graceful-fs": "^4.2.9", + "micromatch": "^4.0.4", + "pretty-format": "^27.5.1", + "slash": "^3.0.0", + "stack-utils": "^2.0.3" }, "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-matcher-utils/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "node_modules/jest-jasmine2/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" }, "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-matcher-utils/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/jest-leak-detector": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-leak-detector/-/jest-leak-detector-27.5.1.tgz", + "integrity": "sha512-POXfWAMvfU6WMUXftV4HolnJfnPOGEu10fscNCA76KBpRRhcMN2c8d3iT2pxQS3HLbA+5X4sOUPzYO2NUyIlHQ==", "dependencies": { - "color-name": "~1.1.4" + "jest-get-type": "^27.5.1", + "pretty-format": "^27.5.1" }, "engines": { - "node": ">=7.0.0" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-matcher-utils/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" + "node_modules/jest-leak-detector/node_modules/jest-get-type": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-get-type/-/jest-get-type-27.5.1.tgz", + "integrity": "sha512-2KY95ksYSaK7DMBWQn6dQz3kqAf3BB64y2udeG+hv4KfSOb9qwcYQstTJc1KCbsix+wLZWZYN8t7nwX3GOBLRw==", + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } }, - "node_modules/jest-matcher-utils/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "node_modules/jest-matcher-utils": { + "version": "29.7.0", + "resolved": "https://registry.npmjs.org/jest-matcher-utils/-/jest-matcher-utils-29.7.0.tgz", + "integrity": "sha512-sBkD+Xi9DtcChsI3L3u0+N0opgPYnCRPtGcQYrgXmR+hmt/fYfWAL0xRXYU8eWOdfuLgBe0YCW3AFtnRLagq/g==", + "dependencies": { + "chalk": "^4.0.0", + "jest-diff": "^29.7.0", + "jest-get-type": "^29.6.3", + "pretty-format": "^29.7.0" + }, "engines": { - "node": ">=8" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, - "node_modules/jest-matcher-utils/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/jest-matcher-utils/node_modules/ansi-styles": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", + "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" + } + }, + "node_modules/jest-matcher-utils/node_modules/pretty-format": { + "version": "29.7.0", + "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-29.7.0.tgz", + "integrity": "sha512-Pdlw/oPxN+aXdmM9R00JVC9WVFoCLTKJvDVLgmJ+qAffBMxsV85l/Lu7sNx4zSzPyoL2euImuEwHhOXdEgNFZQ==", "dependencies": { - "has-flag": "^4.0.0" + "@jest/schemas": "^29.6.3", + "ansi-styles": "^5.0.0", + "react-is": "^18.0.0" }, "engines": { - "node": ">=8" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, + "node_modules/jest-matcher-utils/node_modules/react-is": { + "version": "18.2.0", + "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.2.0.tgz", + "integrity": "sha512-xWGDIW6x921xtzPkhiULtthJHoJvBbF3q26fzloPCK0hsvxtPVelvftw3zjbHWSkR2km9Z+4uxbDDK/6Zw9B8w==" + }, "node_modules/jest-message-util": { - "version": "27.5.1", - "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-27.5.1.tgz", - "integrity": "sha512-rMyFe1+jnyAAf+NHwTclDz0eAaLkVDdKVHHBFWsBWHnnh5YeJMNWWsv7AbFYXfK3oTqvL7VTWkhNLu1jX24D+g==", + "version": "29.7.0", + "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-29.7.0.tgz", + "integrity": "sha512-GBEV4GRADeP+qtB2+6u61stea8mGcOT4mCtrYISZwfu9/ISHFJ/5zOMXYbpBE9RsS5+Gb63DW4FgmnKJ79Kf6w==", "dependencies": { "@babel/code-frame": "^7.12.13", - "@jest/types": "^27.5.1", + "@jest/types": "^29.6.3", "@types/stack-utils": "^2.0.0", "chalk": "^4.0.0", "graceful-fs": "^4.2.9", "micromatch": "^4.0.4", - "pretty-format": "^27.5.1", + "pretty-format": "^29.7.0", "slash": "^3.0.0", "stack-utils": "^2.0.3" }, "engines": { - "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, "node_modules/jest-message-util/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/jest-message-util/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", + "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", "engines": { "node": ">=10" }, "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "url": "https://github.com/chalk/ansi-styles?sponsor=1" } }, - "node_modules/jest-message-util/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/jest-message-util/node_modules/pretty-format": { + "version": "29.7.0", + "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-29.7.0.tgz", + "integrity": "sha512-Pdlw/oPxN+aXdmM9R00JVC9WVFoCLTKJvDVLgmJ+qAffBMxsV85l/Lu7sNx4zSzPyoL2euImuEwHhOXdEgNFZQ==", "dependencies": { - "color-name": "~1.1.4" + "@jest/schemas": "^29.6.3", + "ansi-styles": "^5.0.0", + "react-is": "^18.0.0" }, "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-message-util/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/jest-message-util/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, - "node_modules/jest-message-util/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } + "node_modules/jest-message-util/node_modules/react-is": { + "version": "18.2.0", + "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.2.0.tgz", + "integrity": "sha512-xWGDIW6x921xtzPkhiULtthJHoJvBbF3q26fzloPCK0hsvxtPVelvftw3zjbHWSkR2km9Z+4uxbDDK/6Zw9B8w==" }, "node_modules/jest-mock": { "version": "27.5.1", @@ -10951,6 +10650,29 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, + "node_modules/jest-mock/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", + "dependencies": { + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/jest-mock/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", + "dependencies": { + "@types/yargs-parser": "*" + } + }, "node_modules/jest-pnp-resolver": { "version": "1.2.3", "resolved": "https://registry.npmjs.org/jest-pnp-resolver/-/jest-pnp-resolver-1.2.3.tgz", @@ -11008,68 +10730,66 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-resolve/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "node_modules/jest-resolve-dependencies/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", "dependencies": { - "color-convert": "^2.0.1" + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" }, "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-resolve/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "node_modules/jest-resolve-dependencies/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "@types/yargs-parser": "*" } }, - "node_modules/jest-resolve/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/jest-resolve/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", "dependencies": { - "color-name": "~1.1.4" + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" }, "engines": { - "node": ">=7.0.0" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-resolve/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/jest-resolve/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" + "node_modules/jest-resolve/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", + "dependencies": { + "@types/yargs-parser": "*" } }, - "node_modules/jest-resolve/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/jest-resolve/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", "dependencies": { - "has-flag": "^4.0.0" + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" }, "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, "node_modules/jest-runner": { @@ -11103,68 +10823,62 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-runner/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "node_modules/jest-runner/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", "dependencies": { - "color-convert": "^2.0.1" + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" }, "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-runner/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "node_modules/jest-runner/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "@types/yargs-parser": "*" } }, - "node_modules/jest-runner/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/jest-runner/node_modules/jest-message-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-27.5.1.tgz", + "integrity": "sha512-rMyFe1+jnyAAf+NHwTclDz0eAaLkVDdKVHHBFWsBWHnnh5YeJMNWWsv7AbFYXfK3oTqvL7VTWkhNLu1jX24D+g==", "dependencies": { - "color-name": "~1.1.4" + "@babel/code-frame": "^7.12.13", + "@jest/types": "^27.5.1", + "@types/stack-utils": "^2.0.0", + "chalk": "^4.0.0", + "graceful-fs": "^4.2.9", + "micromatch": "^4.0.4", + "pretty-format": "^27.5.1", + "slash": "^3.0.0", + "stack-utils": "^2.0.3" }, "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-runner/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/jest-runner/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-runner/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/jest-runner/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", "dependencies": { - "has-flag": "^4.0.0" + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" }, "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, "node_modules/jest-runtime": { @@ -11199,68 +10913,62 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-runtime/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "node_modules/jest-runtime/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", "dependencies": { - "color-convert": "^2.0.1" + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" }, "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-runtime/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "node_modules/jest-runtime/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "@types/yargs-parser": "*" } }, - "node_modules/jest-runtime/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/jest-runtime/node_modules/jest-message-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-27.5.1.tgz", + "integrity": "sha512-rMyFe1+jnyAAf+NHwTclDz0eAaLkVDdKVHHBFWsBWHnnh5YeJMNWWsv7AbFYXfK3oTqvL7VTWkhNLu1jX24D+g==", "dependencies": { - "color-name": "~1.1.4" + "@babel/code-frame": "^7.12.13", + "@jest/types": "^27.5.1", + "@types/stack-utils": "^2.0.0", + "chalk": "^4.0.0", + "graceful-fs": "^4.2.9", + "micromatch": "^4.0.4", + "pretty-format": "^27.5.1", + "slash": "^3.0.0", + "stack-utils": "^2.0.3" }, "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-runtime/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/jest-runtime/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-runtime/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/jest-runtime/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", "dependencies": { - "has-flag": "^4.0.0" + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" }, "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, "node_modules/jest-serializer": { @@ -11307,71 +11015,107 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-snapshot/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "node_modules/jest-snapshot/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", "dependencies": { - "color-convert": "^2.0.1" + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" }, "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-snapshot/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "node_modules/jest-snapshot/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, + "@types/yargs-parser": "*" + } + }, + "node_modules/jest-snapshot/node_modules/diff-sequences": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/diff-sequences/-/diff-sequences-27.5.1.tgz", + "integrity": "sha512-k1gCAXAsNgLwEL+Y8Wvl+M6oEFj5bgazfZULpS5CneoPPXRaCCW7dm+q21Ky2VEE5X+VeRDBVg1Pcvvsr4TtNQ==", "engines": { - "node": ">=10" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/jest-snapshot/node_modules/expect": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/expect/-/expect-27.5.1.tgz", + "integrity": "sha512-E1q5hSUG2AmYQwQJ041nvgpkODHQvB+RKlB4IYdru6uJsyFTRyZAP463M+1lINorwbqAmUggi6+WwkD8lCS/Dw==", + "dependencies": { + "@jest/types": "^27.5.1", + "jest-get-type": "^27.5.1", + "jest-matcher-utils": "^27.5.1", + "jest-message-util": "^27.5.1" }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-snapshot/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/jest-snapshot/node_modules/jest-diff": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-diff/-/jest-diff-27.5.1.tgz", + "integrity": "sha512-m0NvkX55LDt9T4mctTEgnZk3fmEg3NRYutvMPWM/0iPnkFj2wIeF45O1718cMSOFO1vINkqmxqD8vE37uTEbqw==", "dependencies": { - "color-name": "~1.1.4" + "chalk": "^4.0.0", + "diff-sequences": "^27.5.1", + "jest-get-type": "^27.5.1", + "pretty-format": "^27.5.1" }, "engines": { - "node": ">=7.0.0" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-snapshot/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" + "node_modules/jest-snapshot/node_modules/jest-get-type": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-get-type/-/jest-get-type-27.5.1.tgz", + "integrity": "sha512-2KY95ksYSaK7DMBWQn6dQz3kqAf3BB64y2udeG+hv4KfSOb9qwcYQstTJc1KCbsix+wLZWZYN8t7nwX3GOBLRw==", + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } }, - "node_modules/jest-snapshot/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "node_modules/jest-snapshot/node_modules/jest-matcher-utils": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-matcher-utils/-/jest-matcher-utils-27.5.1.tgz", + "integrity": "sha512-z2uTx/T6LBaCoNWNFWwChLBKYxTMcGBRjAt+2SbP929/Fflb9aa5LGma654Rz8z9HLxsrUaYzxE9T/EFIL/PAw==", + "dependencies": { + "chalk": "^4.0.0", + "jest-diff": "^27.5.1", + "jest-get-type": "^27.5.1", + "pretty-format": "^27.5.1" + }, "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-snapshot/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/jest-snapshot/node_modules/jest-message-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-27.5.1.tgz", + "integrity": "sha512-rMyFe1+jnyAAf+NHwTclDz0eAaLkVDdKVHHBFWsBWHnnh5YeJMNWWsv7AbFYXfK3oTqvL7VTWkhNLu1jX24D+g==", "dependencies": { - "has-flag": "^4.0.0" + "@babel/code-frame": "^7.12.13", + "@jest/types": "^27.5.1", + "@types/stack-utils": "^2.0.0", + "chalk": "^4.0.0", + "graceful-fs": "^4.2.9", + "micromatch": "^4.0.4", + "pretty-format": "^27.5.1", + "slash": "^3.0.0", + "stack-utils": "^2.0.3" }, "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-util": { + "node_modules/jest-snapshot/node_modules/jest-util": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", @@ -11387,68 +11131,20 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-util/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/jest-util/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/jest-util/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-util/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/jest-util/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" - } - }, - "node_modules/jest-util/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/jest-util": { + "version": "29.7.0", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-29.7.0.tgz", + "integrity": "sha512-z6EbKajIpqGKU56y5KBUgy1dt1ihhQJgWzUlZHArA/+X2ad7Cb5iF+AK1EWVL/Bo7Rz9uurpqw6SiBCefUbCGA==", "dependencies": { - "has-flag": "^4.0.0" + "@jest/types": "^29.6.3", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" }, "engines": { - "node": ">=8" + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, "node_modules/jest-validate": { @@ -11467,68 +11163,35 @@ "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-validate/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/jest-validate/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "node_modules/jest-validate/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" }, "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-validate/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/jest-validate/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-validate/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/jest-validate/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" + "@types/yargs-parser": "*" } }, - "node_modules/jest-validate/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dependencies": { - "has-flag": "^4.0.0" - }, + "node_modules/jest-validate/node_modules/jest-get-type": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-get-type/-/jest-get-type-27.5.1.tgz", + "integrity": "sha512-2KY95ksYSaK7DMBWQn6dQz3kqAf3BB64y2udeG+hv4KfSOb9qwcYQstTJc1KCbsix+wLZWZYN8t7nwX3GOBLRw==", "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, "node_modules/jest-watch-typeahead": { @@ -11575,6 +11238,17 @@ "node": ">=8" } }, + "node_modules/jest-watch-typeahead/node_modules/@jest/schemas": { + "version": "28.1.3", + "resolved": "https://registry.npmjs.org/@jest/schemas/-/schemas-28.1.3.tgz", + "integrity": "sha512-/l/VWsdt/aBXgjshLWOFyFt3IVdYypu5y2Wn2rOO1un6nkqIn8SLXzgIMYXFyYsRWDyF5EthmKJMIdJvk08grg==", + "dependencies": { + "@sinclair/typebox": "^0.24.1" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" + } + }, "node_modules/jest-watch-typeahead/node_modules/@jest/test-result": { "version": "28.1.3", "resolved": "https://registry.npmjs.org/@jest/test-result/-/test-result-28.1.3.tgz", @@ -11605,59 +11279,22 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-watch-typeahead/node_modules/@types/yargs": { - "version": "17.0.24", - "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-17.0.24.tgz", - "integrity": "sha512-6i0aC7jV6QzQB8ne1joVZ0eSFIstHsCrobmOtghM11yGlH0j43FKL2UhWdELkyps0zuf7qVTUVCCR+tgSlyLLw==", - "dependencies": { - "@types/yargs-parser": "*" - } + "node_modules/jest-watch-typeahead/node_modules/@sinclair/typebox": { + "version": "0.24.51", + "resolved": "https://registry.npmjs.org/@sinclair/typebox/-/typebox-0.24.51.tgz", + "integrity": "sha512-1P1OROm/rdubP5aFDSZQILU0vrLCJ4fvHt6EoqHEM+2D/G5MK3bIaymUKLit8Js9gbns5UyJnkP/TZROLw4tUA==" }, "node_modules/jest-watch-typeahead/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/jest-watch-typeahead/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", + "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", "engines": { "node": ">=10" }, "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/jest-watch-typeahead/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" + "url": "https://github.com/chalk/ansi-styles?sponsor=1" } }, - "node_modules/jest-watch-typeahead/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-watch-typeahead/node_modules/emittery": { "version": "0.10.2", "resolved": "https://registry.npmjs.org/emittery/-/emittery-0.10.2.tgz", @@ -11669,14 +11306,6 @@ "url": "https://github.com/sindresorhus/emittery?sponsor=1" } }, - "node_modules/jest-watch-typeahead/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" - } - }, "node_modules/jest-watch-typeahead/node_modules/jest-message-util": { "version": "28.1.3", "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-28.1.3.tgz", @@ -11783,17 +11412,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-watch-typeahead/node_modules/pretty-format/node_modules/ansi-styles": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", - "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-watch-typeahead/node_modules/react-is": { "version": "18.2.0", "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.2.0.tgz", @@ -11858,17 +11476,6 @@ "url": "https://github.com/chalk/ansi-regex?sponsor=1" } }, - "node_modules/jest-watch-typeahead/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, "node_modules/jest-watcher": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-watcher/-/jest-watcher-27.5.1.tgz", @@ -11883,71 +11490,46 @@ "string-length": "^4.0.1" }, "engines": { - "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" - } - }, - "node_modules/jest-watcher/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/jest-watcher/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-watcher/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "node_modules/jest-watcher/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", "dependencies": { - "color-name": "~1.1.4" + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" }, "engines": { - "node": ">=7.0.0" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, - "node_modules/jest-watcher/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/jest-watcher/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" + "node_modules/jest-watcher/node_modules/@types/yargs": { + "version": "16.0.6", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.6.tgz", + "integrity": "sha512-oTP7/Q13GSPrgcwEwdlnkoZSQ1Hg9THe644qq8PG6hhJzjZ3qj1JjEFPIwWV/IXVs5XGIVqtkNOS9kh63WIJ+A==", + "dependencies": { + "@types/yargs-parser": "*" } }, - "node_modules/jest-watcher/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/jest-watcher/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", "dependencies": { - "has-flag": "^4.0.0" + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" }, "engines": { - "node": ">=8" + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } }, "node_modules/jest-worker": { @@ -11963,14 +11545,6 @@ "node": ">= 10.13.0" } }, - "node_modules/jest-worker/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" - } - }, "node_modules/jest-worker/node_modules/supports-color": { "version": "8.1.1", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", @@ -13281,9 +12855,9 @@ } }, "node_modules/postcss": { - "version": "8.4.30", - "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.4.30.tgz", - "integrity": "sha512-7ZEao1g4kd68l97aWG/etQKPKq07us0ieSZ2TnFDk11i0ZfDW2AwKHYU8qv4MZKqN2fdBfg+7q0ES06UA73C1g==", + "version": "8.4.31", + "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.4.31.tgz", + "integrity": "sha512-PS08Iboia9mts/2ygV3eLpY5ghnUcfLV/EXTOW1E2qYxJKGGBUtNjN76FYHnMs36RmARn41bC0AZmn+rR0OVpQ==", "funding": [ { "type": "opencollective", @@ -14769,70 +14343,6 @@ "node": ">=14" } }, - "node_modules/react-dev-utils/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/react-dev-utils/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/react-dev-utils/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/react-dev-utils/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/react-dev-utils/node_modules/escape-string-regexp": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", - "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/react-dev-utils/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" - } - }, "node_modules/react-dev-utils/node_modules/loader-utils": { "version": "3.2.1", "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-3.2.1.tgz", @@ -14841,17 +14351,6 @@ "node": ">= 12.13.0" } }, - "node_modules/react-dev-utils/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, "node_modules/react-dom": { "version": "18.2.0", "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-18.2.0.tgz", @@ -15235,6 +14734,11 @@ } } }, + "node_modules/resolve-url-loader/node_modules/convert-source-map": { + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.9.0.tgz", + "integrity": "sha512-ASFBup0Mz1uyiIjANan1jzLQami9z1PoYSZCiiYW2FczPbenXc45FZdBZLzOT+r6+iciuEModtmCti+hjaAk0A==" + }, "node_modules/resolve-url-loader/node_modules/picocolors": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-0.2.1.tgz", @@ -15332,14 +14836,6 @@ "rollup": "^2.0.0" } }, - "node_modules/rollup-plugin-terser/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" - } - }, "node_modules/rollup-plugin-terser/node_modules/jest-worker": { "version": "26.6.2", "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-26.6.2.tgz", @@ -15361,17 +14857,6 @@ "randombytes": "^2.1.0" } }, - "node_modules/rollup-plugin-terser/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, "node_modules/run-parallel": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz", @@ -16352,14 +15837,14 @@ } }, "node_modules/supports-color": { - "version": "5.5.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", - "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", + "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", "dependencies": { - "has-flag": "^3.0.0" + "has-flag": "^4.0.0" }, "engines": { - "node": ">=4" + "node": ">=8" } }, "node_modules/supports-hyperlinks": { @@ -16374,25 +15859,6 @@ "node": ">=8" } }, - "node_modules/supports-hyperlinks/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" - } - }, - "node_modules/supports-hyperlinks/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, "node_modules/supports-preserve-symlinks-flag": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", @@ -16436,6 +15902,43 @@ "node": ">=4.0.0" } }, + "node_modules/svgo/node_modules/ansi-styles": { + "version": "3.2.1", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", + "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", + "dependencies": { + "color-convert": "^1.9.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/svgo/node_modules/chalk": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", + "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", + "dependencies": { + "ansi-styles": "^3.2.1", + "escape-string-regexp": "^1.0.5", + "supports-color": "^5.3.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/svgo/node_modules/color-convert": { + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz", + "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==", + "dependencies": { + "color-name": "1.1.3" + } + }, + "node_modules/svgo/node_modules/color-name": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", + "integrity": "sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw==" + }, "node_modules/svgo/node_modules/css-select": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/css-select/-/css-select-2.1.0.tgz", @@ -16481,6 +15984,22 @@ "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-1.3.1.tgz", "integrity": "sha512-BSKB+TSpMpFI/HOxCNr1O8aMOTZ8hT3pM3GQ0w/mWRmkhEDSFJkkyzz4XQsBV44BChwGkrDfMyjVD0eA2aFV3w==" }, + "node_modules/svgo/node_modules/escape-string-regexp": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", + "integrity": "sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==", + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/svgo/node_modules/has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw==", + "engines": { + "node": ">=4" + } + }, "node_modules/svgo/node_modules/nth-check": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/nth-check/-/nth-check-1.0.2.tgz", @@ -16489,6 +16008,17 @@ "boolbase": "~1.0.0" } }, + "node_modules/svgo/node_modules/supports-color": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dependencies": { + "has-flag": "^3.0.0" + }, + "engines": { + "node": ">=4" + } + }, "node_modules/symbol-tree": { "version": "3.2.4", "resolved": "https://registry.npmjs.org/symbol-tree/-/symbol-tree-3.2.4.tgz", @@ -17138,6 +16668,11 @@ "node": ">=10.12.0" } }, + "node_modules/v8-to-istanbul/node_modules/convert-source-map": { + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.9.0.tgz", + "integrity": "sha512-ASFBup0Mz1uyiIjANan1jzLQami9z1PoYSZCiiYW2FczPbenXc45FZdBZLzOT+r6+iciuEModtmCti+hjaAk0A==" + }, "node_modules/vary": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", @@ -17982,36 +17517,6 @@ "url": "https://github.com/chalk/wrap-ansi?sponsor=1" } }, - "node_modules/wrap-ansi/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/wrap-ansi/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/wrap-ansi/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/wrappy": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", diff --git a/package.json b/package.json index 44bb48e..0009714 100644 --- a/package.json +++ b/package.json @@ -7,9 +7,9 @@ "@testing-library/react": "^13.4.0", "@testing-library/user-event": "^13.5.0", "@types/jest": "^29.5.5", - "@types/node": "^20.6.5", - "@types/react": "^18.2.22", - "@types/react-dom": "^18.2.7", + "@types/node": "^20.7.1", + "@types/react": "^18.2.23", + "@types/react-dom": "^18.2.8", "react": "^18.2.0", "react-dom": "^18.2.0", "react-scripts": "5.0.1", diff --git a/custom.d.ts b/src/custom.d.ts similarity index 100% rename from custom.d.ts rename to src/custom.d.ts diff --git a/tsconfig.json b/tsconfig.json index a71d860..0f6d15f 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -20,6 +20,5 @@ "noEmit": true, "jsx": "react-jsx" }, - "include": [ - "src", "custom.d.ts" ] + "include": ["src", "src/custom.d.ts" ] } \ No newline at end of file From dd769bb04e228d672b2cd1903f8d84088402c1db Mon Sep 17 00:00:00 2001 From: leekyuho Date: Fri, 29 Sep 2023 17:59:50 +0900 Subject: [PATCH 17/55] =?UTF-8?q?fix:=20git=20=ED=8C=8C=EC=9D=BC=EC=9D=B4?= =?UTF-8?q?=EB=A6=84=20=EB=8C=80=EC=86=8C=EB=AC=B8=EC=9E=90=20=EB=B3=80?= =?UTF-8?q?=EA=B2=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/assets/{Icons => icons}/Back.svg | 0 src/assets/{Icons => icons}/Call.svg | 0 src/assets/{Icons => icons}/Chat.svg | 0 src/assets/{Icons => icons}/Freinds.svg | 0 src/assets/{Icons => icons}/More.svg | 0 src/assets/{Icons => icons}/Plus.svg | 0 src/assets/{Icons => icons}/Send.svg | 0 src/assets/{Iphone => iphone}/Battery.svg | 0 src/assets/{Iphone => iphone}/Clock.svg | 0 src/assets/{Iphone => iphone}/HomeBar.svg | 0 src/assets/{Iphone => iphone}/Signal.svg | 0 src/assets/{Iphone => iphone}/WifiConnection.svg | 0 12 files changed, 0 insertions(+), 0 deletions(-) rename src/assets/{Icons => icons}/Back.svg (100%) rename src/assets/{Icons => icons}/Call.svg (100%) rename src/assets/{Icons => icons}/Chat.svg (100%) rename src/assets/{Icons => icons}/Freinds.svg (100%) rename src/assets/{Icons => icons}/More.svg (100%) rename src/assets/{Icons => icons}/Plus.svg (100%) rename src/assets/{Icons => icons}/Send.svg (100%) rename src/assets/{Iphone => iphone}/Battery.svg (100%) rename src/assets/{Iphone => iphone}/Clock.svg (100%) rename src/assets/{Iphone => iphone}/HomeBar.svg (100%) rename src/assets/{Iphone => iphone}/Signal.svg (100%) rename src/assets/{Iphone => iphone}/WifiConnection.svg (100%) diff --git a/src/assets/Icons/Back.svg b/src/assets/icons/Back.svg similarity index 100% rename from src/assets/Icons/Back.svg rename to src/assets/icons/Back.svg diff --git a/src/assets/Icons/Call.svg b/src/assets/icons/Call.svg similarity index 100% rename from src/assets/Icons/Call.svg rename to src/assets/icons/Call.svg diff --git a/src/assets/Icons/Chat.svg b/src/assets/icons/Chat.svg similarity index 100% rename from src/assets/Icons/Chat.svg rename to src/assets/icons/Chat.svg diff --git a/src/assets/Icons/Freinds.svg b/src/assets/icons/Freinds.svg similarity index 100% rename from src/assets/Icons/Freinds.svg rename to src/assets/icons/Freinds.svg diff --git a/src/assets/Icons/More.svg b/src/assets/icons/More.svg similarity index 100% rename from src/assets/Icons/More.svg rename to src/assets/icons/More.svg diff --git a/src/assets/Icons/Plus.svg b/src/assets/icons/Plus.svg similarity index 100% rename from src/assets/Icons/Plus.svg rename to src/assets/icons/Plus.svg diff --git a/src/assets/Icons/Send.svg b/src/assets/icons/Send.svg similarity index 100% rename from src/assets/Icons/Send.svg rename to src/assets/icons/Send.svg diff --git a/src/assets/Iphone/Battery.svg b/src/assets/iphone/Battery.svg similarity index 100% rename from src/assets/Iphone/Battery.svg rename to src/assets/iphone/Battery.svg diff --git a/src/assets/Iphone/Clock.svg b/src/assets/iphone/Clock.svg similarity index 100% rename from src/assets/Iphone/Clock.svg rename to src/assets/iphone/Clock.svg diff --git a/src/assets/Iphone/HomeBar.svg b/src/assets/iphone/HomeBar.svg similarity index 100% rename from src/assets/Iphone/HomeBar.svg rename to src/assets/iphone/HomeBar.svg diff --git a/src/assets/Iphone/Signal.svg b/src/assets/iphone/Signal.svg similarity index 100% rename from src/assets/Iphone/Signal.svg rename to src/assets/iphone/Signal.svg diff --git a/src/assets/Iphone/WifiConnection.svg b/src/assets/iphone/WifiConnection.svg similarity index 100% rename from src/assets/Iphone/WifiConnection.svg rename to src/assets/iphone/WifiConnection.svg From 5bbd96fffa960db4f67613973571d91562a6e657 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Fri, 29 Sep 2023 18:16:03 +0900 Subject: [PATCH 18/55] =?UTF-8?q?chore:=20favicon=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- public/favicon.ico | Bin 1150 -> 1150 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/public/favicon.ico b/public/favicon.ico index 7537528f36b737dba52d4740d6c4cfa910bfaf58..2521a4d2b73e68df5e91b73d0ab5ff5e11e04beb 100644 GIT binary patch literal 1150 zcmb7@%WD%+6vppN<`L{9nMvCu8f!9Rv1%hKQFKwNs2lNxXrZ-LqZ@TA=uRlOP+aQX zr4?K#;veA3jVQQsC6u}nR0MJ3>+^g!xkDykMZ!0^bMN_`bLO0Lm9pd)hDx4Ib=gs> zqLkV!k}cWk?#rK2ayC5Fm45GgbdV^KFFGuGD0(mY(G%C);~8yIvV)i$RTJG6eHP&_ z;u&pdD@=xcJjh%SKZEMo(6;9z@nlV(*_gi*%zkL##GCav_Ntz0?qkE)ks-@(`eb;< zTlm_1Hc$KT%Qp5cWq8wH&9`rrVY`;jyLBx@JQu+BEbWJRw62Gk zS;^#2KFxpfY6+I3Fma`b_U$ruEJjG?1LS-Q@ob=L!(97BmNn4v4?U~tS_cgW;iRWk z77Vo$8i2ERm3p32YSBu!{<)wn8M1!>Sh@NQ literal 1150 zcmds%Pb-8`6vmITvzb!Xla-xMzz1OE8(2>Ar!=t|ij`t9)F?Hj#6n6|ifmCL3$d^v zc4K2|l+FA+=f38xncSJO>T7MsG9m}FNS z#`3#!O&LzvZbF5Z5T~Ghjd5Lnt-bN_%sr1!$;JMi223%WJjJpcdz From ce617e629516bcee3f4a1443d87af5d7ea68209b Mon Sep 17 00:00:00 2001 From: leekyuho Date: Fri, 29 Sep 2023 20:17:48 +0900 Subject: [PATCH 19/55] =?UTF-8?q?fix:=20text=20=EA=B8=B8=EC=96=B4=EC=A1=8C?= =?UTF-8?q?=EC=9D=84=EB=95=8C=20chat=20bubble=20=EA=B9=A8=EC=A7=90?= =?UTF-8?q?=ED=98=84=EC=83=81=20fix?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/ChatBubble.tsx | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/components/ChatBubble.tsx b/src/components/ChatBubble.tsx index d697ae7..1cc5424 100644 --- a/src/components/ChatBubble.tsx +++ b/src/components/ChatBubble.tsx @@ -42,11 +42,11 @@ const ChatBubbleContainer = styled.div<{isMyChat:boolean}>` } `; const ChatBox = styled.div<{isMyChat:boolean}>` - display: inline-block; + /*display: inline-block;*/ background-color : ${props => (props.isMyChat ? "var(--green)" : "var(--gray-1)")}; max-width : 16.8125rem; width: fit-content; - border-radius: 6.25rem; + border-radius: 1.5rem; margin : ${props => (props.isMyChat ? "0.625rem 1.25rem 0.625rem 0" : "0.625rem 0 0.625rem 1.25rem")}; `; const ChatText = styled(Body2)<{isMyChat:boolean}>` From 977d5be539309978b7cd4426e749479321edf797 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Fri, 29 Sep 2023 20:24:16 +0900 Subject: [PATCH 20/55] =?UTF-8?q?fix:=20=EA=B8=80=EC=94=A8=20=EB=84=98?= =?UTF-8?q?=EC=96=B4=EA=B0=90=20=EC=98=A4=EB=A5=98=20=ED=95=B4=EA=B2=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/ChatBubble.tsx | 1 + 1 file changed, 1 insertion(+) diff --git a/src/components/ChatBubble.tsx b/src/components/ChatBubble.tsx index 1cc5424..aa441ea 100644 --- a/src/components/ChatBubble.tsx +++ b/src/components/ChatBubble.tsx @@ -46,6 +46,7 @@ const ChatBox = styled.div<{isMyChat:boolean}>` background-color : ${props => (props.isMyChat ? "var(--green)" : "var(--gray-1)")}; max-width : 16.8125rem; width: fit-content; + word-break: break-all; border-radius: 1.5rem; margin : ${props => (props.isMyChat ? "0.625rem 1.25rem 0.625rem 0" : "0.625rem 0 0.625rem 1.25rem")}; `; From 7387a02860a60da0fec480db89e0e8424f5605fd Mon Sep 17 00:00:00 2001 From: leekyuho Date: Sat, 30 Sep 2023 23:46:00 +0900 Subject: [PATCH 21/55] =?UTF-8?q?style:=20prettier=20=EC=A0=81=EC=9A=A9=20?= =?UTF-8?q?=EC=BD=94=EB=93=9C=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/App.tsx | 16 +- src/components/ChatBubble.tsx | 100 +++++------ src/components/ChattingEmpty.tsx | 51 +++--- src/components/ChattingFull.tsx | 150 +++++++++-------- src/components/ChattingInput.tsx | 214 +++++++++++++----------- src/components/ChattingProfile.tsx | 115 +++++++------ src/components/HomeIndicator.tsx | 22 +-- src/components/molecules/LikeButton.tsx | 3 + src/custom.d.ts | 12 +- src/index.tsx | 13 +- src/pages/ChattingPage.tsx | 115 +++++++------ src/recoil/state.ts | 38 +++-- src/style/GlobalStyle.tsx | 4 +- src/style/font.tsx | 84 +++++----- 14 files changed, 490 insertions(+), 447 deletions(-) create mode 100644 src/components/molecules/LikeButton.tsx diff --git a/src/App.tsx b/src/App.tsx index 76e73f7..8622e31 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -1,18 +1,18 @@ import GlobalStyle from "./style/GlobalStyle"; -import ChattingPage from "./pages/ChattingPage" +import ChattingPage from "./pages/ChattingPage"; import StatusBar from "./components/StatusBar"; import HomeIndicator from "./components/HomeIndicator"; import "./style/color.css"; function App() { return ( <> - -
- - {/* 나중에 라우터 추가 or Router.js / 그리고 chatting room 여러개*/} - - -
+ +
+ + {/* 나중에 라우터 추가 or Router.js / 그리고 chatting room 여러개*/} + + +
); } diff --git a/src/components/ChatBubble.tsx b/src/components/ChatBubble.tsx index aa441ea..bbd4d15 100644 --- a/src/components/ChatBubble.tsx +++ b/src/components/ChatBubble.tsx @@ -1,58 +1,62 @@ import styled from "styled-components"; import "../style/color.css"; -import { Body2 ,Caption2} from "../style/font"; -interface ChatBubbleProps{ - isMyChat:boolean; - message :string; - chatDate : string; +import { Body2, Caption2 } from "../style/font"; +interface ChatBubbleProps { + isMyChat: boolean; + message: string; + chatDate: string; } -function ChatBubble(props: ChatBubbleProps){ - const date = new Date(props.chatDate); - const hours = date.getHours(); - const minutes = date.getMinutes(); - const isAM = hours < 12 ? true : false; - const hours12 = hours < 13 ? hours : hours-12; - return( - -
- {isAM ? "오전" : "오후"} {hours12}:{minutes<10 ? "0"+minutes : minutes} - - {props.message} - - -
-
- ); +function ChatBubble(props: ChatBubbleProps) { + const date = new Date(props.chatDate); + const hours = date.getHours(); + const minutes = date.getMinutes(); + const isAM = hours < 12 ? true : false; + const hours12 = hours < 13 ? hours : hours - 12; + return ( + +
+ + {isAM ? "오전" : "오후"} {hours12}: + {minutes < 10 ? "0" + minutes : minutes} + + + {props.message} + +
+
+ ); } //user 쪽 채팅과 상대방쪽 채팅 props로 구분 -const ChatBubbleContainer = styled.div<{isMyChat:boolean}>` +const ChatBubbleContainer = styled.div<{ isMyChat: boolean }>` + display: flex; + flex-direction: column; + align-items: ${(props) => (props.isMyChat ? "flex-end" : "flex-start")}; + .chatWrapper { display: flex; - flex-direction : column; - align-items: ${props => (props.isMyChat ? "flex-end" : "flex-start")}; - .chatWrapper{ - display:flex; - flex-direction : ${props => (props.isMyChat ? "row" : "row-reverse")}; - align-items: flex-end; - gap : 0.3125rem; - } - .writeTime{ - margin-bottom : 0.625rem; - } + flex-direction: ${(props) => (props.isMyChat ? "row" : "row-reverse")}; + align-items: flex-end; + gap: 0.3125rem; + } + .writeTime { + margin-bottom: 0.625rem; + } `; -const ChatBox = styled.div<{isMyChat:boolean}>` - /*display: inline-block;*/ - background-color : ${props => (props.isMyChat ? "var(--green)" : "var(--gray-1)")}; - max-width : 16.8125rem; - width: fit-content; - word-break: break-all; - border-radius: 1.5rem; - margin : ${props => (props.isMyChat ? "0.625rem 1.25rem 0.625rem 0" : "0.625rem 0 0.625rem 1.25rem")}; +const ChatBox = styled.div<{ isMyChat: boolean }>` + /*display: inline-block;*/ + background-color: ${(props) => + props.isMyChat ? "var(--green)" : "var(--gray-1)"}; + max-width: 16.8125rem; + width: fit-content; + word-break: break-all; + border-radius: 1.5rem; + margin: ${(props) => + props.isMyChat + ? "0.625rem 1.25rem 0.625rem 0" + : "0.625rem 0 0.625rem 1.25rem"}; `; -const ChatText = styled(Body2)<{isMyChat:boolean}>` - color : ${props => (props.isMyChat ? "var(--gray-1)" : "var(--gray-7)")}; - padding: 0.625rem 1.25rem; +const ChatText = styled(Body2)<{ isMyChat: boolean }>` + color: ${(props) => (props.isMyChat ? "var(--gray-1)" : "var(--gray-7)")}; + padding: 0.625rem 1.25rem; `; -export default ChatBubble; \ No newline at end of file +export default ChatBubble; diff --git a/src/components/ChattingEmpty.tsx b/src/components/ChattingEmpty.tsx index 0a76add..cc03acf 100644 --- a/src/components/ChattingEmpty.tsx +++ b/src/components/ChattingEmpty.tsx @@ -2,35 +2,34 @@ import { ReactComponent as Chat } from "../assets/icons/Chat.svg"; import styled from "styled-components"; import { Body2 } from "../style/font"; -function ChattingEmpty(){ - return( - - - - 상대방과 대화를
- 시작해보세요 -
-
- ); +function ChattingEmpty() { + return ( + + + + 상대방과 대화를 +
+ 시작해보세요 +
+
+ ); } const ChattingEmptyWrapper = styled.div` - width: 23.4375rem; - height: 37.69rem; - position : relative; - .defaultChat{ - position : absolute; - text-align: center; - left: 8.25rem; - top: 17.935rem; - } + width: 23.4375rem; + height: 37.69rem; + position: relative; + .defaultChat { + position: absolute; + text-align: center; + left: 8.25rem; + top: 17.935rem; + } `; const StyledChat = styled(Chat)` - position : absolute; - width: 1.9375rem; - height: 1.9375rem; - left : 10.75rem; - top :15.315rem; + position: absolute; + width: 1.9375rem; + height: 1.9375rem; + left: 10.75rem; + top: 15.315rem; `; export default ChattingEmpty; diff --git a/src/components/ChattingFull.tsx b/src/components/ChattingFull.tsx index b59a67c..8d98bb9 100644 --- a/src/components/ChattingFull.tsx +++ b/src/components/ChattingFull.tsx @@ -1,85 +1,87 @@ import styled from "styled-components"; import "../style/color.css"; -import {Caption1} from "../style/font"; -import { useEffect, useRef} from "react"; +import { Caption1 } from "../style/font"; +import { useEffect, useRef } from "react"; import ChatBubble from "./ChatBubble"; import { useRecoilValue } from "recoil"; -import { chatListByIdState, nowUserIdState} from "../recoil/state"; -interface ChattingProps{ - chatRoomId : number; - isUser:boolean; +import { chatListByIdState, nowUserIdState } from "../recoil/state"; +interface ChattingProps { + chatRoomId: number; + isUser: boolean; } -const dayList = ["일","월", "화","수", "목","금", "토"]; -function ChattingFull(props:ChattingProps){ - // //현재 채팅방 chat list - const chatList = useRecoilValue(chatListByIdState(props.chatRoomId)); - //현재 사용중인 user의 id - const nowUser = useRecoilValue(nowUserIdState); - //chat 추가 되면 scroll 밑으로 - const scrollRef = useRef(null); - //chat 추가되면 scroll 내리고, localstorage 저장 - useEffect(()=>{ - if(scrollRef.current){ - scrollRef.current.scrollTop = scrollRef.current.scrollHeight; - } - localStorage.setItem("chat"+String(props.chatRoomId),JSON.stringify(chatList)); - },[chatList]); - return( - - { - chatList.map((value, index)=>{ - //하루넘어가면 날짜 출력 - let dateChange:boolean = false; - const nowChatDate =new Date(chatList[index].date); - if(index === 0 ){ - dateChange=true; - } - else{ - const lastChatDate =new Date(chatList[index-1].date); - if(lastChatDate.getDate() !== nowChatDate.getDate()){ - dateChange=true; - } - else{ - dateChange=false; - } - } - return( - <> - - {dateChange? - {nowChatDate.getFullYear()}년 {nowChatDate.getMonth()+1}월 {nowChatDate.getDate()}일 ({dayList[nowChatDate.getDay()]}) - :null} - - - - ) - }) - } - +const dayList = ["일", "월", "화", "수", "목", "금", "토"]; +function ChattingFull(props: ChattingProps) { + // //현재 채팅방 chat list + const chatList = useRecoilValue(chatListByIdState(props.chatRoomId)); + //현재 사용중인 user의 id + const nowUser = useRecoilValue(nowUserIdState); + //chat 추가 되면 scroll 밑으로 + const scrollRef = useRef(null); + //chat 추가되면 scroll 내리고, localstorage 저장 + useEffect(() => { + if (scrollRef.current) { + scrollRef.current.scrollTop = scrollRef.current.scrollHeight; + } + localStorage.setItem( + "chat" + String(props.chatRoomId), + JSON.stringify(chatList) ); -}; + }, [chatList]); + return ( + + {chatList.map((value, index) => { + //하루넘어가면 날짜 출력 + let dateChange: boolean = false; + const nowChatDate = new Date(chatList[index].date); + if (index === 0) { + dateChange = true; + } else { + const lastChatDate = new Date(chatList[index - 1].date); + if (lastChatDate.getDate() !== nowChatDate.getDate()) { + dateChange = true; + } else { + dateChange = false; + } + } + return ( + <> + + {dateChange ? ( + + {nowChatDate.getFullYear()}년 {nowChatDate.getMonth() + 1}월{" "} + {nowChatDate.getDate()}일 ({dayList[nowChatDate.getDay()]}) + + ) : null} + + + + ); + })} + + ); +} const ChattingFullWrapper = styled.div` - display : flex; - flex-direction : column; - width: 23.4375rem; - height: 37.69rem; - overflow-y: auto; - scrollbar-width: none; /* Firefox */ - -ms-overflow-style: none; /* Internet Explorer/Edge */ - &::-webkit-scrollbar { - display: none; /* Chrome, Safari*/ - } + display: flex; + flex-direction: column; + width: 23.4375rem; + height: 37.69rem; + overflow-y: auto; + scrollbar-width: none; /* Firefox */ + -ms-overflow-style: none; /* Internet Explorer/Edge */ + &::-webkit-scrollbar { + display: none; /* Chrome, Safari*/ + } `; const DateCaption = styled.div` - display:flex; - justify-content : center; - align-items : center; - .dateBox{ - padding: 0.9375rem 0; - } + display: flex; + justify-content: center; + align-items: center; + .dateBox { + padding: 0.9375rem 0; + } `; export default ChattingFull; diff --git a/src/components/ChattingInput.tsx b/src/components/ChattingInput.tsx index 85672eb..aac39ac 100644 --- a/src/components/ChattingInput.tsx +++ b/src/components/ChattingInput.tsx @@ -3,121 +3,131 @@ import { ReactComponent as Plus } from "../assets/icons/Plus.svg"; import { ReactComponent as Send } from "../assets/icons/Send.svg"; import styled from "styled-components"; import { Body2 } from "../style/font"; -import { chatListByIdState, chatRoomListState, nowUserIdState } from "../recoil/state"; +import { + chatListByIdState, + chatRoomListState, + nowUserIdState, +} from "../recoil/state"; import { useRecoilState, useRecoilValue } from "recoil"; -interface ChattingInputProps{ - chatRoomId : number; +interface ChattingInputProps { + chatRoomId: number; } -interface ChatInfo{ - chatId:number; - userId:number; - message:string; - date:string; +interface ChatInfo { + chatId: number; + userId: number; + message: string; + date: string; } -function ChattingInput(props : ChattingInputProps){ - const [typeMessage, setTypeMessage] = useState("메세지를 입력하세요"); - const [input,setInput] = useState(""); - //현재 사용 user ID - const nowUser = useRecoilValue(nowUserIdState); - //모든 채팅방 list - const [chatRoomList,setChatRoomList] = useRecoilState(chatRoomListState); - const [chatList, setChatList] = useRecoilState(chatListByIdState(props.chatRoomId)); - //메세지창에 메세지 없을 때만 placeholder 출력 - const handleFocus = ()=>{ - setTypeMessage(""); +function ChattingInput(props: ChattingInputProps) { + const [typeMessage, setTypeMessage] = useState("메세지를 입력하세요"); + const [input, setInput] = useState(""); + //현재 사용 user ID + const nowUser = useRecoilValue(nowUserIdState); + //모든 채팅방 list + const [chatRoomList, setChatRoomList] = useRecoilState(chatRoomListState); + const [chatList, setChatList] = useRecoilState( + chatListByIdState(props.chatRoomId) + ); + //메세지창에 메세지 없을 때만 placeholder 출력 + const handleFocus = () => { + setTypeMessage(""); + }; + const handleBlur = () => { + if (input.trim() === "") { + setTypeMessage("메세지를 입력하세요"); } - const handleBlur = ()=>{ - if(input.trim() === ""){ - setTypeMessage("메세지를 입력하세요"); - } + }; + const handleSubmit = (e: any) => { + e.preventDefault(); + if (input.trim() !== "") { + const chatInstance: ChatInfo = { + chatId: chatList.length, //현재 chatlength+1 + userId: nowUser, + message: input, + date: String(new Date()), + }; + const copy = [...chatList]; + copy.push(chatInstance); + setChatList(copy); + setInput(""); } - const handleSubmit = (e:any)=>{ - e.preventDefault(); - if(input.trim() !== ""){ - const chatInstance:ChatInfo = { - chatId:chatList.length,//현재 chatlength+1 - userId:nowUser, - message: input, - date: String(new Date()) - } - const copy = [...chatList]; - copy.push(chatInstance); - setChatList(copy); - setInput(""); - } - } - const handleOnChange = (e:any)=>{ - setInput(e.target.value); - } - return( - - - - - - {typeMessage} - - - ); + }; + const handleOnChange = (e: any) => { + setInput(e.target.value); + }; + return ( + + + + + + + {typeMessage} + + + + ); } const ChattingInputWrapper = styled.div` - width: 23.4375rem; - height: 3.69rem; - position: relative; + width: 23.4375rem; + height: 3.69rem; + position: relative; + position: absolute; + top: 42rem; + .placeHolder { + pointer-events: none; /*input이 묻히기 때문에 제외*/ position: absolute; - top : 42rem; - .placeHolder{ - pointer-events: none; /*input이 묻히기 때문에 제외*/ - position : absolute; - top: 1.56rem; - left: 4.38rem; - } + top: 1.56rem; + left: 4.38rem; + } `; const StyledPlus = styled(Plus)` - position: absolute; - width: 1.25rem; - height: 1.25rem; - padding: 0.25rem; - left : 1rem; - top : 1.44rem; + position: absolute; + width: 1.25rem; + height: 1.25rem; + padding: 0.25rem; + left: 1rem; + top: 1.44rem; `; const StyledSend = styled(Send)` - position: absolute; - width: 1.1875rem; - height: 1.1875rem; - padding: 0.28125rem; - top:1.47rem; - right : 0.97rem; - cursor : pointer; - &:hover{ - color : #FFFFFF; - filter : brightness(300%); - } + position: absolute; + width: 1.1875rem; + height: 1.1875rem; + padding: 0.28125rem; + top: 1.47rem; + right: 0.97rem; + cursor: pointer; + &:hover { + color: #ffffff; + filter: brightness(300%); + } `; const StyledForm = styled.form` - .message-input{ - border : none; - position: absolute; - background-color : var(--gray-1); - top:0.94rem; - left:3.12rem; - width: 14.75rem; - height: 2.75rem; - border-radius: 6.25rem; - padding-left:1.25rem; - padding-right:1.25rem; - font-family : 'Pretendard-Regular';/*globalstyle 왜 적용안되는지?*/ - color: var(--gray-7); - font-size: 1.125rem; - font-style: normal; - font-weight: 500; - line-height: 1.5rem; /* 133.333% */ - letter-spacing: -0.0255rem; - } + .message-input { + border: none; + position: absolute; + background-color: var(--gray-1); + top: 0.94rem; + left: 3.12rem; + width: 14.75rem; + height: 2.75rem; + border-radius: 6.25rem; + padding-left: 1.25rem; + padding-right: 1.25rem; + font-family: "Pretendard-Regular"; /*globalstyle 왜 적용안되는지?*/ + color: var(--gray-7); + font-size: 1.125rem; + font-style: normal; + font-weight: 500; + line-height: 1.5rem; /* 133.333% */ + letter-spacing: -0.0255rem; + } `; export default ChattingInput; diff --git a/src/components/ChattingProfile.tsx b/src/components/ChattingProfile.tsx index 3409d25..6f89f77 100644 --- a/src/components/ChattingProfile.tsx +++ b/src/components/ChattingProfile.tsx @@ -7,71 +7,82 @@ import "../style/color.css"; import { usersState } from "../recoil/state"; import { useRecoilValue } from "recoil"; import styled from "styled-components"; -interface ChattingProfileProps{ - userId:number; +interface ChattingProfileProps { + userId: number; } -function ChattingProfile(props:ChattingProfileProps){ - const users = useRecoilValue(usersState); - return( - - - - - - - - {users[props.userId].name} - {users[props.userId].isWorking} - - {users[props.userId].company}/{users[props.userId].department}/{users[props.userId].rank} - - - ); +function ChattingProfile(props: ChattingProfileProps) { + const users = useRecoilValue(usersState); + return ( + + + + + + + + {users[props.userId].name} + + {users[props.userId].isWorking} + + + + {users[props.userId].company}/{users[props.userId].department}/ + {users[props.userId].rank} + + + + ); } const ChattingProfileWrapper = styled.div` - position:relative; - width: 22.1875rem; - height: 3rem; - padding: 0.5rem 0.625rem; + position: relative; + width: 22.1875rem; + height: 3rem; + padding: 0.5rem 0.625rem; `; const StyledBack = styled(Back)` - position:absolute; - width: 0.625rem; - height: 1.25rem; - padding: 0.25rem 0.625rem; - left: 0.625rem; - top: 1.19rem; + position: absolute; + width: 0.625rem; + height: 1.25rem; + padding: 0.25rem 0.625rem; + left: 0.625rem; + top: 1.19rem; `; const StyledFriends = styled(Friends)` - position:absolute; - width: 3rem; - height: 3rem; - left: 3.56rem; - top: 0.5rem; + position: absolute; + width: 3rem; + height: 3rem; + left: 3.56rem; + top: 0.5rem; `; const StyledCall = styled(Call)` - position:absolute; - width: 1.125rem; - height: 1.125rem; - padding: 0.3125rem; - right: 3.375rem; - top: 1.125rem; + position: absolute; + width: 1.125rem; + height: 1.125rem; + padding: 0.3125rem; + right: 3.375rem; + top: 1.125rem; `; const StyledMore = styled(More)` - position:absolute; - right: 0.625rem; - top: 1.125rem; + position: absolute; + right: 0.625rem; + top: 1.125rem; `; const UserInfoWrapper = styled.div` - position:absolute; - left:7.06rem; - padding-top:0.2rem; - display:flex; - flex-direction:column; - align-items: flex-start; /*왼쪽으로 정렬*/ + position: absolute; + left: 7.06rem; + padding-top: 0.2rem; + display: flex; + flex-direction: column; + align-items: flex-start; /*왼쪽으로 정렬*/ `; const UserWrapper = styled.div` - display:flex; - gap : 0.31rem; + display: flex; + gap: 0.31rem; `; -export default ChattingProfile; \ No newline at end of file +export default ChattingProfile; diff --git a/src/components/HomeIndicator.tsx b/src/components/HomeIndicator.tsx index d84f998..d9c973b 100644 --- a/src/components/HomeIndicator.tsx +++ b/src/components/HomeIndicator.tsx @@ -1,19 +1,19 @@ import { ReactComponent as HomeBar } from "../assets/iphone/HomeBar.svg"; import styled from "styled-components"; -function HomeIndicator(){ - return( - - - - ); +function HomeIndicator() { + return ( + + + + ); } const HomeBarWrapper = styled.div` - width: 23.4375rem; - height: 2.125rem; + width: 23.4375rem; + height: 2.125rem; `; const StyledHomeBar = styled(HomeBar)` - width: 8.375rem; - height: 0.3125rem; - padding: 1.3125rem 7.5rem 0.5rem 7.5625rem; + width: 8.375rem; + height: 0.3125rem; + padding: 1.3125rem 7.5rem 0.5rem 7.5625rem; `; export default HomeIndicator; diff --git a/src/components/molecules/LikeButton.tsx b/src/components/molecules/LikeButton.tsx new file mode 100644 index 0000000..610c68d --- /dev/null +++ b/src/components/molecules/LikeButton.tsx @@ -0,0 +1,3 @@ +export const LikeButton = () => { + return <>; +}; diff --git a/src/custom.d.ts b/src/custom.d.ts index 436ba68..a36e260 100644 --- a/src/custom.d.ts +++ b/src/custom.d.ts @@ -1,6 +1,6 @@ -declare module '*.svg' { - import React = require('react'); - export const ReactComponent: React.FC>; - const src: string; - export default src; -} \ No newline at end of file +declare module "*.svg" { + import React = require("react"); + export const ReactComponent: React.FC>; + const src: string; + export default src; +} diff --git a/src/index.tsx b/src/index.tsx index 2bcae0f..ace36dc 100644 --- a/src/index.tsx +++ b/src/index.tsx @@ -1,11 +1,10 @@ -import React from 'react'; -import ReactDOM from 'react-dom/client'; -import { RecoilRoot } from 'recoil'; -import App from './App'; +import React from "react"; +import ReactDOM from "react-dom/client"; +import { RecoilRoot } from "recoil"; +import App from "./App"; - -const rootElement = document.getElementById('root'); -if (!rootElement) throw new Error('Failed to find the root element'); +const rootElement = document.getElementById("root"); +if (!rootElement) throw new Error("Failed to find the root element"); const root = ReactDOM.createRoot(rootElement); root.render( diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index 5c5c855..2290b10 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -3,59 +3,72 @@ import ChattingFull from "../components/ChattingFull"; import ChattingInput from "../components/ChattingInput"; import ChattingProfile from "../components/ChattingProfile"; import styled from "styled-components"; -import {useState, useEffect} from "react"; +import { useState, useEffect } from "react"; import { useRecoilState, useRecoilValue } from "recoil"; -import { chatListByIdState, chatRoomListState, nowUserIdState } from "../recoil/state"; -interface ChattingPageProps{ - chatRoomId:number; +import { + chatListByIdState, + chatRoomListState, + nowUserIdState, +} from "../recoil/state"; +interface ChattingPageProps { + chatRoomId: number; } -function ChattingPage(props:ChattingPageProps){ - //chatting 전체 리스트 - const chatRoomList = useRecoilValue(chatRoomListState); - //해당 채팅방 chatting list - const [chatListById, setChatListById] = useRecoilState(chatListByIdState(props.chatRoomId)); - //채팅방 사용자 2명 - const roomUsers = chatRoomList[props.chatRoomId].userList; - //user switch 상태 - const [switchUser,setSwitchUser] = useState(0); - //list 길이 체크해서 빈 채팅방 or 채팅있는 채팅방 - const chatList = chatRoomList[props.chatRoomId].chatList; - //현재 사용중인 user의 id(login user 아님) - const [nowUserId, setNowUserId] = useRecoilState(nowUserIdState); - //localstorage에 없으면 json 파일 저장, 있으면 chatList 불러옴 - const initializeChat = localStorage.getItem("chat"+String(props.chatRoomId)); - useEffect(()=>{ - if(initializeChat===null){ - localStorage.setItem("chat"+String(props.chatRoomId),JSON.stringify(chatListById)); - } - else{ - setChatListById(JSON.parse(initializeChat)); - } - },[]) - - //0,1로 switch 하면서 채팅방 userlist의 0,1인덱스의 user로 전환 - const handleUserSwitch = ()=>{ - if(switchUser === 0){ - setSwitchUser(1); - } - else if(switchUser === 1){ - setSwitchUser(0); - } - setNowUserId(roomUsers[switchUser]); - }; - return( -
-
- -
- - {chatList.length !== 0 ? : } - -
- ); +function ChattingPage(props: ChattingPageProps) { + //chatting 전체 리스트 + const chatRoomList = useRecoilValue(chatRoomListState); + //해당 채팅방 chatting list + const [chatListById, setChatListById] = useRecoilState( + chatListByIdState(props.chatRoomId) + ); + //채팅방 사용자 2명 + const roomUsers = chatRoomList[props.chatRoomId].userList; + //user switch 상태 + const [switchUser, setSwitchUser] = useState(0); + //list 길이 체크해서 빈 채팅방 or 채팅있는 채팅방 + const chatList = chatRoomList[props.chatRoomId].chatList; + //현재 사용중인 user의 id(login user 아님) + const [nowUserId, setNowUserId] = useRecoilState(nowUserIdState); + //localstorage에 없으면 json 파일 저장, 있으면 chatList 불러옴 + const initializeChat = localStorage.getItem( + "chat" + String(props.chatRoomId) + ); + useEffect(() => { + if (initializeChat === null) { + localStorage.setItem( + "chat" + String(props.chatRoomId), + JSON.stringify(chatListById) + ); + } else { + setChatListById(JSON.parse(initializeChat)); + } + }, []); + + //0,1로 switch 하면서 채팅방 userlist의 0,1인덱스의 user로 전환 + const handleUserSwitch = () => { + if (switchUser === 0) { + setSwitchUser(1); + } else if (switchUser === 1) { + setSwitchUser(0); + } + setNowUserId(roomUsers[switchUser]); + }; + return ( +
+
+ +
+ + {chatList.length !== 0 ? ( + + ) : ( + + )} + +
+ ); } const Divider = styled.hr` - border: 0.0625rem solid var(--gray-3); - margin : 0; + border: 0.0625rem solid var(--gray-3); + margin: 0; `; -export default ChattingPage; \ No newline at end of file +export default ChattingPage; diff --git a/src/recoil/state.ts b/src/recoil/state.ts index bd14cf2..38a5ae9 100644 --- a/src/recoil/state.ts +++ b/src/recoil/state.ts @@ -1,36 +1,38 @@ -import {atom, atomFamily, selector, selectorFamily} from 'recoil'; -import userData from '../data/userData.json'; -import chatData from '../data/chatData.json'; +import { atom, atomFamily, selector, selectorFamily } from "recoil"; +import userData from "../data/userData.json"; +import chatData from "../data/chatData.json"; //현재 login한 user,나머지 user list, chattingRoom list export const loginUserState = atom({ - key : 'loginUserState', - default: userData.users[0], + key: "loginUserState", + default: userData.users[0], }); //초기 사용 user는 0번 고정 export const nowUserIdState = atom({ - key : 'nowUserIdState', - default : userData.users[0].userId, + key: "nowUserIdState", + default: userData.users[0].userId, }); //user제외 나머지 friends export const friendsState = atom({ - key : 'friendsState', - default : userData.users.slice(1), + key: "friendsState", + default: userData.users.slice(1), }); //총 user데이터 export const usersState = atom({ - key : 'usersState', - default : userData.users, + key: "usersState", + default: userData.users, }); export const chatRoomListState = atom({ - key : 'chatRoomListState', - default : chatData.chattings, + key: "chatRoomListState", + default: chatData.chattings, }); export const chatListByIdState = atomFamily({ - key: 'chatListByIdState', - default: (chatRoomId: number) => { - const chatRoom = chatData.chattings.find(room => room.chatRoomId === chatRoomId); - return chatRoom ? chatRoom.chatList : []; - }, + key: "chatListByIdState", + default: (chatRoomId: number) => { + const chatRoom = chatData.chattings.find( + (room) => room.chatRoomId === chatRoomId + ); + return chatRoom ? chatRoom.chatList : []; + }, }); diff --git a/src/style/GlobalStyle.tsx b/src/style/GlobalStyle.tsx index 85f26f1..99641ea 100644 --- a/src/style/GlobalStyle.tsx +++ b/src/style/GlobalStyle.tsx @@ -1,4 +1,4 @@ -import {createGlobalStyle} from "styled-components"; +import { createGlobalStyle } from "styled-components"; import reset from "styled-reset"; import "./color.css"; const GlobalStyle = createGlobalStyle` @@ -32,4 +32,4 @@ const GlobalStyle = createGlobalStyle` } `; -export default GlobalStyle; \ No newline at end of file +export default GlobalStyle; diff --git a/src/style/font.tsx b/src/style/font.tsx index 8edc5ad..d9900fd 100644 --- a/src/style/font.tsx +++ b/src/style/font.tsx @@ -1,48 +1,48 @@ -import styled from 'styled-components'; +import styled from "styled-components"; import "../style/color.css"; -export const Heading1 =styled.div` - color: ${props => props.color || 'var(--white)'}; - font-size: 1.5rem; - font-style: normal; - font-weight: 700; - line-height: 1.375rem; /* 91.667% */ - letter-spacing: -0.0255rem; +export const Heading1 = styled.div` + color: ${(props) => props.color || "var(--white)"}; + font-size: 1.5rem; + font-style: normal; + font-weight: 700; + line-height: 1.375rem; /* 91.667% */ + letter-spacing: -0.0255rem; `; -export const Heading2 =styled.div` - color: ${props => props.color || 'var(--white)'}; - font-size: 1.375rem; - font-style: normal; - font-weight: 700; - line-height: 1.375rem; /* 100% */ - letter-spacing: -0.0255rem; +export const Heading2 = styled.div` + color: ${(props) => props.color || "var(--white)"}; + font-size: 1.375rem; + font-style: normal; + font-weight: 700; + line-height: 1.375rem; /* 100% */ + letter-spacing: -0.0255rem; `; -export const Body1 =styled.div` - color: ${props => props.color || 'var(--white)'}; - font-size: 1.125rem; - font-style: normal; - font-weight: 700; - line-height: 1.375rem; /* 122.222% */ - letter-spacing: -0.0255rem; +export const Body1 = styled.div` + color: ${(props) => props.color || "var(--white)"}; + font-size: 1.125rem; + font-style: normal; + font-weight: 700; + line-height: 1.375rem; /* 122.222% */ + letter-spacing: -0.0255rem; `; -export const Body2 =styled.div` - color: ${props => props.color || 'var(--white)'}; - font-size: 1.125rem; - font-style: normal; - font-weight: 500; - line-height: 1.5rem; /* 133.333% */ - letter-spacing: -0.0255rem; +export const Body2 = styled.div` + color: ${(props) => props.color || "var(--white)"}; + font-size: 1.125rem; + font-style: normal; + font-weight: 500; + line-height: 1.5rem; /* 133.333% */ + letter-spacing: -0.0255rem; `; -export const Caption1 =styled.div` - color: ${props => props.color || 'var(--white)'}; - font-size: 0.875rem; - font-style: normal; - font-weight: 500; - line-height: 1.375rem; /* 157.143% */ +export const Caption1 = styled.div` + color: ${(props) => props.color || "var(--white)"}; + font-size: 0.875rem; + font-style: normal; + font-weight: 500; + line-height: 1.375rem; /* 157.143% */ +`; +export const Caption2 = styled.div` + color: ${(props) => props.color || "var(--white)"}; + font-size: 0.875rem; + font-style: normal; + font-weight: 300; + line-height: 1.375rem; /* 157.143% */ `; -export const Caption2 =styled.div` - color: ${props => props.color || 'var(--white)'}; - font-size: 0.875rem; - font-style: normal; - font-weight: 300; - line-height: 1.375rem; /* 157.143% */ -`; \ No newline at end of file From 2f37bdd726d2170787a56634786cfa3e3f5bed2c Mon Sep 17 00:00:00 2001 From: leekyuho Date: Sun, 1 Oct 2023 00:43:53 +0900 Subject: [PATCH 22/55] =?UTF-8?q?refactor:=20chatting=20full=20empty=20?= =?UTF-8?q?=EB=B3=91=ED=95=A9?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/ChattingEmpty.tsx | 35 --------- src/components/ChattingFull.tsx | 87 ---------------------- src/components/ChattingRoom.tsx | 121 +++++++++++++++++++++++++++++++ src/pages/ChattingPage.tsx | 10 +-- 4 files changed, 124 insertions(+), 129 deletions(-) delete mode 100644 src/components/ChattingEmpty.tsx delete mode 100644 src/components/ChattingFull.tsx create mode 100644 src/components/ChattingRoom.tsx diff --git a/src/components/ChattingEmpty.tsx b/src/components/ChattingEmpty.tsx deleted file mode 100644 index cc03acf..0000000 --- a/src/components/ChattingEmpty.tsx +++ /dev/null @@ -1,35 +0,0 @@ -import { ReactComponent as Chat } from "../assets/icons/Chat.svg"; -import styled from "styled-components"; -import { Body2 } from "../style/font"; - -function ChattingEmpty() { - return ( - - - - 상대방과 대화를 -
- 시작해보세요 -
-
- ); -} -const ChattingEmptyWrapper = styled.div` - width: 23.4375rem; - height: 37.69rem; - position: relative; - .defaultChat { - position: absolute; - text-align: center; - left: 8.25rem; - top: 17.935rem; - } -`; -const StyledChat = styled(Chat)` - position: absolute; - width: 1.9375rem; - height: 1.9375rem; - left: 10.75rem; - top: 15.315rem; -`; -export default ChattingEmpty; diff --git a/src/components/ChattingFull.tsx b/src/components/ChattingFull.tsx deleted file mode 100644 index 8d98bb9..0000000 --- a/src/components/ChattingFull.tsx +++ /dev/null @@ -1,87 +0,0 @@ -import styled from "styled-components"; -import "../style/color.css"; -import { Caption1 } from "../style/font"; -import { useEffect, useRef } from "react"; -import ChatBubble from "./ChatBubble"; -import { useRecoilValue } from "recoil"; -import { chatListByIdState, nowUserIdState } from "../recoil/state"; -interface ChattingProps { - chatRoomId: number; - isUser: boolean; -} -const dayList = ["일", "월", "화", "수", "목", "금", "토"]; -function ChattingFull(props: ChattingProps) { - // //현재 채팅방 chat list - const chatList = useRecoilValue(chatListByIdState(props.chatRoomId)); - //현재 사용중인 user의 id - const nowUser = useRecoilValue(nowUserIdState); - //chat 추가 되면 scroll 밑으로 - const scrollRef = useRef(null); - //chat 추가되면 scroll 내리고, localstorage 저장 - useEffect(() => { - if (scrollRef.current) { - scrollRef.current.scrollTop = scrollRef.current.scrollHeight; - } - localStorage.setItem( - "chat" + String(props.chatRoomId), - JSON.stringify(chatList) - ); - }, [chatList]); - return ( - - {chatList.map((value, index) => { - //하루넘어가면 날짜 출력 - let dateChange: boolean = false; - const nowChatDate = new Date(chatList[index].date); - if (index === 0) { - dateChange = true; - } else { - const lastChatDate = new Date(chatList[index - 1].date); - if (lastChatDate.getDate() !== nowChatDate.getDate()) { - dateChange = true; - } else { - dateChange = false; - } - } - return ( - <> - - {dateChange ? ( - - {nowChatDate.getFullYear()}년 {nowChatDate.getMonth() + 1}월{" "} - {nowChatDate.getDate()}일 ({dayList[nowChatDate.getDay()]}) - - ) : null} - - - - ); - })} - - ); -} -const ChattingFullWrapper = styled.div` - display: flex; - flex-direction: column; - width: 23.4375rem; - height: 37.69rem; - overflow-y: auto; - scrollbar-width: none; /* Firefox */ - -ms-overflow-style: none; /* Internet Explorer/Edge */ - &::-webkit-scrollbar { - display: none; /* Chrome, Safari*/ - } -`; -const DateCaption = styled.div` - display: flex; - justify-content: center; - align-items: center; - .dateBox { - padding: 0.9375rem 0; - } -`; -export default ChattingFull; diff --git a/src/components/ChattingRoom.tsx b/src/components/ChattingRoom.tsx new file mode 100644 index 0000000..d124f90 --- /dev/null +++ b/src/components/ChattingRoom.tsx @@ -0,0 +1,121 @@ +import styled from "styled-components"; +import "../style/color.css"; +import { ReactComponent as Chat } from "../assets/icons/Chat.svg"; +import { Caption1, Body2 } from "../style/font"; +import { useEffect, useRef } from "react"; +import ChatBubble from "./ChatBubble"; +import { useRecoilValue } from "recoil"; +import { chatListByIdState, nowUserIdState } from "../recoil/state"; +interface ChattingProps { + chatRoomId: number; + isUser: boolean; +} +const dayList = ["일", "월", "화", "수", "목", "금", "토"]; +function ChattingRoom(props: ChattingProps) { + // //현재 채팅방 chat list + const chatList = useRecoilValue(chatListByIdState(props.chatRoomId)); + //현재 사용중인 user의 id + const nowUser = useRecoilValue(nowUserIdState); + //chat 추가 되면 scroll 밑으로 + const scrollRef = useRef(null); + //chat 추가되면 scroll 내리고, localstorage 저장 + useEffect(() => { + if (scrollRef.current) { + scrollRef.current.scrollTop = scrollRef.current.scrollHeight; + } + localStorage.setItem( + "chat" + String(props.chatRoomId), + JSON.stringify(chatList) + ); + console.log(chatList); + }, [chatList]); + if (chatList.length === 0) { + //chatting 없을 시 empty 출력 + return ( + + + + 상대방과 대화를 +
+ 시작해보세요 +
+
+ ); + } else { + return ( + + {chatList.map((value, index) => { + //하루넘어가면 날짜 출력 + let dateChange: boolean = false; + const nowChatDate = new Date(chatList[index].date); + if (index === 0) { + dateChange = true; + } else { + const lastChatDate = new Date(chatList[index - 1].date); + if (lastChatDate.getDate() !== nowChatDate.getDate()) { + dateChange = true; + } else { + dateChange = false; + } + } + return ( + <> + + {dateChange ? ( + + {nowChatDate.getFullYear()}년 {nowChatDate.getMonth() + 1}월{" "} + {nowChatDate.getDate()}일 ({dayList[nowChatDate.getDay()]}) + + ) : null} + + + + ); + })} + + ); + } +} +const ChattingEmptyWrapper = styled.div` + width: 23.4375rem; + height: 37.69rem; + position: relative; + .defaultChat { + position: absolute; + text-align: center; + left: 8.25rem; + top: 17.935rem; + } +`; +const StyledChat = styled(Chat)` + position: absolute; + width: 1.9375rem; + height: 1.9375rem; + left: 10.75rem; + top: 15.315rem; +`; +const ChattingFullWrapper = styled.div` + display: flex; + flex-direction: column; + width: 23.4375rem; + height: 37.69rem; + overflow-y: auto; + scrollbar-width: none; /* Firefox */ + -ms-overflow-style: none; /* Internet Explorer/Edge */ + &::-webkit-scrollbar { + display: none; /* Chrome, Safari*/ + } +`; +const DateCaption = styled.div` + display: flex; + justify-content: center; + align-items: center; + .dateBox { + padding: 0.9375rem 0; + } +`; +export default ChattingRoom; diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index 2290b10..dda48d4 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -1,5 +1,4 @@ -import ChattingEmpty from "../components/ChattingEmpty"; -import ChattingFull from "../components/ChattingFull"; +import ChattingRoom from "../components/ChattingRoom"; import ChattingInput from "../components/ChattingInput"; import ChattingProfile from "../components/ChattingProfile"; import styled from "styled-components"; @@ -58,11 +57,8 @@ function ChattingPage(props: ChattingPageProps) { - {chatList.length !== 0 ? ( - - ) : ( - - )} + {/* props.chatRoomId */} + ); From d3bde64abb581f999a9a389395e4ad7cd10f6abe Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 4 Oct 2023 11:22:47 +0900 Subject: [PATCH 23/55] =?UTF-8?q?feat:=20route=20=EC=B4=88=EA=B8=B0=20?= =?UTF-8?q?=EC=84=B8=ED=8C=85?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- package-lock.json | 39 +++++++++++++++++++++++++++++++++++++++ package.json | 1 + src/App.tsx | 9 +++++++-- src/index.tsx | 9 ++++++--- src/pages/Home.tsx | 18 ++++++++++++++++++ 5 files changed, 71 insertions(+), 5 deletions(-) create mode 100644 src/pages/Home.tsx diff --git a/package-lock.json b/package-lock.json index 9487c0a..07f339b 100644 --- a/package-lock.json +++ b/package-lock.json @@ -17,6 +17,7 @@ "@types/react-dom": "^18.2.8", "react": "^18.2.0", "react-dom": "^18.2.0", + "react-router-dom": "^6.16.0", "react-scripts": "5.0.1", "recoil": "^0.7.7", "styled-components": "^6.0.8", @@ -3585,6 +3586,14 @@ } } }, + "node_modules/@remix-run/router": { + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/@remix-run/router/-/router-1.9.0.tgz", + "integrity": "sha512-bV63itrKBC0zdT27qYm6SDZHlkXwFL1xMBuhkn+X7l0+IIhNaH5wuuvZKp6eKhCD4KFhujhfhCT1YxXW6esUIA==", + "engines": { + "node": ">=14.0.0" + } + }, "node_modules/@rollup/plugin-babel": { "version": "5.3.1", "resolved": "https://registry.npmjs.org/@rollup/plugin-babel/-/plugin-babel-5.3.1.tgz", @@ -14381,6 +14390,36 @@ "node": ">=0.10.0" } }, + "node_modules/react-router": { + "version": "6.16.0", + "resolved": "https://registry.npmjs.org/react-router/-/react-router-6.16.0.tgz", + "integrity": "sha512-VT4Mmc4jj5YyjpOi5jOf0I+TYzGpvzERy4ckNSvSh2RArv8LLoCxlsZ2D+tc7zgjxcY34oTz2hZaeX5RVprKqA==", + "dependencies": { + "@remix-run/router": "1.9.0" + }, + "engines": { + "node": ">=14.0.0" + }, + "peerDependencies": { + "react": ">=16.8" + } + }, + "node_modules/react-router-dom": { + "version": "6.16.0", + "resolved": "https://registry.npmjs.org/react-router-dom/-/react-router-dom-6.16.0.tgz", + "integrity": "sha512-aTfBLv3mk/gaKLxgRDUPbPw+s4Y/O+ma3rEN1u8EgEpLpPe6gNjIsWt9rxushMHHMb7mSwxRGdGlGdvmFsyPIg==", + "dependencies": { + "@remix-run/router": "1.9.0", + "react-router": "6.16.0" + }, + "engines": { + "node": ">=14.0.0" + }, + "peerDependencies": { + "react": ">=16.8", + "react-dom": ">=16.8" + } + }, "node_modules/react-scripts": { "version": "5.0.1", "resolved": "https://registry.npmjs.org/react-scripts/-/react-scripts-5.0.1.tgz", diff --git a/package.json b/package.json index 0009714..ab12d2e 100644 --- a/package.json +++ b/package.json @@ -12,6 +12,7 @@ "@types/react-dom": "^18.2.8", "react": "^18.2.0", "react-dom": "^18.2.0", + "react-router-dom": "^6.16.0", "react-scripts": "5.0.1", "recoil": "^0.7.7", "styled-components": "^6.0.8", diff --git a/src/App.tsx b/src/App.tsx index 8622e31..8a507c3 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -2,6 +2,8 @@ import GlobalStyle from "./style/GlobalStyle"; import ChattingPage from "./pages/ChattingPage"; import StatusBar from "./components/StatusBar"; import HomeIndicator from "./components/HomeIndicator"; +import { Routes, Route } from "react-router-dom"; +import Home from "./pages/Home"; import "./style/color.css"; function App() { return ( @@ -9,8 +11,11 @@ function App() {
- {/* 나중에 라우터 추가 or Router.js / 그리고 chatting room 여러개*/} - + + {/* 나중에 라우터 추가 or Router.js / 그리고 chatting room 여러개*/} + } /> + } /> +
diff --git a/src/index.tsx b/src/index.tsx index ace36dc..0391131 100644 --- a/src/index.tsx +++ b/src/index.tsx @@ -1,6 +1,7 @@ import React from "react"; import ReactDOM from "react-dom/client"; import { RecoilRoot } from "recoil"; +import { BrowserRouter } from "react-router-dom"; import App from "./App"; const rootElement = document.getElementById("root"); @@ -8,8 +9,10 @@ if (!rootElement) throw new Error("Failed to find the root element"); const root = ReactDOM.createRoot(rootElement); root.render( - - - + + + + + ); diff --git a/src/pages/Home.tsx b/src/pages/Home.tsx new file mode 100644 index 0000000..59212d6 --- /dev/null +++ b/src/pages/Home.tsx @@ -0,0 +1,18 @@ +import { useNavigate } from "react-router-dom"; +const Home = () => { + const movePage = useNavigate(); + return ( +
+ Home + +
+ ); +}; + +export default Home; From eb325cad4634878ed900af20b6d27b971e50a2e0 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 4 Oct 2023 17:19:21 +0900 Subject: [PATCH 24/55] =?UTF-8?q?feat:=20page=20=EB=B6=84=EB=A6=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 82 ++++++++++++-------------- src/App.tsx | 11 ++-- src/components/ChatBubble.tsx | 9 +-- src/components/ChattingProfile.tsx | 12 +++- src/components/ChattingRoom.tsx | 25 +++----- src/data/chatData.json | 88 ++++++++++++++-------------- src/pages/ChatPage.tsx | 28 +++++++++ src/pages/ChattingPage.tsx | 4 +- src/pages/{Home.tsx => HomePage.tsx} | 11 +++- src/pages/ProfilePage.tsx | 11 ++++ src/utils/dateForm.ts | 30 ++++++++++ 11 files changed, 190 insertions(+), 121 deletions(-) create mode 100644 src/pages/ChatPage.tsx rename src/pages/{Home.tsx => HomePage.tsx} (59%) create mode 100644 src/pages/ProfilePage.tsx create mode 100644 src/utils/dateForm.ts diff --git a/README.md b/README.md index 6ab8e98..d92fbbe 100644 --- a/README.md +++ b/README.md @@ -1,66 +1,56 @@ -# 서론 +# 4주차 미션: React-Messenger 💌 -안녕하세요 🙌🏻 18기 프론트 운영진 김문기입니다. 이번 미션에서는 드디어 투두리스트에서 벗어나 새로운 프로젝트인 **messenger** 만들기를 진행합니다. +## 서론 -이번주는 특별히 **디자이너와의 협업**으로 진행되는 미션입니다. 디자이너분께서 열심히 리디자인 한 메신저 프로젝트를 여러분들께서 구현해주시면 됩니다. +안녕하세요 🙌🏻 프론트엔드 운영진 김문기입니다. -동시에, 이번주부터는 새로 **TypeScript**를 적용해보려고 합니다. +다들 저번주 미션은 어떠셨나요? 이번주에는 저번 과제를 확장하여 보다 더 완성도 높은 메신저 서비스를 만들어 봅시다. -프로젝트의 규모가 커지게 될 수록, 컴포넌트가 가지는 props의 종류 또한 다양해지게 됩니다. 무지성 코딩을 하다보면 가끔 이 props의 구성과 이름, 어떤 타입이 들어가야 하는지 헷갈리기 마련이죠. 보통 그럴 때 다시 컴포넌트 정의 부분으로 돌아가 props의 구성을 보고 오곤 합니다. +이번주 과제의 목표는 React에서 **Routing**을 구현하는 방법과 **상태를 관리**하는 방법에 대해 익숙해지는 것입니다. 해당 부분을 잘 고려하시면서 미션을 수행해 주세요! -하지만 이럴 때, typescript를 적용한다면 컴포넌트의 구성과 그 이름, 심지어 타입까지 한번에 자동완성으로 편리하게 관리할 수 있고, 생산성이 증대되겠죠. +또한, 이번주에는 디자이너 측에서 QA를 전달해주실 예정입니다. 전달받은 QA에 대해 디자이너와 소통 후, 이를 고쳐보시는 과정도 수행해주세요! -또한, **React Hooks**에 조금 더 익숙해지는 것을 목표로 합니다. 여러 Hook들이 있지만 그 중에서도 `useState`, `useEffect`, `useRef`를 중점적으로 사용해 보는 미션인데요, React를 사용하면서 굉장히 자주 쓰이는 Hook들이기 때문에 이 부분을 집중적으로 공부해 보아요! +그럼 이번주도 파이팅입니다 😤 -그럼 이번 미션도 파이팅입니다!!🎉 +## 미션 -# 미션 +### 미션 목표 -## Key Questions - -- JavaScript를 사용할때에 비해 TypeScript를 사용할 때의 장점은 무엇인가요? -- 디자이너로부터 전달받은 피그마 링크 혹은, 피그마 캡처본 -- 컴포넌트를 분리한 기준은 무엇인가요? -- 디자인 시스템을 적용하면서 느낀 점은 무엇인가요? -- 디자이너와 소통하며 느낀점은 무엇인가요? +- SPA의 개념을 이해하고, 그에 따른 라우팅을 구현합니다. +- 디자이너로부터 QA를 전달받고, 이에 대한 대응합니다. +- React에서 사용하는 상태 관리 방법에 익숙해집니다. +- UI 컴포넌트의 중복을 줄여 봅니다. +- 코드를 확장/재사용/리팩토링하는 방법을 이해합니다. -## 미션 목표 +### 기한 -- TypeScript를 사용해봅시다. -- useState로 컴포넌트의 상태를 관리합니다. -- useEffect와 useRef의 사용법을 이해합니다. -- styled-components를 통한 CSS-in-JS 및 CSS Preprocessor의 사용법에 익숙해집니다. +2023년 11월 3일 금요일 (기한 엄수!) -## 기한 +### 필수 요건 -2023년 9월 29일 금요일 +- 친구 목록 페이지, 채팅 목록 페이지, 설정 페이지 세 부분으로 구성합니다. +- 채팅 목록을 누르면 3주차 미션에서 구현했던 채팅방으로 이동합니다. +- 검색 기능을 추가하여 검색한 내용과 일치하는 이름을 가진 사용자만 화면에 표시합니다. +- (선택) 각자 메신저에 추가하고 싶거나, 구현하고 싶은 기능 마음껏 구현합니다. ✨ +- Custom hooks를 통해 중복되는 로직을 줄입니다. -## 필수 구현 기능 +### 선택 사항 -- 피그마를 보고 [결과화면](https://3th-fb-messenger.netlify.app)과 같이 구현합니다. -- 디자인 시스템을 구축합니다. -- 채팅방 상단의 프로필을 클릭하면 사용자를 변경할 수 있습니다. -- 메세지를 보내면 채팅방 하단으로 스크롤을 이동시킵니다. -- 메세지에 유저 정보(프로필 사진, 이름)를 표시합니다. -- user와 message 데이터를 json 파일에 저장합니다. -- UI는 **반응형을 제외**하고 피그마파일을 따라서 진행합니다. +- Recoil, Redux 등의 상태 관리 라이브러리를 적용해 봅니다. +- Base UI component system을 통해 UI 컴포넌트의 코드 재사용성을 높입니다. -### 추가 구현 기능 - -- 더블 클릭 하면 감정표현을 추가합니다. -- 그 외 추가하고 싶은 기능이 있다면 마음껏 추가해 주세요! +## Key Questions -참고로 이번 과제는 다음주까지 이어지는 과제이므로 **확장성**을 충분히 고려해 주세요. 참고로 **4주차 과제에서는 유저 및 기능 추가와 Routing을** 진행합니다. 이를 위해 [recoil](https://recoiljs.org/ko/)이나 [redux](https://ko.redux.js.org/introduction/getting-started/)를 이용한 상태관리를 미리 해보시는 것을 추천합니다!! 모두 공식문서 많이 읽어보시고 자신만의 상태관리 조합도 찾아보면 재밌을 거에요 XD +- 디자이너로부터 받은 QA 목록 +- QA 반영한 커밋(or 브랜치) 링크 (커밋 분리 필수!!!) +- Routing +- SPA +- 상태관리 ## 링크 및 참고자료 -- [React docs - Hook](https://ko.reactjs.org/docs/hooks-intro.html) -- [React의 Hooks 완벽 정복하기](https://velog.io/@velopert/react-hooks#1-usestate) -- [useEffect 완벽 가이드](https://overreacted.io/ko/a-complete-guide-to-useeffect/) -- [코딩 컨벤션](https://ui.toast.com/fe-guide/ko_CODING-CONVENTION) -- [타입스크립트 핸드북](https://joshua1988.github.io/ts/intro.html) -- [리액트 프로젝트에서 타입스크립트 사용하기 (시리즈)](https://velog.io/@velopert/series/react-with-typescript) -- [디자인 시스템 구축기](https://yozm.wishket.com/magazine/detail/1830/) -- [[영상] : 컴포넌트에 대한 이해](https://www.youtube.com/watch?v=21eiJc90ggo) -- [Styled Component로 디자인 시스템 구축하기](https://zaat.dev/blog/building-a-design-system-in-react-with-styled-components/) -- [ts 절대경로 설정하기](https://tesseractjh.tistory.com/232) +- [React Router v6 튜토리얼](https://velog.io/@velopert/react-router-v6-tutorial) +- [(선택) react-router v6에서는 어떤 것들이 변했을까?](https://blog.woolta.com/categories/1/posts/211) +- [React 상태 관리 가이드](https://www.stevy.dev/react-state-management-guide/) +- [Flux 패턴이란?](https://velog.io/@huurray/React%EC%9D%98-%ED%83%84%EC%83%9D%EA%B3%BC-Flux-%ED%8C%A8%ED%84%B4%EC%97%90-%EB%8C%80%ED%95%98%EC%97%AC) +- [useReducer](https://www.daleseo.com/react-hooks-use-reducer/) diff --git a/src/App.tsx b/src/App.tsx index 8a507c3..1195380 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -3,7 +3,9 @@ import ChattingPage from "./pages/ChattingPage"; import StatusBar from "./components/StatusBar"; import HomeIndicator from "./components/HomeIndicator"; import { Routes, Route } from "react-router-dom"; -import Home from "./pages/Home"; +import HomePage from "./pages/HomePage"; +import ChatPage from "./pages/ChatPage"; +import ProfilePage from "./pages/ProfilePage"; import "./style/color.css"; function App() { return ( @@ -12,9 +14,10 @@ function App() {
- {/* 나중에 라우터 추가 or Router.js / 그리고 chatting room 여러개*/} - } /> - } /> + } /> + } /> + } /> + } />
diff --git a/src/components/ChatBubble.tsx b/src/components/ChatBubble.tsx index bbd4d15..f225d01 100644 --- a/src/components/ChatBubble.tsx +++ b/src/components/ChatBubble.tsx @@ -1,23 +1,18 @@ import styled from "styled-components"; import "../style/color.css"; import { Body2, Caption2 } from "../style/font"; +import { chatBubbleTime } from "../utils/dateForm"; interface ChatBubbleProps { isMyChat: boolean; message: string; chatDate: string; } function ChatBubble(props: ChatBubbleProps) { - const date = new Date(props.chatDate); - const hours = date.getHours(); - const minutes = date.getMinutes(); - const isAM = hours < 12 ? true : false; - const hours12 = hours < 13 ? hours : hours - 12; return (
- {isAM ? "오전" : "오후"} {hours12}: - {minutes < 10 ? "0" + minutes : minutes} + {chatBubbleTime(props.chatDate)} {props.message} diff --git a/src/components/ChattingProfile.tsx b/src/components/ChattingProfile.tsx index 6f89f77..2473cb0 100644 --- a/src/components/ChattingProfile.tsx +++ b/src/components/ChattingProfile.tsx @@ -7,14 +7,20 @@ import "../style/color.css"; import { usersState } from "../recoil/state"; import { useRecoilValue } from "recoil"; import styled from "styled-components"; +import { useNavigate } from "react-router-dom"; interface ChattingProfileProps { userId: number; } function ChattingProfile(props: ChattingProfileProps) { const users = useRecoilValue(usersState); + const navigate = useNavigate(); return ( - + { + navigate("/chat"); + }} + /> @@ -52,6 +58,10 @@ const StyledBack = styled(Back)` padding: 0.25rem 0.625rem; left: 0.625rem; top: 1.19rem; + &:hover { + color: #ffffff; + filter: brightness(300%); + } `; const StyledFriends = styled(Friends)` position: absolute; diff --git a/src/components/ChattingRoom.tsx b/src/components/ChattingRoom.tsx index d124f90..875055d 100644 --- a/src/components/ChattingRoom.tsx +++ b/src/components/ChattingRoom.tsx @@ -6,16 +6,18 @@ import { useEffect, useRef } from "react"; import ChatBubble from "./ChatBubble"; import { useRecoilValue } from "recoil"; import { chatListByIdState, nowUserIdState } from "../recoil/state"; +import { checkDateChange, dateChangeFormat } from "../utils/dateForm"; interface ChattingProps { chatRoomId: number; isUser: boolean; } -const dayList = ["일", "월", "화", "수", "목", "금", "토"]; +// const dayList = ["일", "월", "화", "수", "목", "금", "토"]; function ChattingRoom(props: ChattingProps) { // //현재 채팅방 chat list const chatList = useRecoilValue(chatListByIdState(props.chatRoomId)); //현재 사용중인 user의 id const nowUser = useRecoilValue(nowUserIdState); + let prevDate: string = ""; //chat 추가 되면 scroll 밑으로 const scrollRef = useRef(null); //chat 추가되면 scroll 내리고, localstorage 저장 @@ -27,7 +29,6 @@ function ChattingRoom(props: ChattingProps) { "chat" + String(props.chatRoomId), JSON.stringify(chatList) ); - console.log(chatList); }, [chatList]); if (chatList.length === 0) { //chatting 없을 시 empty 출력 @@ -46,25 +47,17 @@ function ChattingRoom(props: ChattingProps) { {chatList.map((value, index) => { //하루넘어가면 날짜 출력 - let dateChange: boolean = false; - const nowChatDate = new Date(chatList[index].date); - if (index === 0) { - dateChange = true; - } else { - const lastChatDate = new Date(chatList[index - 1].date); - if (lastChatDate.getDate() !== nowChatDate.getDate()) { - dateChange = true; - } else { - dateChange = false; - } - } + let dateChange: boolean = checkDateChange( + prevDate, + chatList[index].date + ); + prevDate = chatList[index].date; return ( <> {dateChange ? ( - {nowChatDate.getFullYear()}년 {nowChatDate.getMonth() + 1}월{" "} - {nowChatDate.getDate()}일 ({dayList[nowChatDate.getDay()]}) + {dateChangeFormat(prevDate)} ) : null} diff --git a/src/data/chatData.json b/src/data/chatData.json index 3a66d68..92ec852 100644 --- a/src/data/chatData.json +++ b/src/data/chatData.json @@ -1,45 +1,45 @@ { - "chattings": [ - { - "chatRoomId": 0, - "userList": [0,3], - "chatList":[ - { - "chatId":0, - "userId":0, - "message" :"에어팟을 끼고 일해도 힘듭니다", - "date": "Thu Sep 28 2023 09:41:56 GMT+0900 (한국 표준시)" - }, - { - "chatId":1, - "userId":3, - "message" :"앗 그렇군뇽 그냥 하세요", - "date": "Thu Sep 28 2023 10:31:42 GMT+0900 (한국 표준시)" - } - ] - }, - { - "chatRoomId": 1, - "userList": [0,2], - "chatList":[ - { - "chatId":0, - "userId":0, - "message" :"배고파요", - "date": "Fri May 5 2023 16:18:14 GMT+0900 (한국 표준시)" - }, - { - "chatId":1, - "userId":2, - "message" :"네", - "date": "Fri May 5 2023 16:18:14 GMT+0900 (한국 표준시)" - } - ] - }, - { - "chatRoomId": 2, - "userList": [0,4], - "chatList":[] - } - ] -} \ No newline at end of file + "chattings": [ + { + "chatRoomId": 0, + "userList": [0, 3], + "chatList": [ + { + "chatId": 0, + "userId": 0, + "message": "에어팟을 끼고 일해도 힘듭니다", + "date": "Thu Sep 28 2023 09:41:56 GMT+0900 (한국 표준시)" + }, + { + "chatId": 1, + "userId": 3, + "message": "앗 그렇군뇽 그냥 하세요", + "date": "Thu Sep 28 2023 10:31:42 GMT+0900 (한국 표준시)" + } + ] + }, + { + "chatRoomId": 1, + "userList": [0, 2], + "chatList": [ + { + "chatId": 0, + "userId": 0, + "message": "배고파요", + "date": "Wed Oct 4 2023 16:18:14 GMT+0900 (한국 표준시)" + }, + { + "chatId": 1, + "userId": 2, + "message": "네", + "date": "Wed Oct 4 2023 16:18:16 GMT+0900 (한국 표준시)" + } + ] + }, + { + "chatRoomId": 2, + "userList": [0, 4], + "chatList": [] + } + ] +} diff --git a/src/pages/ChatPage.tsx b/src/pages/ChatPage.tsx new file mode 100644 index 0000000..b06ac76 --- /dev/null +++ b/src/pages/ChatPage.tsx @@ -0,0 +1,28 @@ +import { useNavigate } from "react-router-dom"; +import { useRecoilState } from "recoil"; +import { chatRoomListState } from "../recoil/state"; +const ChatPage = () => { + const movePage = useNavigate(); + const roomList = useRecoilState(chatRoomListState); + return ( +
+ Chat + + +
+ ); +}; + +export default ChatPage; diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index dda48d4..193cbea 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -9,6 +9,7 @@ import { chatRoomListState, nowUserIdState, } from "../recoil/state"; +import { useParams } from "react-router-dom"; interface ChattingPageProps { chatRoomId: number; } @@ -31,6 +32,7 @@ function ChattingPage(props: ChattingPageProps) { const initializeChat = localStorage.getItem( "chat" + String(props.chatRoomId) ); + let { id } = useParams(); useEffect(() => { if (initializeChat === null) { localStorage.setItem( @@ -40,6 +42,7 @@ function ChattingPage(props: ChattingPageProps) { } else { setChatListById(JSON.parse(initializeChat)); } + console.log(Number(id)); }, []); //0,1로 switch 하면서 채팅방 userlist의 0,1인덱스의 user로 전환 @@ -57,7 +60,6 @@ function ChattingPage(props: ChattingPageProps) {
- {/* props.chatRoomId */} diff --git a/src/pages/Home.tsx b/src/pages/HomePage.tsx similarity index 59% rename from src/pages/Home.tsx rename to src/pages/HomePage.tsx index 59212d6..1b35b20 100644 --- a/src/pages/Home.tsx +++ b/src/pages/HomePage.tsx @@ -1,5 +1,5 @@ import { useNavigate } from "react-router-dom"; -const Home = () => { +const HomePage = () => { const movePage = useNavigate(); return (
@@ -11,8 +11,15 @@ const Home = () => { > chat +
); }; -export default Home; +export default HomePage; diff --git a/src/pages/ProfilePage.tsx b/src/pages/ProfilePage.tsx new file mode 100644 index 0000000..4017b02 --- /dev/null +++ b/src/pages/ProfilePage.tsx @@ -0,0 +1,11 @@ +import { useNavigate } from "react-router-dom"; +const ProfilePage = () => { + const movePage = useNavigate(); + return ( +
+ +
+ ); +}; + +export default ProfilePage; diff --git a/src/utils/dateForm.ts b/src/utils/dateForm.ts new file mode 100644 index 0000000..bdb40a3 --- /dev/null +++ b/src/utils/dateForm.ts @@ -0,0 +1,30 @@ +export const chatBubbleTime = (chatDate: string) => { + const date = new Date(chatDate); + const hours = date.getHours(); + const minutes = date.getMinutes(); + const isAM = hours < 12 ? true : false; + const hours12 = hours < 13 ? hours : hours - 12; + return `${isAM ? "오전" : "오후"} ${hours12}:${ + minutes < 10 ? "0" + minutes : minutes + }`; +}; + +export const checkDateChange = (date1: string, date2: string) => { + const dateObj1 = new Date(date1); + const dateObj2 = new Date(date2); + if ( + dateObj1.getFullYear() === dateObj2.getFullYear() && + dateObj1.getMonth() === dateObj2.getMonth() && + dateObj1.getDate() === dateObj2.getDate() + ) { + return false; + } + return true; +}; + +export const dateChangeFormat = (date: string) => { + const dateObj = new Date(date); + const dayList = ["일", "월", "화", "수", "목", "금", "토"]; + return `${dateObj.getFullYear()}년 ${dateObj.getMonth() + 1}월${" "} + ${dateObj.getDate()}일 (${dayList[dateObj.getDay()]})`; +}; From 34e81f1e5c39c922239c6693d146a0df346020bf Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 4 Oct 2023 17:55:02 +0900 Subject: [PATCH 25/55] =?UTF-8?q?refactor:=20components=20=ED=8C=8C?= =?UTF-8?q?=EC=9D=BC=20=EA=B5=AC=EC=A1=B0=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/App.tsx | 2 +- src/components/{ => chatting}/ChatBubble.tsx | 6 ++-- .../{ => chatting}/ChattingInput.tsx | 12 ++++---- .../{ => chatting}/ChattingProfile.tsx | 14 ++++----- .../{ => chatting}/ChattingRoom.tsx | 10 +++---- .../{molecules => chatting}/LikeButton.tsx | 0 src/data/chatData.json | 12 +++++--- src/pages/ChatPage.tsx | 2 +- src/pages/ChattingPage.tsx | 30 ++++++++----------- 9 files changed, 44 insertions(+), 44 deletions(-) rename src/components/{ => chatting}/ChatBubble.tsx (92%) rename src/components/{ => chatting}/ChattingInput.tsx (91%) rename src/components/{ => chatting}/ChattingProfile.tsx (83%) rename src/components/{ => chatting}/ChattingRoom.tsx (90%) rename src/components/{molecules => chatting}/LikeButton.tsx (100%) diff --git a/src/App.tsx b/src/App.tsx index 1195380..fec38a1 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -16,7 +16,7 @@ function App() { } /> } /> - } /> + } /> } /> diff --git a/src/components/ChatBubble.tsx b/src/components/chatting/ChatBubble.tsx similarity index 92% rename from src/components/ChatBubble.tsx rename to src/components/chatting/ChatBubble.tsx index f225d01..cb11533 100644 --- a/src/components/ChatBubble.tsx +++ b/src/components/chatting/ChatBubble.tsx @@ -1,7 +1,7 @@ import styled from "styled-components"; -import "../style/color.css"; -import { Body2, Caption2 } from "../style/font"; -import { chatBubbleTime } from "../utils/dateForm"; +import "../../style/color.css"; +import { Body2, Caption2 } from "../../style/font"; +import { chatBubbleTime } from "../../utils/dateForm"; interface ChatBubbleProps { isMyChat: boolean; message: string; diff --git a/src/components/ChattingInput.tsx b/src/components/chatting/ChattingInput.tsx similarity index 91% rename from src/components/ChattingInput.tsx rename to src/components/chatting/ChattingInput.tsx index aac39ac..e2890d1 100644 --- a/src/components/ChattingInput.tsx +++ b/src/components/chatting/ChattingInput.tsx @@ -1,13 +1,13 @@ import { useState } from "react"; -import { ReactComponent as Plus } from "../assets/icons/Plus.svg"; -import { ReactComponent as Send } from "../assets/icons/Send.svg"; +import { ReactComponent as Plus } from "../../assets/icons/Plus.svg"; +import { ReactComponent as Send } from "../../assets/icons/Send.svg"; import styled from "styled-components"; -import { Body2 } from "../style/font"; +import { Body2 } from "../../style/font"; import { chatListByIdState, chatRoomListState, nowUserIdState, -} from "../recoil/state"; +} from "../../recoil/state"; import { useRecoilState, useRecoilValue } from "recoil"; interface ChattingInputProps { chatRoomId: number; @@ -17,14 +17,13 @@ interface ChatInfo { userId: number; message: string; date: string; + like: number; } function ChattingInput(props: ChattingInputProps) { const [typeMessage, setTypeMessage] = useState("메세지를 입력하세요"); const [input, setInput] = useState(""); //현재 사용 user ID const nowUser = useRecoilValue(nowUserIdState); - //모든 채팅방 list - const [chatRoomList, setChatRoomList] = useRecoilState(chatRoomListState); const [chatList, setChatList] = useRecoilState( chatListByIdState(props.chatRoomId) ); @@ -45,6 +44,7 @@ function ChattingInput(props: ChattingInputProps) { userId: nowUser, message: input, date: String(new Date()), + like: 0, }; const copy = [...chatList]; copy.push(chatInstance); diff --git a/src/components/ChattingProfile.tsx b/src/components/chatting/ChattingProfile.tsx similarity index 83% rename from src/components/ChattingProfile.tsx rename to src/components/chatting/ChattingProfile.tsx index 2473cb0..b07ef24 100644 --- a/src/components/ChattingProfile.tsx +++ b/src/components/chatting/ChattingProfile.tsx @@ -1,10 +1,10 @@ -import { ReactComponent as Back } from "../assets/icons/Back.svg"; -import { ReactComponent as Call } from "../assets/icons/Call.svg"; -import { ReactComponent as Friends } from "../assets/icons/Freinds.svg"; -import { ReactComponent as More } from "../assets/icons/More.svg"; -import { Heading2, Caption1 } from "../style/font"; -import "../style/color.css"; -import { usersState } from "../recoil/state"; +import { ReactComponent as Back } from "../../assets/icons/Back.svg"; +import { ReactComponent as Call } from "../../assets/icons/Call.svg"; +import { ReactComponent as Friends } from "../../assets/icons/Freinds.svg"; +import { ReactComponent as More } from "../../assets/icons/More.svg"; +import { Heading2, Caption1 } from "../../style/font"; +import "../../style/color.css"; +import { usersState } from "../../recoil/state"; import { useRecoilValue } from "recoil"; import styled from "styled-components"; import { useNavigate } from "react-router-dom"; diff --git a/src/components/ChattingRoom.tsx b/src/components/chatting/ChattingRoom.tsx similarity index 90% rename from src/components/ChattingRoom.tsx rename to src/components/chatting/ChattingRoom.tsx index 875055d..1ad21a9 100644 --- a/src/components/ChattingRoom.tsx +++ b/src/components/chatting/ChattingRoom.tsx @@ -1,12 +1,12 @@ import styled from "styled-components"; -import "../style/color.css"; -import { ReactComponent as Chat } from "../assets/icons/Chat.svg"; -import { Caption1, Body2 } from "../style/font"; +import "../../style/color.css"; +import { ReactComponent as Chat } from "../../assets/icons/Chat.svg"; +import { Caption1, Body2 } from "../../style/font"; import { useEffect, useRef } from "react"; import ChatBubble from "./ChatBubble"; import { useRecoilValue } from "recoil"; -import { chatListByIdState, nowUserIdState } from "../recoil/state"; -import { checkDateChange, dateChangeFormat } from "../utils/dateForm"; +import { chatListByIdState, nowUserIdState } from "../../recoil/state"; +import { checkDateChange, dateChangeFormat } from "../../utils/dateForm"; interface ChattingProps { chatRoomId: number; isUser: boolean; diff --git a/src/components/molecules/LikeButton.tsx b/src/components/chatting/LikeButton.tsx similarity index 100% rename from src/components/molecules/LikeButton.tsx rename to src/components/chatting/LikeButton.tsx diff --git a/src/data/chatData.json b/src/data/chatData.json index 92ec852..7cac42f 100644 --- a/src/data/chatData.json +++ b/src/data/chatData.json @@ -8,13 +8,15 @@ "chatId": 0, "userId": 0, "message": "에어팟을 끼고 일해도 힘듭니다", - "date": "Thu Sep 28 2023 09:41:56 GMT+0900 (한국 표준시)" + "date": "Thu Sep 28 2023 09:41:56 GMT+0900 (한국 표준시)", + "like": 0 }, { "chatId": 1, "userId": 3, "message": "앗 그렇군뇽 그냥 하세요", - "date": "Thu Sep 28 2023 10:31:42 GMT+0900 (한국 표준시)" + "date": "Thu Sep 28 2023 10:31:42 GMT+0900 (한국 표준시)", + "like": 0 } ] }, @@ -26,13 +28,15 @@ "chatId": 0, "userId": 0, "message": "배고파요", - "date": "Wed Oct 4 2023 16:18:14 GMT+0900 (한국 표준시)" + "date": "Wed Oct 4 2023 16:18:14 GMT+0900 (한국 표준시)", + "like": 0 }, { "chatId": 1, "userId": 2, "message": "네", - "date": "Wed Oct 4 2023 16:18:16 GMT+0900 (한국 표준시)" + "date": "Wed Oct 4 2023 16:18:16 GMT+0900 (한국 표준시)", + "like": 0 } ] }, diff --git a/src/pages/ChatPage.tsx b/src/pages/ChatPage.tsx index b06ac76..0adb9b9 100644 --- a/src/pages/ChatPage.tsx +++ b/src/pages/ChatPage.tsx @@ -3,7 +3,7 @@ import { useRecoilState } from "recoil"; import { chatRoomListState } from "../recoil/state"; const ChatPage = () => { const movePage = useNavigate(); - const roomList = useRecoilState(chatRoomListState); + //const roomList = useRecoilState(chatRoomListState); return (
Chat diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index 193cbea..5796839 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -1,6 +1,6 @@ -import ChattingRoom from "../components/ChattingRoom"; -import ChattingInput from "../components/ChattingInput"; -import ChattingProfile from "../components/ChattingProfile"; +import ChattingRoom from "../components/chatting/ChattingRoom"; +import ChattingInput from "../components/chatting/ChattingInput"; +import ChattingProfile from "../components/chatting/ChattingProfile"; import styled from "styled-components"; import { useState, useEffect } from "react"; import { useRecoilState, useRecoilValue } from "recoil"; @@ -10,33 +10,29 @@ import { nowUserIdState, } from "../recoil/state"; import { useParams } from "react-router-dom"; -interface ChattingPageProps { - chatRoomId: number; -} -function ChattingPage(props: ChattingPageProps) { + +function ChattingPage() { + let { id } = useParams(); //chatting 전체 리스트 const chatRoomList = useRecoilValue(chatRoomListState); //해당 채팅방 chatting list const [chatListById, setChatListById] = useRecoilState( - chatListByIdState(props.chatRoomId) + chatListByIdState(Number(id)) ); //채팅방 사용자 2명 - const roomUsers = chatRoomList[props.chatRoomId].userList; + const roomUsers = chatRoomList[Number(id)].userList; //user switch 상태 const [switchUser, setSwitchUser] = useState(0); //list 길이 체크해서 빈 채팅방 or 채팅있는 채팅방 - const chatList = chatRoomList[props.chatRoomId].chatList; + const chatList = chatRoomList[Number(id)].chatList; //현재 사용중인 user의 id(login user 아님) const [nowUserId, setNowUserId] = useRecoilState(nowUserIdState); //localstorage에 없으면 json 파일 저장, 있으면 chatList 불러옴 - const initializeChat = localStorage.getItem( - "chat" + String(props.chatRoomId) - ); - let { id } = useParams(); + const initializeChat = localStorage.getItem("chat" + String(Number(id))); useEffect(() => { if (initializeChat === null) { localStorage.setItem( - "chat" + String(props.chatRoomId), + "chat" + String(Number(id)), JSON.stringify(chatListById) ); } else { @@ -60,8 +56,8 @@ function ChattingPage(props: ChattingPageProps) {
- - + + ); } From 53d5cc4cbc1e53b454de34cc7627e83196c159f5 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Sat, 7 Oct 2023 01:10:25 +0900 Subject: [PATCH 26/55] =?UTF-8?q?refactor:=20=EB=94=94=EC=9E=90=EC=9D=B8?= =?UTF-8?q?=20=EB=B0=9C=ED=91=9C=20chatpage=20message=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/App.tsx | 9 +++++---- src/components/chat/ChatCard.tsx | 10 ++++++++++ src/data/chatData.json | 4 ++-- src/pages/ChatPage.tsx | 2 ++ 4 files changed, 19 insertions(+), 6 deletions(-) create mode 100644 src/components/chat/ChatCard.tsx diff --git a/src/App.tsx b/src/App.tsx index fec38a1..5893a7e 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -14,10 +14,11 @@ function App() {
- } /> - } /> - } /> - } /> + {/* } /> + } /> */} + {/* } /> */} + } /> + {/* } /> */}
diff --git a/src/components/chat/ChatCard.tsx b/src/components/chat/ChatCard.tsx new file mode 100644 index 0000000..1f9c308 --- /dev/null +++ b/src/components/chat/ChatCard.tsx @@ -0,0 +1,10 @@ +import styled from "styled-components"; +const ChatCard = () => { + return ; +}; +export default ChatCard; + +const ChatCardWrapper = styled.div` + height: 7.5rem; + background-color: white; +`; diff --git a/src/data/chatData.json b/src/data/chatData.json index 7cac42f..f1e25d6 100644 --- a/src/data/chatData.json +++ b/src/data/chatData.json @@ -7,14 +7,14 @@ { "chatId": 0, "userId": 0, - "message": "에어팟을 끼고 일해도 힘듭니다", + "message": "오늘 회의가 다음주로 미뤄졌다고 하네요.", "date": "Thu Sep 28 2023 09:41:56 GMT+0900 (한국 표준시)", "like": 0 }, { "chatId": 1, "userId": 3, - "message": "앗 그렇군뇽 그냥 하세요", + "message": "그럼 오늘은 일찍 퇴근합시다", "date": "Thu Sep 28 2023 10:31:42 GMT+0900 (한국 표준시)", "like": 0 } diff --git a/src/pages/ChatPage.tsx b/src/pages/ChatPage.tsx index 0adb9b9..df26c48 100644 --- a/src/pages/ChatPage.tsx +++ b/src/pages/ChatPage.tsx @@ -1,6 +1,7 @@ import { useNavigate } from "react-router-dom"; import { useRecoilState } from "recoil"; import { chatRoomListState } from "../recoil/state"; +import ChatCard from "../components/chat/ChatCard"; const ChatPage = () => { const movePage = useNavigate(); //const roomList = useRecoilState(chatRoomListState); @@ -21,6 +22,7 @@ const ChatPage = () => { > 1 + ); }; From b34891d51cf00bc3a2b99fc4ce0bdc39976089b6 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Sat, 7 Oct 2023 01:23:10 +0900 Subject: [PATCH 27/55] =?UTF-8?q?chore:=20dummy=20=EB=8D=B0=EC=9D=B4?= =?UTF-8?q?=ED=84=B0=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/data/chatData.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/data/chatData.json b/src/data/chatData.json index f1e25d6..48ad558 100644 --- a/src/data/chatData.json +++ b/src/data/chatData.json @@ -7,7 +7,7 @@ { "chatId": 0, "userId": 0, - "message": "오늘 회의가 다음주로 미뤄졌다고 하네요.", + "message": "오늘 회의가 다음주로 미뤄졌다고 하네요", "date": "Thu Sep 28 2023 09:41:56 GMT+0900 (한국 표준시)", "like": 0 }, From bcb751eb4c9e1711c586656eaf6a46089aafeaf3 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Tue, 10 Oct 2023 20:27:57 +0900 Subject: [PATCH 28/55] =?UTF-8?q?feat:=20chat=20page=20=EC=9E=84=EC=8B=9C?= =?UTF-8?q?=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/App.tsx | 10 +-- src/assets/icons/Chat.svg | 6 +- src/assets/icons/EmptyChat.svg | 4 + src/assets/icons/People.svg | 7 ++ src/assets/icons/Search.svg | 4 + src/assets/icons/Setting.svg | 3 + src/components/Footer.tsx | 84 +++++++++++++++++++++ src/components/HomeIndicator.tsx | 12 ++- src/components/StatusBar.tsx | 2 +- src/components/chat/ChatCard.tsx | 61 ++++++++++++++- src/components/chat/ChatCardList.tsx | 35 +++++++++ src/components/chat/ChatHeader.tsx | 23 ++++++ src/components/chat/ChatSearch.tsx | 74 ++++++++++++++++++ src/components/chatting/ChattingInput.tsx | 7 +- src/components/chatting/ChattingProfile.tsx | 2 +- src/components/chatting/ChattingRoom.tsx | 8 +- src/pages/ChatPage.tsx | 29 +++---- src/pages/ChattingPage.tsx | 14 +++- src/pages/ProfilePage.tsx | 3 +- src/style/GlobalStyle.tsx | 2 +- 20 files changed, 340 insertions(+), 50 deletions(-) create mode 100644 src/assets/icons/EmptyChat.svg create mode 100644 src/assets/icons/People.svg create mode 100644 src/assets/icons/Search.svg create mode 100644 src/assets/icons/Setting.svg create mode 100644 src/components/Footer.tsx create mode 100644 src/components/chat/ChatCardList.tsx create mode 100644 src/components/chat/ChatHeader.tsx create mode 100644 src/components/chat/ChatSearch.tsx diff --git a/src/App.tsx b/src/App.tsx index 5893a7e..d04d14e 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -14,13 +14,11 @@ function App() {
- {/* } /> - } /> */} - {/* } /> */} - } /> - {/* } /> */} + } /> + } /> + } /> + } /> -
); diff --git a/src/assets/icons/Chat.svg b/src/assets/icons/Chat.svg index 7165415..94f7f03 100644 --- a/src/assets/icons/Chat.svg +++ b/src/assets/icons/Chat.svg @@ -1,4 +1,4 @@ - - - + + + \ No newline at end of file diff --git a/src/assets/icons/EmptyChat.svg b/src/assets/icons/EmptyChat.svg new file mode 100644 index 0000000..7165415 --- /dev/null +++ b/src/assets/icons/EmptyChat.svg @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/src/assets/icons/People.svg b/src/assets/icons/People.svg new file mode 100644 index 0000000..6a46b2b --- /dev/null +++ b/src/assets/icons/People.svg @@ -0,0 +1,7 @@ + + + + + + + \ No newline at end of file diff --git a/src/assets/icons/Search.svg b/src/assets/icons/Search.svg new file mode 100644 index 0000000..7e1bc27 --- /dev/null +++ b/src/assets/icons/Search.svg @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/src/assets/icons/Setting.svg b/src/assets/icons/Setting.svg new file mode 100644 index 0000000..dde0e4d --- /dev/null +++ b/src/assets/icons/Setting.svg @@ -0,0 +1,3 @@ + + + \ No newline at end of file diff --git a/src/components/Footer.tsx b/src/components/Footer.tsx new file mode 100644 index 0000000..80b6f9a --- /dev/null +++ b/src/components/Footer.tsx @@ -0,0 +1,84 @@ +import styled from "styled-components"; +import { ReactComponent as People } from "../assets/icons/People.svg"; +import { ReactComponent as Chat } from "../assets/icons/Chat.svg"; +import { ReactComponent as Setting } from "../assets/icons/Setting.svg"; +import { Navigate, useNavigate } from "react-router-dom"; +interface FooterProps { + page: string; +} +//page에 따라 버튼색 변환 +const getPeopleIconStyles = (page: string) => { + if (page === "people") { + return "fill: var(--green);"; + } else { + return "fill: var(--gray-6);"; + } +}; +const getChatIconStyles = (page: string) => { + if (page === "chat") { + return "fill: var(--green);"; + } else { + return "fill: var(--gray-6);"; + } +}; +const getSettingIconStyles = (page: string) => { + if (page === "setting") { + return "fill: var(--green);"; + } else { + return "fill: var(--gray-6);"; + } +}; +const Footer = ({ page }: FooterProps) => { + const navigate = useNavigate(); + return ( + + { + navigate("/profile"); + }} + page={page} + /> + { + navigate("/chat"); + }} + page={page} + /> + + + ); +}; +const FooterWrapper = styled.div` + height: 2.875rem; + background-color: var(--gray-1); + position: relative; +`; +const PeopleIcon = styled(People)` + padding: 0.125rem; + position: absolute; + left: 5.125rem; + top: 1rem; + path { + ${(props) => getPeopleIconStyles(props.page)} + } +`; + +const ChatIcon = styled(Chat)` + padding: 0.125rem; + position: absolute; + left: 10.9385rem; + top: 1rem; + path { + ${(props) => getChatIconStyles(props.page)} + } +`; +const SettingIcon = styled(Setting)` + padding: 0.188rem 0.216rem; + position: absolute; + right: 4.813rem; + top: 1rem; + path { + ${(props) => getSettingIconStyles(props.page)} + } +`; +export default Footer; diff --git a/src/components/HomeIndicator.tsx b/src/components/HomeIndicator.tsx index d9c973b..1d1a20c 100644 --- a/src/components/HomeIndicator.tsx +++ b/src/components/HomeIndicator.tsx @@ -1,15 +1,19 @@ import { ReactComponent as HomeBar } from "../assets/iphone/HomeBar.svg"; import styled from "styled-components"; -function HomeIndicator() { +interface HomeIndicatorProps { + color: string; +} +const HomeIndicator = ({ color }: HomeIndicatorProps) => { return ( - + ); -} +}; const HomeBarWrapper = styled.div` - width: 23.4375rem; height: 2.125rem; + background-color: ${(props) => props.color || "var(--black)"}; + border-radius: 0 0 1.25rem 1.25rem; `; const StyledHomeBar = styled(HomeBar)` width: 8.375rem; diff --git a/src/components/StatusBar.tsx b/src/components/StatusBar.tsx index 5bc8b32..c737388 100644 --- a/src/components/StatusBar.tsx +++ b/src/components/StatusBar.tsx @@ -17,7 +17,7 @@ function StatusBar() { } const StatusBarWrapper = styled.div` width: 23.4375rem; - height: 2.9375rem; + height: 2.938rem; position: relative; `; diff --git a/src/components/chat/ChatCard.tsx b/src/components/chat/ChatCard.tsx index 1f9c308..7aafa1e 100644 --- a/src/components/chat/ChatCard.tsx +++ b/src/components/chat/ChatCard.tsx @@ -1,10 +1,67 @@ import styled from "styled-components"; +import { ReactComponent as Friends } from "../../assets/icons/Freinds.svg"; +import { Body2, Caption1, Caption2, Heading2 } from "../../style/font"; +//chatpage 에서 chatlist가져오고, 넘기기. 넘기면 room에 따라서 chat 미리보기 card에 props 넘기고, 마지막 chat시간 내용 +//도 알아야함 const ChatCard = () => { - return ; + return ( + + + + +
+ 신현재 + 근무 중 +
+ + 즐거운 저녁되세요 + + + + + 오전 10:24 + + + ); }; export default ChatCard; const ChatCardWrapper = styled.div` height: 7.5rem; - background-color: white; + background-color: var(--black); + display: flex; + justify-content: center; + align-items: center; + position: relative; + .last-chat-time { + position: absolute; + top: 1.25rem; + right: 1rem; + } +`; +const ChatContentWrapper = styled.div` + display: flex; + width: 20.9375rem; + height: 5rem; +`; +const ChatContent = styled.div` + width: 14.0625rem; + height: 5rem; + background-color: var(--black); + display: flex; + flex-direction: column; + .user-info { + display: flex; + gap: 0.5rem; + } + .last-chat { + width: 14.0625rem; + height: 3.125rem; + padding-top: 0.5rem; + } +`; +const FriendsIcon = styled(Friends)` + width: 3.5rem; + height: 3.5rem; + padding-right: 0.75rem; `; diff --git a/src/components/chat/ChatCardList.tsx b/src/components/chat/ChatCardList.tsx new file mode 100644 index 0000000..78d83a3 --- /dev/null +++ b/src/components/chat/ChatCardList.tsx @@ -0,0 +1,35 @@ +import styled from "styled-components"; +import ChatCard from "./ChatCard"; +import { useRecoilValue } from "recoil"; +import { chatRoomListState } from "../../recoil/state"; + +const ChatCardList = () => { + const chatList = useRecoilValue(chatRoomListState); + return ( + + { + //chatList. + // + } + + + + + + + + + ); +}; +export default ChatCardList; + +const ChatCardListWrapper = styled.div` + height: 34.375rem; + background-color: var(--black); + overflow-y: auto; + scrollbar-width: none; /* Firefox */ + -ms-overflow-style: none; /* Internet Explorer/Edge */ + &::-webkit-scrollbar { + display: none; /* Chrome, Safari*/ + } +`; diff --git a/src/components/chat/ChatHeader.tsx b/src/components/chat/ChatHeader.tsx new file mode 100644 index 0000000..9dbbdae --- /dev/null +++ b/src/components/chat/ChatHeader.tsx @@ -0,0 +1,23 @@ +import styled from "styled-components"; +import { Heading1 } from "../../style/font"; + +const ChatHeader = () => { + return ( + + + 대화 + + + ); +}; +export default ChatHeader; + +const ChatHeaderWrapper = styled.div` + height: 4.25rem; + display: flex; + align-items: center; + border-bottom: solid 0.0625rem var(--gray-3); + .chat-logo { + padding-left: 1.25rem; + } +`; diff --git a/src/components/chat/ChatSearch.tsx b/src/components/chat/ChatSearch.tsx new file mode 100644 index 0000000..548631c --- /dev/null +++ b/src/components/chat/ChatSearch.tsx @@ -0,0 +1,74 @@ +import styled from "styled-components"; +import { ReactComponent as Search } from "../../assets/icons/Search.svg"; +import { useState } from "react"; +const ChatSearch = () => { + const [input, setInput] = useState(""); + + const handleSubmit = (e: React.FormEvent) => { + e.preventDefault(); + if (input.trim() !== "") { + setInput(""); + } + }; + const handleOnChange = (e: React.ChangeEvent) => { + setInput(e.target.value); + console.log(input); + }; + return ( + + + + + + + ); +}; +export default ChatSearch; +const ChatSearchWrapper = styled.div` + height: 4.125rem; + background-color: var(--black); + display: flex; + justify-content: center; + align-items: center; + position: relative; +`; +const StyledForm = styled.form` + .search-input { + border: none; + background-color: var(--gray-1); + width: 16.6875rem; + height: 2.875rem; + border-radius: 3.125rem; + padding-left: 4.25rem; + font-family: "Pretendard-Regular"; /*globalstyle 왜 적용안되는지?*/ + color: var(--gray-7); + font-size: 1.125rem; + font-style: normal; + font-weight: 500; + line-height: 1.5rem; /* 133.333% */ + letter-spacing: -0.0255rem; + &::placeholder { + font-family: "Pretendard-Regular"; + color: var(--gray-4); + font-size: 1.125rem; + font-style: normal; + font-weight: 500; + line-height: 1.5rem; /* 133.333% */ + letter-spacing: -0.0255rem; + } + } +`; +const SearchIcon = styled(Search)` + position: absolute; + width: 1.4375rem; + height: 1.4375rem; + padding: 0.21875rem 0.15625rem; + left: 2.44rem; + top: 1.12rem; +`; diff --git a/src/components/chatting/ChattingInput.tsx b/src/components/chatting/ChattingInput.tsx index e2890d1..032d2a9 100644 --- a/src/components/chatting/ChattingInput.tsx +++ b/src/components/chatting/ChattingInput.tsx @@ -77,10 +77,9 @@ function ChattingInput(props: ChattingInputProps) { } const ChattingInputWrapper = styled.div` width: 23.4375rem; - height: 3.69rem; + height: 3.6875rem; position: relative; - position: absolute; - top: 42rem; + .placeHolder { pointer-events: none; /*input이 묻히기 때문에 제외*/ position: absolute; @@ -121,7 +120,7 @@ const StyledForm = styled.form` border-radius: 6.25rem; padding-left: 1.25rem; padding-right: 1.25rem; - font-family: "Pretendard-Regular"; /*globalstyle 왜 적용안되는지?*/ + font-family: "Pretendard-Regular"; color: var(--gray-7); font-size: 1.125rem; font-style: normal; diff --git a/src/components/chatting/ChattingProfile.tsx b/src/components/chatting/ChattingProfile.tsx index b07ef24..541e680 100644 --- a/src/components/chatting/ChattingProfile.tsx +++ b/src/components/chatting/ChattingProfile.tsx @@ -26,7 +26,7 @@ function ChattingProfile(props: ChattingProfileProps) { - {users[props.userId].name} + {users[props.userId].name} { const movePage = useNavigate(); //const roomList = useRecoilState(chatRoomListState); return ( -
- Chat - - - +
+ + + +
+
); }; diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index 5796839..9b47ad9 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -10,6 +10,7 @@ import { nowUserIdState, } from "../recoil/state"; import { useParams } from "react-router-dom"; +import HomeIndicator from "../components/HomeIndicator"; function ChattingPage() { let { id } = useParams(); @@ -38,7 +39,8 @@ function ChattingPage() { } else { setChatListById(JSON.parse(initializeChat)); } - console.log(Number(id)); + //페이지가 불릴 때, 현재 user도 재설정 + setNowUserId(roomUsers[switchUser]); }, []); //0,1로 switch 하면서 채팅방 userlist의 0,1인덱스의 user로 전환 @@ -56,13 +58,17 @@ function ChattingPage() {
- + + ); } const Divider = styled.hr` - border: 0.0625rem solid var(--gray-3); - margin: 0; + background-color = var(--black); + border : none; + border-bottom: solid 0.0625rem var(--gray-3); + margin-top: 0.25rem; + margin-bottom :0rem; `; export default ChattingPage; diff --git a/src/pages/ProfilePage.tsx b/src/pages/ProfilePage.tsx index 4017b02..83888b4 100644 --- a/src/pages/ProfilePage.tsx +++ b/src/pages/ProfilePage.tsx @@ -1,9 +1,10 @@ import { useNavigate } from "react-router-dom"; +import Footer from "../components/Footer"; const ProfilePage = () => { - const movePage = useNavigate(); return (
+
); }; diff --git a/src/style/GlobalStyle.tsx b/src/style/GlobalStyle.tsx index 99641ea..c4f19a9 100644 --- a/src/style/GlobalStyle.tsx +++ b/src/style/GlobalStyle.tsx @@ -27,7 +27,7 @@ const GlobalStyle = createGlobalStyle` } .pageWrapper{ /*pageWrapper는 header footer 제외 높이*/ width: 23.4375rem; - height: 45.6875rem; + height: 47.8125rem; position : relative; } `; From d10feb0c5f0d0c9db64fd5de97b11f216a93412d Mon Sep 17 00:00:00 2001 From: leekyuho Date: Tue, 10 Oct 2023 22:38:41 +0900 Subject: [PATCH 29/55] =?UTF-8?q?feat:=20footer=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/App.tsx | 6 +++--- src/components/Footer.tsx | 9 +++++++-- src/components/chat/ChatCard.tsx | 15 ++++++++++----- src/components/chat/ChatCardList.tsx | 16 ++++------------ src/data/chatData.json | 25 ++++++++++++++++++++----- src/pages/ChatPage.tsx | 6 ------ src/pages/HomePage.tsx | 25 ------------------------- src/pages/ProfilePage.tsx | 6 +++--- src/pages/SettingPage.tsx | 12 ++++++++++++ 9 files changed, 59 insertions(+), 61 deletions(-) delete mode 100644 src/pages/HomePage.tsx create mode 100644 src/pages/SettingPage.tsx diff --git a/src/App.tsx b/src/App.tsx index d04d14e..77b49ca 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -3,10 +3,10 @@ import ChattingPage from "./pages/ChattingPage"; import StatusBar from "./components/StatusBar"; import HomeIndicator from "./components/HomeIndicator"; import { Routes, Route } from "react-router-dom"; -import HomePage from "./pages/HomePage"; import ChatPage from "./pages/ChatPage"; import ProfilePage from "./pages/ProfilePage"; import "./style/color.css"; +import SettingPage from "./pages/SettingPage"; function App() { return ( <> @@ -14,10 +14,10 @@ function App() {
- } /> + } /> } /> } /> - } /> + } />
diff --git a/src/components/Footer.tsx b/src/components/Footer.tsx index 80b6f9a..60ad2ce 100644 --- a/src/components/Footer.tsx +++ b/src/components/Footer.tsx @@ -34,7 +34,7 @@ const Footer = ({ page }: FooterProps) => { { - navigate("/profile"); + navigate("/"); }} page={page} /> @@ -44,7 +44,12 @@ const Footer = ({ page }: FooterProps) => { }} page={page} /> - + { + navigate("/setting"); + }} + page={page} + /> ); }; diff --git a/src/components/chat/ChatCard.tsx b/src/components/chat/ChatCard.tsx index 7aafa1e..abd691a 100644 --- a/src/components/chat/ChatCard.tsx +++ b/src/components/chat/ChatCard.tsx @@ -1,20 +1,24 @@ import styled from "styled-components"; +import { useNavigate } from "react-router-dom"; import { ReactComponent as Friends } from "../../assets/icons/Freinds.svg"; import { Body2, Caption1, Caption2, Heading2 } from "../../style/font"; -//chatpage 에서 chatlist가져오고, 넘기기. 넘기면 room에 따라서 chat 미리보기 card에 props 넘기고, 마지막 chat시간 내용 -//도 알아야함 const ChatCard = () => { + const navigate = useNavigate(); return ( - + { + navigate("/chat/0"); + }} + > - +
신현재 근무 중
- 즐거운 저녁되세요 + 회의 때 공유드린 파일 확인해보셨나요?
@@ -33,6 +37,7 @@ const ChatCardWrapper = styled.div` justify-content: center; align-items: center; position: relative; + cursor: pointer; .last-chat-time { position: absolute; top: 1.25rem; diff --git a/src/components/chat/ChatCardList.tsx b/src/components/chat/ChatCardList.tsx index 78d83a3..a3a1097 100644 --- a/src/components/chat/ChatCardList.tsx +++ b/src/components/chat/ChatCardList.tsx @@ -2,22 +2,14 @@ import styled from "styled-components"; import ChatCard from "./ChatCard"; import { useRecoilValue } from "recoil"; import { chatRoomListState } from "../../recoil/state"; - +import { useNavigate } from "react-router-dom"; const ChatCardList = () => { const chatList = useRecoilValue(chatRoomListState); return ( - { - //chatList. - // - } - - - - - - - + {chatList.map((value, index) => { + return ; + })} ); }; diff --git a/src/data/chatData.json b/src/data/chatData.json index 48ad558..38bf5fe 100644 --- a/src/data/chatData.json +++ b/src/data/chatData.json @@ -26,15 +26,15 @@ "chatList": [ { "chatId": 0, - "userId": 0, - "message": "배고파요", + "userId": 2, + "message": "회의 때 공유드린 파일 확인해보셨나요?", "date": "Wed Oct 4 2023 16:18:14 GMT+0900 (한국 표준시)", "like": 0 }, { "chatId": 1, - "userId": 2, - "message": "네", + "userId": 0, + "message": "네 확인했습니다. 감사합니다!", "date": "Wed Oct 4 2023 16:18:16 GMT+0900 (한국 표준시)", "like": 0 } @@ -43,7 +43,22 @@ { "chatRoomId": 2, "userList": [0, 4], - "chatList": [] + "chatList": [ + { + "chatId": 0, + "userId": 0, + "message": "안녕하세요", + "date": "Wed Oct 6 2023 16:18:14 GMT+0900 (한국 표준시)", + "like": 0 + }, + { + "chatId": 1, + "userId": 2, + "message": "고생하셨습니다. 부장님도 주말 잘 보내세요.", + "date": "Wed Oct 7 2023 16:18:16 GMT+0900 (한국 표준시)", + "like": 0 + } + ] } ] } diff --git a/src/pages/ChatPage.tsx b/src/pages/ChatPage.tsx index b4024e6..d0ca18c 100644 --- a/src/pages/ChatPage.tsx +++ b/src/pages/ChatPage.tsx @@ -1,15 +1,9 @@ -import { useNavigate } from "react-router-dom"; -import { useRecoilState } from "recoil"; -import { chatRoomListState } from "../recoil/state"; -import ChatCard from "../components/chat/ChatCard"; -import styled from "styled-components"; import ChatSearch from "../components/chat/ChatSearch"; import ChatHeader from "../components/chat/ChatHeader"; import ChatCardList from "../components/chat/ChatCardList"; import HomeIndicator from "../components/HomeIndicator"; import Footer from "../components/Footer"; const ChatPage = () => { - const movePage = useNavigate(); //const roomList = useRecoilState(chatRoomListState); return (
diff --git a/src/pages/HomePage.tsx b/src/pages/HomePage.tsx deleted file mode 100644 index 1b35b20..0000000 --- a/src/pages/HomePage.tsx +++ /dev/null @@ -1,25 +0,0 @@ -import { useNavigate } from "react-router-dom"; -const HomePage = () => { - const movePage = useNavigate(); - return ( -
- Home - - -
- ); -}; - -export default HomePage; diff --git a/src/pages/ProfilePage.tsx b/src/pages/ProfilePage.tsx index 83888b4..b650c9d 100644 --- a/src/pages/ProfilePage.tsx +++ b/src/pages/ProfilePage.tsx @@ -1,10 +1,10 @@ -import { useNavigate } from "react-router-dom"; import Footer from "../components/Footer"; +import HomeIndicator from "../components/HomeIndicator"; const ProfilePage = () => { return ( -
- +
+
); }; diff --git a/src/pages/SettingPage.tsx b/src/pages/SettingPage.tsx new file mode 100644 index 0000000..aae50a0 --- /dev/null +++ b/src/pages/SettingPage.tsx @@ -0,0 +1,12 @@ +import Footer from "../components/Footer"; +import HomeIndicator from "../components/HomeIndicator"; +const SettingPage = () => { + return ( +
+
+ +
+ ); +}; + +export default SettingPage; From e81ee50c1a7cbc40ba1d2b7366641054ac560884 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 11 Oct 2023 21:52:32 +0900 Subject: [PATCH 30/55] =?UTF-8?q?feat:=20chatcard=20=EA=B5=AC=ED=98=84,=20?= =?UTF-8?q?=ED=95=B4=EB=8B=B9=20=EC=B1=84=ED=8C=85=EB=B0=A9=20navigate?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/chat/ChatCard.tsx | 25 +++++++++++++++++++++---- src/components/chat/ChatCardList.tsx | 3 ++- src/pages/ChattingPage.tsx | 1 + 3 files changed, 24 insertions(+), 5 deletions(-) diff --git a/src/components/chat/ChatCard.tsx b/src/components/chat/ChatCard.tsx index abd691a..a5c600d 100644 --- a/src/components/chat/ChatCard.tsx +++ b/src/components/chat/ChatCard.tsx @@ -2,20 +2,37 @@ import styled from "styled-components"; import { useNavigate } from "react-router-dom"; import { ReactComponent as Friends } from "../../assets/icons/Freinds.svg"; import { Body2, Caption1, Caption2, Heading2 } from "../../style/font"; -const ChatCard = () => { +import { useRecoilValue } from "recoil"; +import { chatRoomListState, usersState } from "../../recoil/state"; +interface ChatCardProps { + index: number; +} +const ChatCard = ({ index }: ChatCardProps) => { const navigate = useNavigate(); + const chattings = useRecoilValue(chatRoomListState); + const users = useRecoilValue(usersState); + //해당하는 채팅방의 상대방 userid + const userId = chattings[index].userList[1]; return ( { - navigate("/chat/0"); + navigate("/chat/" + index); }} >
- 신현재 - 근무 중 + {users[userId].name} + {users[userId].isWorking === "근무 중" ? ( + + {users[userId].isWorking} + + ) : ( + + {users[userId].isWorking} + + )}
회의 때 공유드린 파일 확인해보셨나요? diff --git a/src/components/chat/ChatCardList.tsx b/src/components/chat/ChatCardList.tsx index a3a1097..76de7ee 100644 --- a/src/components/chat/ChatCardList.tsx +++ b/src/components/chat/ChatCardList.tsx @@ -3,12 +3,13 @@ import ChatCard from "./ChatCard"; import { useRecoilValue } from "recoil"; import { chatRoomListState } from "../../recoil/state"; import { useNavigate } from "react-router-dom"; +// 나중에 index 말고 value로 넘겨서 order에 맞게 최신순대로 출력 const ChatCardList = () => { const chatList = useRecoilValue(chatRoomListState); return ( {chatList.map((value, index) => { - return ; + return ; })} ); diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index 9b47ad9..ae64d9b 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -13,6 +13,7 @@ import { useParams } from "react-router-dom"; import HomeIndicator from "../components/HomeIndicator"; function ChattingPage() { + //id받아서 해당 id에 해당하는 chat 찾기 let { id } = useParams(); //chatting 전체 리스트 const chatRoomList = useRecoilValue(chatRoomListState); From 927256deda8390878e24120f2164f9372373908b Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 18 Oct 2023 17:14:20 +0900 Subject: [PATCH 31/55] =?UTF-8?q?feat:=20chatcard=20=EA=B0=80=EC=9E=A5=20?= =?UTF-8?q?=EC=B5=9C=EA=B7=BC=20=EB=A9=94=EC=84=B8=EC=A7=80=20=EC=B6=9C?= =?UTF-8?q?=EB=A0=A5=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/chat/ChatCard.tsx | 13 +++++++++++-- src/components/chat/ChatCardList.tsx | 3 ++- src/recoil/state.ts | 4 ++-- 3 files changed, 15 insertions(+), 5 deletions(-) diff --git a/src/components/chat/ChatCard.tsx b/src/components/chat/ChatCard.tsx index a5c600d..6e75b70 100644 --- a/src/components/chat/ChatCard.tsx +++ b/src/components/chat/ChatCard.tsx @@ -3,7 +3,12 @@ import { useNavigate } from "react-router-dom"; import { ReactComponent as Friends } from "../../assets/icons/Freinds.svg"; import { Body2, Caption1, Caption2, Heading2 } from "../../style/font"; import { useRecoilValue } from "recoil"; -import { chatRoomListState, usersState } from "../../recoil/state"; +import { + chatListByIdState, + chatRoomListState, + usersState, +} from "../../recoil/state"; +//chatListById 값 새로 하나 들어오면 리렌더,그리고 채팅방 최신순 순서 또한 set interface ChatCardProps { index: number; } @@ -11,6 +16,9 @@ const ChatCard = ({ index }: ChatCardProps) => { const navigate = useNavigate(); const chattings = useRecoilValue(chatRoomListState); const users = useRecoilValue(usersState); + //마지막 chatting + const chatListById = useRecoilValue(chatListByIdState(index)); + const lastChat = chatListById[chatListById.length - 1]; //해당하는 채팅방의 상대방 userid const userId = chattings[index].userList[1]; return ( @@ -35,12 +43,13 @@ const ChatCard = ({ index }: ChatCardProps) => { )}
- 회의 때 공유드린 파일 확인해보셨나요? + {lastChat.message} 오전 10:24 + {/* {lastChat.date} */} ); diff --git a/src/components/chat/ChatCardList.tsx b/src/components/chat/ChatCardList.tsx index 76de7ee..ab8e8cc 100644 --- a/src/components/chat/ChatCardList.tsx +++ b/src/components/chat/ChatCardList.tsx @@ -3,7 +3,8 @@ import ChatCard from "./ChatCard"; import { useRecoilValue } from "recoil"; import { chatRoomListState } from "../../recoil/state"; import { useNavigate } from "react-router-dom"; -// 나중에 index 말고 value로 넘겨서 order에 맞게 최신순대로 출력 +// 나중에 index 말고 value로 넘겨서 order에 맞게 최신순대로 출력, order 배열 따로 만들어서 그에 맞는 +//chatcard 출력 const ChatCardList = () => { const chatList = useRecoilValue(chatRoomListState); return ( diff --git a/src/recoil/state.ts b/src/recoil/state.ts index 38a5ae9..8d1d15f 100644 --- a/src/recoil/state.ts +++ b/src/recoil/state.ts @@ -21,12 +21,12 @@ export const usersState = atom({ key: "usersState", default: userData.users, }); - +//채팅 외의 Room에 대한 정보에 사용 export const chatRoomListState = atom({ key: "chatRoomListState", default: chatData.chattings, }); - +//chatting 출력에 사용 export const chatListByIdState = atomFamily({ key: "chatListByIdState", default: (chatRoomId: number) => { From e49af8ec380e2c37e3879af8cd6a131162282d3f Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 18 Oct 2023 17:35:20 +0900 Subject: [PATCH 32/55] =?UTF-8?q?feat:=20chatCard=20=EC=8B=9C=EA=B0=84=20?= =?UTF-8?q?=EC=98=88=EC=99=B8=EC=B2=98=EB=A6=AC,=20dateForm=20=ED=8C=8C?= =?UTF-8?q?=EC=9D=BC=20=ED=95=A8=EC=88=98=20=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/chat/ChatCard.tsx | 4 ++-- src/data/chatData.json | 7 +++++++ src/utils/dateForm.ts | 31 +++++++++++++++++++++++++++++++ 3 files changed, 40 insertions(+), 2 deletions(-) diff --git a/src/components/chat/ChatCard.tsx b/src/components/chat/ChatCard.tsx index 6e75b70..76e292b 100644 --- a/src/components/chat/ChatCard.tsx +++ b/src/components/chat/ChatCard.tsx @@ -8,6 +8,7 @@ import { chatRoomListState, usersState, } from "../../recoil/state"; +import { chatCardDateFormat } from "../../utils/dateForm"; //chatListById 값 새로 하나 들어오면 리렌더,그리고 채팅방 최신순 순서 또한 set interface ChatCardProps { index: number; @@ -48,8 +49,7 @@ const ChatCard = ({ index }: ChatCardProps) => { - 오전 10:24 - {/* {lastChat.date} */} + {chatCardDateFormat(lastChat.date)} ); diff --git a/src/data/chatData.json b/src/data/chatData.json index 38bf5fe..1ff8330 100644 --- a/src/data/chatData.json +++ b/src/data/chatData.json @@ -57,6 +57,13 @@ "message": "고생하셨습니다. 부장님도 주말 잘 보내세요.", "date": "Wed Oct 7 2023 16:18:16 GMT+0900 (한국 표준시)", "like": 0 + }, + { + "chatId": 2, + "userId": 0, + "message": "혹시 어제 보내드린 자료 확인하셨나요?", + "date": "Wed Oct 17 2023 16:18:16 GMT+0900 (한국 표준시)", + "like": 0 } ] } diff --git a/src/utils/dateForm.ts b/src/utils/dateForm.ts index bdb40a3..662caa7 100644 --- a/src/utils/dateForm.ts +++ b/src/utils/dateForm.ts @@ -28,3 +28,34 @@ export const dateChangeFormat = (date: string) => { return `${dateObj.getFullYear()}년 ${dateObj.getMonth() + 1}월${" "} ${dateObj.getDate()}일 (${dayList[dateObj.getDay()]})`; }; + +export const chatCardDateFormat = (date: string) => { + const dateObj = new Date(date); + const nowDate = new Date(); + if ( + // 같은 날일때 시간출력 (오전 00:00) + dateObj.getFullYear() === nowDate.getFullYear() && + dateObj.getMonth() === nowDate.getMonth() && + dateObj.getDate() === nowDate.getDate() + ) { + return chatBubbleTime(dateObj.toString()); + } else if ( + // 어제일 때 어제 출력 (어제) + dateObj.getFullYear() === nowDate.getFullYear() && + dateObj.getMonth() === nowDate.getMonth() && + dateObj.getDate() === nowDate.getDate() - 1 + ) { + return `어제`; + } else if ( + // 같은 해일 때 날짜 출력 (00월 00일) + dateObj.getFullYear() === nowDate.getFullYear() + ) { + return `${dateObj.getMonth() + 1}월${" "}${dateObj.getDate()}일`; + } else if ( + // 다른 해일 때 년도 포함 날짜 출력 (0000.00.00) + dateObj.getFullYear() !== nowDate.getFullYear() + ) { + return `${dateObj.getFullYear()}.${" "}${dateObj.getMonth() + 1}.${" "} +${dateObj.getDate()}`; + } +}; From 35f9fa1eaa08e5a3fb0f99f6d177761f30f514e3 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Mon, 30 Oct 2023 19:21:25 +0900 Subject: [PATCH 33/55] =?UTF-8?q?feat:=20profile=20page=20header=20?= =?UTF-8?q?=EB=B0=8F=20navbar=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/chat/ChatCard.tsx | 1 - src/components/profile/ProfileHeader.tsx | 82 ++++++++++++++++++++++++ src/pages/ProfilePage.tsx | 11 ++++ 3 files changed, 93 insertions(+), 1 deletion(-) create mode 100644 src/components/profile/ProfileHeader.tsx diff --git a/src/components/chat/ChatCard.tsx b/src/components/chat/ChatCard.tsx index 76e292b..81791f5 100644 --- a/src/components/chat/ChatCard.tsx +++ b/src/components/chat/ChatCard.tsx @@ -9,7 +9,6 @@ import { usersState, } from "../../recoil/state"; import { chatCardDateFormat } from "../../utils/dateForm"; -//chatListById 값 새로 하나 들어오면 리렌더,그리고 채팅방 최신순 순서 또한 set interface ChatCardProps { index: number; } diff --git a/src/components/profile/ProfileHeader.tsx b/src/components/profile/ProfileHeader.tsx new file mode 100644 index 0000000..b9a1161 --- /dev/null +++ b/src/components/profile/ProfileHeader.tsx @@ -0,0 +1,82 @@ +import styled from "styled-components"; +import { Body1, Heading1 } from "../../style/font"; +interface ProfileHeaderProps { + favorite: boolean; + setFavorite: React.Dispatch>; +} +const ProfileHeader: React.FC = ({ + favorite, + setFavorite, +}) => { + const favoriteToggle = () => { + setFavorite(true); + }; + const allToggle = () => { + setFavorite(false); + }; + return ( + + + + 친구 + + + + + {favorite ? ( + 전체 + ) : ( + 전체 + )} + + + {favorite ? ( + 즐겨찾기 + ) : ( + 즐겨찾기 + )} + + + + ); +}; +export default ProfileHeader; +const ProfileHeaderWrapper = styled.div` + height: 6.9375rem; + display: flex; + flex-direction: column; +`; +const ProfileLogoWrapper = styled.div` + height: 4.3125rem; + display: flex; + align-items: center; + .chat-logo { + padding-left: 1.25rem; + } +`; +const ProfileNav = styled.div` + display: flex; + gap: 1.38rem; + padding-left: 1.34rem; + height: 2.5625rem; + border-bottom: solid 0.0625rem var(--gray-3); +`; +const NavAll = styled.div<{ favorite: boolean }>` + width: 2.75rem; + height: 2.5625rem; + border-bottom: solid 0.0625rem + ${(props) => (props.favorite ? "var(--gray-3)" : "var(--green)")}; + display: flex; + align-items: center; + justify-content: center; +`; +const NavFavorite = styled.div<{ favorite: boolean }>` + width: 4.75rem; + height: 2.5625rem; + border-bottom: solid 0.0625rem + ${(props) => (props.favorite ? "var(--green)" : "var(--gray-3)")}; + display: flex; + align-items: center; + justify-content: center; +`; +// border-bottom: solid 0.0625rem var(--gray-3); diff --git a/src/pages/ProfilePage.tsx b/src/pages/ProfilePage.tsx index b650c9d..694a950 100644 --- a/src/pages/ProfilePage.tsx +++ b/src/pages/ProfilePage.tsx @@ -1,12 +1,23 @@ +import styled from "styled-components"; import Footer from "../components/Footer"; import HomeIndicator from "../components/HomeIndicator"; +import ProfileHeader from "../components/profile/ProfileHeader"; +import { useState } from "react"; const ProfilePage = () => { + //즐겨찾기 toggle + const [favorite, setFavorite] = useState(false); return (
+ + + {favorite ? : null}
); }; +const Space = styled.div` + height: 3rem; +`; export default ProfilePage; From 70b80aa92bb6e5de393ebeceb64a8ab094113d1b Mon Sep 17 00:00:00 2001 From: leekyuho Date: Tue, 31 Oct 2023 12:11:42 +0900 Subject: [PATCH 34/55] =?UTF-8?q?feat:=20profile=20page=20=EA=B5=AC?= =?UTF-8?q?=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/assets/icons/Next.svg | 3 + src/components/Footer.tsx | 3 + src/components/profile/ProfileCard.tsx | 75 ++++++++++++++++++++++++ src/components/profile/ProfileHeader.tsx | 5 +- src/components/profile/ProfileList.tsx | 25 ++++++++ src/data/chatData.json | 2 +- src/data/userData.json | 38 ++++++------ src/pages/ProfilePage.tsx | 8 +-- src/style/GlobalStyle.tsx | 2 +- 9 files changed, 132 insertions(+), 29 deletions(-) create mode 100644 src/assets/icons/Next.svg create mode 100644 src/components/profile/ProfileCard.tsx create mode 100644 src/components/profile/ProfileList.tsx diff --git a/src/assets/icons/Next.svg b/src/assets/icons/Next.svg new file mode 100644 index 0000000..9a38c25 --- /dev/null +++ b/src/assets/icons/Next.svg @@ -0,0 +1,3 @@ + + + \ No newline at end of file diff --git a/src/components/Footer.tsx b/src/components/Footer.tsx index 60ad2ce..d5c5ba4 100644 --- a/src/components/Footer.tsx +++ b/src/components/Footer.tsx @@ -66,6 +66,7 @@ const PeopleIcon = styled(People)` path { ${(props) => getPeopleIconStyles(props.page)} } + cursor: pointer; `; const ChatIcon = styled(Chat)` @@ -76,6 +77,7 @@ const ChatIcon = styled(Chat)` path { ${(props) => getChatIconStyles(props.page)} } + cursor: pointer; `; const SettingIcon = styled(Setting)` padding: 0.188rem 0.216rem; @@ -85,5 +87,6 @@ const SettingIcon = styled(Setting)` path { ${(props) => getSettingIconStyles(props.page)} } + cursor: pointer; `; export default Footer; diff --git a/src/components/profile/ProfileCard.tsx b/src/components/profile/ProfileCard.tsx new file mode 100644 index 0000000..d17a043 --- /dev/null +++ b/src/components/profile/ProfileCard.tsx @@ -0,0 +1,75 @@ +import styled from "styled-components"; +import { ReactComponent as Friends } from "../../assets/icons/Freinds.svg"; +import { ReactComponent as Next } from "../../assets/icons/Next.svg"; +import { Body2, Caption1, Heading2 } from "../../style/font"; +import { useRecoilValue } from "recoil"; +import { friendsState } from "../../recoil/state"; +interface ProfileCardProps { + userIndex: number; +} +const ProfileCard = (props: ProfileCardProps) => { + const users = useRecoilValue(friendsState); + return ( + + + + +
+ + {users[props.userIndex].name} + + {users[props.userIndex].isWorking === "근무 중" ? ( + + {users[props.userIndex].isWorking} + + ) : ( + + {users[props.userIndex].isWorking} + + )} +
+ + {users[props.userIndex].company}/{users[props.userIndex].department} + /{users[props.userIndex].rank} + + +
+
+
+ ); +}; +export default ProfileCard; + +const ProfileCardWrapper = styled.div` + height: 6rem; + display: flex; + justify-content: center; + align-items: center; +`; +const ProfileContentWrapper = styled.div` + height: 3.5rem; + width: 20.9375rem; + display: flex; +`; +const ProfileContent = styled.div` + width: 16.7475rem; + display: flex; + flex-direction: column; + position: relative; + .user-info { + display: flex; + gap: 0.5rem; + } +`; +const FriendsIcon = styled(Friends)` + width: 3.5rem; + height: 3.5rem; + padding-right: 0.69rem; +`; +const NextIcon = styled(Next)` + position: absolute; + right: 0; + top: 1rem; + width: 0.625rem; + height: 1.25rem; +`; diff --git a/src/components/profile/ProfileHeader.tsx b/src/components/profile/ProfileHeader.tsx index b9a1161..44e8365 100644 --- a/src/components/profile/ProfileHeader.tsx +++ b/src/components/profile/ProfileHeader.tsx @@ -56,7 +56,7 @@ const ProfileLogoWrapper = styled.div` `; const ProfileNav = styled.div` display: flex; - gap: 1.38rem; + gap: 1rem; padding-left: 1.34rem; height: 2.5625rem; border-bottom: solid 0.0625rem var(--gray-3); @@ -69,6 +69,7 @@ const NavAll = styled.div<{ favorite: boolean }>` display: flex; align-items: center; justify-content: center; + cursor: pointer; `; const NavFavorite = styled.div<{ favorite: boolean }>` width: 4.75rem; @@ -78,5 +79,5 @@ const NavFavorite = styled.div<{ favorite: boolean }>` display: flex; align-items: center; justify-content: center; + cursor: pointer; `; -// border-bottom: solid 0.0625rem var(--gray-3); diff --git a/src/components/profile/ProfileList.tsx b/src/components/profile/ProfileList.tsx new file mode 100644 index 0000000..3c7a761 --- /dev/null +++ b/src/components/profile/ProfileList.tsx @@ -0,0 +1,25 @@ +import { useRecoilValue } from "recoil"; +import styled from "styled-components"; +import { friendsState } from "../../recoil/state"; +import ProfileCard from "./ProfileCard"; +const ProfileList: React.FC = () => { + const userList = useRecoilValue(friendsState); + return ( + + {userList.map((value, index) => { + return ; + })} + + ); +}; +export default ProfileList; + +const ProfileListWrapper = styled.div` + height: 35.8745rem; + overflow-y: auto; + scrollbar-width: none; /* Firefox */ + -ms-overflow-style: none; /* Internet Explorer/Edge */ + &::-webkit-scrollbar { + display: none; /* Chrome, Safari*/ + } +`; diff --git a/src/data/chatData.json b/src/data/chatData.json index 1ff8330..ef4de73 100644 --- a/src/data/chatData.json +++ b/src/data/chatData.json @@ -53,7 +53,7 @@ }, { "chatId": 1, - "userId": 2, + "userId": 4, "message": "고생하셨습니다. 부장님도 주말 잘 보내세요.", "date": "Wed Oct 7 2023 16:18:16 GMT+0900 (한국 표준시)", "like": 0 diff --git a/src/data/userData.json b/src/data/userData.json index 3847485..f6cf0c3 100644 --- a/src/data/userData.json +++ b/src/data/userData.json @@ -4,55 +4,55 @@ "userId": 0, "name": "신현재", "profileImage": "", - "company":"삼성전자", + "company": "삼성전자", "department": "HR", - "rank":"부장", - "isWorking":"근무 중" + "rank": "부장", + "isWorking": "근무 중" }, { "userId": 1, "name": "신낸재", "profileImage": "", - "company":"카카오뱅크", + "company": "카카오뱅크", "department": "프로덕트팀", - "rank":"팀장", - "isWorking":"퇴근" + "rank": "팀장", + "isWorking": "퇴근" }, { "userId": 2, "name": "현재", "profileImage": "", - "company":"하나은행", + "company": "하나은행", "department": "영업1팀", - "rank":"차장", - "isWorking":"퇴근" + "rank": "차장", + "isWorking": "퇴근" }, { "userId": 3, "name": "나는낸재", "profileImage": "", - "company":"제일기획", + "company": "제일기획", "department": "기획2팀", - "rank":"팀장", - "isWorking":"퇴근" + "rank": "팀장", + "isWorking": "퇴근" }, { "userId": 4, "name": "Hyunjae Shin", "profileImage": "", - "company":"삼성전자", + "company": "삼성전자", "department": "글로벌사업부", - "rank":"부장", - "isWorking":"근무 중" + "rank": "부장", + "isWorking": "근무 중" }, { "userId": 5, "name": "신현재다", "profileImage": "", - "company":"삼성전자", + "company": "삼성전자", "department": "DX", - "rank":"부장", - "isWorking":"근무 중" + "rank": "부장", + "isWorking": "근무 중" } ] -} \ No newline at end of file +} diff --git a/src/pages/ProfilePage.tsx b/src/pages/ProfilePage.tsx index 694a950..5e57bec 100644 --- a/src/pages/ProfilePage.tsx +++ b/src/pages/ProfilePage.tsx @@ -3,21 +3,17 @@ import Footer from "../components/Footer"; import HomeIndicator from "../components/HomeIndicator"; import ProfileHeader from "../components/profile/ProfileHeader"; import { useState } from "react"; +import ProfileList from "../components/profile/ProfileList"; const ProfilePage = () => { //즐겨찾기 toggle const [favorite, setFavorite] = useState(false); return (
- - {favorite ? : null} +
); }; - -const Space = styled.div` - height: 3rem; -`; export default ProfilePage; diff --git a/src/style/GlobalStyle.tsx b/src/style/GlobalStyle.tsx index c4f19a9..315d2b9 100644 --- a/src/style/GlobalStyle.tsx +++ b/src/style/GlobalStyle.tsx @@ -25,7 +25,7 @@ const GlobalStyle = createGlobalStyle` border-radius: 1.25rem; background-color : var(--black); } - .pageWrapper{ /*pageWrapper는 header footer 제외 높이*/ + .pageWrapper{ /*pageWrapper는 status bar footer 제외 높이*/ width: 23.4375rem; height: 47.8125rem; position : relative; From 690f6d6fd6746e4ddc80c725c9314289f8e122f0 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Tue, 31 Oct 2023 18:52:17 +0900 Subject: [PATCH 35/55] =?UTF-8?q?feat:=20=EC=A6=90=EA=B2=A8=EC=B0=BE?= =?UTF-8?q?=EA=B8=B0=20=EA=B8=B0=EB=8A=A5=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/assets/icons/GreenDot.svg | 3 + src/assets/icons/Star.svg | 1 + src/components/profile/ProfileCard.tsx | 78 +++++++++++++++++++++--- src/components/profile/ProfileHeader.tsx | 14 +++++ src/components/profile/ProfileList.tsx | 31 +++++++--- src/data/userData.json | 18 ++++-- src/pages/ProfilePage.tsx | 2 +- src/recoil/state.ts | 5 ++ 8 files changed, 128 insertions(+), 24 deletions(-) create mode 100644 src/assets/icons/GreenDot.svg create mode 100644 src/assets/icons/Star.svg diff --git a/src/assets/icons/GreenDot.svg b/src/assets/icons/GreenDot.svg new file mode 100644 index 0000000..65f1886 --- /dev/null +++ b/src/assets/icons/GreenDot.svg @@ -0,0 +1,3 @@ + + + \ No newline at end of file diff --git a/src/assets/icons/Star.svg b/src/assets/icons/Star.svg new file mode 100644 index 0000000..5a89317 --- /dev/null +++ b/src/assets/icons/Star.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/src/components/profile/ProfileCard.tsx b/src/components/profile/ProfileCard.tsx index d17a043..cb04d75 100644 --- a/src/components/profile/ProfileCard.tsx +++ b/src/components/profile/ProfileCard.tsx @@ -1,17 +1,57 @@ import styled from "styled-components"; +//state +import { useRecoilState, useSetRecoilState } from "recoil"; +import { friendsState, greenDotState } from "../../recoil/state"; +import { useState } from "react"; +//icons, fonts import { ReactComponent as Friends } from "../../assets/icons/Freinds.svg"; import { ReactComponent as Next } from "../../assets/icons/Next.svg"; +import { ReactComponent as Star } from "../../assets/icons/Star.svg"; import { Body2, Caption1, Heading2 } from "../../style/font"; -import { useRecoilValue } from "recoil"; -import { friendsState } from "../../recoil/state"; interface ProfileCardProps { userIndex: number; + favorite: boolean; // 현재 페이지 상태 } const ProfileCard = (props: ProfileCardProps) => { - const users = useRecoilValue(friendsState); + const [users, setUsers] = useRecoilState(friendsState); + const setGreenDot = useSetRecoilState(greenDotState); + //favorite 버튼 toggle + const [favoriteToggle, setFavoriteToggle] = useState(false); + //우클릭 시 메뉴 + const handleOnContextMenu = (e: React.MouseEvent) => { + e.preventDefault(); + setFavoriteToggle(!favoriteToggle); + }; + const handleFavoriteClick = () => { + const copy = [...users]; + if (copy[props.userIndex].favorite === 0) { + copy[props.userIndex] = { + ...copy[props.userIndex], + favorite: 1, + }; + } else if (copy[props.userIndex].favorite === 1) { + copy[props.userIndex] = { + ...copy[props.userIndex], + favorite: 0, + }; + } + //현재 즐겨찾기 상태일 때는 업데이트 점 X + if (props.favorite === false) { + setGreenDot(true); + } + setUsers(copy); + setFavoriteToggle(!favoriteToggle); + }; return ( - - + + + + + +
@@ -32,7 +72,7 @@ const ProfileCard = (props: ProfileCardProps) => { {users[props.userIndex].company}/{users[props.userIndex].department} /{users[props.userIndex].rank} - + {favoriteToggle === false ? : null} @@ -43,13 +83,19 @@ export default ProfileCard; const ProfileCardWrapper = styled.div` height: 6rem; display: flex; - justify-content: center; + justify-content: flex-start; align-items: center; + position: relative; `; -const ProfileContentWrapper = styled.div` +//transition svg 작아짐 이슈로 absolute 설정 +const ProfileContentWrapper = styled.div<{ favoriteToggle: boolean }>` + display: flex; + position: absolute; height: 3.5rem; width: 20.9375rem; - display: flex; + left: ${(props) => (props.favoriteToggle ? "6rem" : "1.25rem")}; + top: 1.25rem; + transition: left 0.3s ease; `; const ProfileContent = styled.div` width: 16.7475rem; @@ -73,3 +119,17 @@ const NextIcon = styled(Next)` width: 0.625rem; height: 1.25rem; `; +const StarIcon = styled(Star)` + width: 1.25rem; + height: 1.25rem; + color: var(--black); +`; +const FavoriteButton = styled.div<{ favoriteToggle: boolean }>` + width: ${(props) => (props.favoriteToggle === true ? "4.25rem" : "0rem")}; + height: 6rem; + background-color: var(--green); + display: flex; + justify-content: center; + align-items: center; + transition: width 0.3s ease; +`; diff --git a/src/components/profile/ProfileHeader.tsx b/src/components/profile/ProfileHeader.tsx index 44e8365..fb0f1fe 100644 --- a/src/components/profile/ProfileHeader.tsx +++ b/src/components/profile/ProfileHeader.tsx @@ -1,5 +1,8 @@ import styled from "styled-components"; +import { ReactComponent as GreenDot } from "../../assets/icons/GreenDot.svg"; import { Body1, Heading1 } from "../../style/font"; +import { useRecoilState } from "recoil"; +import { greenDotState } from "../../recoil/state"; interface ProfileHeaderProps { favorite: boolean; setFavorite: React.Dispatch>; @@ -8,7 +11,11 @@ const ProfileHeader: React.FC = ({ favorite, setFavorite, }) => { + const [greenDot, setGreenDot] = useRecoilState(greenDotState); const favoriteToggle = () => { + if (greenDot === true) { + setGreenDot(false); + } setFavorite(true); }; const allToggle = () => { @@ -35,6 +42,7 @@ const ProfileHeader: React.FC = ({ ) : ( 즐겨찾기 )} + {greenDot ? : null} @@ -80,4 +88,10 @@ const NavFavorite = styled.div<{ favorite: boolean }>` align-items: center; justify-content: center; cursor: pointer; + position: relative; +`; +const GreenDotIcon = styled(GreenDot)` + position: absolute; + top: 0.75rem; + right: 0.1rem; `; diff --git a/src/components/profile/ProfileList.tsx b/src/components/profile/ProfileList.tsx index 3c7a761..415004b 100644 --- a/src/components/profile/ProfileList.tsx +++ b/src/components/profile/ProfileList.tsx @@ -2,15 +2,30 @@ import { useRecoilValue } from "recoil"; import styled from "styled-components"; import { friendsState } from "../../recoil/state"; import ProfileCard from "./ProfileCard"; -const ProfileList: React.FC = () => { +interface ProfileListProps { + favorite: boolean; +} +const ProfileList: React.FC = ({ favorite }) => { const userList = useRecoilValue(friendsState); - return ( - - {userList.map((value, index) => { - return ; - })} - - ); + if (favorite === false) { + return ( + + {userList.map((value, index) => { + return ; + })} + + ); + } else { + return ( + + {userList.map((value, index) => + value.favorite === 1 ? ( + + ) : null + )} + + ); + } }; export default ProfileList; diff --git a/src/data/userData.json b/src/data/userData.json index f6cf0c3..3400a27 100644 --- a/src/data/userData.json +++ b/src/data/userData.json @@ -7,7 +7,8 @@ "company": "삼성전자", "department": "HR", "rank": "부장", - "isWorking": "근무 중" + "isWorking": "근무 중", + "favorite": 0 }, { "userId": 1, @@ -16,7 +17,8 @@ "company": "카카오뱅크", "department": "프로덕트팀", "rank": "팀장", - "isWorking": "퇴근" + "isWorking": "퇴근", + "favorite": 0 }, { "userId": 2, @@ -25,7 +27,8 @@ "company": "하나은행", "department": "영업1팀", "rank": "차장", - "isWorking": "퇴근" + "isWorking": "퇴근", + "favorite": 0 }, { "userId": 3, @@ -34,7 +37,8 @@ "company": "제일기획", "department": "기획2팀", "rank": "팀장", - "isWorking": "퇴근" + "isWorking": "퇴근", + "favorite": 0 }, { "userId": 4, @@ -43,7 +47,8 @@ "company": "삼성전자", "department": "글로벌사업부", "rank": "부장", - "isWorking": "근무 중" + "isWorking": "근무 중", + "favorite": 0 }, { "userId": 5, @@ -52,7 +57,8 @@ "company": "삼성전자", "department": "DX", "rank": "부장", - "isWorking": "근무 중" + "isWorking": "근무 중", + "favorite": 0 } ] } diff --git a/src/pages/ProfilePage.tsx b/src/pages/ProfilePage.tsx index 5e57bec..780492d 100644 --- a/src/pages/ProfilePage.tsx +++ b/src/pages/ProfilePage.tsx @@ -10,7 +10,7 @@ const ProfilePage = () => { return (
- +
diff --git a/src/recoil/state.ts b/src/recoil/state.ts index 8d1d15f..32160d5 100644 --- a/src/recoil/state.ts +++ b/src/recoil/state.ts @@ -36,3 +36,8 @@ export const chatListByIdState = atomFamily({ return chatRoom ? chatRoom.chatList : []; }, }); +//즐겨찾기 추가 시 초록점 생성 toggle +export const greenDotState = atom({ + key: "greenDotState", + default: false, +}); From f64a7307fca443c6341d3a8da47dc38bbfc3f71b Mon Sep 17 00:00:00 2001 From: leekyuho Date: Tue, 31 Oct 2023 22:20:56 +0900 Subject: [PATCH 36/55] =?UTF-8?q?fix:=20chatting=20user=20change=20?= =?UTF-8?q?=EB=B0=80=EB=A6=BC=20=ED=95=B4=EA=B2=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/chatting/ChattingProfile.tsx | 14 ++++++------ src/pages/ChattingPage.tsx | 24 +++++++++++++++++---- 2 files changed, 28 insertions(+), 10 deletions(-) diff --git a/src/components/chatting/ChattingProfile.tsx b/src/components/chatting/ChattingProfile.tsx index 541e680..2205ec3 100644 --- a/src/components/chatting/ChattingProfile.tsx +++ b/src/components/chatting/ChattingProfile.tsx @@ -9,7 +9,7 @@ import { useRecoilValue } from "recoil"; import styled from "styled-components"; import { useNavigate } from "react-router-dom"; interface ChattingProfileProps { - userId: number; + targetId: number; } function ChattingProfile(props: ChattingProfileProps) { const users = useRecoilValue(usersState); @@ -26,20 +26,22 @@ function ChattingProfile(props: ChattingProfileProps) { - {users[props.userId].name} + + {users[props.targetId].name} + - {users[props.userId].isWorking} + {users[props.targetId].isWorking} - {users[props.userId].company}/{users[props.userId].department}/ - {users[props.userId].rank} + {users[props.targetId].company}/{users[props.targetId].department}/ + {users[props.targetId].rank} diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index ae64d9b..359d9e0 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -23,6 +23,8 @@ function ChattingPage() { ); //채팅방 사용자 2명 const roomUsers = chatRoomList[Number(id)].userList; + //상대방 user + const [targetUserId, setTargetUserId] = useState(roomUsers[1]); //user switch 상태 const [switchUser, setSwitchUser] = useState(0); //list 길이 체크해서 빈 채팅방 or 채팅있는 채팅방 @@ -41,22 +43,36 @@ function ChattingPage() { setChatListById(JSON.parse(initializeChat)); } //페이지가 불릴 때, 현재 user도 재설정 - setNowUserId(roomUsers[switchUser]); + setNowUserId(roomUsers[0]); + setTargetUserId(roomUsers[1]); }, []); - + // useEffect(()=>{ + // setTargetUserId(roomUsers[switchUser]); + // if (switchUser === 0) { + // setSwitchUser(1); + // } else if (switchUser === 1) { + // setSwitchUser(0); + // } + // setNowUserId(roomUsers[switchUser]); + // }, [switchUser]) //0,1로 switch 하면서 채팅방 userlist의 0,1인덱스의 user로 전환 const handleUserSwitch = () => { if (switchUser === 0) { + setTargetUserId(roomUsers[0]); + setNowUserId(roomUsers[1]); setSwitchUser(1); } else if (switchUser === 1) { + setTargetUserId(roomUsers[1]); + setNowUserId(roomUsers[0]); setSwitchUser(0); } - setNowUserId(roomUsers[switchUser]); + //setNowUserId(roomUsers[switchUser]); + console.log(targetUserId, nowUserId); }; return (
- +
From dbcc44195238b541cf9a569cfeec8414e91f0ebe Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 1 Nov 2023 01:02:22 +0900 Subject: [PATCH 37/55] =?UTF-8?q?feat=20:=20profile=20page=20navigate=20?= =?UTF-8?q?=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/profile/ProfileCard.tsx | 36 ++++++++++++++++++++++---- src/pages/ChattingPage.tsx | 12 --------- src/style/GlobalStyle.tsx | 2 +- 3 files changed, 32 insertions(+), 18 deletions(-) diff --git a/src/components/profile/ProfileCard.tsx b/src/components/profile/ProfileCard.tsx index cb04d75..1894c43 100644 --- a/src/components/profile/ProfileCard.tsx +++ b/src/components/profile/ProfileCard.tsx @@ -1,19 +1,28 @@ import styled from "styled-components"; -//state -import { useRecoilState, useSetRecoilState } from "recoil"; -import { friendsState, greenDotState } from "../../recoil/state"; -import { useState } from "react"; +//react, recoil +import { useRecoilState, useRecoilValue, useSetRecoilState } from "recoil"; +import { + chatRoomListState, + friendsState, + greenDotState, +} from "../../recoil/state"; +import { useRef, useState } from "react"; //icons, fonts import { ReactComponent as Friends } from "../../assets/icons/Freinds.svg"; import { ReactComponent as Next } from "../../assets/icons/Next.svg"; import { ReactComponent as Star } from "../../assets/icons/Star.svg"; import { Body2, Caption1, Heading2 } from "../../style/font"; +import { useNavigate } from "react-router-dom"; interface ProfileCardProps { userIndex: number; favorite: boolean; // 현재 페이지 상태 } const ProfileCard = (props: ProfileCardProps) => { + const navigate = useNavigate(); + const chatList = useRecoilValue(chatRoomListState); + //사용자 제외 친구 list const [users, setUsers] = useRecoilState(friendsState); + //즐겨찾기 추가 시 dot const setGreenDot = useSetRecoilState(greenDotState); //favorite 버튼 toggle const [favoriteToggle, setFavoriteToggle] = useState(false); @@ -22,6 +31,7 @@ const ProfileCard = (props: ProfileCardProps) => { e.preventDefault(); setFavoriteToggle(!favoriteToggle); }; + //즐겨찾기 click const handleFavoriteClick = () => { const copy = [...users]; if (copy[props.userIndex].favorite === 0) { @@ -42,6 +52,19 @@ const ProfileCard = (props: ProfileCardProps) => { setUsers(copy); setFavoriteToggle(!favoriteToggle); }; + //navigate + //friend index에 해당하는 채팅으로 navigate + const handleNavigate = () => { + const chatNumber = chatList.findIndex( + (chatRoom) => chatRoom.userList[1] === props.userIndex + ); + if (chatNumber === -1) { + alert("채팅 없음 미구현"); + } else { + navigate("/chat/" + chatNumber); + } + }; + return ( { {users[props.userIndex].company}/{users[props.userIndex].department} /{users[props.userIndex].rank} - {favoriteToggle === false ? : null} + {favoriteToggle === false ? ( + + ) : null} @@ -118,6 +143,7 @@ const NextIcon = styled(Next)` top: 1rem; width: 0.625rem; height: 1.25rem; + cursor: pointer; `; const StarIcon = styled(Star)` width: 1.25rem; diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index 359d9e0..b0a20a3 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -46,16 +46,6 @@ function ChattingPage() { setNowUserId(roomUsers[0]); setTargetUserId(roomUsers[1]); }, []); - // useEffect(()=>{ - // setTargetUserId(roomUsers[switchUser]); - // if (switchUser === 0) { - // setSwitchUser(1); - // } else if (switchUser === 1) { - // setSwitchUser(0); - // } - // setNowUserId(roomUsers[switchUser]); - // }, [switchUser]) - //0,1로 switch 하면서 채팅방 userlist의 0,1인덱스의 user로 전환 const handleUserSwitch = () => { if (switchUser === 0) { setTargetUserId(roomUsers[0]); @@ -66,8 +56,6 @@ function ChattingPage() { setNowUserId(roomUsers[0]); setSwitchUser(0); } - //setNowUserId(roomUsers[switchUser]); - console.log(targetUserId, nowUserId); }; return (
diff --git a/src/style/GlobalStyle.tsx b/src/style/GlobalStyle.tsx index 315d2b9..486ed1c 100644 --- a/src/style/GlobalStyle.tsx +++ b/src/style/GlobalStyle.tsx @@ -30,6 +30,6 @@ const GlobalStyle = createGlobalStyle` height: 47.8125rem; position : relative; } + } `; - export default GlobalStyle; From 5c0ffea79e38b598c20807fb7e1add63a1afd0c7 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 1 Nov 2023 01:08:02 +0900 Subject: [PATCH 38/55] =?UTF-8?q?chore=20:=20=EB=B0=98=EC=9D=91=ED=98=95?= =?UTF-8?q?=20=ED=85=8C=EC=8A=A4=ED=8A=B8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/style/GlobalStyle.tsx | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/style/GlobalStyle.tsx b/src/style/GlobalStyle.tsx index 486ed1c..e3193cc 100644 --- a/src/style/GlobalStyle.tsx +++ b/src/style/GlobalStyle.tsx @@ -21,15 +21,16 @@ const GlobalStyle = createGlobalStyle` } .mainWrapper{ width: 23.4375rem; - height: 50.75rem; + height: 40.75rem; border-radius: 1.25rem; background-color : var(--black); } .pageWrapper{ /*pageWrapper는 status bar footer 제외 높이*/ width: 23.4375rem; - height: 47.8125rem; + height: 37.8125rem; position : relative; } } + `; export default GlobalStyle; From 94db1c69f125e6170b0470097be5488238bf82ea Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 1 Nov 2023 01:15:46 +0900 Subject: [PATCH 39/55] =?UTF-8?q?chore=20:=20=EB=B0=98=EC=9D=91=ED=98=95?= =?UTF-8?q?=20test?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/style/GlobalStyle.tsx | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/src/style/GlobalStyle.tsx b/src/style/GlobalStyle.tsx index e3193cc..8d94208 100644 --- a/src/style/GlobalStyle.tsx +++ b/src/style/GlobalStyle.tsx @@ -21,16 +21,24 @@ const GlobalStyle = createGlobalStyle` } .mainWrapper{ width: 23.4375rem; - height: 40.75rem; + height: 50.75rem; border-radius: 1.25rem; background-color : var(--black); } .pageWrapper{ /*pageWrapper는 status bar footer 제외 높이*/ width: 23.4375rem; - height: 37.8125rem; + height: 47.8125rem; position : relative; } } + @media (max-width: 768px) { + .mainWrapper { + height: 42.75rem; + } + .pageWrapper { + height: 39.8125rem; + } + } `; export default GlobalStyle; From 09efb03ab37a3557c6972825bf7d12a7ebd3cb3b Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 1 Nov 2023 01:35:17 +0900 Subject: [PATCH 40/55] =?UTF-8?q?fix=20:=20=EB=B0=98=EC=9D=91=ED=98=95=20?= =?UTF-8?q?=EC=A7=A4=EB=A6=BC=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/style/GlobalStyle.tsx | 12 +++++------- 1 file changed, 5 insertions(+), 7 deletions(-) diff --git a/src/style/GlobalStyle.tsx b/src/style/GlobalStyle.tsx index 8d94208..ae0bfe0 100644 --- a/src/style/GlobalStyle.tsx +++ b/src/style/GlobalStyle.tsx @@ -31,14 +31,12 @@ const GlobalStyle = createGlobalStyle` position : relative; } } - @media (max-width: 768px) { - .mainWrapper { - height: 42.75rem; - } - - .pageWrapper { - height: 39.8125rem; + @media (max-width: 768px) { /* 모바일 화면 크기에 따라 조정 */ + body { + transform: scale(0.9); /* 모바일 화면에서 90% 크기로 축소 */ + transform-origin: center; } } `; + export default GlobalStyle; From 5e1645b7daf3f86a93da1b088187620d8c04dc42 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 1 Nov 2023 01:59:01 +0900 Subject: [PATCH 41/55] =?UTF-8?q?fix=20:=20media-query=20=EC=88=98?= =?UTF-8?q?=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/style/GlobalStyle.tsx | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-) diff --git a/src/style/GlobalStyle.tsx b/src/style/GlobalStyle.tsx index ae0bfe0..6a04ff8 100644 --- a/src/style/GlobalStyle.tsx +++ b/src/style/GlobalStyle.tsx @@ -15,6 +15,10 @@ const GlobalStyle = createGlobalStyle` justify-content: center; align-items: center; font-family: 'Pretendard-Regular'; + @media (max-width: 768px) { + transform: scale(0.9); + transform-origin: center; + } } input{ outline: none; @@ -31,12 +35,6 @@ const GlobalStyle = createGlobalStyle` position : relative; } } - @media (max-width: 768px) { /* 모바일 화면 크기에 따라 조정 */ - body { - transform: scale(0.9); /* 모바일 화면에서 90% 크기로 축소 */ - transform-origin: center; - } - } `; export default GlobalStyle; From 915dbb2b4ced8b64a46d7b69ea9a5a99415bedd9 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 1 Nov 2023 02:27:43 +0900 Subject: [PATCH 42/55] =?UTF-8?q?fix:=20profile=EC=97=90=EC=84=9C=20chatti?= =?UTF-8?q?ng=20mapping=20=EC=98=A4=EB=A5=98=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/profile/ProfileCard.tsx | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/components/profile/ProfileCard.tsx b/src/components/profile/ProfileCard.tsx index 1894c43..b82296f 100644 --- a/src/components/profile/ProfileCard.tsx +++ b/src/components/profile/ProfileCard.tsx @@ -56,8 +56,9 @@ const ProfileCard = (props: ProfileCardProps) => { //friend index에 해당하는 채팅으로 navigate const handleNavigate = () => { const chatNumber = chatList.findIndex( - (chatRoom) => chatRoom.userList[1] === props.userIndex + (chatRoom) => chatRoom.userList[1] === props.userIndex + 1 ); + console.log(chatNumber); if (chatNumber === -1) { alert("채팅 없음 미구현"); } else { From 43352fe11a8007bdc4b2b34986bf2239524c138f Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 1 Nov 2023 02:28:16 +0900 Subject: [PATCH 43/55] =?UTF-8?q?test:=20dummy=20data=20=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/data/chatData.json | 61 ++++++++++++++++++++++++++++++++++++++++++ src/recoil/state.ts | 2 +- 2 files changed, 62 insertions(+), 1 deletion(-) diff --git a/src/data/chatData.json b/src/data/chatData.json index ef4de73..8830d0c 100644 --- a/src/data/chatData.json +++ b/src/data/chatData.json @@ -66,6 +66,67 @@ "like": 0 } ] + }, + { + "chatRoomId": 3, + "userList": [0, 1], + "chatList": [ + { + "chatId": 0, + "userId": 0, + "message": "오늘 정말 고생하셨습니다.", + "date": "Thu Sep 22 2022 19:18:14 GMT+0900 (한국 표준시)", + "like": 0 + }, + { + "chatId": 1, + "userId": 1, + "message": "네, 고생하셨습니다. 조심해서 들어가세요.", + "date": "Thu Sep 22 2022 19:34:16 GMT+0900 (한국 표준시)", + "like": 0 + }, + { + "chatId": 2, + "userId": 0, + "message": "혹시 오늘 점심에 통화 가능하신가요?", + "date": "Fri Sep 23 2022 09:22:16 GMT+0900 (한국 표준시)", + "like": 0 + }, + { + "chatId": 3, + "userId": 1, + "message": "네, 가능합니다.", + "date": "Fri Sep 23 2022 09:24:16 GMT+0900 (한국 표준시)", + "like": 0 + } + ] + }, + { + "chatRoomId": 4, + "userList": [0, 5], + "chatList": [ + { + "chatId": 0, + "userId": 5, + "message": "이만 퇴근해보겠습니다.", + "date": "Tue Jul 12 2022 18:20:14 GMT+0900 (한국 표준시)", + "like": 0 + }, + { + "chatId": 1, + "userId": 0, + "message": "네, 부장님 나이스", + "date": "Tue Jul 12 2022 18:37:16 GMT+0900 (한국 표준시)", + "like": 0 + }, + { + "chatId": 2, + "userId": 5, + "message": "부탁드린 자료 준비 되었을까요?", + "date": "Wed Jul 13 2022 10:32:16 GMT+0900 (한국 표준시)", + "like": 0 + } + ] } ] } diff --git a/src/recoil/state.ts b/src/recoil/state.ts index 32160d5..ba45240 100644 --- a/src/recoil/state.ts +++ b/src/recoil/state.ts @@ -1,4 +1,4 @@ -import { atom, atomFamily, selector, selectorFamily } from "recoil"; +import { atom, atomFamily } from "recoil"; import userData from "../data/userData.json"; import chatData from "../data/chatData.json"; //현재 login한 user,나머지 user list, chattingRoom list From e55114ef6c8050d025366cb5245536049d55e452 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 1 Nov 2023 12:35:32 +0900 Subject: [PATCH 44/55] =?UTF-8?q?feat:=20=EC=A2=8B=EC=95=84=EC=9A=94=20?= =?UTF-8?q?=EA=B8=B0=EB=8A=A5=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/assets/icons/Liked.svg | 4 ++ src/assets/icons/NotLiked.svg | 4 ++ src/components/chatting/ChatBubble.tsx | 69 ++++++++++++++++++++++-- src/components/chatting/ChattingRoom.tsx | 5 ++ src/components/chatting/LikeButton.tsx | 46 +++++++++++++++- src/data/chatData.json | 4 +- 6 files changed, 125 insertions(+), 7 deletions(-) create mode 100644 src/assets/icons/Liked.svg create mode 100644 src/assets/icons/NotLiked.svg diff --git a/src/assets/icons/Liked.svg b/src/assets/icons/Liked.svg new file mode 100644 index 0000000..01dd007 --- /dev/null +++ b/src/assets/icons/Liked.svg @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/src/assets/icons/NotLiked.svg b/src/assets/icons/NotLiked.svg new file mode 100644 index 0000000..bed0f60 --- /dev/null +++ b/src/assets/icons/NotLiked.svg @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/src/components/chatting/ChatBubble.tsx b/src/components/chatting/ChatBubble.tsx index cb11533..349451b 100644 --- a/src/components/chatting/ChatBubble.tsx +++ b/src/components/chatting/ChatBubble.tsx @@ -1,23 +1,73 @@ +//style import styled from "styled-components"; import "../../style/color.css"; import { Body2, Caption2 } from "../../style/font"; +import { ReactComponent as Liked } from "../../assets/icons/Liked.svg"; +//components import { chatBubbleTime } from "../../utils/dateForm"; +import { LikeButton } from "./LikeButton"; +import { useState } from "react"; +import { useRecoilState } from "recoil"; +import { chatListByIdState } from "../../recoil/state"; + interface ChatBubbleProps { isMyChat: boolean; message: string; chatDate: string; + isLiked: number; + index: number; + roomId: number; } function ChatBubble(props: ChatBubbleProps) { + const [likeToggle, setLikeToggle] = useState(false); + //좋아요 정보 변경 + const [chatList, setChatList] = useRecoilState( + chatListByIdState(props.roomId) + ); + //더블클릭 시 좋아요 이벤트 + const handleDoubleClick = (e: React.MouseEvent) => { + e.preventDefault(); + setLikeToggle(!likeToggle); + }; + const handleLikeClick = () => { + console.log("like!"); + const copy = [...chatList]; + if (chatList[props.index].like === 0) { + copy[props.index] = { + ...copy[props.index], + like: 1, + }; + } else if (chatList[props.index].like === 1) { + copy[props.index] = { + ...copy[props.index], + like: 0, + }; + } + setChatList(copy); + setLikeToggle(!likeToggle); + }; + return ( - +
{chatBubbleTime(props.chatDate)} + {chatList[props.index].like === 1 ? ( + + ) : null} {props.message}
+ {likeToggle ? ( +
+ +
+ ) : null}
); } @@ -31,17 +81,24 @@ const ChatBubbleContainer = styled.div<{ isMyChat: boolean }>` flex-direction: ${(props) => (props.isMyChat ? "row" : "row-reverse")}; align-items: flex-end; gap: 0.3125rem; + position: relative; } .writeTime { margin-bottom: 0.625rem; } + /*더블클릭 선택 막기*/ + user-select: none; /* standard syntax */ + -webkit-user-select: none; /* webkit (safari, chrome) browsers */ + -moz-user-select: none; /* mozilla browsers */ + -khtml-user-select: none; /* webkit (konqueror) browsers */ + -ms-user-select: none; /* IE10+ */ `; const ChatBox = styled.div<{ isMyChat: boolean }>` - /*display: inline-block;*/ background-color: ${(props) => props.isMyChat ? "var(--green)" : "var(--gray-1)"}; max-width: 16.8125rem; width: fit-content; + position: relative; word-break: break-all; border-radius: 1.5rem; margin: ${(props) => @@ -53,5 +110,11 @@ const ChatText = styled(Body2)<{ isMyChat: boolean }>` color: ${(props) => (props.isMyChat ? "var(--gray-1)" : "var(--gray-7)")}; padding: 0.625rem 1.25rem; `; - +const MessageLike = styled(Liked)<{ isMyChat: boolean }>` + position: absolute; + ${(props) => (props.isMyChat ? "left:-0.1rem" : "right:-0.1rem")}; + bottom: 0rem; + width: 1.25rem; + height: 1.25rem; +`; export default ChatBubble; diff --git a/src/components/chatting/ChattingRoom.tsx b/src/components/chatting/ChattingRoom.tsx index edae697..88c9e87 100644 --- a/src/components/chatting/ChattingRoom.tsx +++ b/src/components/chatting/ChattingRoom.tsx @@ -1,7 +1,9 @@ +//style import styled from "styled-components"; import "../../style/color.css"; import { ReactComponent as EmptyChat } from "../../assets/icons/EmptyChat.svg"; import { Caption1, Body2 } from "../../style/font"; +//component import { useEffect, useRef } from "react"; import ChatBubble from "./ChatBubble"; import { useRecoilValue } from "recoil"; @@ -63,6 +65,9 @@ function ChattingRoom(props: ChattingProps) { isMyChat={chatList[index].userId === nowUser} message={chatList[index].message} chatDate={chatList[index].date} + isLiked={chatList[index].like} + index={index} + roomId={props.chatRoomId} /> ); diff --git a/src/components/chatting/LikeButton.tsx b/src/components/chatting/LikeButton.tsx index 610c68d..844ad24 100644 --- a/src/components/chatting/LikeButton.tsx +++ b/src/components/chatting/LikeButton.tsx @@ -1,3 +1,45 @@ -export const LikeButton = () => { - return <>; +import styled from "styled-components"; +import { ReactComponent as Liked } from "../../assets/icons/Liked.svg"; +import { ReactComponent as NotLiked } from "../../assets/icons/NotLiked.svg"; +import { Caption1 } from "../../style/font"; + +interface LikeButtonProps { + isMyChat: boolean; + isLiked: number; +} +export const LikeButton = (props: LikeButtonProps) => { + if (props.isLiked === 1) { + return ( + + + 취소 + + ); + } else { + return ( + + + 좋아요 + + ); + } }; + +const LikeButtonWrapper = styled.div<{ isMyChat: boolean; isLiked: boolean }>` + width: ${(props) => (props.isLiked ? "4.125rem" : "4.875rem")}; + height: 1.625rem; + border-radius: 6.25rem; + background-color: #d9d9d9; + ${(props) => + props.isMyChat ? "margin-right : 1.25rem" : "margin-left : 1.25rem"}; + display: flex; + align-items: center; + gap: 0.25rem; + + /*더블클릭 선택 막기*/ + user-select: none; /* standard syntax */ + -webkit-user-select: none; /* webkit (safari, chrome) browsers */ + -moz-user-select: none; /* mozilla browsers */ + -khtml-user-select: none; /* webkit (konqueror) browsers */ + -ms-user-select: none; /* IE10+ */ +`; diff --git a/src/data/chatData.json b/src/data/chatData.json index 8830d0c..cd7e5e7 100644 --- a/src/data/chatData.json +++ b/src/data/chatData.json @@ -55,14 +55,14 @@ "chatId": 1, "userId": 4, "message": "고생하셨습니다. 부장님도 주말 잘 보내세요.", - "date": "Wed Oct 7 2023 16:18:16 GMT+0900 (한국 표준시)", + "date": "Wed Oct 7 2023 19:07:16 GMT+0900 (한국 표준시)", "like": 0 }, { "chatId": 2, "userId": 0, "message": "혹시 어제 보내드린 자료 확인하셨나요?", - "date": "Wed Oct 17 2023 16:18:16 GMT+0900 (한국 표준시)", + "date": "Wed Oct 17 2023 13:18:16 GMT+0900 (한국 표준시)", "like": 0 } ] From 8904080da6d02f558a3b0fec2f66fcc211e6795d Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 1 Nov 2023 12:40:29 +0900 Subject: [PATCH 45/55] =?UTF-8?q?refactor=20:=20import=20=EC=A3=BC?= =?UTF-8?q?=EC=84=9D=EC=B2=98=EB=A6=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/Footer.tsx | 2 ++ src/components/HomeIndicator.tsx | 1 + src/components/StatusBar.tsx | 1 + src/components/chat/ChatCard.tsx | 4 +++- src/components/chat/ChatCardList.tsx | 3 ++- src/components/chat/ChatSearch.tsx | 2 ++ src/components/chatting/ChattingInput.tsx | 4 +++- src/components/chatting/ChattingProfile.tsx | 4 +++- src/components/chatting/LikeButton.tsx | 1 + src/components/profile/ProfileCard.tsx | 13 +++++++------ src/components/profile/ProfileHeader.tsx | 2 ++ src/components/profile/ProfileList.tsx | 4 +++- 12 files changed, 30 insertions(+), 11 deletions(-) diff --git a/src/components/Footer.tsx b/src/components/Footer.tsx index d5c5ba4..5bec0b8 100644 --- a/src/components/Footer.tsx +++ b/src/components/Footer.tsx @@ -1,7 +1,9 @@ +//style import styled from "styled-components"; import { ReactComponent as People } from "../assets/icons/People.svg"; import { ReactComponent as Chat } from "../assets/icons/Chat.svg"; import { ReactComponent as Setting } from "../assets/icons/Setting.svg"; +//component import { Navigate, useNavigate } from "react-router-dom"; interface FooterProps { page: string; diff --git a/src/components/HomeIndicator.tsx b/src/components/HomeIndicator.tsx index 1d1a20c..fa112c3 100644 --- a/src/components/HomeIndicator.tsx +++ b/src/components/HomeIndicator.tsx @@ -1,3 +1,4 @@ +//style import { ReactComponent as HomeBar } from "../assets/iphone/HomeBar.svg"; import styled from "styled-components"; interface HomeIndicatorProps { diff --git a/src/components/StatusBar.tsx b/src/components/StatusBar.tsx index c737388..bc216c5 100644 --- a/src/components/StatusBar.tsx +++ b/src/components/StatusBar.tsx @@ -1,3 +1,4 @@ +//style import { ReactComponent as Battery } from "../assets/iphone/Battery.svg"; import { ReactComponent as Clock } from "../assets/iphone/Clock.svg"; import { ReactComponent as Signal } from "../assets/iphone/Signal.svg"; diff --git a/src/components/chat/ChatCard.tsx b/src/components/chat/ChatCard.tsx index 81791f5..25e8975 100644 --- a/src/components/chat/ChatCard.tsx +++ b/src/components/chat/ChatCard.tsx @@ -1,7 +1,9 @@ +//style import styled from "styled-components"; -import { useNavigate } from "react-router-dom"; import { ReactComponent as Friends } from "../../assets/icons/Freinds.svg"; import { Body2, Caption1, Caption2, Heading2 } from "../../style/font"; +//component +import { useNavigate } from "react-router-dom"; import { useRecoilValue } from "recoil"; import { chatListByIdState, diff --git a/src/components/chat/ChatCardList.tsx b/src/components/chat/ChatCardList.tsx index ab8e8cc..5f3afd6 100644 --- a/src/components/chat/ChatCardList.tsx +++ b/src/components/chat/ChatCardList.tsx @@ -1,8 +1,9 @@ +//style import styled from "styled-components"; +//component import ChatCard from "./ChatCard"; import { useRecoilValue } from "recoil"; import { chatRoomListState } from "../../recoil/state"; -import { useNavigate } from "react-router-dom"; // 나중에 index 말고 value로 넘겨서 order에 맞게 최신순대로 출력, order 배열 따로 만들어서 그에 맞는 //chatcard 출력 const ChatCardList = () => { diff --git a/src/components/chat/ChatSearch.tsx b/src/components/chat/ChatSearch.tsx index 548631c..44f97d3 100644 --- a/src/components/chat/ChatSearch.tsx +++ b/src/components/chat/ChatSearch.tsx @@ -1,5 +1,7 @@ +//style import styled from "styled-components"; import { ReactComponent as Search } from "../../assets/icons/Search.svg"; +//component import { useState } from "react"; const ChatSearch = () => { const [input, setInput] = useState(""); diff --git a/src/components/chatting/ChattingInput.tsx b/src/components/chatting/ChattingInput.tsx index 032d2a9..a79fda1 100644 --- a/src/components/chatting/ChattingInput.tsx +++ b/src/components/chatting/ChattingInput.tsx @@ -1,8 +1,10 @@ -import { useState } from "react"; +//style import { ReactComponent as Plus } from "../../assets/icons/Plus.svg"; import { ReactComponent as Send } from "../../assets/icons/Send.svg"; import styled from "styled-components"; import { Body2 } from "../../style/font"; +//component +import { useState } from "react"; import { chatListByIdState, chatRoomListState, diff --git a/src/components/chatting/ChattingProfile.tsx b/src/components/chatting/ChattingProfile.tsx index 2205ec3..9aad88e 100644 --- a/src/components/chatting/ChattingProfile.tsx +++ b/src/components/chatting/ChattingProfile.tsx @@ -1,12 +1,14 @@ +//style import { ReactComponent as Back } from "../../assets/icons/Back.svg"; import { ReactComponent as Call } from "../../assets/icons/Call.svg"; import { ReactComponent as Friends } from "../../assets/icons/Freinds.svg"; import { ReactComponent as More } from "../../assets/icons/More.svg"; import { Heading2, Caption1 } from "../../style/font"; import "../../style/color.css"; +import styled from "styled-components"; +//component import { usersState } from "../../recoil/state"; import { useRecoilValue } from "recoil"; -import styled from "styled-components"; import { useNavigate } from "react-router-dom"; interface ChattingProfileProps { targetId: number; diff --git a/src/components/chatting/LikeButton.tsx b/src/components/chatting/LikeButton.tsx index 844ad24..48c3b60 100644 --- a/src/components/chatting/LikeButton.tsx +++ b/src/components/chatting/LikeButton.tsx @@ -1,3 +1,4 @@ +//style import styled from "styled-components"; import { ReactComponent as Liked } from "../../assets/icons/Liked.svg"; import { ReactComponent as NotLiked } from "../../assets/icons/NotLiked.svg"; diff --git a/src/components/profile/ProfileCard.tsx b/src/components/profile/ProfileCard.tsx index b82296f..f9e1430 100644 --- a/src/components/profile/ProfileCard.tsx +++ b/src/components/profile/ProfileCard.tsx @@ -1,5 +1,10 @@ +//style +import { ReactComponent as Friends } from "../../assets/icons/Freinds.svg"; +import { ReactComponent as Next } from "../../assets/icons/Next.svg"; +import { ReactComponent as Star } from "../../assets/icons/Star.svg"; +import { Body2, Caption1, Heading2 } from "../../style/font"; import styled from "styled-components"; -//react, recoil +//component import { useRecoilState, useRecoilValue, useSetRecoilState } from "recoil"; import { chatRoomListState, @@ -7,12 +12,8 @@ import { greenDotState, } from "../../recoil/state"; import { useRef, useState } from "react"; -//icons, fonts -import { ReactComponent as Friends } from "../../assets/icons/Freinds.svg"; -import { ReactComponent as Next } from "../../assets/icons/Next.svg"; -import { ReactComponent as Star } from "../../assets/icons/Star.svg"; -import { Body2, Caption1, Heading2 } from "../../style/font"; import { useNavigate } from "react-router-dom"; + interface ProfileCardProps { userIndex: number; favorite: boolean; // 현재 페이지 상태 diff --git a/src/components/profile/ProfileHeader.tsx b/src/components/profile/ProfileHeader.tsx index fb0f1fe..02c646b 100644 --- a/src/components/profile/ProfileHeader.tsx +++ b/src/components/profile/ProfileHeader.tsx @@ -1,6 +1,8 @@ +//style import styled from "styled-components"; import { ReactComponent as GreenDot } from "../../assets/icons/GreenDot.svg"; import { Body1, Heading1 } from "../../style/font"; +//component import { useRecoilState } from "recoil"; import { greenDotState } from "../../recoil/state"; interface ProfileHeaderProps { diff --git a/src/components/profile/ProfileList.tsx b/src/components/profile/ProfileList.tsx index 415004b..05b8122 100644 --- a/src/components/profile/ProfileList.tsx +++ b/src/components/profile/ProfileList.tsx @@ -1,5 +1,7 @@ -import { useRecoilValue } from "recoil"; +//style import styled from "styled-components"; +//component +import { useRecoilValue } from "recoil"; import { friendsState } from "../../recoil/state"; import ProfileCard from "./ProfileCard"; interface ProfileListProps { From 9da37228824669ef82433759a7242f662284c69f Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 1 Nov 2023 17:07:22 +0900 Subject: [PATCH 46/55] =?UTF-8?q?feat:=20setting=20page=20=EA=B5=AC?= =?UTF-8?q?=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/assets/icons/{Freinds.svg => Friends.svg} | 0 src/assets/icons/Pencil.svg | 4 + src/components/chat/ChatCard.tsx | 2 +- src/components/chatting/ChatBubble.tsx | 1 - src/components/chatting/ChattingProfile.tsx | 2 +- src/components/profile/ProfileCard.tsx | 25 ++++++- src/components/setting/MyProfile.tsx | 37 ++++++++++ src/components/setting/SettingHeader.tsx | 26 +++++++ src/components/setting/SettingLink.tsx | 74 +++++++++++++++++++ src/pages/SettingPage.tsx | 7 ++ 10 files changed, 172 insertions(+), 6 deletions(-) rename src/assets/icons/{Freinds.svg => Friends.svg} (100%) create mode 100644 src/assets/icons/Pencil.svg create mode 100644 src/components/setting/MyProfile.tsx create mode 100644 src/components/setting/SettingHeader.tsx create mode 100644 src/components/setting/SettingLink.tsx diff --git a/src/assets/icons/Freinds.svg b/src/assets/icons/Friends.svg similarity index 100% rename from src/assets/icons/Freinds.svg rename to src/assets/icons/Friends.svg diff --git a/src/assets/icons/Pencil.svg b/src/assets/icons/Pencil.svg new file mode 100644 index 0000000..cde659e --- /dev/null +++ b/src/assets/icons/Pencil.svg @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/src/components/chat/ChatCard.tsx b/src/components/chat/ChatCard.tsx index 25e8975..d53aa38 100644 --- a/src/components/chat/ChatCard.tsx +++ b/src/components/chat/ChatCard.tsx @@ -1,6 +1,6 @@ //style import styled from "styled-components"; -import { ReactComponent as Friends } from "../../assets/icons/Freinds.svg"; +import { ReactComponent as Friends } from "../../assets/icons/Friends.svg"; import { Body2, Caption1, Caption2, Heading2 } from "../../style/font"; //component import { useNavigate } from "react-router-dom"; diff --git a/src/components/chatting/ChatBubble.tsx b/src/components/chatting/ChatBubble.tsx index 349451b..8f0064a 100644 --- a/src/components/chatting/ChatBubble.tsx +++ b/src/components/chatting/ChatBubble.tsx @@ -30,7 +30,6 @@ function ChatBubble(props: ChatBubbleProps) { setLikeToggle(!likeToggle); }; const handleLikeClick = () => { - console.log("like!"); const copy = [...chatList]; if (chatList[props.index].like === 0) { copy[props.index] = { diff --git a/src/components/chatting/ChattingProfile.tsx b/src/components/chatting/ChattingProfile.tsx index 9aad88e..b223774 100644 --- a/src/components/chatting/ChattingProfile.tsx +++ b/src/components/chatting/ChattingProfile.tsx @@ -1,7 +1,7 @@ //style import { ReactComponent as Back } from "../../assets/icons/Back.svg"; import { ReactComponent as Call } from "../../assets/icons/Call.svg"; -import { ReactComponent as Friends } from "../../assets/icons/Freinds.svg"; +import { ReactComponent as Friends } from "../../assets/icons/Friends.svg"; import { ReactComponent as More } from "../../assets/icons/More.svg"; import { Heading2, Caption1 } from "../../style/font"; import "../../style/color.css"; diff --git a/src/components/profile/ProfileCard.tsx b/src/components/profile/ProfileCard.tsx index f9e1430..d958c87 100644 --- a/src/components/profile/ProfileCard.tsx +++ b/src/components/profile/ProfileCard.tsx @@ -1,5 +1,5 @@ //style -import { ReactComponent as Friends } from "../../assets/icons/Freinds.svg"; +import { ReactComponent as Friends } from "../../assets/icons/Friends.svg"; import { ReactComponent as Next } from "../../assets/icons/Next.svg"; import { ReactComponent as Star } from "../../assets/icons/Star.svg"; import { Body2, Caption1, Heading2 } from "../../style/font"; @@ -66,9 +66,28 @@ const ProfileCard = (props: ProfileCardProps) => { navigate("/chat/" + chatNumber); } }; - + //모바일 터치 슬라이드 구현 + const touchStartX = useRef(null); + const handleTouchStart = (e: React.TouchEvent) => { + touchStartX.current = e.touches[0].clientX; + }; + const handleTouchEnd = (e: React.TouchEvent) => { + if (touchStartX.current) { + const touchEndX = e.changedTouches[0].clientX; + //X 움직인거리 + const moveX = touchEndX - touchStartX.current; + if (moveX > 50) { + setFavoriteToggle(!favoriteToggle); + } + touchStartX.current = null; + } + }; return ( - + { + const user = useRecoilValue(loginUserState); + return ( + + + {user.name} + + {user.company}/{user.department}/{user.rank} + + 010-1234-5678 + + ); +}; +export default MyProfile; +const MyProfileWrapper = styled.div` + display: flex; + height: 14.438rem; + width: 23.4375rem; + flex-direction: column; + align-items: center; + & > ${Heading1} { + margin: 0.935rem 0 0.625rem 0; + } + border-bottom: solid 0.0625rem var(--gray-3); +`; +const PeopleIcon = styled(People)` + width: 7.4375rem; + height: 7.4375rem; +`; diff --git a/src/components/setting/SettingHeader.tsx b/src/components/setting/SettingHeader.tsx new file mode 100644 index 0000000..b9ffdfb --- /dev/null +++ b/src/components/setting/SettingHeader.tsx @@ -0,0 +1,26 @@ +//style +import styled from "styled-components"; +import { Heading1 } from "../../style/font"; +import { ReactComponent as Pencil } from "../../assets/icons/Pencil.svg"; +const SettingHeader = () => { + return ( + + 내 프로필 + + + ); +}; +export default SettingHeader; + +const SettingHeaderWrapper = styled.div` + height: 4.3125rem; + display: flex; + justify-content: space-between; + align-items: center; + & :first-child { + padding-left: 1.25rem; + } + & :last-child { + padding-right: 1.26rem; + } +`; diff --git a/src/components/setting/SettingLink.tsx b/src/components/setting/SettingLink.tsx new file mode 100644 index 0000000..4135be7 --- /dev/null +++ b/src/components/setting/SettingLink.tsx @@ -0,0 +1,74 @@ +//style +import styled from "styled-components"; +import { Body1 } from "../../style/font"; +import { ReactComponent as Next } from "../../assets/icons/Next.svg"; +const SettingLink = () => { + return ( + + + 명함 + + + + SNS + + + 인스타그램 + + + + 이메일 + + + + 홈페이지 + + + + ); +}; +export default SettingLink; +const SettingLinkWrapper = styled.div` + display: flex; + flex-direction: column; + height: 24rem; +`; +const NextIcon = styled(Next)` + padding: 0.25rem 0.56rem 0.25rem 0.56rem; +`; +const BussinessCard = styled.div` + display: flex; + height: 3.75rem; + width: 23.4375rem; + justify-content: space-between; + align-items: center; + margin-top: 0.3125rem; + & > ${Body1} { + margin-left: 1.25rem; + } + & > ${NextIcon} { + margin-right: 0.69rem; + } +`; +const SNSHeader = styled.div` + height: 4.19rem; + width: 22.1875rem; + display: flex; + justify-content: flex-start; + align-items: center; + padding-top: 0.5rem; + margin-left: 1.25rem; +`; +const SNSLink = styled.div` + height: 3.75rem; + display: flex; + width: 23.4375rem; + justify-content: space-between; + align-items: center; + & > ${Body1} { + margin-left: 1.25rem; + } + & > ${NextIcon} { + margin-right: 0.69rem; + } +`; diff --git a/src/pages/SettingPage.tsx b/src/pages/SettingPage.tsx index aae50a0..b28c28a 100644 --- a/src/pages/SettingPage.tsx +++ b/src/pages/SettingPage.tsx @@ -1,8 +1,15 @@ +//component import Footer from "../components/Footer"; import HomeIndicator from "../components/HomeIndicator"; +import MyProfile from "../components/setting/MyProfile"; +import SettingHeader from "../components/setting/SettingHeader"; +import SettingLink from "../components/setting/SettingLink"; const SettingPage = () => { return (
+ + +
From bbef77c8e1654fdc5391b7feb6a0042807fcfac2 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 1 Nov 2023 17:45:15 +0900 Subject: [PATCH 47/55] =?UTF-8?q?feat:=20touch=20slide=20=EA=B5=AC?= =?UTF-8?q?=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/profile/ProfileCard.tsx | 8 +++++++- src/components/profile/ProfileList.tsx | 2 ++ 2 files changed, 9 insertions(+), 1 deletion(-) diff --git a/src/components/profile/ProfileCard.tsx b/src/components/profile/ProfileCard.tsx index d958c87..012a563 100644 --- a/src/components/profile/ProfileCard.tsx +++ b/src/components/profile/ProfileCard.tsx @@ -77,7 +77,13 @@ const ProfileCard = (props: ProfileCardProps) => { //X 움직인거리 const moveX = touchEndX - touchStartX.current; if (moveX > 50) { - setFavoriteToggle(!favoriteToggle); + if (favoriteToggle === false) { + setFavoriteToggle(!favoriteToggle); + } + } else if (moveX < -50) { + if (favoriteToggle === true) { + setFavoriteToggle(!favoriteToggle); + } } touchStartX.current = null; } diff --git a/src/components/profile/ProfileList.tsx b/src/components/profile/ProfileList.tsx index 05b8122..987f661 100644 --- a/src/components/profile/ProfileList.tsx +++ b/src/components/profile/ProfileList.tsx @@ -39,4 +39,6 @@ const ProfileListWrapper = styled.div` &::-webkit-scrollbar { display: none; /* Chrome, Safari*/ } + overflow-x: hidden; `; +//즐겨찾기 버튼 좌우 스크롤 방지 From 88173b882397dc8293cd26b31f6f8ca387e87b01 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 1 Nov 2023 21:01:36 +0900 Subject: [PATCH 48/55] =?UTF-8?q?fix:=20=EB=A9=94=EC=84=B8=EC=A7=80=20?= =?UTF-8?q?=EC=9E=85=EB=A0=A5=20placeholder=20=EC=9C=84=EC=B9=98=20?= =?UTF-8?q?=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/chat/ChatSearch.tsx | 1 - src/components/chatting/ChattingInput.tsx | 3 ++- src/components/chatting/ChattingRoom.tsx | 1 + src/components/profile/ProfileCard.tsx | 2 +- 4 files changed, 4 insertions(+), 3 deletions(-) diff --git a/src/components/chat/ChatSearch.tsx b/src/components/chat/ChatSearch.tsx index 44f97d3..b044701 100644 --- a/src/components/chat/ChatSearch.tsx +++ b/src/components/chat/ChatSearch.tsx @@ -5,7 +5,6 @@ import { ReactComponent as Search } from "../../assets/icons/Search.svg"; import { useState } from "react"; const ChatSearch = () => { const [input, setInput] = useState(""); - const handleSubmit = (e: React.FormEvent) => { e.preventDefault(); if (input.trim() !== "") { diff --git a/src/components/chatting/ChattingInput.tsx b/src/components/chatting/ChattingInput.tsx index a79fda1..a3dbcc5 100644 --- a/src/components/chatting/ChattingInput.tsx +++ b/src/components/chatting/ChattingInput.tsx @@ -77,6 +77,7 @@ function ChattingInput(props: ChattingInputProps) { ); } + const ChattingInputWrapper = styled.div` width: 23.4375rem; height: 3.6875rem; @@ -85,7 +86,7 @@ const ChattingInputWrapper = styled.div` .placeHolder { pointer-events: none; /*input이 묻히기 때문에 제외*/ position: absolute; - top: 1.56rem; + top: 1.69rem; left: 4.38rem; } `; diff --git a/src/components/chatting/ChattingRoom.tsx b/src/components/chatting/ChattingRoom.tsx index 88c9e87..ecf0028 100644 --- a/src/components/chatting/ChattingRoom.tsx +++ b/src/components/chatting/ChattingRoom.tsx @@ -21,6 +21,7 @@ function ChattingRoom(props: ChattingProps) { //chat 추가 되면 scroll 밑으로 const scrollRef = useRef(null); //chat 추가되면 scroll 내리고, localstorage 저장 + //마지막 채팅 시간 순으로 정렬 useEffect(() => { if (scrollRef.current) { scrollRef.current.scrollTop = scrollRef.current.scrollHeight; diff --git a/src/components/profile/ProfileCard.tsx b/src/components/profile/ProfileCard.tsx index 012a563..4664274 100644 --- a/src/components/profile/ProfileCard.tsx +++ b/src/components/profile/ProfileCard.tsx @@ -54,7 +54,7 @@ const ProfileCard = (props: ProfileCardProps) => { setFavoriteToggle(!favoriteToggle); }; //navigate - //friend index에 해당하는 채팅으로 navigate + //friend index가 상대방인 채팅으로 navigate const handleNavigate = () => { const chatNumber = chatList.findIndex( (chatRoom) => chatRoom.userList[1] === props.userIndex + 1 From 1d5e96cd8f002d4b0096a50bec4a3a7b42f3c431 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 1 Nov 2023 21:57:11 +0900 Subject: [PATCH 49/55] =?UTF-8?q?refactor=20:=20=EC=83=81=EB=8C=80?= =?UTF-8?q?=EB=B0=A9=20profile=20flex=EB=A1=9C=20=EB=A6=AC=ED=8C=A9?= =?UTF-8?q?=ED=86=A0=EB=A7=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/chatting/ChattingProfile.tsx | 29 ++++++++------------- src/pages/ChattingPage.tsx | 9 ++++--- 2 files changed, 17 insertions(+), 21 deletions(-) diff --git a/src/components/chatting/ChattingProfile.tsx b/src/components/chatting/ChattingProfile.tsx index b223774..5a17728 100644 --- a/src/components/chatting/ChattingProfile.tsx +++ b/src/components/chatting/ChattingProfile.tsx @@ -12,6 +12,7 @@ import { useRecoilValue } from "recoil"; import { useNavigate } from "react-router-dom"; interface ChattingProfileProps { targetId: number; + onUserSwitch: () => void; } function ChattingProfile(props: ChattingProfileProps) { const users = useRecoilValue(usersState); @@ -24,9 +25,7 @@ function ChattingProfile(props: ChattingProfileProps) { }} /> - - - + {users[props.targetId].name} @@ -46,54 +45,48 @@ function ChattingProfile(props: ChattingProfileProps) { {users[props.targetId].rank} + + ); } const ChattingProfileWrapper = styled.div` - position: relative; width: 22.1875rem; height: 3rem; padding: 0.5rem 0.625rem; + display: flex; + align-items: center; `; const StyledBack = styled(Back)` - position: absolute; width: 0.625rem; height: 1.25rem; padding: 0.25rem 0.625rem; - left: 0.625rem; - top: 1.19rem; + cursor: pointer; &:hover { color: #ffffff; filter: brightness(300%); } `; const StyledFriends = styled(Friends)` - position: absolute; width: 3rem; height: 3rem; - left: 3.56rem; - top: 0.5rem; + margin-left: 1.06rem; `; const StyledCall = styled(Call)` - position: absolute; width: 1.125rem; height: 1.125rem; padding: 0.3125rem; - right: 3.375rem; - top: 1.125rem; `; const StyledMore = styled(More)` - position: absolute; - right: 0.625rem; - top: 1.125rem; + margin-left: 0.625rem; `; const UserInfoWrapper = styled.div` - position: absolute; - left: 7.06rem; + width: 11.25rem; padding-top: 0.2rem; display: flex; flex-direction: column; align-items: flex-start; /*왼쪽으로 정렬*/ + margin-left: 0.5rem; `; const UserWrapper = styled.div` display: flex; diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index b0a20a3..c300187 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -59,9 +59,12 @@ function ChattingPage() { }; return (
-
- -
+ {/*
*/} + + {/*
*/} From 13a9768be791401ed4f2569ecdd83fa594880b98 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 1 Nov 2023 22:24:55 +0900 Subject: [PATCH 50/55] =?UTF-8?q?feat:=20=EB=A7=81=ED=81=AC=20=EC=97=B0?= =?UTF-8?q?=EA=B2=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/App.tsx | 5 +++-- src/assets/icons/Instagram.svg | 1 + src/assets/icons/Link.svg | 3 +++ src/components/setting/SettingLink.tsx | 22 ++++++++++++++++++++-- 4 files changed, 27 insertions(+), 4 deletions(-) create mode 100644 src/assets/icons/Instagram.svg create mode 100644 src/assets/icons/Link.svg diff --git a/src/App.tsx b/src/App.tsx index 77b49ca..7707245 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -1,11 +1,12 @@ +//style import GlobalStyle from "./style/GlobalStyle"; +import "./style/color.css"; +//component import ChattingPage from "./pages/ChattingPage"; import StatusBar from "./components/StatusBar"; -import HomeIndicator from "./components/HomeIndicator"; import { Routes, Route } from "react-router-dom"; import ChatPage from "./pages/ChatPage"; import ProfilePage from "./pages/ProfilePage"; -import "./style/color.css"; import SettingPage from "./pages/SettingPage"; function App() { return ( diff --git a/src/assets/icons/Instagram.svg b/src/assets/icons/Instagram.svg new file mode 100644 index 0000000..9b0ca8c --- /dev/null +++ b/src/assets/icons/Instagram.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/src/assets/icons/Link.svg b/src/assets/icons/Link.svg new file mode 100644 index 0000000..fd15e73 --- /dev/null +++ b/src/assets/icons/Link.svg @@ -0,0 +1,3 @@ + + + \ No newline at end of file diff --git a/src/components/setting/SettingLink.tsx b/src/components/setting/SettingLink.tsx index 4135be7..565adf5 100644 --- a/src/components/setting/SettingLink.tsx +++ b/src/components/setting/SettingLink.tsx @@ -1,8 +1,11 @@ //style import styled from "styled-components"; import { Body1 } from "../../style/font"; +import { ReactComponent as Link } from "../../assets/icons/Link.svg"; import { ReactComponent as Next } from "../../assets/icons/Next.svg"; const SettingLink = () => { + const designerUrl = "https://www.instagram.com/naenzae_/"; + const developerUrl = "https://www.instagram.com/2_95k/"; return ( @@ -14,11 +17,19 @@ const SettingLink = () => { 인스타그램 - + { + window.open(designerUrl); + }} + /> 이메일 - + { + window.open(developerUrl); + }} + /> 홈페이지 @@ -33,6 +44,10 @@ const SettingLinkWrapper = styled.div` flex-direction: column; height: 24rem; `; +const LinkIcon = styled(Link)` + padding: 0.25rem 0.25rem 0.25rem 0.56rem; + cursor: pointer; +`; const NextIcon = styled(Next)` padding: 0.25rem 0.56rem 0.25rem 0.56rem; `; @@ -68,6 +83,9 @@ const SNSLink = styled.div` & > ${Body1} { margin-left: 1.25rem; } + & > ${LinkIcon} { + margin-right: 0.69rem; + } & > ${NextIcon} { margin-right: 0.69rem; } From 2f635d3141ede697b90c6ac1f8b06ec326250aeb Mon Sep 17 00:00:00 2001 From: leekyuho Date: Wed, 1 Nov 2023 22:30:43 +0900 Subject: [PATCH 51/55] =?UTF-8?q?fix:=20=EB=AA=A8=EB=B0=94=EC=9D=BC=20chat?= =?UTF-8?q?=20profile=20=EA=B9=A8=EC=A7=90=20fix?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/chatting/ChattingProfile.tsx | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/components/chatting/ChattingProfile.tsx b/src/components/chatting/ChattingProfile.tsx index 5a17728..3077438 100644 --- a/src/components/chatting/ChattingProfile.tsx +++ b/src/components/chatting/ChattingProfile.tsx @@ -78,10 +78,10 @@ const StyledCall = styled(Call)` padding: 0.3125rem; `; const StyledMore = styled(More)` - margin-left: 0.625rem; + margin-left: 0.31rem; `; const UserInfoWrapper = styled.div` - width: 11.25rem; + width: 12.25rem; padding-top: 0.2rem; display: flex; flex-direction: column; From b1f3269e207751ec8a706942203b7c6696fadf25 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Fri, 3 Nov 2023 13:44:26 +0900 Subject: [PATCH 52/55] =?UTF-8?q?feat:=20=EA=B2=80=EC=83=89=20=EA=B8=B0?= =?UTF-8?q?=EB=8A=A5=20=EA=B5=AC=ED=98=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/chat/ChatCardList.tsx | 43 ++++++++++++++++++++++------ src/components/chat/ChatSearch.tsx | 5 ++-- src/data/chatData.json | 4 +-- src/pages/ChatPage.tsx | 1 + src/recoil/state.ts | 5 ++++ 5 files changed, 46 insertions(+), 12 deletions(-) diff --git a/src/components/chat/ChatCardList.tsx b/src/components/chat/ChatCardList.tsx index 5f3afd6..153f11b 100644 --- a/src/components/chat/ChatCardList.tsx +++ b/src/components/chat/ChatCardList.tsx @@ -3,18 +3,45 @@ import styled from "styled-components"; //component import ChatCard from "./ChatCard"; import { useRecoilValue } from "recoil"; -import { chatRoomListState } from "../../recoil/state"; +import { + chatRoomListState, + nameSearchState, + usersState, +} from "../../recoil/state"; // 나중에 index 말고 value로 넘겨서 order에 맞게 최신순대로 출력, order 배열 따로 만들어서 그에 맞는 //chatcard 출력 const ChatCardList = () => { const chatList = useRecoilValue(chatRoomListState); - return ( - - {chatList.map((value, index) => { - return ; - })} - - ); + const searchInput = useRecoilValue(nameSearchState); + const users = useRecoilValue(usersState); + const input = useRecoilValue(nameSearchState); + //검색 이름에 해당하는 card 만 true return + const nameSearch = (userId: number) => { + if (users[userId].name.includes(input)) { + return true; + } else { + return false; + } + }; + if (searchInput === "") { + return ( + + {chatList.map((value, index) => { + return ; + })} + + ); + } else { + return ( + + {chatList.map((value, index) => { + return nameSearch(value.userList[1]) ? ( + + ) : null; + })} + + ); + } }; export default ChatCardList; diff --git a/src/components/chat/ChatSearch.tsx b/src/components/chat/ChatSearch.tsx index b044701..940b0ca 100644 --- a/src/components/chat/ChatSearch.tsx +++ b/src/components/chat/ChatSearch.tsx @@ -3,8 +3,10 @@ import styled from "styled-components"; import { ReactComponent as Search } from "../../assets/icons/Search.svg"; //component import { useState } from "react"; +import { useRecoilState } from "recoil"; +import { nameSearchState } from "../../recoil/state"; const ChatSearch = () => { - const [input, setInput] = useState(""); + const [input, setInput] = useRecoilState(nameSearchState); const handleSubmit = (e: React.FormEvent) => { e.preventDefault(); if (input.trim() !== "") { @@ -13,7 +15,6 @@ const ChatSearch = () => { }; const handleOnChange = (e: React.ChangeEvent) => { setInput(e.target.value); - console.log(input); }; return ( diff --git a/src/data/chatData.json b/src/data/chatData.json index cd7e5e7..0d66d80 100644 --- a/src/data/chatData.json +++ b/src/data/chatData.json @@ -8,14 +8,14 @@ "chatId": 0, "userId": 0, "message": "오늘 회의가 다음주로 미뤄졌다고 하네요", - "date": "Thu Sep 28 2023 09:41:56 GMT+0900 (한국 표준시)", + "date": "Thu Nov 2 2023 09:41:56 GMT+0900 (한국 표준시)", "like": 0 }, { "chatId": 1, "userId": 3, "message": "그럼 오늘은 일찍 퇴근합시다", - "date": "Thu Sep 28 2023 10:31:42 GMT+0900 (한국 표준시)", + "date": "Thu Nov 2 2023 10:31:42 GMT+0900 (한국 표준시)", "like": 0 } ] diff --git a/src/pages/ChatPage.tsx b/src/pages/ChatPage.tsx index d0ca18c..f74d68c 100644 --- a/src/pages/ChatPage.tsx +++ b/src/pages/ChatPage.tsx @@ -5,6 +5,7 @@ import HomeIndicator from "../components/HomeIndicator"; import Footer from "../components/Footer"; const ChatPage = () => { //const roomList = useRecoilState(chatRoomListState); + return (
diff --git a/src/recoil/state.ts b/src/recoil/state.ts index ba45240..d2e4b33 100644 --- a/src/recoil/state.ts +++ b/src/recoil/state.ts @@ -41,3 +41,8 @@ export const greenDotState = atom({ key: "greenDotState", default: false, }); +//이름 찾기 input +export const nameSearchState = atom({ + key: "nameSearchState", + default: "", +}); From 7a3fe456178a89ad7d8e29521f41e087f741523f Mon Sep 17 00:00:00 2001 From: leekyuho Date: Fri, 3 Nov 2023 13:50:51 +0900 Subject: [PATCH 53/55] =?UTF-8?q?chore:=20=EB=B6=88=ED=95=84=EC=9A=94?= =?UTF-8?q?=ED=95=9C=20=EC=84=A0=EC=96=B8=20=EC=A0=95=EB=A6=AC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/chat/ChatSearch.tsx | 1 - src/components/chatting/ChattingInput.tsx | 6 +----- src/pages/ChattingPage.tsx | 6 ++---- src/pages/ProfilePage.tsx | 1 - 4 files changed, 3 insertions(+), 11 deletions(-) diff --git a/src/components/chat/ChatSearch.tsx b/src/components/chat/ChatSearch.tsx index 940b0ca..4bdb77f 100644 --- a/src/components/chat/ChatSearch.tsx +++ b/src/components/chat/ChatSearch.tsx @@ -2,7 +2,6 @@ import styled from "styled-components"; import { ReactComponent as Search } from "../../assets/icons/Search.svg"; //component -import { useState } from "react"; import { useRecoilState } from "recoil"; import { nameSearchState } from "../../recoil/state"; const ChatSearch = () => { diff --git a/src/components/chatting/ChattingInput.tsx b/src/components/chatting/ChattingInput.tsx index a3dbcc5..74453f8 100644 --- a/src/components/chatting/ChattingInput.tsx +++ b/src/components/chatting/ChattingInput.tsx @@ -5,11 +5,7 @@ import styled from "styled-components"; import { Body2 } from "../../style/font"; //component import { useState } from "react"; -import { - chatListByIdState, - chatRoomListState, - nowUserIdState, -} from "../../recoil/state"; +import { chatListByIdState, nowUserIdState } from "../../recoil/state"; import { useRecoilState, useRecoilValue } from "recoil"; interface ChattingInputProps { chatRoomId: number; diff --git a/src/pages/ChattingPage.tsx b/src/pages/ChattingPage.tsx index c300187..51d915a 100644 --- a/src/pages/ChattingPage.tsx +++ b/src/pages/ChattingPage.tsx @@ -3,7 +3,7 @@ import ChattingInput from "../components/chatting/ChattingInput"; import ChattingProfile from "../components/chatting/ChattingProfile"; import styled from "styled-components"; import { useState, useEffect } from "react"; -import { useRecoilState, useRecoilValue } from "recoil"; +import { useRecoilState, useRecoilValue, useSetRecoilState } from "recoil"; import { chatListByIdState, chatRoomListState, @@ -27,10 +27,8 @@ function ChattingPage() { const [targetUserId, setTargetUserId] = useState(roomUsers[1]); //user switch 상태 const [switchUser, setSwitchUser] = useState(0); - //list 길이 체크해서 빈 채팅방 or 채팅있는 채팅방 - const chatList = chatRoomList[Number(id)].chatList; //현재 사용중인 user의 id(login user 아님) - const [nowUserId, setNowUserId] = useRecoilState(nowUserIdState); + const setNowUserId = useSetRecoilState(nowUserIdState); //localstorage에 없으면 json 파일 저장, 있으면 chatList 불러옴 const initializeChat = localStorage.getItem("chat" + String(Number(id))); useEffect(() => { diff --git a/src/pages/ProfilePage.tsx b/src/pages/ProfilePage.tsx index 780492d..c2426c7 100644 --- a/src/pages/ProfilePage.tsx +++ b/src/pages/ProfilePage.tsx @@ -1,4 +1,3 @@ -import styled from "styled-components"; import Footer from "../components/Footer"; import HomeIndicator from "../components/HomeIndicator"; import ProfileHeader from "../components/profile/ProfileHeader"; From ad7c8a945c80aa0f28022dacc3abbbc0d23b5c16 Mon Sep 17 00:00:00 2001 From: leekyuho Date: Fri, 3 Nov 2023 16:16:28 +0900 Subject: [PATCH 54/55] =?UTF-8?q?chore:=20=EC=A6=90=EA=B2=A8=EC=B0=BE?= =?UTF-8?q?=EA=B8=B0=20=EB=B2=84=ED=8A=BC=20cursor=20=ED=8F=AC=EC=9D=B8?= =?UTF-8?q?=ED=84=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/chatting/ChattingRoom.tsx | 1 - src/components/profile/ProfileCard.tsx | 1 + 2 files changed, 1 insertion(+), 1 deletion(-) diff --git a/src/components/chatting/ChattingRoom.tsx b/src/components/chatting/ChattingRoom.tsx index ecf0028..88c9e87 100644 --- a/src/components/chatting/ChattingRoom.tsx +++ b/src/components/chatting/ChattingRoom.tsx @@ -21,7 +21,6 @@ function ChattingRoom(props: ChattingProps) { //chat 추가 되면 scroll 밑으로 const scrollRef = useRef(null); //chat 추가되면 scroll 내리고, localstorage 저장 - //마지막 채팅 시간 순으로 정렬 useEffect(() => { if (scrollRef.current) { scrollRef.current.scrollTop = scrollRef.current.scrollHeight; diff --git a/src/components/profile/ProfileCard.tsx b/src/components/profile/ProfileCard.tsx index 4664274..d921e0c 100644 --- a/src/components/profile/ProfileCard.tsx +++ b/src/components/profile/ProfileCard.tsx @@ -185,4 +185,5 @@ const FavoriteButton = styled.div<{ favoriteToggle: boolean }>` justify-content: center; align-items: center; transition: width 0.3s ease; + cursor: pointer; `; From 3bc8e05a9d91810103eb28462235d18e13cd834b Mon Sep 17 00:00:00 2001 From: leekyuho Date: Fri, 3 Nov 2023 16:37:30 +0900 Subject: [PATCH 55/55] =?UTF-8?q?refactor:=20placeholder=20=EC=BB=A4?= =?UTF-8?q?=EC=8A=A4=ED=85=80=20=ED=9B=85=20=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/chatting/ChattingInput.tsx | 27 ++++++++++----------- src/utils/usePlaceholder.tsx | 29 +++++++++++++++++++++++ 2 files changed, 42 insertions(+), 14 deletions(-) create mode 100644 src/utils/usePlaceholder.tsx diff --git a/src/components/chatting/ChattingInput.tsx b/src/components/chatting/ChattingInput.tsx index 74453f8..57e9ab6 100644 --- a/src/components/chatting/ChattingInput.tsx +++ b/src/components/chatting/ChattingInput.tsx @@ -7,6 +7,7 @@ import { Body2 } from "../../style/font"; import { useState } from "react"; import { chatListByIdState, nowUserIdState } from "../../recoil/state"; import { useRecoilState, useRecoilValue } from "recoil"; +import useInputPlaceholder from "../../utils/usePlaceholder"; interface ChattingInputProps { chatRoomId: number; } @@ -18,22 +19,22 @@ interface ChatInfo { like: number; } function ChattingInput(props: ChattingInputProps) { - const [typeMessage, setTypeMessage] = useState("메세지를 입력하세요"); - const [input, setInput] = useState(""); //현재 사용 user ID const nowUser = useRecoilValue(nowUserIdState); const [chatList, setChatList] = useRecoilState( chatListByIdState(props.chatRoomId) ); - //메세지창에 메세지 없을 때만 placeholder 출력 - const handleFocus = () => { - setTypeMessage(""); - }; - const handleBlur = () => { - if (input.trim() === "") { - setTypeMessage("메세지를 입력하세요"); - } - }; + //placeholder custom hook + const { + typeMessage, + setTypeMessage, + input, + setInput, + handleFocus, + handleBlur, + handleOnChange, + } = useInputPlaceholder(); + const handleSubmit = (e: any) => { e.preventDefault(); if (input.trim() !== "") { @@ -50,9 +51,7 @@ function ChattingInput(props: ChattingInputProps) { setInput(""); } }; - const handleOnChange = (e: any) => { - setInput(e.target.value); - }; + return ( diff --git a/src/utils/usePlaceholder.tsx b/src/utils/usePlaceholder.tsx new file mode 100644 index 0000000..b620385 --- /dev/null +++ b/src/utils/usePlaceholder.tsx @@ -0,0 +1,29 @@ +import { useState } from "react"; + +const useInputPlaceholder = () => { + const [typeMessage, setTypeMessage] = useState("메세지를 입력하세요"); + const [input, setInput] = useState(""); + + const handleFocus = () => { + setTypeMessage(""); + }; + const handleBlur = () => { + if (input.trim() === "") { + setTypeMessage("메세지를 입력하세요"); + } + }; + const handleOnChange = (e: any) => { + setInput(e.target.value); + }; + + return { + typeMessage, + setTypeMessage, + input, + setInput, + handleFocus, + handleBlur, + handleOnChange, + }; +}; +export default useInputPlaceholder;