Configure TCP / IP Client and Server for Network Communication

I'm trying to learn a little about socket programming, and I came across TcpListener and TcpClient to use as I read that they are a bit easier for beginners. The main point of what I want to do is to have a small form that can be run on my laptop and on another laptop on the same network and so that they can communicate, that is, send a line of text to each other. As soon as I have it, I hope that it will develop further :)

So far I have created both a client and a server program using msdn and various manuals found on the Internet. I can make them communicate when they are working on one laptop, however, when I move the client to another laptop, I will not go anywhere. I think my main problem is that I don’t quite understand how the client finds the server IP address, because I think I can hardcode it, but when I return at another time, I’m sure that the IP address will change. Is there a way to get them to connect more dynamically to cover a changing IP address? My current client code is:

public void msg(string mesg) { lstProgress.Items.Add(">> " + mesg); } private void btnConnect_Click(object sender, EventArgs e) { string message = "Test"; try { // Create a TcpClient. // Note, for this client to work you need to have a TcpServer // connected to the same address as specified by the server, port // combination. Int32 port = 1333; TcpClient client = new TcpClient(<not sure>, port); //Unsure of IP to use. // Translate the passed message into ASCII and store it as a Byte array. Byte[] data = System.Text.Encoding.ASCII.GetBytes(message); // Get a client stream for reading and writing. // Stream stream = client.GetStream(); NetworkStream stream = client.GetStream(); // Send the message to the connected TcpServer. stream.Write(data, 0, data.Length); lstProgress.Items.Add(String.Format("Sent: {0}", message)); // Receive the TcpServer.response. // Buffer to store the response bytes. data = new Byte[256]; // String to store the response ASCII representation. String responseData = String.Empty; // Read the first batch of the TcpServer response bytes. Int32 bytes = stream.Read(data, 0, data.Length); responseData = System.Text.Encoding.ASCII.GetString(data, 0, bytes); lstProgress.Items.Add(String.Format("Received: {0}", responseData)); // Close everything. stream.Close(); client.Close(); } catch (ArgumentNullException an) { lstProgress.Items.Add(String.Format("ArgumentNullException: {0}", an)); } catch (SocketException se) { lstProgress.Items.Add(String.Format("SocketException: {0}", se)); } } 

My current server code is:

  private void Prog_Load(object sender, EventArgs e) { bw.WorkerSupportsCancellation = true; bw.WorkerReportsProgress = true; bw.DoWork += new DoWorkEventHandler(bw_DoWork); bw.ProgressChanged += new ProgressChangedEventHandler(bw_ProgressChanged); if (bw.IsBusy != true) { bw.RunWorkerAsync(); } } private void bw_ProgressChanged(object sender, ProgressChangedEventArgs e) { lstProgress.Items.Add(e.UserState); } private void bw_DoWork(object sender, DoWorkEventArgs e) { BackgroundWorker worker = sender as BackgroundWorker; if ((worker.CancellationPending == true)) { e.Cancel = true; } else { try { // Set the TcpListener on port 1333. Int32 port = 1333; //IPAddress localAddr = IPAddress.Parse("127.0.0.1"); TcpListener server = new TcpListener(IPAddress.Any, port); // Start listening for client requests. server.Start(); // Buffer for reading data Byte[] bytes = new Byte[256]; String data = null; // Enter the listening loop. while (true) { bw.ReportProgress(0, "Waiting for a connection... "); // Perform a blocking call to accept requests. // You could also user server.AcceptSocket() here. TcpClient client = server.AcceptTcpClient(); bw.ReportProgress(0, "Connected!"); data = null; // Get a stream object for reading and writing NetworkStream stream = client.GetStream(); int i; // Loop to receive all the data sent by the client. while ((i = stream.Read(bytes, 0, bytes.Length)) != 0) { // Translate data bytes to a ASCII string. data = System.Text.Encoding.ASCII.GetString(bytes, 0, i); bw.ReportProgress(0, String.Format("Received: {0}", data)); // Process the data sent by the client. data = String.Format("I Have Received Your Message: {0}", data); byte[] mssg = System.Text.Encoding.ASCII.GetBytes(data); // Send back a response. stream.Write(mssg, 0, mssg.Length); bw.ReportProgress(0, String.Format("Sent: {0}", data)); } // Shutdown and end connection client.Close(); } } catch (SocketException se) { bw.ReportProgress(0, String.Format("SocketException: {0}", se)); } } } 

As you can probably say I'm new to this, so if there is a better way to implement this, I am more than happy to find out! Thanks for any help in advance :)

My solution thanks to the answers below:

 private String IPAddressCheck() { var IPAddr = Dns.GetHostEntry("HostName"); IPAddress ipString = null; foreach (var IP in IPAddr.AddressList) { if(IPAddress.TryParse(IP.ToString(), out ipString) && IP.AddressFamily == AddressFamily.InterNetwork) { break; } } return ipString.ToString(); } private void btnConnect_Click(object sender, EventArgs e) { string message = "Test"; try { Int32 port = 1337; string IPAddr = IPAddressCheck(); TcpClient client = new TcpClient(IPAddr, port); 

I'm not sure if this is the best solution, but it works well, so thanks for the answers :)

+6
source share
2 answers

Not quite sure what you mean by "a more dynamic way to capture change ip". Taking the beginner's guess where you have:

 TcpClient client = new TcpClient(<not sure>, port); //Unsure of IP to use. 

You can run both the client and the server on the same computer and use the loopback local IP address:

 IPAddress.Parse("127.0.0.1") 

If they work on different computers, just replace 127.0.0.1 with any IP address used by the server (this does not imply the use of NAT or firewalls).

If you do not want to use IP addresses, you can always use hostnames (they can be considered more "dynamic"), but this will require a configured DNS setting (for local systems):

 TcpClient client = new TcpClient("testMachine1", 1333); 

Good to learn socket programming. I am a developer of the networkcomms.net network library, so you should also work in the opposite direction from a working example while learning, please check this wpf chat example .

+1
source

If you know the name of the computer you want to connect to, you can easily find your IP address using System.Net.DNS.

 var ip = System.Net.Dns.GetHostEntry("JacksLaptop"); string ipString = ip.AddressList[0].ToString(); 

The IP address that you think you are using may not be the same as at location 0 of this array, so keep an eye on this.

+1
source

All Articles