From 055b9c3df2feaaf58b12382ad80251a074540348 Mon Sep 17 00:00:00 2001 From: eunwoo-levi Date: Mon, 8 Jul 2024 22:46:39 +0900 Subject: [PATCH 1/7] first commit --- .env | 0 api/socketio.ts | 27 + app/page.tsx | 7 +- components/chat/client.tsx | 49 ++ components/chat/socket.ts | 5 + components/page/AccountForm.tsx | 1 - next.config.js | 4 + package-lock.json | 990 +++++++++++++++++++++++++++++++- package.json | 28 +- server.ts | 36 ++ 10 files changed, 1109 insertions(+), 38 deletions(-) create mode 100644 .env create mode 100644 api/socketio.ts create mode 100644 components/chat/client.tsx create mode 100644 components/chat/socket.ts create mode 100644 next.config.js create mode 100644 server.ts diff --git a/.env b/.env new file mode 100644 index 0000000..e69de29 diff --git a/api/socketio.ts b/api/socketio.ts new file mode 100644 index 0000000..8c8cded --- /dev/null +++ b/api/socketio.ts @@ -0,0 +1,27 @@ +import { Server as NetServer } from 'http' +import { NextApiRequest } from 'next' +import { Server as SocketIOServer } from 'socket.io' + + +export default function SocketHandler(req: NextApiRequest, res: any) { + if (res.socket.server.io) { + console.log('Socket is already running') + } else { + console.log('Socket is initializing') + const httpServer: NetServer = res.socket.server as any + const io = new SocketIOServer(httpServer, { + path: '/api/socketio', + }) + res.socket.server.io = io + + io.on('connection', (socket) => { + console.log('New client connected') + + socket.on('chat-message', (msg: { user: string; text: string }) => { + // 모든 클라이언트에게 메시지를 브로드캐스트 + io.emit('chat-message', msg) + }) + }) + } + res.end() +} \ No newline at end of file diff --git a/app/page.tsx b/app/page.tsx index 35da5aa..6fea3dc 100644 --- a/app/page.tsx +++ b/app/page.tsx @@ -1,9 +1,14 @@ +import Chat from "@/components/chat/client"; + export default function Home() { return (
Item 1
-
Item 2
+
+ 실시간 채팅 + +
Item 3
diff --git a/components/chat/client.tsx b/components/chat/client.tsx new file mode 100644 index 0000000..212e74b --- /dev/null +++ b/components/chat/client.tsx @@ -0,0 +1,49 @@ +"use client"; + +import { useEffect, useState } from "react"; +import { socket } from "../chat/socket"; + +export default function Chat() { + const [isConnected, setIsConnected] = useState(false); + const [transport, setTransport] = useState("N/A"); + + useEffect(() => { + console.log("Initializing socket connection"); + + function onConnect() { + console.log("Connected to server"); + setIsConnected(true); + setTransport(socket.io.engine.transport.name); + + socket.io.engine.on("upgrade", (transport: any) => { + console.log("Transport upgraded:", transport.name); + setTransport(transport.name); + }); + } + + function onDisconnect() { + console.log("Disconnected from server"); + setIsConnected(false); + setTransport("N/A"); + } + + socket.on("connect", onConnect); + socket.on("disconnect", onDisconnect); + socket.on("connect_error", (err) => { + console.error("Connection error:", err); + }); + + return () => { + socket.off("connect", onConnect); + socket.off("disconnect", onDisconnect); + socket.off("connect_error"); + }; + }, []); + + return ( +
+

Status: {isConnected ? "connected" : "disconnected"}

+

Transport: {transport}

+
+ ); +} diff --git a/components/chat/socket.ts b/components/chat/socket.ts new file mode 100644 index 0000000..2f43610 --- /dev/null +++ b/components/chat/socket.ts @@ -0,0 +1,5 @@ +"use client"; + +import { io } from "socket.io-client"; + +export const socket = io("http://localhost:3000"); \ No newline at end of file diff --git a/components/page/AccountForm.tsx b/components/page/AccountForm.tsx index 385e073..1d439fd 100644 --- a/components/page/AccountForm.tsx +++ b/components/page/AccountForm.tsx @@ -1,4 +1,3 @@ -import Link from "next/link"; import Input from "./Input"; import NewAccount from "./NewAccount"; diff --git a/next.config.js b/next.config.js new file mode 100644 index 0000000..658404a --- /dev/null +++ b/next.config.js @@ -0,0 +1,4 @@ +/** @type {import('next').NextConfig} */ +const nextConfig = {}; + +module.exports = nextConfig; diff --git a/package-lock.json b/package-lock.json index 39257c9..e56c731 100644 --- a/package-lock.json +++ b/package-lock.json @@ -7,19 +7,27 @@ "": { "name": "frontend", "version": "0.1.0", + "license": "ISC", "dependencies": { + "cors": "^2.8.5", + "express": "^4.19.2", + "http": "^0.0.1-security", "next": "14.2.4", "react": "^18", - "react-dom": "^18" + "react-dom": "^18", + "socket.io": "^4.7.5", + "socket.io-client": "^4.7.5" }, "devDependencies": { - "@types/node": "^20", + "@types/node": "^20.14.10", "@types/react": "^18", "@types/react-dom": "^18", + "@types/socket.io": "^3.0.2", "eslint": "^8", "eslint-config-next": "14.2.4", "postcss": "^8", "tailwindcss": "^3.4.1", + "ts-node": "^10.9.2", "typescript": "^5" } }, @@ -35,6 +43,30 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/@cspotcode/source-map-support": { + "version": "0.8.1", + "resolved": "https://registry.npmjs.org/@cspotcode/source-map-support/-/source-map-support-0.8.1.tgz", + "integrity": "sha512-IchNf6dN4tHoMFIn/7OE8LWZ19Y6q/67Bmf6vnGREv8RSbBVb9LPJxEcnwrcwX6ixSvaiGoomAUvu4YSxXrVgw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@jridgewell/trace-mapping": "0.3.9" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/@cspotcode/source-map-support/node_modules/@jridgewell/trace-mapping": { + "version": "0.3.9", + "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.9.tgz", + "integrity": "sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@jridgewell/resolve-uri": "^3.0.3", + "@jridgewell/sourcemap-codec": "^1.4.10" + } + }, "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", @@ -418,6 +450,12 @@ "integrity": "sha512-qC/xYId4NMebE6w/V33Fh9gWxLgURiNYgVNObbJl2LZv0GUUItCcCqC5axQSwRaAgaxl2mELq1rMzlswaQ0Zxg==", "dev": true }, + "node_modules/@socket.io/component-emitter": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/@socket.io/component-emitter/-/component-emitter-3.1.2.tgz", + "integrity": "sha512-9BCxFwvbGg/RsZK9tjXd8s4UcwR0MWeFQ1XEKIQVVvAGJyINdrqKMcTRyLoK8Rse1GjzLV9cwjWV1olXRWEXVA==", + "license": "MIT" + }, "node_modules/@swc/counter": { "version": "0.1.3", "resolved": "https://registry.npmjs.org/@swc/counter/-/counter-0.1.3.tgz", @@ -432,6 +470,49 @@ "tslib": "^2.4.0" } }, + "node_modules/@tsconfig/node10": { + "version": "1.0.11", + "resolved": "https://registry.npmjs.org/@tsconfig/node10/-/node10-1.0.11.tgz", + "integrity": "sha512-DcRjDCujK/kCk/cUe8Xz8ZSpm8mS3mNNpta+jGCA6USEDfktlNvm1+IuZ9eTcDbNk41BHwpHHeW+N1lKCz4zOw==", + "dev": true, + "license": "MIT" + }, + "node_modules/@tsconfig/node12": { + "version": "1.0.11", + "resolved": "https://registry.npmjs.org/@tsconfig/node12/-/node12-1.0.11.tgz", + "integrity": "sha512-cqefuRsh12pWyGsIoBKJA9luFu3mRxCA+ORZvA4ktLSzIuCUtWVxGIuXigEwO5/ywWFMZ2QEGKWvkZG1zDMTag==", + "dev": true, + "license": "MIT" + }, + "node_modules/@tsconfig/node14": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/@tsconfig/node14/-/node14-1.0.3.tgz", + "integrity": "sha512-ysT8mhdixWK6Hw3i1V2AeRqZ5WfXg1G43mqoYlM2nc6388Fq5jcXyr5mRsqViLx/GJYdoL0bfXD8nmF+Zn/Iow==", + "dev": true, + "license": "MIT" + }, + "node_modules/@tsconfig/node16": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/@tsconfig/node16/-/node16-1.0.4.tgz", + "integrity": "sha512-vxhUy4J8lyeyinH7Azl1pdd43GJhZH/tP2weN8TntQblOY+A0XbT8DJk1/oCPuOOyg/Ja757rG0CgHcWC8OfMA==", + "dev": true, + "license": "MIT" + }, + "node_modules/@types/cookie": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/@types/cookie/-/cookie-0.4.1.tgz", + "integrity": "sha512-XW/Aa8APYr6jSVVA1y/DEIZX0/GMKLEVekNG727R8cs56ahETkRAy/3DR7+fJyh7oUgGwNQaRfXCun0+KbWY7Q==", + "license": "MIT" + }, + "node_modules/@types/cors": { + "version": "2.8.17", + "resolved": "https://registry.npmjs.org/@types/cors/-/cors-2.8.17.tgz", + "integrity": "sha512-8CGDvrBj1zgo2qE+oS3pOCyYNqCPryMWY2bGfwA0dcfopWGgxs+78df0Rs3rc9THP4JkOhLsAa+15VdpAqkcUA==", + "license": "MIT", + "dependencies": { + "@types/node": "*" + } + }, "node_modules/@types/json5": { "version": "0.0.29", "resolved": "https://registry.npmjs.org/@types/json5/-/json5-0.0.29.tgz", @@ -439,10 +520,10 @@ "dev": true }, "node_modules/@types/node": { - "version": "20.14.9", - "resolved": "https://registry.npmjs.org/@types/node/-/node-20.14.9.tgz", - "integrity": "sha512-06OCtnTXtWOZBJlRApleWndH4JsRVs1pDCc8dLSQp+7PpUpX3ePdHyeNSFTeSe7FtKyQkrlPvHwJOW3SLd8Oyg==", - "dev": true, + "version": "20.14.10", + "resolved": "https://registry.npmjs.org/@types/node/-/node-20.14.10.tgz", + "integrity": "sha512-MdiXf+nDuMvY0gJKxyfZ7/6UFsETO7mGKF54MVD/ekJS6HdFtpZFBgrh6Pseu64XTb2MLyFPlbW6hj8HYRQNOQ==", + "license": "MIT", "dependencies": { "undici-types": "~5.26.4" } @@ -472,6 +553,17 @@ "@types/react": "*" } }, + "node_modules/@types/socket.io": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/@types/socket.io/-/socket.io-3.0.2.tgz", + "integrity": "sha512-pu0sN9m5VjCxBZVK8hW37ZcMe8rjn4HHggBN5CbaRTvFwv5jOmuIRZEuddsBPa9Th0ts0SIo3Niukq+95cMBbQ==", + "deprecated": "This is a stub types definition. socket.io provides its own type definitions, so you do not need this installed.", + "dev": true, + "license": "MIT", + "dependencies": { + "socket.io": "*" + } + }, "node_modules/@typescript-eslint/parser": { "version": "7.2.0", "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-7.2.0.tgz", @@ -605,6 +697,19 @@ "integrity": "sha512-zuVdFrMJiuCDQUMCzQaD6KL28MjnqqN8XnAqiEq9PNm/hCPTSGfrXCOfwj1ow4LFb/tNymJPwsNbVePc1xFqrQ==", "dev": true }, + "node_modules/accepts": { + "version": "1.3.8", + "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.8.tgz", + "integrity": "sha512-PYAthTa2m2VKxuvSD3DPC/Gy+U+sOA1LAuT8mkmRuvw+NACSaeXEQ+NHcVF7rONl6qcaxV3Uuemwawk+7+SJLw==", + "license": "MIT", + "dependencies": { + "mime-types": "~2.1.34", + "negotiator": "0.6.3" + }, + "engines": { + "node": ">= 0.6" + } + }, "node_modules/acorn": { "version": "8.12.1", "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.12.1.tgz", @@ -626,6 +731,19 @@ "acorn": "^6.0.0 || ^7.0.0 || ^8.0.0" } }, + "node_modules/acorn-walk": { + "version": "8.3.3", + "resolved": "https://registry.npmjs.org/acorn-walk/-/acorn-walk-8.3.3.tgz", + "integrity": "sha512-MxXdReSRhGO7VlFe1bRG/oI7/mdLV9B9JJT0N8vZOhF7gFRR5l3M8W9G8JxmKV+JC5mGqJ0QvqfSOLsCPa4nUw==", + "dev": true, + "license": "MIT", + "dependencies": { + "acorn": "^8.11.0" + }, + "engines": { + "node": ">=0.4.0" + } + }, "node_modules/ajv": { "version": "6.12.6", "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", @@ -722,6 +840,12 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/array-flatten": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", + "integrity": "sha512-PCVAQswWemu6UdxsDFFX/+gVeYqKAod3D3UVm91jHwynguOwAvYPhx8nNlM++NqRcK6CxxpUafjmhIdKiHibqg==", + "license": "MIT" + }, "node_modules/array-includes": { "version": "3.1.8", "resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.8.tgz", @@ -922,6 +1046,15 @@ "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", "dev": true }, + "node_modules/base64id": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/base64id/-/base64id-2.0.0.tgz", + "integrity": "sha512-lGe34o6EHj9y3Kts9R4ZYs/Gr+6N7MCaMlIFA3F1R2O5/m7K06AxfSeO5530PEERE6/WyEg3lsuyw4GHlPZHog==", + "license": "MIT", + "engines": { + "node": "^4.5.0 || >= 5.9" + } + }, "node_modules/binary-extensions": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.3.0.tgz", @@ -934,6 +1067,45 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/body-parser": { + "version": "1.20.2", + "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.20.2.tgz", + "integrity": "sha512-ml9pReCu3M61kGlqoTm2umSXTlRTuGTx0bfYj+uIUKKYycG5NtSbeetV3faSU6R7ajOPw0g/J1PvK4qNy7s5bA==", + "license": "MIT", + "dependencies": { + "bytes": "3.1.2", + "content-type": "~1.0.5", + "debug": "2.6.9", + "depd": "2.0.0", + "destroy": "1.2.0", + "http-errors": "2.0.0", + "iconv-lite": "0.4.24", + "on-finished": "2.4.1", + "qs": "6.11.0", + "raw-body": "2.5.2", + "type-is": "~1.6.18", + "unpipe": "1.0.0" + }, + "engines": { + "node": ">= 0.8", + "npm": "1.2.8000 || >= 1.4.16" + } + }, + "node_modules/body-parser/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "license": "MIT", + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/body-parser/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "license": "MIT" + }, "node_modules/brace-expansion": { "version": "1.1.11", "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", @@ -967,11 +1139,19 @@ "node": ">=10.16.0" } }, + "node_modules/bytes": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", + "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, "node_modules/call-bind": { "version": "1.0.7", "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.7.tgz", "integrity": "sha512-GHTSNSYICQ7scH7sZ+M2rFopRoLh8t2bLSW6BbgrtLsahOIB5iyAVJf9GjWK3cYTDaMj4XdBpM1cA6pIS0Kv2w==", - "dev": true, "dependencies": { "es-define-property": "^1.0.0", "es-errors": "^1.3.0", @@ -1113,6 +1293,62 @@ "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", "dev": true }, + "node_modules/content-disposition": { + "version": "0.5.4", + "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.4.tgz", + "integrity": "sha512-FveZTNuGw04cxlAiWbzi6zTAL/lhehaWbTtgluJh4/E95DqMwTmha3KZN1aAWA8cFIhHzMZUvLevkw5Rqk+tSQ==", + "license": "MIT", + "dependencies": { + "safe-buffer": "5.2.1" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/content-type": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.5.tgz", + "integrity": "sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/cookie": { + "version": "0.4.2", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.4.2.tgz", + "integrity": "sha512-aSWTXFzaKWkvHO1Ny/s+ePFpvKsPnjc551iI41v3ny/ow6tBG5Vd+FuqGNhh1LxOmVzOlGUriIlOaokOvhaStA==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/cookie-signature": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", + "integrity": "sha512-QADzlaHc8icV8I7vbaJXJwod9HWYp8uCqf1xa4OfNu1T7JVxQIrUgOWtHdNDtPiywmFbiS12VjotIXLrKM3orQ==", + "license": "MIT" + }, + "node_modules/cors": { + "version": "2.8.5", + "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", + "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", + "license": "MIT", + "dependencies": { + "object-assign": "^4", + "vary": "^1" + }, + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/create-require": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/create-require/-/create-require-1.1.1.tgz", + "integrity": "sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ==", + "dev": true, + "license": "MIT" + }, "node_modules/cross-spawn": { "version": "7.0.3", "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.3.tgz", @@ -1206,7 +1442,6 @@ "version": "4.3.5", "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.5.tgz", "integrity": "sha512-pt0bNEmneDIvdL1Xsd9oDQ/wrQRkXDT4AUWlNZNPKvW5x/jyO9VFXkJUP07vQ2upmw5PlaITaPKc31jK13V+jg==", - "dev": true, "dependencies": { "ms": "2.1.2" }, @@ -1261,7 +1496,6 @@ "version": "1.1.4", "resolved": "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.4.tgz", "integrity": "sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==", - "dev": true, "dependencies": { "es-define-property": "^1.0.0", "es-errors": "^1.3.0", @@ -1291,12 +1525,41 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/depd": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", + "integrity": "sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==", + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/destroy": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.2.0.tgz", + "integrity": "sha512-2sJGJTaXIIaR1w4iJSNoN0hnMY7Gpc/n8D4qSCJw8QqFWXf7cuAgnEHxBpweaVcPevC2l3KpjYCx3NypQQgaJg==", + "license": "MIT", + "engines": { + "node": ">= 0.8", + "npm": "1.2.8000 || >= 1.4.16" + } + }, "node_modules/didyoumean": { "version": "1.2.2", "resolved": "https://registry.npmjs.org/didyoumean/-/didyoumean-1.2.2.tgz", "integrity": "sha512-gxtyfqMg7GKyhQmb056K7M3xszy/myH8w+B4RT+QXBQsvAOdc3XymqDDPHx1BgPgsdAA5SIifona89YtRATDzw==", "dev": true }, + "node_modules/diff": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/diff/-/diff-4.0.2.tgz", + "integrity": "sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==", + "dev": true, + "license": "BSD-3-Clause", + "engines": { + "node": ">=0.3.1" + } + }, "node_modules/dir-glob": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-3.0.1.tgz", @@ -1333,12 +1596,70 @@ "integrity": "sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==", "dev": true }, + "node_modules/ee-first": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", + "integrity": "sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==", + "license": "MIT" + }, "node_modules/emoji-regex": { "version": "9.2.2", "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-9.2.2.tgz", "integrity": "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==", "dev": true }, + "node_modules/encodeurl": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", + "integrity": "sha512-TPJXq8JqFaVYm2CWmPvnP2Iyo4ZSM7/QKcSmuMLDObfpH5fi7RUGmd/rTDf+rut/saiDiQEeVTNgAmJEdAOx0w==", + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/engine.io": { + "version": "6.5.5", + "resolved": "https://registry.npmjs.org/engine.io/-/engine.io-6.5.5.tgz", + "integrity": "sha512-C5Pn8Wk+1vKBoHghJODM63yk8MvrO9EWZUfkAt5HAqIgPE4/8FF0PEGHXtEd40l223+cE5ABWuPzm38PHFXfMA==", + "license": "MIT", + "dependencies": { + "@types/cookie": "^0.4.1", + "@types/cors": "^2.8.12", + "@types/node": ">=10.0.0", + "accepts": "~1.3.4", + "base64id": "2.0.0", + "cookie": "~0.4.1", + "cors": "~2.8.5", + "debug": "~4.3.1", + "engine.io-parser": "~5.2.1", + "ws": "~8.17.1" + }, + "engines": { + "node": ">=10.2.0" + } + }, + "node_modules/engine.io-client": { + "version": "6.5.4", + "resolved": "https://registry.npmjs.org/engine.io-client/-/engine.io-client-6.5.4.tgz", + "integrity": "sha512-GeZeeRjpD2qf49cZQ0Wvh/8NJNfeXkXXcoGh+F77oEAgo9gUHwT1fCRxSNU+YEEaysOJTnsFHmM5oAcPy4ntvQ==", + "license": "MIT", + "dependencies": { + "@socket.io/component-emitter": "~3.1.0", + "debug": "~4.3.1", + "engine.io-parser": "~5.2.1", + "ws": "~8.17.1", + "xmlhttprequest-ssl": "~2.0.0" + } + }, + "node_modules/engine.io-parser": { + "version": "5.2.2", + "resolved": "https://registry.npmjs.org/engine.io-parser/-/engine.io-parser-5.2.2.tgz", + "integrity": "sha512-RcyUFKA93/CXH20l4SoVvzZfrSDMOTUS3bWVpTt2FuFP+XYrL8i8oonHP7WInRyVHXh0n/ORtoeiE1os+8qkSw==", + "license": "MIT", + "engines": { + "node": ">=10.0.0" + } + }, "node_modules/enhanced-resolve": { "version": "5.17.0", "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.17.0.tgz", @@ -1416,7 +1737,6 @@ "version": "1.0.0", "resolved": "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.0.tgz", "integrity": "sha512-jxayLKShrEqqzJ0eumQbVhTYQM27CfT1T35+gCgDFoL82JLsXqTJ76zv6A0YLOgEnLUMvLzsDsGIrl8NFpT2gQ==", - "dev": true, "dependencies": { "get-intrinsic": "^1.2.4" }, @@ -1428,7 +1748,6 @@ "version": "1.3.0", "resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz", "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==", - "dev": true, "engines": { "node": ">= 0.4" } @@ -1530,6 +1849,12 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/escape-html": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", + "integrity": "sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==", + "license": "MIT" + }, "node_modules/escape-string-regexp": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", @@ -1954,6 +2279,81 @@ "node": ">=0.10.0" } }, + "node_modules/etag": { + "version": "1.8.1", + "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", + "integrity": "sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/express": { + "version": "4.19.2", + "resolved": "https://registry.npmjs.org/express/-/express-4.19.2.tgz", + "integrity": "sha512-5T6nhjsT+EOMzuck8JjBHARTHfMht0POzlA60WV2pMD3gyXw2LZnZ+ueGdNxG+0calOJcWKbpFcuzLZ91YWq9Q==", + "license": "MIT", + "dependencies": { + "accepts": "~1.3.8", + "array-flatten": "1.1.1", + "body-parser": "1.20.2", + "content-disposition": "0.5.4", + "content-type": "~1.0.4", + "cookie": "0.6.0", + "cookie-signature": "1.0.6", + "debug": "2.6.9", + "depd": "2.0.0", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "etag": "~1.8.1", + "finalhandler": "1.2.0", + "fresh": "0.5.2", + "http-errors": "2.0.0", + "merge-descriptors": "1.0.1", + "methods": "~1.1.2", + "on-finished": "2.4.1", + "parseurl": "~1.3.3", + "path-to-regexp": "0.1.7", + "proxy-addr": "~2.0.7", + "qs": "6.11.0", + "range-parser": "~1.2.1", + "safe-buffer": "5.2.1", + "send": "0.18.0", + "serve-static": "1.15.0", + "setprototypeof": "1.2.0", + "statuses": "2.0.1", + "type-is": "~1.6.18", + "utils-merge": "1.0.1", + "vary": "~1.1.2" + }, + "engines": { + "node": ">= 0.10.0" + } + }, + "node_modules/express/node_modules/cookie": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.6.0.tgz", + "integrity": "sha512-U71cyTamuh1CRNCfpGY6to28lxvNwPG4Guz/EVjgf3Jmzv0vlDp1atT9eS5dDjMYHucpHbWns6Lwf3BKz6svdw==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/express/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "license": "MIT", + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/express/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "license": "MIT" + }, "node_modules/fast-deep-equal": { "version": "3.1.3", "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", @@ -2033,6 +2433,39 @@ "node": ">=8" } }, + "node_modules/finalhandler": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.2.0.tgz", + "integrity": "sha512-5uXcUVftlQMFnWC9qu/svkWv3GTd2PfUhK/3PLkYNAe7FbqJMt3515HaxE6eRL74GdsriiwujiawdaB1BpEISg==", + "license": "MIT", + "dependencies": { + "debug": "2.6.9", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "on-finished": "2.4.1", + "parseurl": "~1.3.3", + "statuses": "2.0.1", + "unpipe": "~1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/finalhandler/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "license": "MIT", + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/finalhandler/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "license": "MIT" + }, "node_modules/find-up": { "version": "5.0.0", "resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz", @@ -2094,6 +2527,24 @@ "url": "https://github.com/sponsors/isaacs" } }, + "node_modules/forwarded": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", + "integrity": "sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/fresh": { + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", + "integrity": "sha512-zJ2mQYM18rEFOudeV4GShTGIQ7RbzA7ozbU9I/XBpm7kqgMywgmylMwXHxZJmkVoYkna9d2pVXVXPdYTP9ej8Q==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, "node_modules/fs.realpath": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", @@ -2118,7 +2569,6 @@ "version": "1.1.2", "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz", "integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==", - "dev": true, "funding": { "url": "https://github.com/sponsors/ljharb" } @@ -2154,7 +2604,6 @@ "version": "1.2.4", "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.2.4.tgz", "integrity": "sha512-5uYhsJH8VJBTv7oslg4BznJYhDoRI6waYCxMmCdnTrcCrHA/fCFKoTFz2JKKE0HdDFUF7/oQuhzumXJK7paBRQ==", - "dev": true, "dependencies": { "es-errors": "^1.3.0", "function-bind": "^1.1.2", @@ -2311,7 +2760,6 @@ "version": "1.0.1", "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.0.1.tgz", "integrity": "sha512-d65bNlIadxvpb/A2abVdlqKqV563juRnZ1Wtk6s1sIR8uNsXR70xqIzVqxVf1eTqDunwT2MkczEeaezCKTZhwA==", - "dev": true, "dependencies": { "get-intrinsic": "^1.1.3" }, @@ -2352,7 +2800,6 @@ "version": "1.0.2", "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.2.tgz", "integrity": "sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==", - "dev": true, "dependencies": { "es-define-property": "^1.0.0" }, @@ -2364,7 +2811,6 @@ "version": "1.0.3", "resolved": "https://registry.npmjs.org/has-proto/-/has-proto-1.0.3.tgz", "integrity": "sha512-SJ1amZAJUiZS+PhsVLf5tGydlaVB8EdFpaSO4gmiUKUOxk8qzn5AIy4ZeJUmh22znIdk/uMAUT2pl3FxzVUH+Q==", - "dev": true, "engines": { "node": ">= 0.4" }, @@ -2376,7 +2822,6 @@ "version": "1.0.3", "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.3.tgz", "integrity": "sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A==", - "dev": true, "engines": { "node": ">= 0.4" }, @@ -2403,7 +2848,6 @@ "version": "2.0.2", "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.2.tgz", "integrity": "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==", - "dev": true, "dependencies": { "function-bind": "^1.1.2" }, @@ -2411,6 +2855,39 @@ "node": ">= 0.4" } }, + "node_modules/http": { + "version": "0.0.1-security", + "resolved": "https://registry.npmjs.org/http/-/http-0.0.1-security.tgz", + "integrity": "sha512-RnDvP10Ty9FxqOtPZuxtebw1j4L/WiqNMDtuc1YMH1XQm5TgDRaR1G9u8upL6KD1bXHSp9eSXo/ED+8Q7FAr+g==" + }, + "node_modules/http-errors": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-2.0.0.tgz", + "integrity": "sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==", + "license": "MIT", + "dependencies": { + "depd": "2.0.0", + "inherits": "2.0.4", + "setprototypeof": "1.2.0", + "statuses": "2.0.1", + "toidentifier": "1.0.1" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/iconv-lite": { + "version": "0.4.24", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", + "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", + "license": "MIT", + "dependencies": { + "safer-buffer": ">= 2.1.2 < 3" + }, + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/ignore": { "version": "5.3.1", "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.3.1.tgz", @@ -2459,8 +2936,7 @@ "node_modules/inherits": { "version": "2.0.4", "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", - "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", - "dev": true + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==" }, "node_modules/internal-slot": { "version": "1.0.7", @@ -2476,6 +2952,15 @@ "node": ">= 0.4" } }, + "node_modules/ipaddr.js": { + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", + "integrity": "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==", + "license": "MIT", + "engines": { + "node": ">= 0.10" + } + }, "node_modules/is-arguments": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/is-arguments/-/is-arguments-1.1.1.tgz", @@ -3072,6 +3557,28 @@ "node": "14 || >=16.14" } }, + "node_modules/make-error": { + "version": "1.3.6", + "resolved": "https://registry.npmjs.org/make-error/-/make-error-1.3.6.tgz", + "integrity": "sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw==", + "dev": true, + "license": "ISC" + }, + "node_modules/media-typer": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", + "integrity": "sha512-dq+qelQ9akHpcOl/gUVRTxVIOkAJ1wR3QAvb4RsVjS8oVoFjDGTc679wJYmUmknUF5HwMLOgb5O+a3KxfWapPQ==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/merge-descriptors": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", + "integrity": "sha512-cCi6g3/Zr1iqQi6ySbseM1Xvooa98N0w31jzUYrXPX2xqObmFGHJ0tQ5u74H3mVh7wLouTseZyYIq39g8cNp1w==", + "license": "MIT" + }, "node_modules/merge2": { "version": "1.4.1", "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", @@ -3081,6 +3588,15 @@ "node": ">= 8" } }, + "node_modules/methods": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", + "integrity": "sha512-iclAHeNqNm68zFtnZ0e+1L2yUIdvzNoauKU4WBA3VvH/vPFieF7qfRlwUZU+DA9P9bPXIS90ulxoUoCH23sV2w==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, "node_modules/micromatch": { "version": "4.0.7", "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.7.tgz", @@ -3094,6 +3610,39 @@ "node": ">=8.6" } }, + "node_modules/mime": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", + "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==", + "license": "MIT", + "bin": { + "mime": "cli.js" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/mime-db": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/mime-types": { + "version": "2.1.35", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", + "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "license": "MIT", + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } + }, "node_modules/minimatch": { "version": "3.1.2", "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", @@ -3127,8 +3676,7 @@ "node_modules/ms": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", - "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", - "dev": true + "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" }, "node_modules/mz": { "version": "2.7.0", @@ -3164,6 +3712,15 @@ "integrity": "sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==", "dev": true }, + "node_modules/negotiator": { + "version": "0.6.3", + "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.3.tgz", + "integrity": "sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, "node_modules/next": { "version": "14.2.4", "resolved": "https://registry.npmjs.org/next/-/next-14.2.4.tgz", @@ -3253,7 +3810,6 @@ "version": "4.1.1", "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==", - "dev": true, "engines": { "node": ">=0.10.0" } @@ -3271,7 +3827,6 @@ "version": "1.13.2", "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.2.tgz", "integrity": "sha512-IRZSRuzJiynemAXPYtPe5BoI/RESNYR7TYm50MC5Mqbd3Jmw5y790sErYw3V6SryFJD64b74qQQs9wn5Bg/k3g==", - "dev": true, "engines": { "node": ">= 0.4" }, @@ -3402,6 +3957,18 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/on-finished": { + "version": "2.4.1", + "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.4.1.tgz", + "integrity": "sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==", + "license": "MIT", + "dependencies": { + "ee-first": "1.1.1" + }, + "engines": { + "node": ">= 0.8" + } + }, "node_modules/once": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", @@ -3470,6 +4037,15 @@ "node": ">=6" } }, + "node_modules/parseurl": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", + "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==", + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, "node_modules/path-exists": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", @@ -3519,6 +4095,12 @@ "url": "https://github.com/sponsors/isaacs" } }, + "node_modules/path-to-regexp": { + "version": "0.1.7", + "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz", + "integrity": "sha512-5DFkuoqlv1uYQKxy8omFBeJPQcdoE07Kv2sferDCrAq1ohOU+MSDswDIbnx3YAM60qIOnYa53wBhXW0EbMonrQ==", + "license": "MIT" + }, "node_modules/path-type": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/path-type/-/path-type-4.0.0.tgz", @@ -3741,6 +4323,19 @@ "react-is": "^16.13.1" } }, + "node_modules/proxy-addr": { + "version": "2.0.7", + "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.7.tgz", + "integrity": "sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==", + "license": "MIT", + "dependencies": { + "forwarded": "0.2.0", + "ipaddr.js": "1.9.1" + }, + "engines": { + "node": ">= 0.10" + } + }, "node_modules/punycode": { "version": "2.3.1", "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz", @@ -3750,6 +4345,21 @@ "node": ">=6" } }, + "node_modules/qs": { + "version": "6.11.0", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.11.0.tgz", + "integrity": "sha512-MvjoMCJwEarSbUYk5O+nmoSzSutSsTwF85zcHPQ9OrlFoZOYIjaqBAJIqIXjptyD5vThxGq52Xu/MaJzRkIk4Q==", + "license": "BSD-3-Clause", + "dependencies": { + "side-channel": "^1.0.4" + }, + "engines": { + "node": ">=0.6" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/queue-microtask": { "version": "1.2.3", "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", @@ -3770,6 +4380,30 @@ } ] }, + "node_modules/range-parser": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.1.tgz", + "integrity": "sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/raw-body": { + "version": "2.5.2", + "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.5.2.tgz", + "integrity": "sha512-8zGqypfENjCIqGhgXToC8aB2r7YrBX+AQAfIPs/Mlk+BtPTztOvTS01NRW/3Eh60J+a48lt8qsCzirQ6loCVfA==", + "license": "MIT", + "dependencies": { + "bytes": "3.1.2", + "http-errors": "2.0.0", + "iconv-lite": "0.4.24", + "unpipe": "1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, "node_modules/react": { "version": "18.3.1", "resolved": "https://registry.npmjs.org/react/-/react-18.3.1.tgz", @@ -3982,6 +4616,26 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/safe-buffer": { + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", + "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "MIT" + }, "node_modules/safe-regex-test": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/safe-regex-test/-/safe-regex-test-1.0.3.tgz", @@ -3999,6 +4653,12 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/safer-buffer": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", + "license": "MIT" + }, "node_modules/scheduler": { "version": "0.23.2", "resolved": "https://registry.npmjs.org/scheduler/-/scheduler-0.23.2.tgz", @@ -4019,11 +4679,70 @@ "node": ">=10" } }, + "node_modules/send": { + "version": "0.18.0", + "resolved": "https://registry.npmjs.org/send/-/send-0.18.0.tgz", + "integrity": "sha512-qqWzuOjSFOuqPjFe4NOsMLafToQQwBSOEpS+FwEt3A2V3vKubTquT3vmLTQpFgMXp8AlFWFuP1qKaJZOtPpVXg==", + "license": "MIT", + "dependencies": { + "debug": "2.6.9", + "depd": "2.0.0", + "destroy": "1.2.0", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "etag": "~1.8.1", + "fresh": "0.5.2", + "http-errors": "2.0.0", + "mime": "1.6.0", + "ms": "2.1.3", + "on-finished": "2.4.1", + "range-parser": "~1.2.1", + "statuses": "2.0.1" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/send/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "license": "MIT", + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/send/node_modules/debug/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "license": "MIT" + }, + "node_modules/send/node_modules/ms": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", + "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", + "license": "MIT" + }, + "node_modules/serve-static": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.15.0.tgz", + "integrity": "sha512-XGuRDNjXUijsUL0vl6nSD7cwURuzEgglbOaFuZM9g3kwDXOWVTck0jLzjPzGD+TazWbboZYu52/9/XPdUgne9g==", + "license": "MIT", + "dependencies": { + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "parseurl": "~1.3.3", + "send": "0.18.0" + }, + "engines": { + "node": ">= 0.8.0" + } + }, "node_modules/set-function-length": { "version": "1.2.2", "resolved": "https://registry.npmjs.org/set-function-length/-/set-function-length-1.2.2.tgz", "integrity": "sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==", - "dev": true, "dependencies": { "define-data-property": "^1.1.4", "es-errors": "^1.3.0", @@ -4051,6 +4770,12 @@ "node": ">= 0.4" } }, + "node_modules/setprototypeof": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", + "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==", + "license": "ISC" + }, "node_modules/shebang-command": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", @@ -4076,7 +4801,6 @@ "version": "1.0.6", "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.6.tgz", "integrity": "sha512-fDW/EZ6Q9RiO8eFG8Hj+7u/oW+XrPTIChwCOM2+th2A6OblDtYYIpve9m+KvI9Z4C9qSEXlaGR6bTEYHReuglA==", - "dev": true, "dependencies": { "call-bind": "^1.0.7", "es-errors": "^1.3.0", @@ -4111,6 +4835,62 @@ "node": ">=8" } }, + "node_modules/socket.io": { + "version": "4.7.5", + "resolved": "https://registry.npmjs.org/socket.io/-/socket.io-4.7.5.tgz", + "integrity": "sha512-DmeAkF6cwM9jSfmp6Dr/5/mfMwb5Z5qRrSXLpo3Fq5SqyU8CMF15jIN4ZhfSwu35ksM1qmHZDQ/DK5XTccSTvA==", + "license": "MIT", + "dependencies": { + "accepts": "~1.3.4", + "base64id": "~2.0.0", + "cors": "~2.8.5", + "debug": "~4.3.2", + "engine.io": "~6.5.2", + "socket.io-adapter": "~2.5.2", + "socket.io-parser": "~4.2.4" + }, + "engines": { + "node": ">=10.2.0" + } + }, + "node_modules/socket.io-adapter": { + "version": "2.5.5", + "resolved": "https://registry.npmjs.org/socket.io-adapter/-/socket.io-adapter-2.5.5.tgz", + "integrity": "sha512-eLDQas5dzPgOWCk9GuuJC2lBqItuhKI4uxGgo9aIV7MYbk2h9Q6uULEh8WBzThoI7l+qU9Ast9fVUmkqPP9wYg==", + "license": "MIT", + "dependencies": { + "debug": "~4.3.4", + "ws": "~8.17.1" + } + }, + "node_modules/socket.io-client": { + "version": "4.7.5", + "resolved": "https://registry.npmjs.org/socket.io-client/-/socket.io-client-4.7.5.tgz", + "integrity": "sha512-sJ/tqHOCe7Z50JCBCXrsY3I2k03iOiUe+tj1OmKeD2lXPiGH/RUCdTZFoqVyN7l1MnpIzPrGtLcijffmeouNlQ==", + "license": "MIT", + "dependencies": { + "@socket.io/component-emitter": "~3.1.0", + "debug": "~4.3.2", + "engine.io-client": "~6.5.2", + "socket.io-parser": "~4.2.4" + }, + "engines": { + "node": ">=10.0.0" + } + }, + "node_modules/socket.io-parser": { + "version": "4.2.4", + "resolved": "https://registry.npmjs.org/socket.io-parser/-/socket.io-parser-4.2.4.tgz", + "integrity": "sha512-/GbIKmo8ioc+NIWIhwdecY0ge+qVBSMdgxGygevmdHj24bsfgtCmcUUcQ5ZzcylGFHsN3k4HB4Cgkl96KVnuew==", + "license": "MIT", + "dependencies": { + "@socket.io/component-emitter": "~3.1.0", + "debug": "~4.3.1" + }, + "engines": { + "node": ">=10.0.0" + } + }, "node_modules/source-map-js": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/source-map-js/-/source-map-js-1.2.0.tgz", @@ -4119,6 +4899,15 @@ "node": ">=0.10.0" } }, + "node_modules/statuses": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz", + "integrity": "sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==", + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, "node_modules/stop-iteration-iterator": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/stop-iteration-iterator/-/stop-iteration-iterator-1.0.0.tgz", @@ -4488,6 +5277,15 @@ "node": ">=8.0" } }, + "node_modules/toidentifier": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.1.tgz", + "integrity": "sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==", + "license": "MIT", + "engines": { + "node": ">=0.6" + } + }, "node_modules/ts-api-utils": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/ts-api-utils/-/ts-api-utils-1.3.0.tgz", @@ -4506,6 +5304,57 @@ "integrity": "sha512-Y/arvbn+rrz3JCKl9C4kVNfTfSm2/mEp5FSz5EsZSANGPSlQrpRI5M4PKF+mJnE52jOO90PnPSc3Ur3bTQw0gA==", "dev": true }, + "node_modules/ts-node": { + "version": "10.9.2", + "resolved": "https://registry.npmjs.org/ts-node/-/ts-node-10.9.2.tgz", + "integrity": "sha512-f0FFpIdcHgn8zcPSbf1dRevwt047YMnaiJM3u2w2RewrB+fob/zePZcrOyQoLMMO7aBIddLcQIEK5dYjkLnGrQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@cspotcode/source-map-support": "^0.8.0", + "@tsconfig/node10": "^1.0.7", + "@tsconfig/node12": "^1.0.7", + "@tsconfig/node14": "^1.0.0", + "@tsconfig/node16": "^1.0.2", + "acorn": "^8.4.1", + "acorn-walk": "^8.1.1", + "arg": "^4.1.0", + "create-require": "^1.1.0", + "diff": "^4.0.1", + "make-error": "^1.1.1", + "v8-compile-cache-lib": "^3.0.1", + "yn": "3.1.1" + }, + "bin": { + "ts-node": "dist/bin.js", + "ts-node-cwd": "dist/bin-cwd.js", + "ts-node-esm": "dist/bin-esm.js", + "ts-node-script": "dist/bin-script.js", + "ts-node-transpile-only": "dist/bin-transpile.js", + "ts-script": "dist/bin-script-deprecated.js" + }, + "peerDependencies": { + "@swc/core": ">=1.2.50", + "@swc/wasm": ">=1.2.50", + "@types/node": "*", + "typescript": ">=2.7" + }, + "peerDependenciesMeta": { + "@swc/core": { + "optional": true + }, + "@swc/wasm": { + "optional": true + } + } + }, + "node_modules/ts-node/node_modules/arg": { + "version": "4.1.3", + "resolved": "https://registry.npmjs.org/arg/-/arg-4.1.3.tgz", + "integrity": "sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA==", + "dev": true, + "license": "MIT" + }, "node_modules/tsconfig-paths": { "version": "3.15.0", "resolved": "https://registry.npmjs.org/tsconfig-paths/-/tsconfig-paths-3.15.0.tgz", @@ -4547,6 +5396,19 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/type-is": { + "version": "1.6.18", + "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.18.tgz", + "integrity": "sha512-TkRKr9sUTxEH8MdfuCSP7VizJyzRNMjj2J2do2Jr3Kym598JVdEksuzPQCnlFPW4ky9Q+iA+ma9BGm06XQBy8g==", + "license": "MIT", + "dependencies": { + "media-typer": "0.3.0", + "mime-types": "~2.1.24" + }, + "engines": { + "node": ">= 0.6" + } + }, "node_modules/typed-array-buffer": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/typed-array-buffer/-/typed-array-buffer-1.0.2.tgz", @@ -4651,8 +5513,16 @@ "node_modules/undici-types": { "version": "5.26.5", "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-5.26.5.tgz", - "integrity": "sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==", - "dev": true + "integrity": "sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==" + }, + "node_modules/unpipe": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", + "integrity": "sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==", + "license": "MIT", + "engines": { + "node": ">= 0.8" + } }, "node_modules/uri-js": { "version": "4.4.1", @@ -4669,6 +5539,31 @@ "integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==", "dev": true }, + "node_modules/utils-merge": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", + "integrity": "sha512-pMZTvIkT1d+TFGvDOqodOclx0QWkkgi6Tdoa8gC8ffGAAqz9pzPTZWAybbsHHoED/ztMtkv/VoYTYyShUn81hA==", + "license": "MIT", + "engines": { + "node": ">= 0.4.0" + } + }, + "node_modules/v8-compile-cache-lib": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz", + "integrity": "sha512-wa7YjyUGfNZngI/vtK0UHAN+lgDCxBPCylVXGp0zu59Fz5aiGtNXaq3DhIov063MorB+VfufLh3JlF2KdTK3xg==", + "dev": true, + "license": "MIT" + }, + "node_modules/vary": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", + "integrity": "sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==", + "license": "MIT", + "engines": { + "node": ">= 0.8" + } + }, "node_modules/which": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", @@ -4872,6 +5767,35 @@ "integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==", "dev": true }, + "node_modules/ws": { + "version": "8.17.1", + "resolved": "https://registry.npmjs.org/ws/-/ws-8.17.1.tgz", + "integrity": "sha512-6XQFvXTkbfUOZOKKILFG1PDK2NDQs4azKQl26T0YS5CxqWLgXajbPZ+h4gZekJyRqFU8pvnbAbbs/3TgRPy+GQ==", + "license": "MIT", + "engines": { + "node": ">=10.0.0" + }, + "peerDependencies": { + "bufferutil": "^4.0.1", + "utf-8-validate": ">=5.0.2" + }, + "peerDependenciesMeta": { + "bufferutil": { + "optional": true + }, + "utf-8-validate": { + "optional": true + } + } + }, + "node_modules/xmlhttprequest-ssl": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/xmlhttprequest-ssl/-/xmlhttprequest-ssl-2.0.0.tgz", + "integrity": "sha512-QKxVRxiRACQcVuQEYFsI1hhkrMlrXHPegbbd1yn9UHOmRxY+si12nQYzri3vbzt8VdTTRviqcKxcyllFas5z2A==", + "engines": { + "node": ">=0.4.0" + } + }, "node_modules/yaml": { "version": "2.4.5", "resolved": "https://registry.npmjs.org/yaml/-/yaml-2.4.5.tgz", @@ -4884,6 +5808,16 @@ "node": ">= 14" } }, + "node_modules/yn": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/yn/-/yn-3.1.1.tgz", + "integrity": "sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=6" + } + }, "node_modules/yocto-queue": { "version": "0.1.0", "resolved": "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz", diff --git a/package.json b/package.json index ffa70b1..af8572d 100644 --- a/package.json +++ b/package.json @@ -3,24 +3,36 @@ "version": "0.1.0", "private": true, "scripts": { - "dev": "next dev", + "dev": "node server.js", "build": "next build", - "start": "next start", + "start": "NODE_ENV=production node server.js", "lint": "next lint" }, "dependencies": { + "cors": "^2.8.5", + "express": "^4.19.2", + "http": "^0.0.1-security", + "next": "14.2.4", "react": "^18", "react-dom": "^18", - "next": "14.2.4" + "socket.io": "^4.7.5", + "socket.io-client": "^4.7.5" }, "devDependencies": { - "typescript": "^5", - "@types/node": "^20", + "@types/node": "^20.14.10", "@types/react": "^18", "@types/react-dom": "^18", + "@types/socket.io": "^3.0.2", + "eslint": "^8", + "eslint-config-next": "14.2.4", "postcss": "^8", "tailwindcss": "^3.4.1", - "eslint": "^8", - "eslint-config-next": "14.2.4" - } + "ts-node": "^10.9.2", + "typescript": "^5" + }, + "description": "This is a [Next.js](https://nextjs.org/) project bootstrapped with [`create-next-app`](https://github.com/vercel/next.js/tree/canary/packages/create-next-app).", + "main": "index.js", + "keywords": [], + "author": "", + "license": "ISC" } diff --git a/server.ts b/server.ts new file mode 100644 index 0000000..3f0dce8 --- /dev/null +++ b/server.ts @@ -0,0 +1,36 @@ +import { createServer } from "http"; +import { parse } from "url"; +import next from "next"; +import { Server } from "socket.io"; + +const dev = process.env.NODE_ENV !== "production"; +const hostname = "localhost"; +const port = 3000; +const app = next({ dev, hostname, port }); +const handle = app.getRequestHandler(); + +app.prepare().then(() => { + const server = createServer((req, res) => { + const parsedUrl = parse(req.url!, true); + handle(req, res, parsedUrl); + }); + + const io = new Server(server, { + cors: { + origin: "*", + methods: ["GET", "POST"] + } + }); + + io.on("connection", (socket) => { + console.log("A user connected"); + + socket.on("disconnect", () => { + console.log("User disconnected"); + }); + }); + + server.listen(port, () => { + console.log(`> Ready on http://${hostname}:${port}`); + }); +}); \ No newline at end of file From bf2671605c3ece51679e20c3dea646c1bfcabde6 Mon Sep 17 00:00:00 2001 From: eunwoo-levi Date: Wed, 10 Jul 2024 17:56:31 +0900 Subject: [PATCH 2/7] first commit for test --- api/socketio.ts | 27 ---- app/create/page.tsx | 16 +++ app/login/page.tsx | 2 +- app/page.tsx | 3 - components/chat/client.tsx | 49 -------- components/chat/socket.ts | 5 - components/create/CreateForm.tsx | 68 ++++++++++ components/{page => login}/AccountForm.tsx | 2 +- components/{page => login}/NewAccount.tsx | 0 components/{page => shared}/Input.tsx | 6 +- fakeServer/db.json | 9 ++ next.config.js => next.config.cjs | 0 package-lock.json | 138 +++++++++++++++++---- package.json | 10 +- server.ts | 36 ------ tsconfig.json | 2 +- 16 files changed, 222 insertions(+), 151 deletions(-) delete mode 100644 api/socketio.ts create mode 100644 app/create/page.tsx delete mode 100644 components/chat/client.tsx delete mode 100644 components/chat/socket.ts create mode 100644 components/create/CreateForm.tsx rename components/{page => login}/AccountForm.tsx (94%) rename components/{page => login}/NewAccount.tsx (100%) rename components/{page => shared}/Input.tsx (65%) create mode 100644 fakeServer/db.json rename next.config.js => next.config.cjs (100%) delete mode 100644 server.ts diff --git a/api/socketio.ts b/api/socketio.ts deleted file mode 100644 index 8c8cded..0000000 --- a/api/socketio.ts +++ /dev/null @@ -1,27 +0,0 @@ -import { Server as NetServer } from 'http' -import { NextApiRequest } from 'next' -import { Server as SocketIOServer } from 'socket.io' - - -export default function SocketHandler(req: NextApiRequest, res: any) { - if (res.socket.server.io) { - console.log('Socket is already running') - } else { - console.log('Socket is initializing') - const httpServer: NetServer = res.socket.server as any - const io = new SocketIOServer(httpServer, { - path: '/api/socketio', - }) - res.socket.server.io = io - - io.on('connection', (socket) => { - console.log('New client connected') - - socket.on('chat-message', (msg: { user: string; text: string }) => { - // 모든 클라이언트에게 메시지를 브로드캐스트 - io.emit('chat-message', msg) - }) - }) - } - res.end() -} \ No newline at end of file diff --git a/app/create/page.tsx b/app/create/page.tsx new file mode 100644 index 0000000..5b3dbb9 --- /dev/null +++ b/app/create/page.tsx @@ -0,0 +1,16 @@ +import CreateForm from "@/components/create/createForm"; + +export default function CreateAccount() { + return ( +
+
+
+

+ Creating a new Account +

+
+ +
+
+ ); +} diff --git a/app/login/page.tsx b/app/login/page.tsx index c34aab1..c36fc19 100644 --- a/app/login/page.tsx +++ b/app/login/page.tsx @@ -1,4 +1,4 @@ -import AccountForm from "@/components/page/AccountForm"; +import AccountForm from "@/components/login/AccountForm"; export default function page() { return ( diff --git a/app/page.tsx b/app/page.tsx index 6fea3dc..a96afb9 100644 --- a/app/page.tsx +++ b/app/page.tsx @@ -1,5 +1,3 @@ -import Chat from "@/components/chat/client"; - export default function Home() { return (
@@ -7,7 +5,6 @@ export default function Home() {
Item 1
실시간 채팅 -
Item 3
diff --git a/components/chat/client.tsx b/components/chat/client.tsx deleted file mode 100644 index 212e74b..0000000 --- a/components/chat/client.tsx +++ /dev/null @@ -1,49 +0,0 @@ -"use client"; - -import { useEffect, useState } from "react"; -import { socket } from "../chat/socket"; - -export default function Chat() { - const [isConnected, setIsConnected] = useState(false); - const [transport, setTransport] = useState("N/A"); - - useEffect(() => { - console.log("Initializing socket connection"); - - function onConnect() { - console.log("Connected to server"); - setIsConnected(true); - setTransport(socket.io.engine.transport.name); - - socket.io.engine.on("upgrade", (transport: any) => { - console.log("Transport upgraded:", transport.name); - setTransport(transport.name); - }); - } - - function onDisconnect() { - console.log("Disconnected from server"); - setIsConnected(false); - setTransport("N/A"); - } - - socket.on("connect", onConnect); - socket.on("disconnect", onDisconnect); - socket.on("connect_error", (err) => { - console.error("Connection error:", err); - }); - - return () => { - socket.off("connect", onConnect); - socket.off("disconnect", onDisconnect); - socket.off("connect_error"); - }; - }, []); - - return ( -
-

Status: {isConnected ? "connected" : "disconnected"}

-

Transport: {transport}

-
- ); -} diff --git a/components/chat/socket.ts b/components/chat/socket.ts deleted file mode 100644 index 2f43610..0000000 --- a/components/chat/socket.ts +++ /dev/null @@ -1,5 +0,0 @@ -"use client"; - -import { io } from "socket.io-client"; - -export const socket = io("http://localhost:3000"); \ No newline at end of file diff --git a/components/create/CreateForm.tsx b/components/create/CreateForm.tsx new file mode 100644 index 0000000..fe98288 --- /dev/null +++ b/components/create/CreateForm.tsx @@ -0,0 +1,68 @@ +"use client"; +import axios from "axios"; +import { useState } from "react"; +import Input from "../shared/Input"; + +export default function CreateForm() { + const [nickname, setNickname] = useState(""); + const [email, setEmail] = useState(""); + const [password, setPassword] = useState(""); + + const handleSubmit = async (event: React.FormEvent) => { + event.preventDefault(); + + try { + const response = await axios.post("http://localhost:3001/", { + nickname, + email, + password, + }); + console.log("회원가입 성공!", response.data); + } catch (error) { + console.error("회원가입 실패! :", error); + } + }; + + return ( +
+ setNickname(e.target.value)} + context="Nickname" + type="text" + placeholder="Enter your nickname" + /> + + setEmail(e.target.value)} + context="Email address" + type="email" + placeholder="Enter your Email" + /> + setPassword(e.target.value)} + context="Password" + type="password" + placeholder="Enter your Password" + /> + +
+ +
+
+ ); +} diff --git a/components/page/AccountForm.tsx b/components/login/AccountForm.tsx similarity index 94% rename from components/page/AccountForm.tsx rename to components/login/AccountForm.tsx index 1d439fd..5b1c55c 100644 --- a/components/page/AccountForm.tsx +++ b/components/login/AccountForm.tsx @@ -1,4 +1,4 @@ -import Input from "./Input"; +import Input from "../shared/Input"; import NewAccount from "./NewAccount"; const AccountForm = () => { diff --git a/components/page/NewAccount.tsx b/components/login/NewAccount.tsx similarity index 100% rename from components/page/NewAccount.tsx rename to components/login/NewAccount.tsx diff --git a/components/page/Input.tsx b/components/shared/Input.tsx similarity index 65% rename from components/page/Input.tsx rename to components/shared/Input.tsx index cb95366..286dd6c 100644 --- a/components/page/Input.tsx +++ b/components/shared/Input.tsx @@ -1,14 +1,18 @@ interface InputProps { + value?: string; + onChange?: (e: React.ChangeEvent) => void; context: string; type: string; placeholder: string; } -const Input = ({ context, type, placeholder }: InputProps) => { +const Input = ({ value, onChange, context, type, placeholder }: InputProps) => { return (

{context}

=4" } }, + "node_modules/axios": { + "version": "1.7.2", + "resolved": "https://registry.npmjs.org/axios/-/axios-1.7.2.tgz", + "integrity": "sha512-2A8QhOMrbomlDuiLeK9XibIBzuHeRcqqNOHp0Cyp5EoJ1IFDh+XZH3A6BkXtv0K4gFGCI0Y4BM7B1wOEi0Rmgw==", + "license": "MIT", + "dependencies": { + "follow-redirects": "^1.15.6", + "form-data": "^4.0.0", + "proxy-from-env": "^1.1.0" + } + }, "node_modules/axobject-query": { "version": "3.1.1", "resolved": "https://registry.npmjs.org/axobject-query/-/axobject-query-3.1.1.tgz", @@ -1278,6 +1297,18 @@ "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", "dev": true }, + "node_modules/combined-stream": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", + "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", + "license": "MIT", + "dependencies": { + "delayed-stream": "~1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, "node_modules/commander": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/commander/-/commander-4.1.1.tgz", @@ -1347,7 +1378,9 @@ "resolved": "https://registry.npmjs.org/create-require/-/create-require-1.1.1.tgz", "integrity": "sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ==", "dev": true, - "license": "MIT" + "license": "MIT", + "optional": true, + "peer": true }, "node_modules/cross-spawn": { "version": "7.0.3", @@ -1525,6 +1558,15 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==", + "license": "MIT", + "engines": { + "node": ">=0.4.0" + } + }, "node_modules/depd": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", @@ -1556,6 +1598,8 @@ "integrity": "sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==", "dev": true, "license": "BSD-3-Clause", + "optional": true, + "peer": true, "engines": { "node": ">=0.3.1" } @@ -2502,6 +2546,26 @@ "integrity": "sha512-X8cqMLLie7KsNUDSdzeN8FYK9rEt4Dt67OsG/DNGnYTSDBG4uFAJFBnUeiV+zCVAvwFy56IjM9sH51jVaEhNxw==", "dev": true }, + "node_modules/follow-redirects": { + "version": "1.15.6", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.6.tgz", + "integrity": "sha512-wWN62YITEaOpSK584EZXJafH1AGpO8RVgElfkuXbTOrPX4fIfOyEpW/CsiNd8JdYrAoOvafRTOEnvsO++qCqFA==", + "funding": [ + { + "type": "individual", + "url": "https://github.com/sponsors/RubenVerborgh" + } + ], + "license": "MIT", + "engines": { + "node": ">=4.0" + }, + "peerDependenciesMeta": { + "debug": { + "optional": true + } + } + }, "node_modules/for-each": { "version": "0.3.3", "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz", @@ -2527,6 +2591,20 @@ "url": "https://github.com/sponsors/isaacs" } }, + "node_modules/form-data": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.0.tgz", + "integrity": "sha512-ETEklSGi5t0QMZuiXoA/Q6vcnxcLQP5vdugSpuAyi6SVGi2clPPp+xgEhuMaHC+zGgn31Kd235W35f7Hykkaww==", + "license": "MIT", + "dependencies": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "mime-types": "^2.1.12" + }, + "engines": { + "node": ">= 6" + } + }, "node_modules/forwarded": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", @@ -3562,7 +3640,9 @@ "resolved": "https://registry.npmjs.org/make-error/-/make-error-1.3.6.tgz", "integrity": "sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw==", "dev": true, - "license": "ISC" + "license": "ISC", + "optional": true, + "peer": true }, "node_modules/media-typer": { "version": "0.3.0", @@ -4336,6 +4416,12 @@ "node": ">= 0.10" } }, + "node_modules/proxy-from-env": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", + "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==", + "license": "MIT" + }, "node_modules/punycode": { "version": "2.3.1", "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz", @@ -5310,6 +5396,8 @@ "integrity": "sha512-f0FFpIdcHgn8zcPSbf1dRevwt047YMnaiJM3u2w2RewrB+fob/zePZcrOyQoLMMO7aBIddLcQIEK5dYjkLnGrQ==", "dev": true, "license": "MIT", + "optional": true, + "peer": true, "dependencies": { "@cspotcode/source-map-support": "^0.8.0", "@tsconfig/node10": "^1.0.7", @@ -5353,7 +5441,9 @@ "resolved": "https://registry.npmjs.org/arg/-/arg-4.1.3.tgz", "integrity": "sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA==", "dev": true, - "license": "MIT" + "license": "MIT", + "optional": true, + "peer": true }, "node_modules/tsconfig-paths": { "version": "3.15.0", @@ -5553,7 +5643,9 @@ "resolved": "https://registry.npmjs.org/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz", "integrity": "sha512-wa7YjyUGfNZngI/vtK0UHAN+lgDCxBPCylVXGp0zu59Fz5aiGtNXaq3DhIov063MorB+VfufLh3JlF2KdTK3xg==", "dev": true, - "license": "MIT" + "license": "MIT", + "optional": true, + "peer": true }, "node_modules/vary": { "version": "1.1.2", @@ -5814,6 +5906,8 @@ "integrity": "sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q==", "dev": true, "license": "MIT", + "optional": true, + "peer": true, "engines": { "node": ">=6" } diff --git a/package.json b/package.json index af8572d..48224a0 100644 --- a/package.json +++ b/package.json @@ -2,13 +2,15 @@ "name": "frontend", "version": "0.1.0", "private": true, + "type": "module", "scripts": { - "dev": "node server.js", + "dev": "next dev", "build": "next build", - "start": "NODE_ENV=production node server.js", + "start": "next start", "lint": "next lint" }, "dependencies": { + "axios": "^1.7.2", "cors": "^2.8.5", "express": "^4.19.2", "http": "^0.0.1-security", @@ -19,15 +21,13 @@ "socket.io-client": "^4.7.5" }, "devDependencies": { - "@types/node": "^20.14.10", + "@types/node": "^20", "@types/react": "^18", "@types/react-dom": "^18", - "@types/socket.io": "^3.0.2", "eslint": "^8", "eslint-config-next": "14.2.4", "postcss": "^8", "tailwindcss": "^3.4.1", - "ts-node": "^10.9.2", "typescript": "^5" }, "description": "This is a [Next.js](https://nextjs.org/) project bootstrapped with [`create-next-app`](https://github.com/vercel/next.js/tree/canary/packages/create-next-app).", diff --git a/server.ts b/server.ts deleted file mode 100644 index 3f0dce8..0000000 --- a/server.ts +++ /dev/null @@ -1,36 +0,0 @@ -import { createServer } from "http"; -import { parse } from "url"; -import next from "next"; -import { Server } from "socket.io"; - -const dev = process.env.NODE_ENV !== "production"; -const hostname = "localhost"; -const port = 3000; -const app = next({ dev, hostname, port }); -const handle = app.getRequestHandler(); - -app.prepare().then(() => { - const server = createServer((req, res) => { - const parsedUrl = parse(req.url!, true); - handle(req, res, parsedUrl); - }); - - const io = new Server(server, { - cors: { - origin: "*", - methods: ["GET", "POST"] - } - }); - - io.on("connection", (socket) => { - console.log("A user connected"); - - socket.on("disconnect", () => { - console.log("User disconnected"); - }); - }); - - server.listen(port, () => { - console.log(`> Ready on http://${hostname}:${port}`); - }); -}); \ No newline at end of file diff --git a/tsconfig.json b/tsconfig.json index e7ff90f..6e25b48 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -21,6 +21,6 @@ "@/*": ["./*"] } }, - "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts"], + "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts", "server.js", "components/chat/client.jsx", "api/socket.ts", "components/chat/client.ts"], "exclude": ["node_modules"] } From 82725c2238592d970286b4a286c726aeb80b6a29 Mon Sep 17 00:00:00 2001 From: eunwoo-levi Date: Sun, 14 Jul 2024 03:05:37 +0900 Subject: [PATCH 3/7] Resolve merge conflicts in Chat components --- app/Chat/{ => [id]}/layout.tsx | 17 +- app/Chat/[id]/page.tsx | 14 + app/Chat/page.tsx | 61 +- app/Create/page.tsx | 74 +++ app/_api/api.ts | 54 ++ app/store.ts | 29 + app/types/ChatRoom.ts | 8 + components/CreateChatRoom.tsx | 85 +++ components/Navbar.tsx | 67 ++- components/chatting/ChatWindow.tsx | 43 +- components/chatting/SideBar.tsx | 108 +++- components/login/AccountForm.tsx | 60 +- components/login/NewAccount.tsx | 3 +- components/page/Input.tsx | 24 + package-lock.json | 878 ++--------------------------- package.json | 8 + 16 files changed, 651 insertions(+), 882 deletions(-) rename app/Chat/{ => [id]}/layout.tsx (60%) create mode 100644 app/Chat/[id]/page.tsx create mode 100644 app/Create/page.tsx create mode 100644 app/_api/api.ts create mode 100644 app/store.ts create mode 100644 app/types/ChatRoom.ts create mode 100644 components/CreateChatRoom.tsx create mode 100644 components/page/Input.tsx diff --git a/app/Chat/layout.tsx b/app/Chat/[id]/layout.tsx similarity index 60% rename from app/Chat/layout.tsx rename to app/Chat/[id]/layout.tsx index ef5cbd7..7fc9835 100644 --- a/app/Chat/layout.tsx +++ b/app/Chat/[id]/layout.tsx @@ -1,8 +1,9 @@ -"use client"; -import Footer from "@/components/chatting/Footer"; -import Header from "@/components/chatting/Header"; -import Sidebar from "@/components/chatting/SideBar"; -import { useState } from "react"; +'use client'; + +import React, { useState } from 'react'; +import Header from "@/components/Header"; +import Sidebar from "@/components/SideBar"; +import Footer from "@/components/Footer"; const Layout: React.FC<{ children: React.ReactNode }> = ({ children }) => { const [isSidebarOpen, setIsSidebarOpen] = useState(true); @@ -13,10 +14,12 @@ const Layout: React.FC<{ children: React.ReactNode }> = ({ children }) => { return (
-
+ {/*
*/}
-
{children}
+
+ {children} +
diff --git a/app/Chat/[id]/page.tsx b/app/Chat/[id]/page.tsx new file mode 100644 index 0000000..17c31c6 --- /dev/null +++ b/app/Chat/[id]/page.tsx @@ -0,0 +1,14 @@ +'use client'; +import { useRouter,useParams } from 'next/navigation'; +import ChatWindow from '@/components/ChatWindow'; + +const ChatPage = () => { +// const router = useRouter(); + const { id } = useParams(); + + if (!id) return
Loading...
; + + return ; +}; + +export default ChatPage; diff --git a/app/Chat/page.tsx b/app/Chat/page.tsx index a003998..e27197d 100644 --- a/app/Chat/page.tsx +++ b/app/Chat/page.tsx @@ -1,5 +1,58 @@ -import ChatWindow from "@/components/chatting/ChatWindow"; +"use client"; -export default function ChatPage() { - return ; -} +import { useEffect, useState } from "react"; +import { getChatting } from "@/app/_api/api"; +import { useAuthStore } from "@/app/store"; +import Link from "next/link"; +import { ChatRoom } from "../types/ChatRoom"; + +const ChatList = () => { + const [chatRooms, setChatRooms] = useState([]); + const [loading, setLoading] = useState(true); + const [error, setError] = useState(null); + const { accessToken } = useAuthStore(); + + useEffect(() => { + const fetchChatRooms = async () => { + if (!accessToken) { + setError("No Access"); + setLoading(false); + return; + } + try { + const data = await getChatting(accessToken); + setChatRooms(data); + } catch (error) { + setError("Failed to load chat rooms. Please try again."); + } finally { + setLoading(false); + } + }; + + fetchChatRooms(); + }, [accessToken]); + + if (loading) return

Loading...

; + if (error) return

{error}

; + + return ( +
+

Your Chat Rooms

+
    + {chatRooms.map((room) => ( +
  • + {room.title} + + Go to Chat + +
  • + ))} +
+
+ ); +}; + +export default ChatList; diff --git a/app/Create/page.tsx b/app/Create/page.tsx new file mode 100644 index 0000000..4422ee1 --- /dev/null +++ b/app/Create/page.tsx @@ -0,0 +1,74 @@ +// pages/create.tsx +"use client"; + +import { useState } from "react"; +import { useRouter } from "next/navigation"; +import { getSignUp } from "@/app/_api/api"; + +const CreateAccount = () => { + const [email, setEmail] = useState(''); + const [password, setPassword] = useState(''); + const [nickname, setNickname] = useState(''); + const [error, setError] = useState(null); + const router = useRouter(); + + const handleSubmit = async (event: React.FormEvent) => { + event.preventDefault(); + try { + await getSignUp(email, password, nickname); + router.push('/login'); + } catch (error) { + setError('Failed to create account. Please try again.'); + } + }; + + return ( +
+

Create an Account

+
+
+ + setEmail(e.target.value)} + className="mt-1 block w-full px-3 py-2 border border-gray-300 rounded-md shadow-sm focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm" + required + /> +
+
+ + setPassword(e.target.value)} + className="mt-1 block w-full px-3 py-2 border border-gray-300 rounded-md shadow-sm focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm" + required + /> +
+
+ + setNickname(e.target.value)} + className="mt-1 block w-full px-3 py-2 border border-gray-300 rounded-md shadow-sm focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm" + required + /> +
+ +
+ {error &&

{error}

} +
+ ); +}; + +export default CreateAccount; diff --git a/app/_api/api.ts b/app/_api/api.ts new file mode 100644 index 0000000..631cf97 --- /dev/null +++ b/app/_api/api.ts @@ -0,0 +1,54 @@ +import axios from 'axios'; +import { useAuthStore } from "../store"; + +const BASE_URL = 'https://api.g-start-up.com/api'; +const accessToken = useAuthStore.getState().accessToken; + +export const getLogin = async (email: string, password: string) => { + const response = await axios.post(`${BASE_URL}/auth/login`, { email, password }); + return response.data.data; +} + +export const getSignUp = async (email: string, password: string, nickname: string) => { + const response = await axios.post(`${BASE_URL}/auth/join`, { email, password, nickname }); + const { accessToken, refreshToken } = response.data; + const setTokens = useAuthStore.getState().setTokens; + setTokens(accessToken, refreshToken); + return response.data; +} + +export const getChatting = async (accessToken: string) => { + const response = await axios.get(`${BASE_URL}/chat`, { + headers: { 'Authorization': `Bearer ${accessToken}` } + }); + return response.data.data; +} + +export const createChatRoom = async (title: string, accessToken: string) => { + const response = await axios.post(`${BASE_URL}/chat`, { title }, { + headers: { 'Authorization': `Bearer ${accessToken}` } + }); + return response.data; +} + +export const getMessages = async (r_id: number, accessToken: string) => { + if (!accessToken) { + console.error('No access token found'); + throw new Error('No access token found'); + } + const response = await axios.get(`${BASE_URL}/chat/${r_id}/messages`, { + headers: { 'Authorization': `Bearer ${accessToken}` } + }); + return response.data.data; +} + +export const deleteChat = async (r_id: number, accessToken: string) => { + if (!accessToken) { + console.error('No access token found'); + throw new Error('No access token found'); + } + await axios.delete(`${BASE_URL}/chat/${r_id}`, { + headers: { 'Authorization': `Bearer ${accessToken}` } + }); + console.log(`Chat room with id ${r_id} deleted successfully`); +} \ No newline at end of file diff --git a/app/store.ts b/app/store.ts new file mode 100644 index 0000000..1264962 --- /dev/null +++ b/app/store.ts @@ -0,0 +1,29 @@ +import {create} from 'zustand'; +import {persist} from 'zustand/middleware' +interface AuthState { + accessToken: string; + refreshToken: string; + setTokens: (accessToken: string, refreshToken: string) => void; + clearTokens: () => void; +} + +// export const useAuthStore = create((set) => ({ +// accessToken: '', +// refreshToken:'', +// setTokens: (accessToken, refreshToken) => set({ accessToken, refreshToken }), +// clearTokens: () => set({ accessToken: '', refreshToken:'' }), +// })); + +export const useAuthStore = create( + persist( + (set,get)=>({ + accessToken:'', + refreshToken:'', + setTokens: (accessToken, refreshToken) => set({ accessToken, refreshToken }), + clearTokens: () => set({ accessToken: '', refreshToken:'' }), + }), + {name:'auth-storage', + getStorage:()=>sessionStorage, + } + ) +) \ No newline at end of file diff --git a/app/types/ChatRoom.ts b/app/types/ChatRoom.ts new file mode 100644 index 0000000..81693bf --- /dev/null +++ b/app/types/ChatRoom.ts @@ -0,0 +1,8 @@ +export interface ChatRoom { + cr_id: number; + title: string; + u_id: number; + cr_created_at: Date; + cr_updated_at: Date; + } + \ No newline at end of file diff --git a/components/CreateChatRoom.tsx b/components/CreateChatRoom.tsx new file mode 100644 index 0000000..3b9f72b --- /dev/null +++ b/components/CreateChatRoom.tsx @@ -0,0 +1,85 @@ +'use client'; + +import { useState, useEffect } from 'react'; +import { useRouter } from 'next/navigation'; +import { createChatRoom } from '@/app/_api/api'; +import { useAuthStore } from '@/app/store'; + +interface CreateChatRoomFormProps { + onClose: () => void; +} + +const CreateChatRoomForm: React.FC = ({ onClose }) => { + const [title, setTitle] = useState(''); + const [error, setError] = useState(null); + const [successMessage, setSuccessMessage] = useState(null); + const { accessToken } = useAuthStore(); + const router = useRouter(); + + const handleSubmit = async (event: React.FormEvent) => { + event.preventDefault(); + if (!accessToken) { + setError('No Access Token available. Please log in again.'); + return; + } + try { + const data = await createChatRoom(title, accessToken); + if (data === null) { + setError('Failed to create chat room. Received null data.'); + return; + } + setSuccessMessage('Chat room created successfully!'); + setError(null); + setTitle(''); + if (data.cr_id) { + onClose(); + router.refresh(); + } else { + setError('Created chat room, but no room ID was returned.'); + } + } catch (error) { + if (error instanceof Error) { + setError(`Failed to create chat room: ${error.message}`); + } else { + setError('An unknown error occurred while creating the chat room.'); + } + } + }; + + // useEffect(() => { + // if (successMessage) { + // router.refresh(); + // } + // }, [successMessage]); + + return ( +
+

Create a New Chat Room

+
+
+ + setTitle(e.target.value)} + className="mt-1 block w-full px-3 py-2 border border-gray-300 rounded-md shadow-sm focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm" + required + /> +
+ +
+ {error &&

{error}

} + {successMessage &&

{successMessage}

} +
+ ); +}; + +export default CreateChatRoomForm; diff --git a/components/Navbar.tsx b/components/Navbar.tsx index 5193330..7f1a9ee 100644 --- a/components/Navbar.tsx +++ b/components/Navbar.tsx @@ -1,19 +1,27 @@ -"use client"; +'use client'; import Link from "next/link"; -import { usePathname } from "next/navigation"; import { useState } from "react"; +import { useAuthStore } from "@/app/store"; +import { useRouter } from "next/navigation"; +import CreateChatRoomForm from "@/components/CreateChatRoom"; const Navbar = () => { - const [showCopied, setShowCopied] = useState(false); - const usepathname = usePathname(); + const [showModal, setShowModal] = useState(false); + const router = useRouter(); + const { accessToken, clearTokens } = useAuthStore(); - const handleCopyEmail = () => { - const email = "www.knu.gmail.com"; - navigator.clipboard.writeText(email).then(() => { - setShowCopied(true); - setTimeout(() => setShowCopied(false), 2000); - }); + const handleLogout = () => { + clearTokens(); + router.push('/Chat'); + }; + + const handleCreateChat = () => { + setShowModal(true); + }; + + const closeModal = () => { + setShowModal(false); }; return ( @@ -25,10 +33,10 @@ const Navbar = () => { InjuryLawAssist
- + HOME - + ABOUT @@ -40,26 +48,37 @@ const Navbar = () => {
- {usepathname !== "/login" ? ( - - Login - + {accessToken ? ( + ) : ( - Logout + Login )}
+ {showModal && ( +
+
+ + +
+
+ )}
); }; diff --git a/components/chatting/ChatWindow.tsx b/components/chatting/ChatWindow.tsx index 2ba85a3..cf7b1d7 100644 --- a/components/chatting/ChatWindow.tsx +++ b/components/chatting/ChatWindow.tsx @@ -1,17 +1,40 @@ -"use client"; -import React, { useState, useEffect, useRef } from "react"; -import ChatBubble from "./ChatBubble"; -import ChatInput from "./ChatInput"; - -const ChatWindow: React.FC = () => { - const [messages, setMessages] = useState<{ text: string; isUser: boolean }[]>( - [] - ); +'use client'; +import React, { useState, useEffect, useRef } from 'react'; +import ChatBubble from './ChatBubble'; +import ChatInput from './ChatInput'; +import { getMessages } from '@/app/_api/api'; +import { useAuthStore } from '@/app/store'; + +interface ChatWindowProps { + r_id: number; +} + +const ChatWindow: React.FC = ({ r_id }) => { + const [messages, setMessages] = useState<{ text: string; isUser: boolean }[]>([]); const messagesEndRef = useRef(null); + const { accessToken } = useAuthStore(); + + useEffect(() => { + if (!r_id || !accessToken) return; + + const fetchMessages = async () => { + const fetchedMessages = await getMessages(r_id, accessToken); + + if (fetchedMessages) { + const formattedMessages = fetchedMessages.map((msg: any) => ({ + text: msg.content, + isUser: msg.isUser, + })); + setMessages(formattedMessages); + } + }; + + fetchMessages(); + }, [r_id, accessToken]); const handleSendMessage = (message: string) => { setMessages((prev) => [...prev, { text: message, isUser: true }]); - setMessages((prev) => [...prev, { text: "asd", isUser: false }]); + setMessages((prev) => [...prev, { text: "자동 응답 메시지", isUser: false }]); // 실제 응답 메시지로 교체하세요 }; useEffect(() => { diff --git a/components/chatting/SideBar.tsx b/components/chatting/SideBar.tsx index 77fbe74..2999ebc 100644 --- a/components/chatting/SideBar.tsx +++ b/components/chatting/SideBar.tsx @@ -1,4 +1,11 @@ -import React from 'react'; +// components/Sidebar.tsx +'use client'; + +import React, { useEffect, useState } from 'react'; +import { getChatting, deleteChat } from '@/app/_api/api'; +import { useAuthStore } from '@/app/store'; +import { ChatRoom } from '@/app/types/ChatRoom'; +import { useRouter } from 'next/navigation'; interface SidebarProps { isOpen: boolean; @@ -6,23 +13,94 @@ interface SidebarProps { } const Sidebar: React.FC = ({ isOpen, toggleSidebar }) => { + const [chatRooms, setChatRooms] = useState([]); + const [loading, setLoading] = useState(true); + const [error, setError] = useState(null); + const [isClient, setIsClient] = useState(false); + const { accessToken } = useAuthStore(); + const router = useRouter(); + + useEffect(() => { + setIsClient(true); + const fetchChatRooms = async () => { + if (!accessToken) { + setError('No Access'); + setLoading(false); + return; + } + try { + const data = await getChatting(accessToken); + setChatRooms(data); + } catch (error) { + setError('Failed to load chat rooms. Please try again.'); + } finally { + setLoading(false); + } + }; + + fetchChatRooms(); + }, [accessToken]); + + const handleDelete = async (r_id: number): Promise => { + try { + await deleteChat(r_id, accessToken); + setChatRooms(chatRooms.filter(room => room.cr_id !== r_id)); + router.refresh(); + } catch (error) { + setError('Failed to delete chat room. Please try again.'); + } + }; + + const handleSelectChatRoom = (r_id: number) => { + router.push(`/Chat/${r_id}`); + }; + + if (!isClient) { + return null; + } + return ( -
-
- -
- {isOpen && ( -
-

Sidebar Content

+
+
+
+
- )} + {isOpen && ( +
+

Your Chat Rooms

+ {loading &&

Loading...

} + {error &&

{error}

} +
    + {chatRooms.map((room) => ( +
  • + {room.title} +
    + + +
    +
  • + ))} +
+
+ )} +
); }; -export default Sidebar; +export default Sidebar; \ No newline at end of file diff --git a/components/login/AccountForm.tsx b/components/login/AccountForm.tsx index d0ddbbc..df4cb2a 100644 --- a/components/login/AccountForm.tsx +++ b/components/login/AccountForm.tsx @@ -1,11 +1,63 @@ -import InputLogin from "../shared/Inputlogin"; +'use client' +import Input from "./Input"; import NewAccount from "./NewAccount"; +import { useState } from "react"; +import { getLogin } from "@/app/_api/api"; +import { useRouter } from "next/navigation" +import { useAuthStore } from "@/app/store"; const AccountForm = () => { + const [email, setEmail] = useState(''); + const [password, setPassword] = useState(''); + const [errorMessage,setErrorMessage] = useState('') + const router = useRouter(); + const setTokens = useAuthStore((state) => state.setTokens); + + const handleSubmit = async (e: React.FormEvent) => { + e.preventDefault(); + try { + const data = await getLogin(email, password); + if (data && data.accessToken && data.refreshToken) { + console.log('Login successful:', data); + setTokens(data.accessToken, data.refreshToken); + router.push('/Chat'); + } else { + throw new Error('Invalid response from server'); + } + } catch (err) { + console.error('Login failed', err); + if (err instanceof Error) { + if (err.message === 'Invalid response from server') { + setErrorMessage('Login failed: Invalid response from server. Please try again.'); + } else if (err.message.includes('Network Error')) { + setErrorMessage('Network error. Please check your internet connection and try again.'); + } else if (err.message.includes('401')) { + setErrorMessage('Invalid email or password. Please check your credentials and try again.'); + } else if (err.message.includes('500')) { + setErrorMessage('Server error. Please try again later.'); + } + } + console.log(errorMessage); + } + } + return ( -
- - + + setEmail(e.target.value)} + /> + setPassword(e.target.value)} + />
- ) =>void; +} + +const Input = ({ context, type, placeholder,value,onChange }: InputProps) => { + return ( +
+

{context}

+ +
+ ); +}; + +export default Input; diff --git a/package-lock.json b/package-lock.json index ec6f0b4..c55d3c7 100644 --- a/package-lock.json +++ b/package-lock.json @@ -7,17 +7,13 @@ "": { "name": "frontend", "version": "0.1.0", - "license": "ISC", "dependencies": { "axios": "^1.7.2", - "cors": "^2.8.5", - "express": "^4.19.2", - "http": "^0.0.1-security", "next": "14.2.4", "react": "^18", "react-dom": "^18", - "socket.io": "^4.7.5", - "socket.io-client": "^4.7.5" + "socket.io-client": "^4.7.5", + "zustand": "^4.5.4" }, "devDependencies": { "@types/node": "^20", @@ -267,126 +263,6 @@ "glob": "10.3.10" } }, - "node_modules/@next/swc-darwin-arm64": { - "version": "14.2.4", - "resolved": "https://registry.npmjs.org/@next/swc-darwin-arm64/-/swc-darwin-arm64-14.2.4.tgz", - "integrity": "sha512-AH3mO4JlFUqsYcwFUHb1wAKlebHU/Hv2u2kb1pAuRanDZ7pD/A/KPD98RHZmwsJpdHQwfEc/06mgpSzwrJYnNg==", - "cpu": [ - "arm64" - ], - "optional": true, - "os": [ - "darwin" - ], - "engines": { - "node": ">= 10" - } - }, - "node_modules/@next/swc-darwin-x64": { - "version": "14.2.4", - "resolved": "https://registry.npmjs.org/@next/swc-darwin-x64/-/swc-darwin-x64-14.2.4.tgz", - "integrity": "sha512-QVadW73sWIO6E2VroyUjuAxhWLZWEpiFqHdZdoQ/AMpN9YWGuHV8t2rChr0ahy+irKX5mlDU7OY68k3n4tAZTg==", - "cpu": [ - "x64" - ], - "optional": true, - "os": [ - "darwin" - ], - "engines": { - "node": ">= 10" - } - }, - "node_modules/@next/swc-linux-arm64-gnu": { - "version": "14.2.4", - "resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-gnu/-/swc-linux-arm64-gnu-14.2.4.tgz", - "integrity": "sha512-KT6GUrb3oyCfcfJ+WliXuJnD6pCpZiosx2X3k66HLR+DMoilRb76LpWPGb4tZprawTtcnyrv75ElD6VncVamUQ==", - "cpu": [ - "arm64" - ], - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">= 10" - } - }, - "node_modules/@next/swc-linux-arm64-musl": { - "version": "14.2.4", - "resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-musl/-/swc-linux-arm64-musl-14.2.4.tgz", - "integrity": "sha512-Alv8/XGSs/ytwQcbCHwze1HmiIkIVhDHYLjczSVrf0Wi2MvKn/blt7+S6FJitj3yTlMwMxII1gIJ9WepI4aZ/A==", - "cpu": [ - "arm64" - ], - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">= 10" - } - }, - "node_modules/@next/swc-linux-x64-gnu": { - "version": "14.2.4", - "resolved": "https://registry.npmjs.org/@next/swc-linux-x64-gnu/-/swc-linux-x64-gnu-14.2.4.tgz", - "integrity": "sha512-ze0ShQDBPCqxLImzw4sCdfnB3lRmN3qGMB2GWDRlq5Wqy4G36pxtNOo2usu/Nm9+V2Rh/QQnrRc2l94kYFXO6Q==", - "cpu": [ - "x64" - ], - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">= 10" - } - }, - "node_modules/@next/swc-linux-x64-musl": { - "version": "14.2.4", - "resolved": "https://registry.npmjs.org/@next/swc-linux-x64-musl/-/swc-linux-x64-musl-14.2.4.tgz", - "integrity": "sha512-8dwC0UJoc6fC7PX70csdaznVMNr16hQrTDAMPvLPloazlcaWfdPogq+UpZX6Drqb1OBlwowz8iG7WR0Tzk/diQ==", - "cpu": [ - "x64" - ], - "optional": true, - "os": [ - "linux" - ], - "engines": { - "node": ">= 10" - } - }, - "node_modules/@next/swc-win32-arm64-msvc": { - "version": "14.2.4", - "resolved": "https://registry.npmjs.org/@next/swc-win32-arm64-msvc/-/swc-win32-arm64-msvc-14.2.4.tgz", - "integrity": "sha512-jxyg67NbEWkDyvM+O8UDbPAyYRZqGLQDTPwvrBBeOSyVWW/jFQkQKQ70JDqDSYg1ZDdl+E3nkbFbq8xM8E9x8A==", - "cpu": [ - "arm64" - ], - "optional": true, - "os": [ - "win32" - ], - "engines": { - "node": ">= 10" - } - }, - "node_modules/@next/swc-win32-ia32-msvc": { - "version": "14.2.4", - "resolved": "https://registry.npmjs.org/@next/swc-win32-ia32-msvc/-/swc-win32-ia32-msvc-14.2.4.tgz", - "integrity": "sha512-twrmN753hjXRdcrZmZttb/m5xaCBFa48Dt3FbeEItpJArxriYDunWxJn+QFXdJ3hPkm4u7CKxncVvnmgQMY1ag==", - "cpu": [ - "ia32" - ], - "optional": true, - "os": [ - "win32" - ], - "engines": { - "node": ">= 10" - } - }, "node_modules/@next/swc-win32-x64-msvc": { "version": "14.2.4", "resolved": "https://registry.npmjs.org/@next/swc-win32-x64-msvc/-/swc-win32-x64-msvc-14.2.4.tgz", @@ -509,21 +385,6 @@ "optional": true, "peer": true }, - "node_modules/@types/cookie": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/@types/cookie/-/cookie-0.4.1.tgz", - "integrity": "sha512-XW/Aa8APYr6jSVVA1y/DEIZX0/GMKLEVekNG727R8cs56ahETkRAy/3DR7+fJyh7oUgGwNQaRfXCun0+KbWY7Q==", - "license": "MIT" - }, - "node_modules/@types/cors": { - "version": "2.8.17", - "resolved": "https://registry.npmjs.org/@types/cors/-/cors-2.8.17.tgz", - "integrity": "sha512-8CGDvrBj1zgo2qE+oS3pOCyYNqCPryMWY2bGfwA0dcfopWGgxs+78df0Rs3rc9THP4JkOhLsAa+15VdpAqkcUA==", - "license": "MIT", - "dependencies": { - "@types/node": "*" - } - }, "node_modules/@types/json5": { "version": "0.0.29", "resolved": "https://registry.npmjs.org/@types/json5/-/json5-0.0.29.tgz", @@ -534,6 +395,7 @@ "version": "20.14.10", "resolved": "https://registry.npmjs.org/@types/node/-/node-20.14.10.tgz", "integrity": "sha512-MdiXf+nDuMvY0gJKxyfZ7/6UFsETO7mGKF54MVD/ekJS6HdFtpZFBgrh6Pseu64XTb2MLyFPlbW6hj8HYRQNOQ==", + "dev": true, "license": "MIT", "dependencies": { "undici-types": "~5.26.4" @@ -543,13 +405,13 @@ "version": "15.7.12", "resolved": "https://registry.npmjs.org/@types/prop-types/-/prop-types-15.7.12.tgz", "integrity": "sha512-5zvhXYtRNRluoE/jAp4GVsSduVUzNWKkOZrCDBWYtE7biZywwdC2AcEzg+cSMLFRfVgeAFqpfNabiPjxFddV1Q==", - "dev": true + "devOptional": true }, "node_modules/@types/react": { "version": "18.3.3", "resolved": "https://registry.npmjs.org/@types/react/-/react-18.3.3.tgz", "integrity": "sha512-hti/R0pS0q1/xx+TsI73XIqk26eBsISZ2R0wUijXIngRK9R/e7Xw/cXVxQK7R5JjW+SV4zGcn5hXjudkN/pLIw==", - "dev": true, + "devOptional": true, "dependencies": { "@types/prop-types": "*", "csstype": "^3.0.2" @@ -697,19 +559,6 @@ "integrity": "sha512-zuVdFrMJiuCDQUMCzQaD6KL28MjnqqN8XnAqiEq9PNm/hCPTSGfrXCOfwj1ow4LFb/tNymJPwsNbVePc1xFqrQ==", "dev": true }, - "node_modules/accepts": { - "version": "1.3.8", - "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.8.tgz", - "integrity": "sha512-PYAthTa2m2VKxuvSD3DPC/Gy+U+sOA1LAuT8mkmRuvw+NACSaeXEQ+NHcVF7rONl6qcaxV3Uuemwawk+7+SJLw==", - "license": "MIT", - "dependencies": { - "mime-types": "~2.1.34", - "negotiator": "0.6.3" - }, - "engines": { - "node": ">= 0.6" - } - }, "node_modules/acorn": { "version": "8.12.1", "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.12.1.tgz", @@ -842,12 +691,6 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/array-flatten": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", - "integrity": "sha512-PCVAQswWemu6UdxsDFFX/+gVeYqKAod3D3UVm91jHwynguOwAvYPhx8nNlM++NqRcK6CxxpUafjmhIdKiHibqg==", - "license": "MIT" - }, "node_modules/array-includes": { "version": "3.1.8", "resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.8.tgz", @@ -1065,15 +908,6 @@ "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", "dev": true }, - "node_modules/base64id": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/base64id/-/base64id-2.0.0.tgz", - "integrity": "sha512-lGe34o6EHj9y3Kts9R4ZYs/Gr+6N7MCaMlIFA3F1R2O5/m7K06AxfSeO5530PEERE6/WyEg3lsuyw4GHlPZHog==", - "license": "MIT", - "engines": { - "node": "^4.5.0 || >= 5.9" - } - }, "node_modules/binary-extensions": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.3.0.tgz", @@ -1086,45 +920,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/body-parser": { - "version": "1.20.2", - "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.20.2.tgz", - "integrity": "sha512-ml9pReCu3M61kGlqoTm2umSXTlRTuGTx0bfYj+uIUKKYycG5NtSbeetV3faSU6R7ajOPw0g/J1PvK4qNy7s5bA==", - "license": "MIT", - "dependencies": { - "bytes": "3.1.2", - "content-type": "~1.0.5", - "debug": "2.6.9", - "depd": "2.0.0", - "destroy": "1.2.0", - "http-errors": "2.0.0", - "iconv-lite": "0.4.24", - "on-finished": "2.4.1", - "qs": "6.11.0", - "raw-body": "2.5.2", - "type-is": "~1.6.18", - "unpipe": "1.0.0" - }, - "engines": { - "node": ">= 0.8", - "npm": "1.2.8000 || >= 1.4.16" - } - }, - "node_modules/body-parser/node_modules/debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "license": "MIT", - "dependencies": { - "ms": "2.0.0" - } - }, - "node_modules/body-parser/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", - "license": "MIT" - }, "node_modules/brace-expansion": { "version": "1.1.11", "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", @@ -1158,19 +953,11 @@ "node": ">=10.16.0" } }, - "node_modules/bytes": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", - "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, "node_modules/call-bind": { "version": "1.0.7", "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.7.tgz", "integrity": "sha512-GHTSNSYICQ7scH7sZ+M2rFopRoLh8t2bLSW6BbgrtLsahOIB5iyAVJf9GjWK3cYTDaMj4XdBpM1cA6pIS0Kv2w==", + "dev": true, "dependencies": { "es-define-property": "^1.0.0", "es-errors": "^1.3.0", @@ -1324,55 +1111,6 @@ "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", "dev": true }, - "node_modules/content-disposition": { - "version": "0.5.4", - "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.4.tgz", - "integrity": "sha512-FveZTNuGw04cxlAiWbzi6zTAL/lhehaWbTtgluJh4/E95DqMwTmha3KZN1aAWA8cFIhHzMZUvLevkw5Rqk+tSQ==", - "license": "MIT", - "dependencies": { - "safe-buffer": "5.2.1" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/content-type": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.5.tgz", - "integrity": "sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/cookie": { - "version": "0.4.2", - "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.4.2.tgz", - "integrity": "sha512-aSWTXFzaKWkvHO1Ny/s+ePFpvKsPnjc551iI41v3ny/ow6tBG5Vd+FuqGNhh1LxOmVzOlGUriIlOaokOvhaStA==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/cookie-signature": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", - "integrity": "sha512-QADzlaHc8icV8I7vbaJXJwod9HWYp8uCqf1xa4OfNu1T7JVxQIrUgOWtHdNDtPiywmFbiS12VjotIXLrKM3orQ==", - "license": "MIT" - }, - "node_modules/cors": { - "version": "2.8.5", - "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", - "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", - "license": "MIT", - "dependencies": { - "object-assign": "^4", - "vary": "^1" - }, - "engines": { - "node": ">= 0.10" - } - }, "node_modules/create-require": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/create-require/-/create-require-1.1.1.tgz", @@ -1412,7 +1150,7 @@ "version": "3.1.3", "resolved": "https://registry.npmjs.org/csstype/-/csstype-3.1.3.tgz", "integrity": "sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==", - "dev": true + "devOptional": true }, "node_modules/damerau-levenshtein": { "version": "1.0.8", @@ -1529,6 +1267,7 @@ "version": "1.1.4", "resolved": "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.4.tgz", "integrity": "sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==", + "dev": true, "dependencies": { "es-define-property": "^1.0.0", "es-errors": "^1.3.0", @@ -1567,25 +1306,6 @@ "node": ">=0.4.0" } }, - "node_modules/depd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", - "integrity": "sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/destroy": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.2.0.tgz", - "integrity": "sha512-2sJGJTaXIIaR1w4iJSNoN0hnMY7Gpc/n8D4qSCJw8QqFWXf7cuAgnEHxBpweaVcPevC2l3KpjYCx3NypQQgaJg==", - "license": "MIT", - "engines": { - "node": ">= 0.8", - "npm": "1.2.8000 || >= 1.4.16" - } - }, "node_modules/didyoumean": { "version": "1.2.2", "resolved": "https://registry.npmjs.org/didyoumean/-/didyoumean-1.2.2.tgz", @@ -1640,48 +1360,12 @@ "integrity": "sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==", "dev": true }, - "node_modules/ee-first": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", - "integrity": "sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==", - "license": "MIT" - }, "node_modules/emoji-regex": { "version": "9.2.2", "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-9.2.2.tgz", "integrity": "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==", "dev": true }, - "node_modules/encodeurl": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", - "integrity": "sha512-TPJXq8JqFaVYm2CWmPvnP2Iyo4ZSM7/QKcSmuMLDObfpH5fi7RUGmd/rTDf+rut/saiDiQEeVTNgAmJEdAOx0w==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/engine.io": { - "version": "6.5.5", - "resolved": "https://registry.npmjs.org/engine.io/-/engine.io-6.5.5.tgz", - "integrity": "sha512-C5Pn8Wk+1vKBoHghJODM63yk8MvrO9EWZUfkAt5HAqIgPE4/8FF0PEGHXtEd40l223+cE5ABWuPzm38PHFXfMA==", - "license": "MIT", - "dependencies": { - "@types/cookie": "^0.4.1", - "@types/cors": "^2.8.12", - "@types/node": ">=10.0.0", - "accepts": "~1.3.4", - "base64id": "2.0.0", - "cookie": "~0.4.1", - "cors": "~2.8.5", - "debug": "~4.3.1", - "engine.io-parser": "~5.2.1", - "ws": "~8.17.1" - }, - "engines": { - "node": ">=10.2.0" - } - }, "node_modules/engine.io-client": { "version": "6.5.4", "resolved": "https://registry.npmjs.org/engine.io-client/-/engine.io-client-6.5.4.tgz", @@ -1781,6 +1465,7 @@ "version": "1.0.0", "resolved": "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.0.tgz", "integrity": "sha512-jxayLKShrEqqzJ0eumQbVhTYQM27CfT1T35+gCgDFoL82JLsXqTJ76zv6A0YLOgEnLUMvLzsDsGIrl8NFpT2gQ==", + "dev": true, "dependencies": { "get-intrinsic": "^1.2.4" }, @@ -1792,6 +1477,7 @@ "version": "1.3.0", "resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz", "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==", + "dev": true, "engines": { "node": ">= 0.4" } @@ -1893,12 +1579,6 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/escape-html": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", - "integrity": "sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==", - "license": "MIT" - }, "node_modules/escape-string-regexp": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", @@ -2323,81 +2003,6 @@ "node": ">=0.10.0" } }, - "node_modules/etag": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", - "integrity": "sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/express": { - "version": "4.19.2", - "resolved": "https://registry.npmjs.org/express/-/express-4.19.2.tgz", - "integrity": "sha512-5T6nhjsT+EOMzuck8JjBHARTHfMht0POzlA60WV2pMD3gyXw2LZnZ+ueGdNxG+0calOJcWKbpFcuzLZ91YWq9Q==", - "license": "MIT", - "dependencies": { - "accepts": "~1.3.8", - "array-flatten": "1.1.1", - "body-parser": "1.20.2", - "content-disposition": "0.5.4", - "content-type": "~1.0.4", - "cookie": "0.6.0", - "cookie-signature": "1.0.6", - "debug": "2.6.9", - "depd": "2.0.0", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "finalhandler": "1.2.0", - "fresh": "0.5.2", - "http-errors": "2.0.0", - "merge-descriptors": "1.0.1", - "methods": "~1.1.2", - "on-finished": "2.4.1", - "parseurl": "~1.3.3", - "path-to-regexp": "0.1.7", - "proxy-addr": "~2.0.7", - "qs": "6.11.0", - "range-parser": "~1.2.1", - "safe-buffer": "5.2.1", - "send": "0.18.0", - "serve-static": "1.15.0", - "setprototypeof": "1.2.0", - "statuses": "2.0.1", - "type-is": "~1.6.18", - "utils-merge": "1.0.1", - "vary": "~1.1.2" - }, - "engines": { - "node": ">= 0.10.0" - } - }, - "node_modules/express/node_modules/cookie": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.6.0.tgz", - "integrity": "sha512-U71cyTamuh1CRNCfpGY6to28lxvNwPG4Guz/EVjgf3Jmzv0vlDp1atT9eS5dDjMYHucpHbWns6Lwf3BKz6svdw==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/express/node_modules/debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "license": "MIT", - "dependencies": { - "ms": "2.0.0" - } - }, - "node_modules/express/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", - "license": "MIT" - }, "node_modules/fast-deep-equal": { "version": "3.1.3", "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", @@ -2477,39 +2082,6 @@ "node": ">=8" } }, - "node_modules/finalhandler": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.2.0.tgz", - "integrity": "sha512-5uXcUVftlQMFnWC9qu/svkWv3GTd2PfUhK/3PLkYNAe7FbqJMt3515HaxE6eRL74GdsriiwujiawdaB1BpEISg==", - "license": "MIT", - "dependencies": { - "debug": "2.6.9", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "on-finished": "2.4.1", - "parseurl": "~1.3.3", - "statuses": "2.0.1", - "unpipe": "~1.0.0" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/finalhandler/node_modules/debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "license": "MIT", - "dependencies": { - "ms": "2.0.0" - } - }, - "node_modules/finalhandler/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", - "license": "MIT" - }, "node_modules/find-up": { "version": "5.0.0", "resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz", @@ -2605,48 +2177,17 @@ "node": ">= 6" } }, - "node_modules/forwarded": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", - "integrity": "sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/fresh": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", - "integrity": "sha512-zJ2mQYM18rEFOudeV4GShTGIQ7RbzA7ozbU9I/XBpm7kqgMywgmylMwXHxZJmkVoYkna9d2pVXVXPdYTP9ej8Q==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, "node_modules/fs.realpath": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", "integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==", "dev": true }, - "node_modules/fsevents": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.3.tgz", - "integrity": "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==", - "dev": true, - "hasInstallScript": true, - "optional": true, - "os": [ - "darwin" - ], - "engines": { - "node": "^8.16.0 || ^10.6.0 || >=11.0.0" - } - }, "node_modules/function-bind": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz", "integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==", + "dev": true, "funding": { "url": "https://github.com/sponsors/ljharb" } @@ -2682,6 +2223,7 @@ "version": "1.2.4", "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.2.4.tgz", "integrity": "sha512-5uYhsJH8VJBTv7oslg4BznJYhDoRI6waYCxMmCdnTrcCrHA/fCFKoTFz2JKKE0HdDFUF7/oQuhzumXJK7paBRQ==", + "dev": true, "dependencies": { "es-errors": "^1.3.0", "function-bind": "^1.1.2", @@ -2838,6 +2380,7 @@ "version": "1.0.1", "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.0.1.tgz", "integrity": "sha512-d65bNlIadxvpb/A2abVdlqKqV563juRnZ1Wtk6s1sIR8uNsXR70xqIzVqxVf1eTqDunwT2MkczEeaezCKTZhwA==", + "dev": true, "dependencies": { "get-intrinsic": "^1.1.3" }, @@ -2878,6 +2421,7 @@ "version": "1.0.2", "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.2.tgz", "integrity": "sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==", + "dev": true, "dependencies": { "es-define-property": "^1.0.0" }, @@ -2889,6 +2433,7 @@ "version": "1.0.3", "resolved": "https://registry.npmjs.org/has-proto/-/has-proto-1.0.3.tgz", "integrity": "sha512-SJ1amZAJUiZS+PhsVLf5tGydlaVB8EdFpaSO4gmiUKUOxk8qzn5AIy4ZeJUmh22znIdk/uMAUT2pl3FxzVUH+Q==", + "dev": true, "engines": { "node": ">= 0.4" }, @@ -2900,6 +2445,7 @@ "version": "1.0.3", "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.3.tgz", "integrity": "sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A==", + "dev": true, "engines": { "node": ">= 0.4" }, @@ -2926,6 +2472,7 @@ "version": "2.0.2", "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.2.tgz", "integrity": "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==", + "dev": true, "dependencies": { "function-bind": "^1.1.2" }, @@ -2933,39 +2480,6 @@ "node": ">= 0.4" } }, - "node_modules/http": { - "version": "0.0.1-security", - "resolved": "https://registry.npmjs.org/http/-/http-0.0.1-security.tgz", - "integrity": "sha512-RnDvP10Ty9FxqOtPZuxtebw1j4L/WiqNMDtuc1YMH1XQm5TgDRaR1G9u8upL6KD1bXHSp9eSXo/ED+8Q7FAr+g==" - }, - "node_modules/http-errors": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-2.0.0.tgz", - "integrity": "sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==", - "license": "MIT", - "dependencies": { - "depd": "2.0.0", - "inherits": "2.0.4", - "setprototypeof": "1.2.0", - "statuses": "2.0.1", - "toidentifier": "1.0.1" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/iconv-lite": { - "version": "0.4.24", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", - "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", - "license": "MIT", - "dependencies": { - "safer-buffer": ">= 2.1.2 < 3" - }, - "engines": { - "node": ">=0.10.0" - } - }, "node_modules/ignore": { "version": "5.3.1", "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.3.1.tgz", @@ -3014,7 +2528,8 @@ "node_modules/inherits": { "version": "2.0.4", "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", - "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==" + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "dev": true }, "node_modules/internal-slot": { "version": "1.0.7", @@ -3030,15 +2545,6 @@ "node": ">= 0.4" } }, - "node_modules/ipaddr.js": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", - "integrity": "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==", - "license": "MIT", - "engines": { - "node": ">= 0.10" - } - }, "node_modules/is-arguments": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/is-arguments/-/is-arguments-1.1.1.tgz", @@ -3644,21 +3150,6 @@ "optional": true, "peer": true }, - "node_modules/media-typer": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", - "integrity": "sha512-dq+qelQ9akHpcOl/gUVRTxVIOkAJ1wR3QAvb4RsVjS8oVoFjDGTc679wJYmUmknUF5HwMLOgb5O+a3KxfWapPQ==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/merge-descriptors": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", - "integrity": "sha512-cCi6g3/Zr1iqQi6ySbseM1Xvooa98N0w31jzUYrXPX2xqObmFGHJ0tQ5u74H3mVh7wLouTseZyYIq39g8cNp1w==", - "license": "MIT" - }, "node_modules/merge2": { "version": "1.4.1", "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", @@ -3668,15 +3159,6 @@ "node": ">= 8" } }, - "node_modules/methods": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", - "integrity": "sha512-iclAHeNqNm68zFtnZ0e+1L2yUIdvzNoauKU4WBA3VvH/vPFieF7qfRlwUZU+DA9P9bPXIS90ulxoUoCH23sV2w==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, "node_modules/micromatch": { "version": "4.0.7", "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.7.tgz", @@ -3690,18 +3172,6 @@ "node": ">=8.6" } }, - "node_modules/mime": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", - "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==", - "license": "MIT", - "bin": { - "mime": "cli.js" - }, - "engines": { - "node": ">=4" - } - }, "node_modules/mime-db": { "version": "1.52.0", "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", @@ -3792,15 +3262,6 @@ "integrity": "sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==", "dev": true }, - "node_modules/negotiator": { - "version": "0.6.3", - "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.3.tgz", - "integrity": "sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, "node_modules/next": { "version": "14.2.4", "resolved": "https://registry.npmjs.org/next/-/next-14.2.4.tgz", @@ -3890,6 +3351,7 @@ "version": "4.1.1", "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==", + "dev": true, "engines": { "node": ">=0.10.0" } @@ -3907,6 +3369,7 @@ "version": "1.13.2", "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.2.tgz", "integrity": "sha512-IRZSRuzJiynemAXPYtPe5BoI/RESNYR7TYm50MC5Mqbd3Jmw5y790sErYw3V6SryFJD64b74qQQs9wn5Bg/k3g==", + "dev": true, "engines": { "node": ">= 0.4" }, @@ -4037,18 +3500,6 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/on-finished": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.4.1.tgz", - "integrity": "sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==", - "license": "MIT", - "dependencies": { - "ee-first": "1.1.1" - }, - "engines": { - "node": ">= 0.8" - } - }, "node_modules/once": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", @@ -4117,15 +3568,6 @@ "node": ">=6" } }, - "node_modules/parseurl": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", - "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, "node_modules/path-exists": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", @@ -4175,12 +3617,6 @@ "url": "https://github.com/sponsors/isaacs" } }, - "node_modules/path-to-regexp": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz", - "integrity": "sha512-5DFkuoqlv1uYQKxy8omFBeJPQcdoE07Kv2sferDCrAq1ohOU+MSDswDIbnx3YAM60qIOnYa53wBhXW0EbMonrQ==", - "license": "MIT" - }, "node_modules/path-type": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/path-type/-/path-type-4.0.0.tgz", @@ -4403,19 +3839,6 @@ "react-is": "^16.13.1" } }, - "node_modules/proxy-addr": { - "version": "2.0.7", - "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.7.tgz", - "integrity": "sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==", - "license": "MIT", - "dependencies": { - "forwarded": "0.2.0", - "ipaddr.js": "1.9.1" - }, - "engines": { - "node": ">= 0.10" - } - }, "node_modules/proxy-from-env": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", @@ -4431,21 +3854,6 @@ "node": ">=6" } }, - "node_modules/qs": { - "version": "6.11.0", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.11.0.tgz", - "integrity": "sha512-MvjoMCJwEarSbUYk5O+nmoSzSutSsTwF85zcHPQ9OrlFoZOYIjaqBAJIqIXjptyD5vThxGq52Xu/MaJzRkIk4Q==", - "license": "BSD-3-Clause", - "dependencies": { - "side-channel": "^1.0.4" - }, - "engines": { - "node": ">=0.6" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/queue-microtask": { "version": "1.2.3", "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", @@ -4466,30 +3874,6 @@ } ] }, - "node_modules/range-parser": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.1.tgz", - "integrity": "sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/raw-body": { - "version": "2.5.2", - "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.5.2.tgz", - "integrity": "sha512-8zGqypfENjCIqGhgXToC8aB2r7YrBX+AQAfIPs/Mlk+BtPTztOvTS01NRW/3Eh60J+a48lt8qsCzirQ6loCVfA==", - "license": "MIT", - "dependencies": { - "bytes": "3.1.2", - "http-errors": "2.0.0", - "iconv-lite": "0.4.24", - "unpipe": "1.0.0" - }, - "engines": { - "node": ">= 0.8" - } - }, "node_modules/react": { "version": "18.3.1", "resolved": "https://registry.npmjs.org/react/-/react-18.3.1.tgz", @@ -4702,26 +4086,6 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/safe-buffer": { - "version": "5.2.1", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", - "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/feross" - }, - { - "type": "patreon", - "url": "https://www.patreon.com/feross" - }, - { - "type": "consulting", - "url": "https://feross.org/support" - } - ], - "license": "MIT" - }, "node_modules/safe-regex-test": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/safe-regex-test/-/safe-regex-test-1.0.3.tgz", @@ -4739,12 +4103,6 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/safer-buffer": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", - "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", - "license": "MIT" - }, "node_modules/scheduler": { "version": "0.23.2", "resolved": "https://registry.npmjs.org/scheduler/-/scheduler-0.23.2.tgz", @@ -4765,70 +4123,11 @@ "node": ">=10" } }, - "node_modules/send": { - "version": "0.18.0", - "resolved": "https://registry.npmjs.org/send/-/send-0.18.0.tgz", - "integrity": "sha512-qqWzuOjSFOuqPjFe4NOsMLafToQQwBSOEpS+FwEt3A2V3vKubTquT3vmLTQpFgMXp8AlFWFuP1qKaJZOtPpVXg==", - "license": "MIT", - "dependencies": { - "debug": "2.6.9", - "depd": "2.0.0", - "destroy": "1.2.0", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "fresh": "0.5.2", - "http-errors": "2.0.0", - "mime": "1.6.0", - "ms": "2.1.3", - "on-finished": "2.4.1", - "range-parser": "~1.2.1", - "statuses": "2.0.1" - }, - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/send/node_modules/debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "license": "MIT", - "dependencies": { - "ms": "2.0.0" - } - }, - "node_modules/send/node_modules/debug/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", - "license": "MIT" - }, - "node_modules/send/node_modules/ms": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", - "license": "MIT" - }, - "node_modules/serve-static": { - "version": "1.15.0", - "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.15.0.tgz", - "integrity": "sha512-XGuRDNjXUijsUL0vl6nSD7cwURuzEgglbOaFuZM9g3kwDXOWVTck0jLzjPzGD+TazWbboZYu52/9/XPdUgne9g==", - "license": "MIT", - "dependencies": { - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "parseurl": "~1.3.3", - "send": "0.18.0" - }, - "engines": { - "node": ">= 0.8.0" - } - }, "node_modules/set-function-length": { "version": "1.2.2", "resolved": "https://registry.npmjs.org/set-function-length/-/set-function-length-1.2.2.tgz", "integrity": "sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==", + "dev": true, "dependencies": { "define-data-property": "^1.1.4", "es-errors": "^1.3.0", @@ -4856,12 +4155,6 @@ "node": ">= 0.4" } }, - "node_modules/setprototypeof": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", - "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==", - "license": "ISC" - }, "node_modules/shebang-command": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", @@ -4887,6 +4180,7 @@ "version": "1.0.6", "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.6.tgz", "integrity": "sha512-fDW/EZ6Q9RiO8eFG8Hj+7u/oW+XrPTIChwCOM2+th2A6OblDtYYIpve9m+KvI9Z4C9qSEXlaGR6bTEYHReuglA==", + "dev": true, "dependencies": { "call-bind": "^1.0.7", "es-errors": "^1.3.0", @@ -4921,34 +4215,6 @@ "node": ">=8" } }, - "node_modules/socket.io": { - "version": "4.7.5", - "resolved": "https://registry.npmjs.org/socket.io/-/socket.io-4.7.5.tgz", - "integrity": "sha512-DmeAkF6cwM9jSfmp6Dr/5/mfMwb5Z5qRrSXLpo3Fq5SqyU8CMF15jIN4ZhfSwu35ksM1qmHZDQ/DK5XTccSTvA==", - "license": "MIT", - "dependencies": { - "accepts": "~1.3.4", - "base64id": "~2.0.0", - "cors": "~2.8.5", - "debug": "~4.3.2", - "engine.io": "~6.5.2", - "socket.io-adapter": "~2.5.2", - "socket.io-parser": "~4.2.4" - }, - "engines": { - "node": ">=10.2.0" - } - }, - "node_modules/socket.io-adapter": { - "version": "2.5.5", - "resolved": "https://registry.npmjs.org/socket.io-adapter/-/socket.io-adapter-2.5.5.tgz", - "integrity": "sha512-eLDQas5dzPgOWCk9GuuJC2lBqItuhKI4uxGgo9aIV7MYbk2h9Q6uULEh8WBzThoI7l+qU9Ast9fVUmkqPP9wYg==", - "license": "MIT", - "dependencies": { - "debug": "~4.3.4", - "ws": "~8.17.1" - } - }, "node_modules/socket.io-client": { "version": "4.7.5", "resolved": "https://registry.npmjs.org/socket.io-client/-/socket.io-client-4.7.5.tgz", @@ -4985,15 +4251,6 @@ "node": ">=0.10.0" } }, - "node_modules/statuses": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz", - "integrity": "sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, "node_modules/stop-iteration-iterator": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/stop-iteration-iterator/-/stop-iteration-iterator-1.0.0.tgz", @@ -5363,15 +4620,6 @@ "node": ">=8.0" } }, - "node_modules/toidentifier": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.1.tgz", - "integrity": "sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==", - "license": "MIT", - "engines": { - "node": ">=0.6" - } - }, "node_modules/ts-api-utils": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/ts-api-utils/-/ts-api-utils-1.3.0.tgz", @@ -5486,19 +4734,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/type-is": { - "version": "1.6.18", - "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.18.tgz", - "integrity": "sha512-TkRKr9sUTxEH8MdfuCSP7VizJyzRNMjj2J2do2Jr3Kym598JVdEksuzPQCnlFPW4ky9Q+iA+ma9BGm06XQBy8g==", - "license": "MIT", - "dependencies": { - "media-typer": "0.3.0", - "mime-types": "~2.1.24" - }, - "engines": { - "node": ">= 0.6" - } - }, "node_modules/typed-array-buffer": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/typed-array-buffer/-/typed-array-buffer-1.0.2.tgz", @@ -5603,16 +4838,8 @@ "node_modules/undici-types": { "version": "5.26.5", "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-5.26.5.tgz", - "integrity": "sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==" - }, - "node_modules/unpipe": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", - "integrity": "sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } + "integrity": "sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==", + "dev": true }, "node_modules/uri-js": { "version": "4.4.1", @@ -5623,21 +4850,21 @@ "punycode": "^2.1.0" } }, + "node_modules/use-sync-external-store": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/use-sync-external-store/-/use-sync-external-store-1.2.0.tgz", + "integrity": "sha512-eEgnFxGQ1Ife9bzYs6VLi8/4X6CObHMw9Qr9tPY43iKwsPw8xE8+EFsf/2cFZ5S3esXgpWgtSCtLNS41F+sKPA==", + "license": "MIT", + "peerDependencies": { + "react": "^16.8.0 || ^17.0.0 || ^18.0.0" + } + }, "node_modules/util-deprecate": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", "integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==", "dev": true }, - "node_modules/utils-merge": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", - "integrity": "sha512-pMZTvIkT1d+TFGvDOqodOclx0QWkkgi6Tdoa8gC8ffGAAqz9pzPTZWAybbsHHoED/ztMtkv/VoYTYyShUn81hA==", - "license": "MIT", - "engines": { - "node": ">= 0.4.0" - } - }, "node_modules/v8-compile-cache-lib": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz", @@ -5647,15 +4874,6 @@ "optional": true, "peer": true }, - "node_modules/vary": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", - "integrity": "sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==", - "license": "MIT", - "engines": { - "node": ">= 0.8" - } - }, "node_modules/which": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", @@ -5923,6 +5141,34 @@ "funding": { "url": "https://github.com/sponsors/sindresorhus" } + }, + "node_modules/zustand": { + "version": "4.5.4", + "resolved": "https://registry.npmjs.org/zustand/-/zustand-4.5.4.tgz", + "integrity": "sha512-/BPMyLKJPtFEvVL0E9E9BTUM63MNyhPGlvxk1XjrfWTUlV+BR8jufjsovHzrtR6YNcBEcL7cMHovL1n9xHawEg==", + "license": "MIT", + "dependencies": { + "use-sync-external-store": "1.2.0" + }, + "engines": { + "node": ">=12.7.0" + }, + "peerDependencies": { + "@types/react": ">=16.8", + "immer": ">=9.0.6", + "react": ">=16.8" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + }, + "immer": { + "optional": true + }, + "react": { + "optional": true + } + } } } } diff --git a/package.json b/package.json index 48224a0..596ea57 100644 --- a/package.json +++ b/package.json @@ -10,6 +10,8 @@ "lint": "next lint" }, "dependencies": { + "axios": "^1.7.2", + "next": "14.2.4", "axios": "^1.7.2", "cors": "^2.8.5", "express": "^4.19.2", @@ -17,6 +19,8 @@ "next": "14.2.4", "react": "^18", "react-dom": "^18", + "socket.io-client": "^4.7.5", + "zustand": "^4.5.4" "socket.io": "^4.7.5", "socket.io-client": "^4.7.5" }, @@ -26,9 +30,13 @@ "@types/react-dom": "^18", "eslint": "^8", "eslint-config-next": "14.2.4", + "eslint": "^8", + "eslint-config-next": "14.2.4", "postcss": "^8", "tailwindcss": "^3.4.1", "typescript": "^5" + } + "typescript": "^5" }, "description": "This is a [Next.js](https://nextjs.org/) project bootstrapped with [`create-next-app`](https://github.com/vercel/next.js/tree/canary/packages/create-next-app).", "main": "index.js", From 66ee198dba3e1da0d008f00e4f887be4c3dff263 Mon Sep 17 00:00:00 2001 From: eunwoo-levi Date: Sun, 14 Jul 2024 03:09:38 +0900 Subject: [PATCH 4/7] solving all conflicts --- app/Chat/layout.tsx | 26 +++++++ app/create/page.tsx | 80 ++++++++++++++++++--- components/login/AccountForm.tsx | 50 +++++++------ components/login/NewAccount.tsx | 2 +- package-lock.json | 120 +++++++++++++++++++++++++++++++ package.json | 11 +-- 6 files changed, 247 insertions(+), 42 deletions(-) create mode 100644 app/Chat/layout.tsx diff --git a/app/Chat/layout.tsx b/app/Chat/layout.tsx new file mode 100644 index 0000000..ef5cbd7 --- /dev/null +++ b/app/Chat/layout.tsx @@ -0,0 +1,26 @@ +"use client"; +import Footer from "@/components/chatting/Footer"; +import Header from "@/components/chatting/Header"; +import Sidebar from "@/components/chatting/SideBar"; +import { useState } from "react"; + +const Layout: React.FC<{ children: React.ReactNode }> = ({ children }) => { + const [isSidebarOpen, setIsSidebarOpen] = useState(true); + + const toggleSidebar = () => { + setIsSidebarOpen(!isSidebarOpen); + }; + + return ( +
+
+
+ +
{children}
+
+
+
+ ); +}; + +export default Layout; diff --git a/app/create/page.tsx b/app/create/page.tsx index 511173d..4422ee1 100644 --- a/app/create/page.tsx +++ b/app/create/page.tsx @@ -1,16 +1,74 @@ -import CreateForm from "@/components/create/CreateForm"; +// pages/create.tsx +"use client"; + +import { useState } from "react"; +import { useRouter } from "next/navigation"; +import { getSignUp } from "@/app/_api/api"; + +const CreateAccount = () => { + const [email, setEmail] = useState(''); + const [password, setPassword] = useState(''); + const [nickname, setNickname] = useState(''); + const [error, setError] = useState(null); + const router = useRouter(); + + const handleSubmit = async (event: React.FormEvent) => { + event.preventDefault(); + try { + await getSignUp(email, password, nickname); + router.push('/login'); + } catch (error) { + setError('Failed to create account. Please try again.'); + } + }; -export default function CreateAccount() { return ( -
-
-
-

- Creating a new Account -

+
+

Create an Account

+ +
+ + setEmail(e.target.value)} + className="mt-1 block w-full px-3 py-2 border border-gray-300 rounded-md shadow-sm focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm" + required + />
- -
+
+ + setPassword(e.target.value)} + className="mt-1 block w-full px-3 py-2 border border-gray-300 rounded-md shadow-sm focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm" + required + /> +
+
+ + setNickname(e.target.value)} + className="mt-1 block w-full px-3 py-2 border border-gray-300 rounded-md shadow-sm focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm" + required + /> +
+ + + {error &&

{error}

}
); -} +}; + +export default CreateAccount; diff --git a/components/login/AccountForm.tsx b/components/login/AccountForm.tsx index df4cb2a..92b97eb 100644 --- a/components/login/AccountForm.tsx +++ b/components/login/AccountForm.tsx @@ -1,15 +1,15 @@ -'use client' -import Input from "./Input"; +"use client"; import NewAccount from "./NewAccount"; import { useState } from "react"; import { getLogin } from "@/app/_api/api"; -import { useRouter } from "next/navigation" +import { useRouter } from "next/navigation"; import { useAuthStore } from "@/app/store"; +import Input from "../page/Input"; const AccountForm = () => { - const [email, setEmail] = useState(''); - const [password, setPassword] = useState(''); - const [errorMessage,setErrorMessage] = useState('') + const [email, setEmail] = useState(""); + const [password, setPassword] = useState(""); + const [errorMessage, setErrorMessage] = useState(""); const router = useRouter(); const setTokens = useAuthStore((state) => state.setTokens); @@ -18,32 +18,40 @@ const AccountForm = () => { try { const data = await getLogin(email, password); if (data && data.accessToken && data.refreshToken) { - console.log('Login successful:', data); + console.log("Login successful:", data); setTokens(data.accessToken, data.refreshToken); - router.push('/Chat'); + router.push("/Chat"); } else { - throw new Error('Invalid response from server'); + throw new Error("Invalid response from server"); } } catch (err) { - console.error('Login failed', err); + console.error("Login failed", err); if (err instanceof Error) { - if (err.message === 'Invalid response from server') { - setErrorMessage('Login failed: Invalid response from server. Please try again.'); - } else if (err.message.includes('Network Error')) { - setErrorMessage('Network error. Please check your internet connection and try again.'); - } else if (err.message.includes('401')) { - setErrorMessage('Invalid email or password. Please check your credentials and try again.'); - } else if (err.message.includes('500')) { - setErrorMessage('Server error. Please try again later.'); + if (err.message === "Invalid response from server") { + setErrorMessage( + "Login failed: Invalid response from server. Please try again." + ); + } else if (err.message.includes("Network Error")) { + setErrorMessage( + "Network error. Please check your internet connection and try again." + ); + } else if (err.message.includes("401")) { + setErrorMessage( + "Invalid email or password. Please check your credentials and try again." + ); + } else if (err.message.includes("500")) { + setErrorMessage("Server error. Please try again later."); } } console.log(errorMessage); } - } + }; return ( -
+ { Need to create an account? Create an account diff --git a/package-lock.json b/package-lock.json index c55d3c7..64c2fb2 100644 --- a/package-lock.json +++ b/package-lock.json @@ -5169,6 +5169,126 @@ "optional": true } } + }, + "node_modules/@next/swc-darwin-arm64": { + "version": "14.2.4", + "resolved": "https://registry.npmjs.org/@next/swc-darwin-arm64/-/swc-darwin-arm64-14.2.4.tgz", + "integrity": "sha512-AH3mO4JlFUqsYcwFUHb1wAKlebHU/Hv2u2kb1pAuRanDZ7pD/A/KPD98RHZmwsJpdHQwfEc/06mgpSzwrJYnNg==", + "cpu": [ + "arm64" + ], + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@next/swc-darwin-x64": { + "version": "14.2.4", + "resolved": "https://registry.npmjs.org/@next/swc-darwin-x64/-/swc-darwin-x64-14.2.4.tgz", + "integrity": "sha512-QVadW73sWIO6E2VroyUjuAxhWLZWEpiFqHdZdoQ/AMpN9YWGuHV8t2rChr0ahy+irKX5mlDU7OY68k3n4tAZTg==", + "cpu": [ + "x64" + ], + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@next/swc-linux-arm64-gnu": { + "version": "14.2.4", + "resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-gnu/-/swc-linux-arm64-gnu-14.2.4.tgz", + "integrity": "sha512-KT6GUrb3oyCfcfJ+WliXuJnD6pCpZiosx2X3k66HLR+DMoilRb76LpWPGb4tZprawTtcnyrv75ElD6VncVamUQ==", + "cpu": [ + "arm64" + ], + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@next/swc-linux-arm64-musl": { + "version": "14.2.4", + "resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-musl/-/swc-linux-arm64-musl-14.2.4.tgz", + "integrity": "sha512-Alv8/XGSs/ytwQcbCHwze1HmiIkIVhDHYLjczSVrf0Wi2MvKn/blt7+S6FJitj3yTlMwMxII1gIJ9WepI4aZ/A==", + "cpu": [ + "arm64" + ], + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@next/swc-linux-x64-gnu": { + "version": "14.2.4", + "resolved": "https://registry.npmjs.org/@next/swc-linux-x64-gnu/-/swc-linux-x64-gnu-14.2.4.tgz", + "integrity": "sha512-ze0ShQDBPCqxLImzw4sCdfnB3lRmN3qGMB2GWDRlq5Wqy4G36pxtNOo2usu/Nm9+V2Rh/QQnrRc2l94kYFXO6Q==", + "cpu": [ + "x64" + ], + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@next/swc-linux-x64-musl": { + "version": "14.2.4", + "resolved": "https://registry.npmjs.org/@next/swc-linux-x64-musl/-/swc-linux-x64-musl-14.2.4.tgz", + "integrity": "sha512-8dwC0UJoc6fC7PX70csdaznVMNr16hQrTDAMPvLPloazlcaWfdPogq+UpZX6Drqb1OBlwowz8iG7WR0Tzk/diQ==", + "cpu": [ + "x64" + ], + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@next/swc-win32-arm64-msvc": { + "version": "14.2.4", + "resolved": "https://registry.npmjs.org/@next/swc-win32-arm64-msvc/-/swc-win32-arm64-msvc-14.2.4.tgz", + "integrity": "sha512-jxyg67NbEWkDyvM+O8UDbPAyYRZqGLQDTPwvrBBeOSyVWW/jFQkQKQ70JDqDSYg1ZDdl+E3nkbFbq8xM8E9x8A==", + "cpu": [ + "arm64" + ], + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@next/swc-win32-ia32-msvc": { + "version": "14.2.4", + "resolved": "https://registry.npmjs.org/@next/swc-win32-ia32-msvc/-/swc-win32-ia32-msvc-14.2.4.tgz", + "integrity": "sha512-twrmN753hjXRdcrZmZttb/m5xaCBFa48Dt3FbeEItpJArxriYDunWxJn+QFXdJ3hPkm4u7CKxncVvnmgQMY1ag==", + "cpu": [ + "ia32" + ], + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">= 10" + } } } } diff --git a/package.json b/package.json index 596ea57..c391bfa 100644 --- a/package.json +++ b/package.json @@ -10,8 +10,6 @@ "lint": "next lint" }, "dependencies": { - "axios": "^1.7.2", - "next": "14.2.4", "axios": "^1.7.2", "cors": "^2.8.5", "express": "^4.19.2", @@ -19,10 +17,9 @@ "next": "14.2.4", "react": "^18", "react-dom": "^18", + "socket.io": "^4.7.5", "socket.io-client": "^4.7.5", "zustand": "^4.5.4" - "socket.io": "^4.7.5", - "socket.io-client": "^4.7.5" }, "devDependencies": { "@types/node": "^20", @@ -30,17 +27,13 @@ "@types/react-dom": "^18", "eslint": "^8", "eslint-config-next": "14.2.4", - "eslint": "^8", - "eslint-config-next": "14.2.4", "postcss": "^8", "tailwindcss": "^3.4.1", "typescript": "^5" - } - "typescript": "^5" }, "description": "This is a [Next.js](https://nextjs.org/) project bootstrapped with [`create-next-app`](https://github.com/vercel/next.js/tree/canary/packages/create-next-app).", "main": "index.js", "keywords": [], "author": "", "license": "ISC" -} +} \ No newline at end of file From 71817d9bcf0f7f1e93951d81cd7f91fb84c5653d Mon Sep 17 00:00:00 2001 From: eunwoo-levi Date: Tue, 16 Jul 2024 20:27:56 +0900 Subject: [PATCH 5/7] fixing all conflicts --- app/page.tsx | 80 +++++++++++++++++++++++++++++++++++++++---- components/Navbar.tsx | 7 ++-- 2 files changed, 75 insertions(+), 12 deletions(-) diff --git a/app/page.tsx b/app/page.tsx index a96afb9..8a8c72e 100644 --- a/app/page.tsx +++ b/app/page.tsx @@ -1,13 +1,79 @@ +"use client"; +import Link from "next/link"; +import { useRouter } from "next/navigation"; +import { useState } from "react"; +import { useAuthStore } from "./store"; +import CreateChatRoomForm from "@/components/CreateChatRoom"; + export default function Home() { + const [showModal, setShowModal] = useState(false); + const router = useRouter(); + const { accessToken, clearTokens } = useAuthStore(); + + const handleLogout = () => { + clearTokens(); + router.push("/Chat"); + }; + + const handleCreateChat = () => { + setShowModal(true); + }; + + const closeModal = () => { + setShowModal(false); + }; + return ( -
-
-
Item 1
-
- 실시간 채팅 + <> +
+ logo + + InjuryLawAssist + +
+ +
+
+ + {accessToken ? ( + + ) : ( + + Login + + )}
-
Item 3
+ {showModal && ( +
+
+ + +
+
+ )}
-
+ ); } diff --git a/components/Navbar.tsx b/components/Navbar.tsx index 7f1a9ee..b278407 100644 --- a/components/Navbar.tsx +++ b/components/Navbar.tsx @@ -1,4 +1,4 @@ -'use client'; +"use client"; import Link from "next/link"; import { useState } from "react"; @@ -13,7 +13,7 @@ const Navbar = () => { const handleLogout = () => { clearTokens(); - router.push('/Chat'); + router.push("/Chat"); }; const handleCreateChat = () => { @@ -39,9 +39,6 @@ const Navbar = () => { ABOUT - - Chat Bot -
From afe37ad90127a1d14e7afa4561c1277b355b04d1 Mon Sep 17 00:00:00 2001 From: eunwoo-levi Date: Tue, 16 Jul 2024 21:36:09 +0900 Subject: [PATCH 6/7] updating --- app/page.tsx | 85 ++++++++++++++++++++------------ components/login/NewAccount.tsx | 8 ++- public/bg.jpg | Bin 0 -> 33854 bytes public/next.svg | 1 - public/vercel.svg | 1 - tailwind.config.ts | 1 + 6 files changed, 58 insertions(+), 38 deletions(-) create mode 100644 public/bg.jpg delete mode 100644 public/next.svg delete mode 100644 public/vercel.svg diff --git a/app/page.tsx b/app/page.tsx index 8a8c72e..6d82315 100644 --- a/app/page.tsx +++ b/app/page.tsx @@ -36,43 +36,66 @@ export default function Home() {
-
-
- - {accessToken ? ( - - ) : ( - - Login - - )} +
+
+ + IN PURSUIT OF JUSTICE, EVERYDAY +
- {showModal && ( -
-
+
+
+
+ + 새로운 채팅을 만들어 보세요! + -
+ + {accessToken ? ( + + ) : ( +
+ 로그인 하기 + + Login + +
+ )} + {showModal && ( +
+
+ + +
+
+ )}
- )} +
+
+
+ +
+
); diff --git a/components/login/NewAccount.tsx b/components/login/NewAccount.tsx index 6761ca6..0208237 100644 --- a/components/login/NewAccount.tsx +++ b/components/login/NewAccount.tsx @@ -1,13 +1,13 @@ import Link from "next/link"; -const NewAccount = () => { +export default function NewAccount() { return (
Need to create an account? Create an account @@ -24,6 +24,4 @@ const NewAccount = () => {
); -}; - -export default NewAccount; +} diff --git a/public/bg.jpg b/public/bg.jpg new file mode 100644 index 0000000000000000000000000000000000000000..478c1eb2c505eed852c186b196651b16c046b396 GIT binary patch literal 33854 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 literal 0 HcmV?d00001 diff --git a/public/next.svg b/public/next.svg deleted file mode 100644 index 5174b28..0000000 --- a/public/next.svg +++ /dev/null @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/public/vercel.svg b/public/vercel.svg deleted file mode 100644 index d2f8422..0000000 --- a/public/vercel.svg +++ /dev/null @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/tailwind.config.ts b/tailwind.config.ts index 7e4bd91..6df2298 100644 --- a/tailwind.config.ts +++ b/tailwind.config.ts @@ -12,6 +12,7 @@ const config: Config = { "gradient-radial": "radial-gradient(var(--tw-gradient-stops))", "gradient-conic": "conic-gradient(from 180deg at 50% 50%, var(--tw-gradient-stops))", + "bgPic" : "url('/bg.jpg')" }, }, }, From e015aba81f407d2f2dd06b46261cf417b911ecf6 Mon Sep 17 00:00:00 2001 From: eunwoo-levi Date: Tue, 16 Jul 2024 22:58:06 +0900 Subject: [PATCH 7/7] new Update --- app/layout.tsx | 1 - app/page.tsx | 114 +++++++++++++++------------------ components/mainpage/Bottom.tsx | 32 +++++++++ components/mainpage/Nav.tsx | 14 ++++ public/bg.jpg | Bin 33854 -> 0 bytes tailwind.config.ts | 1 - 6 files changed, 98 insertions(+), 64 deletions(-) create mode 100644 components/mainpage/Bottom.tsx create mode 100644 components/mainpage/Nav.tsx delete mode 100644 public/bg.jpg diff --git a/app/layout.tsx b/app/layout.tsx index eb0795e..ac80ba3 100644 --- a/app/layout.tsx +++ b/app/layout.tsx @@ -1,7 +1,6 @@ import type { Metadata } from "next"; import { Inter } from "next/font/google"; import "./globals.css"; -import Navbar from "@/components/Navbar"; const inter = Inter({ subsets: ["latin"] }); diff --git a/app/page.tsx b/app/page.tsx index 6d82315..a4e0244 100644 --- a/app/page.tsx +++ b/app/page.tsx @@ -4,6 +4,8 @@ import { useRouter } from "next/navigation"; import { useState } from "react"; import { useAuthStore } from "./store"; import CreateChatRoomForm from "@/components/CreateChatRoom"; +import Nav from "@/components/mainpage/Nav"; +import Bottom from "@/components/mainpage/Bottom"; export default function Home() { const [showModal, setShowModal] = useState(false); @@ -24,79 +26,67 @@ export default function Home() { }; return ( - <> -
- logo - - InjuryLawAssist - -
+
+