"웹 소켓을 이용한 카톡 프로젝트...","웹소켓을 이용한.." 이런 이야기를 많이 들어 봤는데 도대체 웹 소켓이란 무엇인가?
먼저 웹소켓이 만들어진 배경을 알아보자. 인터넷이 나오고 http를 통해서 통신을 하던 시절..서버로 부터 데이터를 가져오기 위해서는 오로지 url을 통한 요청이 유일한 방법이었다. 때문에 아이디 중복 확인 같은 서버로 데이터를 보내는 중간과정에서 새로운 페이지 요청을 하게 되었다.
여기서 발전된 방식이 AJAX통신으로 클라이언트에서 XMLHttpRequest 객체를 이용하여 서버에 요청을 보내면 서버가 응답을 한다. 페이지 요청이 아닌 데이터 요청이라 부분적으로 정보를 갱신할 수 있게 되었다.
하지만 이 AJAX도 결국 HTTP를 이용하기 때문에 요청을 보내야 응답이 온다. 하지만 변경된 데이터를 가져오기 위해서 버튼을 누른다든지 일정 시간 주기로 요청을 보낸다면, 얼마나 귀찮고 자원 낭비인가. 주식 정보를 보려고 하는데 매번 버튼으로 갱신한다? 오 쉣.. 때문에 요청을 보내지 않아도 서버에서 응답을 주는 기술이 필요해졌다.
그렇게 탄생한 것이 websocket이라고 한다.
새로운 기술로 새로운 것을 만드려보려고 하니까 벌써 두근두근하다.
현재 webSocket은 IE10까지 밖에 지원하지 않기 때문에 webSocket.io를 사용하는게 좋아보인다. webSocket.io는 브라우저에 가장 적합한 방법으로 실시간 통신을 구현해준 것이라 보면된다.
그러면 일단 먼저 webSocket을 살짝 경험해보고 가자.
유투브에서 webSocket을 이용한 간단한 채팅 프로그램을 만드는 실습 영상이다.
이 영상을 토대로 조금 어레인지 해서 실습을 해본다.
클라이언트
<body>
<div id="log"></div>
<div id="sendControlls">
<input type="text" placeholder="message" id="text"/>
<button>send</button>
</div>
<script>
const sock = new WebSocket("ws://localhost:8000");
const log = document.getElementById("log");
//웹 접근시 창에서 닉네임 입력
const name = prompt("your name");
// 소켓 최초 접근시 오픈해서 입력한 닉네임을 서버로 보냄
sock.onopen=()=>{
sock.send(JSON.stringify({
type:"name",
data:name
}))
}
// 1.보내면
document.querySelector("button").onclick = ()=>{
const text = document.getElementById("text").value;
// sock.send(text);
sock.send(JSON.stringify({
type:"message",
data:text
}));
log.innerHTML+="<p class='my'>you: "+text+"</p>";
}
// 서버에서 보낸거 받기
sock.onmessage= e=>{
console.log(e);
const json = JSON.parse(e.data);
// useReducer가 action에 따라 상태 구분하듯 type에 따라
if(json.type==="newPeople"){
// 새로운 사람 입장시
if(!json.newChater)return
log.innerHTML+="<p>"+json.newChater+"님이 입장했습니다.</p>";
return
}
if(json.type==="bye"){
// 누군가 나갈시
log.innerHTML+="<p>"+json.name+"님이 퇴장하셨습니다.</p>";
return
}
// 메시지 보낼시
log.innerHTML+="<p>"+json.name+":"+json.data+"</p>";
}
console.log(sock)
</script>
</body>
서버 코드이다.
const server = require("ws").Server;
const s = new server({port:8000});
s.on('connection',ws=>{
// 2. 받고
ws.on('message',message=>{
parseMessage = JSON.parse(message);
// 닉네임 받고
if(parseMessage.type==="name"){
ws.personName = parseMessage.data;
// 접속을 알림
s.clients.forEach(client=>{
client.send(JSON.stringify({
newChater:ws.personName,
type:"newPeople"
}))
})
return
}
// 누군가 메시지를 보내면 모든 s 소켓에 접속한 사람들에게 전송
// 이때 글 보낸 사람도 받아짐
s.clients.forEach(client=>{
// 받은 클라이언트가 보내는 사람이랑 다르면
if(client !== ws){
// 해당 클라이언트에게만 보냄
client.send(JSON.stringify({
name:ws.personName,
data:parseMessage.data,
}));
} ;
//
})
})
// 연결이 끝길때
ws.on('close',()=>{
// 누군가 나감을 알림
s.clients.forEach(client=>{
client.send(JSON.stringify({
name:ws.personName,
type:"bye"
}))
})
})
// 연결될때
console.log("다른 연결이 감지되었습니다.");
})
간단하게 카톡처럼 누군가 서버에 접근하면 등록한 닉네임으로 알리고 서버를 나가면 알려주는 채팅어플이다.
유투브에서는 기능이 어떻게 동작하는 지, 정확한 설명이 없어서 좀 아쉽지만 일단 느낌은 왔다. 이제 socket.io와 react, express를 이용해서 만들어보자. 가능하면 db도 연결해서 말이다.