소스코드, 강의자료 및 동영상 보기는 http://www.topcredu.co.kr, http://ojc.asia 에서 가능 합니다.
7. C# Network 프로그래밍
7-1. 간단한 TCP 클라이언트, 서버
TCP Client & Server 만들기
System.Net.Sockets.TCPClient : TCP 네트웍의 클라이언트 서비스를 제공하고 Socket
클래스를 기본으로 작성 되었다. FTP나 HTTP와 같은 애플리케이션 계층 프로토콜을 개
발하는데 주로 사용 된다.
TCPClient myClient = new TCPClient(“***.***.***.***”, 13);
Stream myStream = myClient.GetStream();
System.Net.Sockets.NetworkStream : Network용 데이터 스트림을 제공한다. 네트웍의
소켓을 통해 데이터를 전송 및 수신하는 표준 닷넷 프레임워크 스트림 방식을 구현한다.
System.Net.Sockets.Socket : 버클리 소켓을 제공한다. 트랜스포트 계층을 지원하며 생
성된 소켓은 Bind() 메소드를 통해 특정한 종단점으로 바운드 되며 Connect 메소드를
통해서 연결이 생성된다. Send(), SendTo() 메소드르 통해 테이터를 소켓으로 전송하며
Receive() 나 ReceiveFrom() 메소드들 통해 소켓으로부터 데이터를 수신한다. 소켓으로
하는 모든 작업이 완료되면 Shutdown() 메소드를 이용해 소켓을 비활성화 한 후 Close()
메소드를 이용해 소켓을 닫는다. 닷넷에서의 소켓은 인터넷의 TcpClient, UdpClient,
WebRequest 그리고 파생된 클래스들의 연결을 맺는데 사용된다.
System.Net.Sockets.TcpListener : TCP 네트웍의 클라이언트 접속을 Listening하며 소켓
클래스를 기반으로 TCP 서비스를 제공하기 위한 서버쪽 클래스이다. FTP, HTTP와 같은
프로토콜을 사용하는 애플리케이션 계층은 TcpListener를 기반으로 작성 될 수 있다.
클라이언트는 서버로 글을 보내기만 하고, 서버는 글을 받아서 출력만 하는 간단한 예제
를 작성해 보자.
[클라이언트]
using System;
using System.IO;
using System.Text;
using System.Net;
using System.Net.Sockets;
class TcpClientTest
{
static void Main(string[] args)
{
TcpClient client = null;
try
{
//LocalHost에 지정 포트로 TCP 연결을 생성하고 데이터를 송수신을
//위한 스트림을 얻는다.
client = new TcpClient();
client.Connect("localhost", 5001);
NetworkStream stream = client.GetStream();
StreamWriter writer = new StreamWriter(stream)
{ AutoFlush = true };
string dataToSend = Console.ReadLine();
while (true)
{
writer.WriteLine(dataToSend);
if (dataToSend.IndexOf("<EOF>") > -1) break;
dataToSend = Console.ReadLine();
}
}
catch (Exception ex)
{
Console.WriteLine(ex.ToString());
}
finally
{
client.Close();
}
}
}
[서버]
using System;
using System.IO;
using System.Text;
using System.Net;
using System.Net.Sockets;
class Server
{
public static void Main()
{
NetworkStream stream = null;
TcpListener tcpListener = null;
Socket clientsocket = null;
StreamReader reader = null;
try
{
//IP주소를 나타내는 객체를 생성,TcpListener를 생성시 인자로 사용할려고
IPAddress ipAd = IPAddress.Parse("127.0.0.1");
//TcpListener Class를 이용하여 클라이언트의 연결을 받아 들인다.
tcpListener = new TcpListener(ipAd, 5001);
tcpListener.Start();
//Client의 접속이 올때까지 블로킹 되는 부분,
//대개 이부분을 Thread로 만들어 보내 버린다.
//백그라운드 Thread에 처리를 맡긴다.
clientsocket = tcpListener.AcceptSocket();
//클라이언트의 데이터를 읽고, 쓰기 위한 스트림을 만든다.
stream = new NetworkStream(clientsocket);
Encoding encode = Encoding.GetEncoding("utf-8");
reader = new StreamReader(stream, encode);
while (true)
{
string str = reader.ReadLine();
Console.WriteLine(str);
}
}
catch (Exception e)
{
Console.WriteLine(e.ToString());
}
finally
{
clientsocket.Close();
}
}
}
위의 예제는 Client는 단순히 보내기만 하고 Server는 단순히 받기만 한다. 적절히 수정
하여 Client가 보내는 것을 서버는 화면에 출력하고 Client에 다시 보내는 EchoClient와
EchoServer를 작성 해보자. 이 경우 Client 역시 보내고 받는 부분의 처리가 가능해야
한다.
7-2. EchoClient, EchoServer
[클라이언트]
using System;
using System.IO;
using System.Text;
using System.Net;
using System.Net.Sockets;
class TcpClientTest
{
static void Main(string[] args)
{
TcpClient client = null;
try
{
//LocalHost에 지정 포트로 TCP Connection을 생성하고 데이터를 송수신
하기
//위한 스트림을 얻는다.
client = new TcpClient();
client.Connect("localhost", 5001);
NetworkStream stream = client.GetStream();
Encoding encode = Encoding.GetEncoding("utf-8");
StreamReader reader = new StreamReader(stream, encode);
StreamWriter writer = new StreamWriter(stream, encode)
{ AutoFlush = true };
string dataToSend = Console.ReadLine();
while (true)
{
writer.WriteLine(dataToSend);
String str = reader.ReadLine();
Console.WriteLine(str);
if (dataToSend.IndexOf("<EOF>") > -1) break;
dataToSend = Console.ReadLine();
}
}
catch (Exception ex)
{
Console.WriteLine(ex.ToString());
}
finally
{
client.Close();
}
}
}
[서버]
using System;
using System.IO;
using System.Text;
using System.Net;
using System.Net.Sockets;
class Server
{
public static void Main()
{
NetworkStream stream = null;
TcpListener tcpListener = null;
Socket clientsocket = null;
StreamReader reader = null;
StreamWriter writer = null;
try
{
//IP주소를 나타내는 객체를 생성,TcpListener를 생성시 인자로 사용할려고
IPAddress ipAd = IPAddress.Parse("127.0.0.1");
//TcpListener Class를 이용하여 클라이언트의 연결을 받아 들인다.
tcpListener = new TcpListener(ipAd, 5001);
tcpListener.Start();
//Client의 접속이 올때 까지 Block 되는 부분, 대개 이부분을 Thread로
만들어 보내 버린다.
//백그라운드 Thread에 처리를 맡긴다.
clientsocket = tcpListener.AcceptSocket();
//클라이언트의 데이터를 읽고, 쓰기 위한 스트림을 만든다.
stream = new NetworkStream(clientsocket);
Encoding encode = Encoding.GetEncoding("utf-8");
reader = new StreamReader(stream, encode);
writer = new StreamWriter(stream, encode) { AutoFlush = true };
while (true)
{
string str = reader.ReadLine();
Console.WriteLine(str);
writer.WriteLine(str);
}
}
catch (Exception e)
{
Console.WriteLine(e.ToString());
}
finally
{
clientsocket.Close();
}
}
}
[질문] 위의 예제에서 Client를 두 개 이상 만들어서 서버에 접속해보자.
과연 어떤 일이 일어 날까? 그리고 그 해결책은 무엇일까? 아마도 멀티 쓰레드를 이용
하여 블록킹 되는 메소드를 쓰레드로 처리를 해야 할것이다. 직접 실습해 보자..
7-3. MultiThread EchoClient, EchoServer
Client Program은 그대로 두고 서버를 다시 만들자.
using System;
using System.IO;
using System.Text;
using System.Net;
using System.Net.Sockets;
using System.Threading;
class ClientHadler
{
Socket socket = null;
NetworkStream stream = null;
StreamReader reader = null;
StreamWriter writer = null;
public ClientHadler(Socket socket)
{
this.socket = socket;
}
public void chat()
{
//클라이언트의 데이터를 읽고, 쓰기 위한 스트림을 만든다.
stream = new NetworkStream(socket);
Encoding encode = Encoding.GetEncoding("utf-8");
reader = new StreamReader(stream, encode);
writer = new StreamWriter(stream, encode) { AutoFlush = true };
while (true)
{
string str = reader.ReadLine();
Console.WriteLine(str);
writer.WriteLine(str);
}
}
}
class Server
{
public static void Main()
{
TcpListener tcpListener = null;
Socket clientsocket = null;
try
{
//IP주소를 나타내는 객체를 생성,TcpListener를 생성시 인자로 사용할려고
IPAddress ipAd = IPAddress.Parse("127.0.0.1");
//TcpListener Class를 이용하여 클라이언트의 연결을 받아 들인다.
tcpListener = new TcpListener(ipAd, 5001);
tcpListener.Start();
//Client의 접속이 올때 까지 Block 되는 부분, 대개 이부분을 Thread로
만들어 보내 버린다.
//백그라운드 Thread에 처리를 맡긴다.
while (true)
{
clientsocket = tcpListener.AcceptSocket();
ClientHadler cHandler = new ClientHadler(clientsocket);
Thread t = new Thread(new ThreadStart(cHandler.chat));
t.Start();
}
}
catch (Exception e)
{
Console.WriteLine(e.ToString());
}
finally
{
clientsocket.Close();
}
}
}
(탑크리에듀 추천 닷넷, C# 과정)

(C#,네트워크강좌)간단한 TCP 클라이언트/서버 구현, 멀티쓰레드 기반 에코우 클라이언트/서버_C추천#/WPF/자마린실무교육학원

  • 1.
    소스코드, 강의자료 및동영상 보기는 http://www.topcredu.co.kr, http://ojc.asia 에서 가능 합니다. 7. C# Network 프로그래밍 7-1. 간단한 TCP 클라이언트, 서버 TCP Client & Server 만들기 System.Net.Sockets.TCPClient : TCP 네트웍의 클라이언트 서비스를 제공하고 Socket 클래스를 기본으로 작성 되었다. FTP나 HTTP와 같은 애플리케이션 계층 프로토콜을 개 발하는데 주로 사용 된다.
  • 2.
    TCPClient myClient =new TCPClient(“***.***.***.***”, 13); Stream myStream = myClient.GetStream(); System.Net.Sockets.NetworkStream : Network용 데이터 스트림을 제공한다. 네트웍의 소켓을 통해 데이터를 전송 및 수신하는 표준 닷넷 프레임워크 스트림 방식을 구현한다. System.Net.Sockets.Socket : 버클리 소켓을 제공한다. 트랜스포트 계층을 지원하며 생 성된 소켓은 Bind() 메소드를 통해 특정한 종단점으로 바운드 되며 Connect 메소드를 통해서 연결이 생성된다. Send(), SendTo() 메소드르 통해 테이터를 소켓으로 전송하며 Receive() 나 ReceiveFrom() 메소드들 통해 소켓으로부터 데이터를 수신한다. 소켓으로 하는 모든 작업이 완료되면 Shutdown() 메소드를 이용해 소켓을 비활성화 한 후 Close() 메소드를 이용해 소켓을 닫는다. 닷넷에서의 소켓은 인터넷의 TcpClient, UdpClient, WebRequest 그리고 파생된 클래스들의 연결을 맺는데 사용된다. System.Net.Sockets.TcpListener : TCP 네트웍의 클라이언트 접속을 Listening하며 소켓 클래스를 기반으로 TCP 서비스를 제공하기 위한 서버쪽 클래스이다. FTP, HTTP와 같은 프로토콜을 사용하는 애플리케이션 계층은 TcpListener를 기반으로 작성 될 수 있다. 클라이언트는 서버로 글을 보내기만 하고, 서버는 글을 받아서 출력만 하는 간단한 예제 를 작성해 보자. [클라이언트] using System; using System.IO; using System.Text; using System.Net; using System.Net.Sockets; class TcpClientTest { static void Main(string[] args) { TcpClient client = null; try { //LocalHost에 지정 포트로 TCP 연결을 생성하고 데이터를 송수신을 //위한 스트림을 얻는다. client = new TcpClient();
  • 3.
    client.Connect("localhost", 5001); NetworkStream stream= client.GetStream(); StreamWriter writer = new StreamWriter(stream) { AutoFlush = true }; string dataToSend = Console.ReadLine(); while (true) { writer.WriteLine(dataToSend); if (dataToSend.IndexOf("<EOF>") > -1) break; dataToSend = Console.ReadLine(); } } catch (Exception ex) { Console.WriteLine(ex.ToString()); } finally { client.Close(); } } } [서버] using System; using System.IO; using System.Text; using System.Net; using System.Net.Sockets; class Server { public static void Main() {
  • 4.
    NetworkStream stream =null; TcpListener tcpListener = null; Socket clientsocket = null; StreamReader reader = null; try { //IP주소를 나타내는 객체를 생성,TcpListener를 생성시 인자로 사용할려고 IPAddress ipAd = IPAddress.Parse("127.0.0.1"); //TcpListener Class를 이용하여 클라이언트의 연결을 받아 들인다. tcpListener = new TcpListener(ipAd, 5001); tcpListener.Start(); //Client의 접속이 올때까지 블로킹 되는 부분, //대개 이부분을 Thread로 만들어 보내 버린다. //백그라운드 Thread에 처리를 맡긴다. clientsocket = tcpListener.AcceptSocket(); //클라이언트의 데이터를 읽고, 쓰기 위한 스트림을 만든다. stream = new NetworkStream(clientsocket); Encoding encode = Encoding.GetEncoding("utf-8"); reader = new StreamReader(stream, encode); while (true) { string str = reader.ReadLine(); Console.WriteLine(str); } } catch (Exception e) { Console.WriteLine(e.ToString()); } finally { clientsocket.Close(); }
  • 5.
    } } 위의 예제는 Client는단순히 보내기만 하고 Server는 단순히 받기만 한다. 적절히 수정 하여 Client가 보내는 것을 서버는 화면에 출력하고 Client에 다시 보내는 EchoClient와 EchoServer를 작성 해보자. 이 경우 Client 역시 보내고 받는 부분의 처리가 가능해야 한다. 7-2. EchoClient, EchoServer [클라이언트] using System; using System.IO; using System.Text; using System.Net; using System.Net.Sockets; class TcpClientTest { static void Main(string[] args) { TcpClient client = null; try { //LocalHost에 지정 포트로 TCP Connection을 생성하고 데이터를 송수신 하기 //위한 스트림을 얻는다. client = new TcpClient(); client.Connect("localhost", 5001); NetworkStream stream = client.GetStream(); Encoding encode = Encoding.GetEncoding("utf-8"); StreamReader reader = new StreamReader(stream, encode); StreamWriter writer = new StreamWriter(stream, encode) { AutoFlush = true };
  • 6.
    string dataToSend =Console.ReadLine(); while (true) { writer.WriteLine(dataToSend); String str = reader.ReadLine(); Console.WriteLine(str); if (dataToSend.IndexOf("<EOF>") > -1) break; dataToSend = Console.ReadLine(); } } catch (Exception ex) { Console.WriteLine(ex.ToString()); } finally { client.Close(); } } } [서버] using System; using System.IO; using System.Text; using System.Net; using System.Net.Sockets; class Server { public static void Main() { NetworkStream stream = null; TcpListener tcpListener = null; Socket clientsocket = null; StreamReader reader = null; StreamWriter writer = null;
  • 7.
    try { //IP주소를 나타내는 객체를생성,TcpListener를 생성시 인자로 사용할려고 IPAddress ipAd = IPAddress.Parse("127.0.0.1"); //TcpListener Class를 이용하여 클라이언트의 연결을 받아 들인다. tcpListener = new TcpListener(ipAd, 5001); tcpListener.Start(); //Client의 접속이 올때 까지 Block 되는 부분, 대개 이부분을 Thread로 만들어 보내 버린다. //백그라운드 Thread에 처리를 맡긴다. clientsocket = tcpListener.AcceptSocket(); //클라이언트의 데이터를 읽고, 쓰기 위한 스트림을 만든다. stream = new NetworkStream(clientsocket); Encoding encode = Encoding.GetEncoding("utf-8"); reader = new StreamReader(stream, encode); writer = new StreamWriter(stream, encode) { AutoFlush = true }; while (true) { string str = reader.ReadLine(); Console.WriteLine(str); writer.WriteLine(str); } } catch (Exception e) { Console.WriteLine(e.ToString()); } finally { clientsocket.Close(); } } }
  • 8.
    [질문] 위의 예제에서Client를 두 개 이상 만들어서 서버에 접속해보자. 과연 어떤 일이 일어 날까? 그리고 그 해결책은 무엇일까? 아마도 멀티 쓰레드를 이용 하여 블록킹 되는 메소드를 쓰레드로 처리를 해야 할것이다. 직접 실습해 보자.. 7-3. MultiThread EchoClient, EchoServer Client Program은 그대로 두고 서버를 다시 만들자. using System; using System.IO; using System.Text; using System.Net; using System.Net.Sockets; using System.Threading; class ClientHadler { Socket socket = null; NetworkStream stream = null; StreamReader reader = null; StreamWriter writer = null; public ClientHadler(Socket socket) { this.socket = socket; } public void chat() { //클라이언트의 데이터를 읽고, 쓰기 위한 스트림을 만든다. stream = new NetworkStream(socket); Encoding encode = Encoding.GetEncoding("utf-8"); reader = new StreamReader(stream, encode); writer = new StreamWriter(stream, encode) { AutoFlush = true };
  • 9.
    while (true) { string str= reader.ReadLine(); Console.WriteLine(str); writer.WriteLine(str); } } } class Server { public static void Main() { TcpListener tcpListener = null; Socket clientsocket = null; try { //IP주소를 나타내는 객체를 생성,TcpListener를 생성시 인자로 사용할려고 IPAddress ipAd = IPAddress.Parse("127.0.0.1"); //TcpListener Class를 이용하여 클라이언트의 연결을 받아 들인다. tcpListener = new TcpListener(ipAd, 5001); tcpListener.Start(); //Client의 접속이 올때 까지 Block 되는 부분, 대개 이부분을 Thread로 만들어 보내 버린다. //백그라운드 Thread에 처리를 맡긴다. while (true) { clientsocket = tcpListener.AcceptSocket(); ClientHadler cHandler = new ClientHadler(clientsocket); Thread t = new Thread(new ThreadStart(cHandler.chat)); t.Start(); }
  • 10.