I'm trying to establish a socket connection to a host/ip address for a specific port. The main things I try to achieve are:
So basically if I specify a host name like google.com
and port 80
this should check if connection works, the same if I specify 173.194.70.101
and port 80
it should work.
If I specify for example host name like google.com
and port 7788
this should not work because that port is not open. If I specify IP: 173.194.70.101
and port ´7788´ this should not work.
If I specify some random host like sdfzsdfaklsf.com
and port 7788
this should not work because the host doesn't exist.
For all the cases above I need the response time for all success/fail ...
I ended up with this code and seams to work fine, however I would like to ask if this is a proper way of doing it?
public string CheckConnection(string ipAddressOrHostName, string portName)
{
Stopwatch timer = new Stopwatch();
timer.Start();
Socket server = null;
string elapsed = string.Empty;
try
{
IPHostEntry hostEntry = Dns.GetHostEntry(ipAddressOrHostName);
IPAddress ipAddress = hostEntry.AddressList[0];
IPEndPoint ip = new IPEndPoint(ipAddress, Convert.ToInt32(portName));
server = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
IAsyncResult result = server.BeginConnect(ip, null, null);
result.AsyncWaitHandle.WaitOne(5000, true);
timer.Stop();
elapsed = timer.ElapsedMilliseconds.ToString();
if (!server.Connected)
{
server.Close();
throw new Exception();
}
else
{
string status = string.Format("Connected succesfully to: {0} in: {1} milliseconds", server.RemoteEndPoint.ToString(), elapsed);
server.Shutdown(SocketShutdown.Both);
server.Close();
return status;
}
}
catch (Exception)
{
timer.Stop();
elapsed = timer.ElapsedMilliseconds.ToString();
return string.Format("Connection failed to: {0}:{1} in: {2} milliseconds", ipAddressOrHostName, portName, elapsed);
}
}
It's pretty good. A few points:
throw new Exception
is not so good because exceptions are not meant as control flow. Restructure the method to not need this hack.IAsyncResult
. No functional change, just more modern style.