<aside> 🌏 소캣 프로그래밍 개념 정리
</aside>
TCP 소캣 프로그래밍이란?
→ Socket을 사용하여 네트워크 통신
을 가능케하는 프로그래밍
→ TCP(프로토콜은 신뢰할 수 있고, 데이터의 순서 전달이 정확) 이외에도 UDP, ICMP등 다양한 프로토콜의 패킷을 만들어 통신할 수 있다.
→ 소캣과 소캣 API는 네트워크를 통해 메시지를 보내는 데 사용
된다. 프로세스간 통신(IPC)의 한 형태를 제공한다.
TCP에 대한 소캣 API 호출 및 데이터 흐름
<aside> 🌏 Wireshark
</aside>
Wireshark란?
→ Host를 통해 나가고 오는 Packet을 Sniff하는 것
→ 라우터가 내부로 향하는 모든 패킷은 broadcasting으로 모든 host에게 패킷을 전달한다.
→ OS는 전달받은 패킷이 자신의 패킷이라면 이를 Application Layer까지 올리고 아닌 것은 discard한다.
→ Wireshark는 이런 패키을 들여다보는 것이지 잡아두는 것이 아님
Source 포트는 OS가 남는 포트를 할당해줌. 일반적으로 사용자가 전할 수 없음. → 매번 달라짐
Gateway의 IP(Software address)뿐만이 아니라 Mac Address(Hardware address)를 알아야하는 이유
→ Application Layer는 IP를 사용하여 다른 장치와 통신하지만 DataLink Layer에서 주소지정은 Mac address를 통해 이루어지기 때문이다.
<aside> 🌏 소캣 프로그래밍 과제1 - 사칙연산
</aside>
첫번째 과제 - 클라이언트가 서버에게 하나의 수식을 줌 (ex. 3 x 4)
서버는 이를 해석해서 클라이언트에게 답을 전달(ex. 12)
client 측 code (in java)
import java.io.*;
import java.net.InetSocketAddress;
import java.net.Socket;
import java.net.SocketAddress;
public class SocketClient{
public static void main(String[] args) throws IOException {
SocketClient cm = new SocketClient();
cm.run(args);
}
void run(String[] args) throws IOException {
//소켓 생성
Socket socket = new Socket();
//주소 생성
SocketAddress address = new InetSocketAddress("127.0.0.1", 18501);
//주소에 해당하는 서버랑 연결
socket.connect(address);
try {
PrintWriter pw=new PrintWriter(socket.getOutputStream());
BufferedReader br=new BufferedReader(new InputStreamReader(socket.getInputStream()));
String result="error";
if(args.length!=3){
System.out.println("인자는" + args.length+" 개가 아닌 인자는 3개여야합니다.");
}else{
result= args[0] + " "+args[1]+" " +args[2];
}
pw.print(result);
pw.flush();
System.out.println("결과: "+br.readLine());
} catch (IOException e) {
e.printStackTrace();
}
}
}
server 측 code (in java)
import java.io.*;
import java.net.ServerSocket;
import java.net.Socket;
public class SocketServer {
public static void main(String[] args) throws IOException{
SocketServer socketServer = new SocketServer();
socketServer.run();
}
public void run() throws IOException{
BufferedWriter bw=null;
ServerSocket server=null;
Socket socket=null;
try {
int port = 18501;
server = new ServerSocket(port);
System.out.println("서버가 준비되었습니다.");
}catch(IOException e){
e.printStackTrace();
}
while(true) {
try {
socket = server.accept(); // 계속 기다리고 있다가 클라이언트가 접속하면 통신할 수 있는 소켓 반환
System.out.println(socket.getInetAddress() + "로 부터 연결요청이 들어옴");
bw = new BufferedWriter(new OutputStreamWriter(socket.getOutputStream()));
InputStream is = socket.getInputStream();
byte[] bytes = new byte[1024];
is.read(bytes);
String data = new String(bytes);
data=data.replaceAll("(\\r|\\n|\\r\\n|\\n\\r)",""); //엔터 제거
data=data.trim();
System.out.println("input: "+data);
String[] inputs = data.split(" ");
if (inputs.length != 3) {
bw.write("에러");
bw.flush();
} else {
Integer result = null;
int input1 = 0, input2 = 0;
boolean checkFlag = false;
try {
input1 = Integer.parseInt(inputs[0]);
input2 = Integer.parseInt(inputs[2]);
} catch (NumberFormatException e) {
bw.write("에러");
bw.flush();
checkFlag = true;
}
if (checkFlag == false) {
if (inputs[1].equals("+")) {
result = input1 + input2;
} else if (inputs[1].equals("-")) {
result = input1 - input2;
} else if (inputs[1].equals("x")) {
result = input1 * input2;
} else if (inputs[1].equals("/")) {
if(input2==0){
result=0;
}else {
result = input1 / input2;
}
}
bw.write(String.valueOf(result));
bw.flush();
}
}
} catch (IOException e) {
e.printStackTrace();
} finally {
if (bw != null) try {
bw.close();
} catch (IOException e) {
}
if (socket != null) try {
socket.close();
} catch (IOException e) {
}
}
}
}
}
client 출력 결과