과제: 기존에 만들었던 무비 앱에 커스텀 훅을 제작하고 실시간 채팅 기능을 만들기
커스텀 훅 자체는 저번 시간에 공부 했기 때문에 설명이 필요 없을 것 같다.
다음으로는 실시간 채팅 부분인데 이 부분은 node express와 socketIO를 이용하여 해결 했다.
실시간 채팅 기능에 사용 되는 소켓 통신은 흔히들 HTTP 통신과 비교하게 되는데
HTTP 통신은 지속적으로 연결 되어 있지 않고 필요한 순간에만 통신하고 답장을 받는 형태로 통신 한다면 소켓 통신은 항상 연결 되어있다는 점이 다르다.
기본적으로 서버의 부하를 줄이기 위해 일반적으로는 항상 서버에 연결하지 않는 방식을 채택하고 사용한다.
그래서 소켓 통신을 위한 서버는 아래와 같이 코드를 입력 한다.
const express = require("express");
const http = require("http");
const socketIO = require("socket.io");
const cors = require("cors");
const app = express();
app.use(cors());
const server = http.createServer(app);
const io = socketIO(server, {
cors: {
origin: "http://localhost:3000", // 허용할 도메인
methods: ["GET", "POST"], // 허용할 HTTP 메소드
},
});
io.on("connection", (socket) => {
console.log("새로운 클라이언트가 연결되었습니다.");
// 클라이언트로부터의 메시지 수신 및 브로드캐스팅
socket.on("message", (message) => {
console.log("새로운 메시지:", message);
io.emit("message", message);
});
// 클라이언트 연결 해제 처리
socket.on("disconnect", () => {
console.log("클라이언트가 연결을 해제하였습니다.");
});
});
server.listen(3001, () => {
console.log("서버가 3001 포트에서 실행 중입니다.");
});
그 다음 채팅을 위한 부분은 아래와 같이 작성한다.
import React, { useState, useEffect } from "react";
import io from "socket.io-client";
const socket = io("http://localhost:3001"); // 서버의 URL에 맞게 변경
function Chat() {
const [username, setUsername] = useState("");
const [messages, setMessages] = useState([]);
const [inputValue, setInputValue] = useState("");
useEffect(() => {
socket.on("message", handleMessage);
return () => {
socket.off("message", handleMessage);
};
}, []);
const handleMessage = (message) => {
setMessages((prevMessages) => [...prevMessages, message]);
};
const handleUsernameChange = (e) => {
setUsername(e.target.value);
};
const handleMessageSend = () => {
if (inputValue.trim() !== "") {
const currentTime = new Date().toLocaleTimeString();
socket.emit("message", {
username,
content: inputValue,
time: currentTime,
});
setInputValue("");
}
};
return (
<div>
<input
type="text"
value={username}
onChange={handleUsernameChange}
placeholder="사용자 이름"
/>
<h2>채팅</h2>
<div>
{messages.map((message, index) => (
<p key={index} style={{ color: message.color }}>
{message.username}: {message.content} - {message.time}
</p>
))}
</div>
<input
type="text"
value={inputValue}
onChange={(e) => setInputValue(e.target.value)}
/>
<button onClick={handleMessageSend}>전송</button>
</div>
);
}
export default Chat;
이런 식으로 작성하고 App.js에서 사용하면 아래와 같이 서로 연결해서 실시간 채팅을 할 수 있다.
추가적으로 작성한 커스텀 훅은 아래와 같다.
import { useCallback, useState } from "react";
const useFavorite = () => {
const [favorite, setFavorite] = useState([]);
const addFavorite = useCallback((e) => {
setFavorite((prev) => {
return [...prev, e];
});
}, []);
console.log(favorite);
const removeFavorite = useCallback((e) => {
setFavorite((prev) => {
const result = prev.filter((element) => e !== element);
return result;
});
}, []);
return { favorite, addFavorite, removeFavorite };
};
export default useFavorite;
마음에 드는 영화를 즐겨찾기 하는 훅이다.
본 후기는 유데미-스나이퍼팩토리 10주 완성 프로젝트캠프 학습 일지 후기로 작성 되었습니다.
#프로젝트캠프 #프로젝트캠프후기 #유데미 #스나이퍼팩토리 #웅진씽크빅 #인사이드아웃 #IT개발캠프 #개발자부트캠프 #리액트 #react #부트캠프 #리액트캠프