소켓 정의
프로토콜
- 데이터 전송을 위한 규약이며, 대표적으로 TCP와 UDP가 있다.
IP
- 컴퓨터에 부여된 논리적 식별 주소
Port
- 네트워크 상에서 통신하기 위해 호스트 내부적으로 프로세스가 할당받는 고유 번호
- 같은 컴퓨터 내에서 프로세스를 식별하기 위한 번호
소켓 통신 과정
서버
- 서버 IP 주소, 포트를 통해 서버 엔드포인트 생성
- Listener 소켓 객체 생성
- Bind(서버 엔드포인트 정보를 Listener 소켓에 연동)
- Listen(클라이언트 대기열 생성)
- Accept(클라이언트 연결 수용)
- Send, Receive(데이터 송수신)
- Close
클라이언트
- 서버 IP 주소, 포트를 통해 서버 엔드포인트 생성
- 클라이언트 소켓 객체 생성
- Connect(클라이언트 소켓을 서버 엔드포인트에 연결)
- Send, Receive
- Close
서버 소켓 기본(블로킹 방식)
[1] 소켓 정보 정의
1
2
3
4
5
6
7
8
9
10
11
12
13
// 로컬 호스트의 이름을 통해 DNS로부터 IP Host Entry 정보를 가져온다.
string host = Dns.GetHostName();
IPHostEntry ipHost = Dns.GetHostEntry(host);
// => Dns.GetHostEntry("도메인 이름 또는 IP 주소")을 통해 IP호스트 정보를 받아올 수 있다.
// 예를 들어 "localhost", "google.com", "127.0.0.1" 가능
// 호스트가 보유한 IP 주소 중 첫 번째를 가져온다.
IPAddress ipAddr = ipHost.AddressList[0];
const int PortNumber = 7777;
// IP 주소와 포트 번호를 통해 IP 연결 말단 객체를 생성한다.
IPEndPoint endPoint = new IPEndPoint(ipAddr, PortNumber);
[2] 리스너 소켓
1
2
3
4
5
6
7
8
9
// TCP 리스너 소켓을 생성한다.
Socket listenSocket = new Socket(endPoint.AddressFamily, SocketType.Stream, ProtocolType.Tcp);
// Bind : 서버 주소와 포트 정보를 소켓에 연동한다.
listenSocket.Bind(endPoint);
// Listen : 클라이언트 대기열을 정의한다.
// backlog(int) : 최대 클라이언트 동시 대기 허용 수
listenSocket.Listen(10);
[3] 연결 및 데이터 송수신
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
while (true)
{
Console.WriteLine("Listening..");
// 클라이언트 소켓의 연결을 수용한다.
// 블로킹 방식
Socket clientSocket = listenSocket.Accept();
// 클라이언트로부터 데이터를 수신한다.
byte[] receiveBuffer = new byte[1024];
int receivedLen = clientSocket.Receive(receiveBuffer);
string receivedString = Encoding.UTF8.GetString(receiveBuffer, 0, receivedLen);
Console.WriteLine($"From Client : {receivedString}");
// 클라이언트에 데이터를 전송한다.
string stringToSend = "Hi Hi Client !";
byte[] sendBuffer = Encoding.UTF8.GetBytes(stringToSend);
clientSocket.Send(sendBuffer);
Console.WriteLine($"Send To Client : {stringToSend}");
// 연결을 종료한다.
clientSocket.Shutdown(SocketShutdown.Both);
clientSocket.Close();
}
클라이언트 소켓 기본
[1] 소켓 생성
1
2
3
4
5
6
7
8
9
10
11
// 연결할 대상 서버의 정보를 정의한다.
string host = Dns.GetHostName();
IPHostEntry ipHost = Dns.GetHostEntry(host);
IPAddress ipAddr = ipHost.AddressList[0];
const int PortNumber = 7777;
// IP 주소와 포트 번호를 통해 IP 연결 말단 객체를 생성한다.
IPEndPoint serverEndPoint = new IPEndPoint(ipAddr, PortNumber);
// TCP 소켓을 생성한다.
Socket socket = new Socket(serverEndPoint.AddressFamily, SocketType.Stream, ProtocolType.Tcp);
[2] 연결 및 데이터 송수신
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
// 서버에 연결한다.
socket.Connect(serverEndPoint);
Console.WriteLine($"Connected To {socket.RemoteEndPoint.ToString()}");
// 서버에 데이터를 전송한다.
string stringToSend = "Hello Server";
byte[] sendBuffer = Encoding.UTF8.GetBytes(stringToSend);
socket.Send(sendBuffer);
Console.WriteLine($"Send To Server : {stringToSend}");
// 서버로부터 데이터를 수신한다.
byte[] receiveBuffer = new byte[1024];
int receivedLen = socket.Receive(receiveBuffer);
string receivedString = Encoding.UTF8.GetString(receiveBuffer, 0, receivedLen);
Console.WriteLine($"From Server : {receivedString}");
// 연결을 종료한다.
socket.Shutdown(SocketShutdown.Both);
socket.Close();
전체 소스 코드
TcpServerBasic.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Net;
using System.Net.Sockets;
class TcpServerBasic
{
public static void Run()
{
// 로컬 호스트의 이름을 통해 IP Host Entry 정보를 가져온다.
string host = Dns.GetHostName();
IPHostEntry ipHost = Dns.GetHostEntry(host);
// 호스트가 보유한 IP 주소 중 첫 번째를 가져온다.
IPAddress ipAddr = ipHost.AddressList[0];
const int PortNumber = 7777;
// IP 주소와 포트 번호를 통해 IP 연결 말단 객체를 생성한다.
IPEndPoint endPoint = new IPEndPoint(ipAddr, PortNumber);
// TCP 리스너 소켓을 생성한다.
Socket listenSocket = new Socket(endPoint.AddressFamily, SocketType.Stream, ProtocolType.Tcp);
try
{
// Bind : 서버 주소와 포트 정보를 소켓에 연동한다.
listenSocket.Bind(endPoint);
// Listen : 클라이언트 대기열을 정의한다.
// backlog(int) : 최대 클라이언트 동시 대기 허용 수
listenSocket.Listen(10);
while (true)
{
Console.WriteLine("\nListening..");
// 클라이언트 소켓의 연결을 수용한다.
// 블로킹 방식
Socket clientSocket = listenSocket.Accept();
Console.WriteLine($"Client Accepted : {clientSocket.RemoteEndPoint}");
// 클라이언트로부터 데이터를 수신한다.
byte[] receiveBuffer = new byte[1024];
int receivedLen = clientSocket.Receive(receiveBuffer);
string receivedString = Encoding.UTF8.GetString(receiveBuffer, 0, receivedLen);
Console.WriteLine($"From Client : {receivedString}");
// 클라이언트에 데이터를 전송한다.
string stringToSend = "Hi Hi Client !";
byte[] sendBuffer = Encoding.UTF8.GetBytes(stringToSend);
clientSocket.Send(sendBuffer);
Console.WriteLine($"Send To Client : {stringToSend}");
// 연결을 종료한다.
clientSocket.Shutdown(SocketShutdown.Both);
clientSocket.Close();
}
}
catch (Exception e)
{
Console.WriteLine(e.Message);
}
}
}
TcpClientBasic.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Net;
using System.Net.Sockets;
class TcpClientBasic
{
public static void Run()
{
// 연결할 대상 서버의 정보를 정의한다.
string host = Dns.GetHostName();
IPHostEntry ipHost = Dns.GetHostEntry(host);
IPAddress ipAddr = ipHost.AddressList[0];
const int PortNumber = 7777;
// IP 주소와 포트 번호를 통해 IP 연결 말단 객체를 생성한다.
IPEndPoint serverEndPoint = new IPEndPoint(ipAddr, PortNumber);
// TCP 소켓을 생성한다.
Socket socket = new Socket(serverEndPoint.AddressFamily, SocketType.Stream, ProtocolType.Tcp);
try
{
// 서버에 연결한다.
socket.Connect(serverEndPoint);
Console.WriteLine($"Connected To {socket.RemoteEndPoint}");
// 서버에 데이터를 전송한다.
string stringToSend = "Hello Server";
byte[] sendBuffer = Encoding.UTF8.GetBytes(stringToSend);
socket.Send(sendBuffer);
Console.WriteLine($"Send To Server : {stringToSend}");
// 서버로부터 데이터를 수신한다.
byte[] receiveBuffer = new byte[1024];
int receivedLen = socket.Receive(receiveBuffer);
string receivedString = Encoding.UTF8.GetString(receiveBuffer, 0, receivedLen);
Console.WriteLine($"From Server : {receivedString}");
// 연결을 종료한다.
socket.Shutdown(SocketShutdown.Both);
socket.Close();
}
catch (Exception e)
{
Console.WriteLine(e.Message);
}
}
}