Unable to test SmtpClient.TimeOut - c#

I am using Visual Studio 2010, .NET 4.0 and I am trying to test the SMTPClient.TimeOut property and actually get it to throw a SmtpException. However, even when I set the TimeOut property to 1 millisecond, it still sends the email which seems like it is sending under a millisecond but what I find interesting is that when I inspect the object I can see a private member variable called timedOut set to true, indicating that it in fact timed out.
Here is my code:
try
{
MailMessage emailMsg = new MailMessage(this.EmailFrom, this.EmailTo, this.EmailSubject, msg);
//SmtpClient emailClient = new SmtpClient(this.EmailServer);
SmtpClient emailClient = new SmtpClient();
emailClient.Credentials = new System.Net.NetworkCredential("username", "password");
emailMsg.IsBodyHtml = true;
emailClient.Timeout = Properties.Settings.Default.SMTPTimeOut;
emailClient.Timeout = 1;
emailClient.Send(emailMsg);
sendingEmail = true;
return sendingEmail;
}
catch (Exception ex)
{
// Handle time out exception here.
}
Has anyone ever seen this or know a better way to test this? Right now I am hitting gmail's smtp.

I believe that you can use telnet. Turn on telnet and use that ip as your smtp server. It would not connect so it should timeout. Have not tested this.
http://technet.microsoft.com/en-us/library/aa995718(v=exchg.65).aspx

To finally test this was working I wrote a very simple TCP server console app on my local machine. I used the following tutorial on how to do this: http://bit.ly/XoHWPC
By creating this console app I was able to take my service which sends email and point it to my local machine (127.0.0.1,25). The TCP Server console app accepted the connection but then I never send a response back.
My service sending the email successfully timed out as expected so I could finally verify it was working properly. Here is a snippet of the TCP Server Console app from the tutorial for a guide. I recommend reading the whole tutorial though if you have time.
Program.cs
using System;
using System.Text;
using System.Net.Sockets;
using System.Threading;
using System.Net;
namespace TCPServer
{
class Program
{
static void Main(string[] args)
{
Server server = new Server();
}
}
}
Server.cs
using System;
using System.Text;
using System.Net.Sockets;
using System.Threading;
using System.Net;
namespace TCPServer
{
public class Server
{
private TcpListener tcpListener;
private Thread listenThread;
public Server()
{
this.tcpListener = new TcpListener(IPAddress.Any, 25);
this.listenThread = new Thread(new ThreadStart(ListenForClients));
this.listenThread.Start();
}
private void ListenForClients()
{
this.tcpListener.Start();
while (true)
{
//blocks until a client has connected to the server
TcpClient client = this.tcpListener.AcceptTcpClient();
//create a thread to handle communication
//with connected client
Thread clientThread = new Thread(new ParameterizedThreadStart(HandleClientComm));
clientThread.Start(client);
}
}
private void HandleClientComm(object client)
{
TcpClient tcpClient = (TcpClient)client;
NetworkStream clientStream = tcpClient.GetStream();
byte[] message = new byte[4096];
int bytesRead;
while (true)
{
bytesRead = 0;
try
{
//blocks until a client sends a message
bytesRead = clientStream.Read(message, 0, 4096);
}
catch
{
//a socket error has occured
break;
}
if (bytesRead == 0)
{
//the client has disconnected from the server
break;
}
//message has successfully been received
ASCIIEncoding encoder = new ASCIIEncoding();
System.Diagnostics.Debug.WriteLine(encoder.GetString(message, 0, bytesRead));
}
tcpClient.Close();
}
}
}

Related

How can I make a server program keep running no matter what happens to a client?

Take a look at the following two programs:
//Server
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Threading.Tasks;
namespace MyServerProgram
{
class Program
{
static void Main(string[] args)
{
IPAddress ip = IPAddress.Parse("127.0.0.1");
int port = 2000;
TcpListener listener = new TcpListener(ip, port);
listener.Start();
TcpClient client = listener.AcceptTcpClient();
Console.WriteLine("Connected " + ((IPEndPoint)client.Client.RemoteEndPoint).Address);
NetworkStream netStream = client.GetStream();
BinaryReader br = new BinaryReader(netStream);
try
{
while (client.Client.Connected)
{
string str = br.ReadString();
Console.WriteLine(str);
}
}
catch (Exception ex)
{
var inner = ex.InnerException as SocketException;
if (inner != null && inner.SocketErrorCode == SocketError.ConnectionReset)
Console.WriteLine("Disconnected");
else
Console.WriteLine(ex.Message);
br.Close();
netStream.Close();
client.Close();
listener.Stop();
}
}
}
}
//Client
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Threading.Tasks;
namespace MyClientProgram
{
class Program
{
static void Main(string[] args)
{
int port = 2000;
TcpClient client = new TcpClient("localhost", port);
NetworkStream netStream = client.GetStream();
BinaryWriter br = new BinaryWriter(netStream);
try
{
int i=1;
while (client.Client.Connected)
{
br.Write(i.ToString());
br.Flush();
i++;
int milliseconds = 2000;
System.Threading.Thread.Sleep(milliseconds);
}
}
catch
{
br.Close();
netStream.Close();
client.Close();
}
}
}
}
The problem I am facing with the Server is, the Server program exits as soon as the client is closed.
I want the server program to keep running no matter what a client does or happens to it.
How can I do that?
Try putting a while loop around your AcceptTcpClient (and associated logic).
To paraphrase from your server code:
boolean keepRunning = true;
while (keepRunning) {
TcpClient client = listener.AcceptTcpClient();
Console.WriteLine("Connected ...") // and other stuff deleted.
// while client connected...
string str = br.ReadString();
// check to see if we should continue running.
keepRunning = ! "quit".equalsIgnoreCase(str);
// Other stuff
Note this is very insecure - any client regardless of where / who they are could terminate your server be sending a "quit" message to your server. In real life, you would probably require a more strict mechanism. Obviously with this mechanism, you will need your client to be able to generate the "quit" message text when you need it to do so.
Another method is to run the whole server in a Thread. Then in another thread, have a method that an operator could use to close the server (e.g. a menu selection in a Swing Application).
There are plenty of options you could choose from to "manage" the shutdown.
Also, as written, your code is single threaded. That is, it will wait for a client to connect, deal with that client and then exit (or if you apply the keepRunning while loop modification wait for the next client to connect). But, only one client can connect to this server at any one time.
To make it multi-threaded (can service multiple clients at one time), put the body of your server (the service code) into a Thread and invoke a new instance of the Thread to serve that client. After starting the service Thread, the main loop simply waits for the next client to connect.
Thus, your main loop will become something like this:
while (keepRunning) {
TcpClient client = listener.AcceptTcpClient();
Console.WriteLine("Connected ...") // and other stuff deleted.
ServiceThread st = new ServiceThread(client);
st.start ();
}
and the Service Thread will be something like:
public class ServiceThread extends Thread {
private TcpClient client;
public ServiceThread (TcpClient client) {
this.client = client;
}
#override
public void run() {
NetworkStream netStream = client.GetStream();
BinaryReader br = new BinaryReader(netStream);
try {
while (client.Client.Connected) {
// Stuff deleted for clarity
}
}
catch (Exception ex) {
// Exception handling stuff deleted for clarity.
}
}
}

Asynchronous tcp client in C# connecting to API... Sporadic errors

I am writing a TCP Client in C# that is meant to connect to a 3rd-party API server. The vendor is insisting the problem is our code. They have provided a sample TCP client .exe to test against their API. I am generally successful connecting to their API with their app and using Packet Sender. I cannot figure out the problem in my code, though, so I'm hoping I can get some help seeing where I'm going wrong.
I have to make an initial call to ensure a setting is correct, then I can make my API call. It seems as though the API call only returns results when I make my call asynchronously. I'll get successful results 2 or 3 times in a row, and then I'll get an error message that is indecipherable without access to the vendor's source code. I got this code from an MSDN sample or someplace else reputable, but I still seem to get an error from the API (it hangs up and stops responding until I restart it) every 5th call or so (it's inconsistent when I get the error). Can someone help me debug my code? I'm genericizing it so that I'm not putting anything specific to the vendor's API here.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Threading.Tasks;
namespace tcp
{
class AsyncClient
{
static void Main(string[] args)
{
SetInitialSetting();
ConnectAsTcpClient();
Console.ReadLine();
}
private static void SetInitialSetting()
{
byte[] data = new byte[1024];
string stringData;
IPAddress ip;
int port;
int recv;
IPAddress.TryParse(#"127.0.0.1", out ip);
port = 10000;
SetInitialSettingString();
Console.WriteLine("[Client] Writing request {0}", ClientRequestString);
using (var client = new TcpClient(ip.ToString(), port))
{
NetworkStream ns = client.GetStream();
ns.Write(ClientRequestBytes, 0, ClientRequestBytes.Length);
stringData = "";
do
{
recv = ns.Read(data, 0, data.Length);
stringData = stringData + Encoding.UTF8.GetString(data, 0, recv);
}
while (ns.DataAvailable);
Console.WriteLine("[Client] Server response was {0}", stringData);
ns.Close();
}
}
private static async void ConnectAsTcpClient()
{
byte[] data = new byte[10025];
IPAddress ip;
int port;
IPAddress.TryParse(#"127.0.0.1", out ip);
port = 10000;
using (var tcpClient = new TcpClient())
{
Console.WriteLine("[Client] Connecting to server");
await tcpClient.ConnectAsync(ip, port);
Console.WriteLine("[Client] Connected to server");
using (var networkStream = tcpClient.GetStream())
{
SetAPICallString();
Console.WriteLine("[Client] Writing request {0}", ClientRequestString);
await networkStream.WriteAsync(ClientRequestBytes, 0, ClientRequestBytes.Length);
var buffer = new byte[4096];
var byteCount = await networkStream.ReadAsync(buffer, 0, buffer.Length);
var response = Encoding.UTF8.GetString(buffer, 0, byteCount);
Console.WriteLine("[Client] Server response was {0}", response);
}
}
}
private static string ClientRequestString;
private static byte[] ClientRequestBytes;
private static void SetInitialSettingString()
{
ClientRequestString = "StringThatSetsTheAPISettingGoesHere";
ClientRequestBytes = Encoding.UTF8.GetBytes(ClientRequestString);
}
private static void SetAPICallString()
{
ClientRequestString = "StringForTheCallToTheAPIThatINeedGoesHere";
ClientRequestBytes = Encoding.UTF8.GetBytes(ClientRequestString);
}
}
}

I can't connect to test a local server started with TcpListener

Disclaimer: this is my first foray into anything directly tcp/socket related. I've read -the- -following- -resources- and am trying to come up with a very simple test application.
I'm trying to develop a local server running with a TcpListener object. I can instantiate it fine and run netstat to see the port in the LISTENING state. However, I can't telnet or create a test client to connect manually. Telnet says simply that it could not open a connection. Trying a test client application throws the exception
An unhandled exception of type 'System.Net.Sockets.SocketException' occurred in System.dll
Additional information: Only one usage of each socket address (protocol/network address/port) is normally permitted
In this SO question, the asker ultimately resolved it via a faulty NIC. How might I look for that?
This leaves me puzzled. How do I ever test or connect to the server? Here's my code.
For the server:
using System;
using System.Configuration;
using System.IO;
using System.Net;
using System.Net.Sockets;
using System.Threading.Tasks;
namespace TcpConsole
{
class Program
{
static void Main(string[] args)
{
var localPort = ConfigurationManager.AppSettings["localPort"];
var portNumber = int.Parse(localPort);
var maxConnections = ConfigurationManager.AppSettings["maxConnections"];
var maxConnectionsNumber = int.Parse(maxConnections);
Console.WriteLine("Preparing to start server on port {0}", portNumber);
Console.WriteLine("Max connections: {0}", maxConnectionsNumber);
var ipHostInfo = Dns.GetHostEntry("localhost");
var ipAddress = ipHostInfo.AddressList[0];
var localEndPoint = new IPEndPoint(ipAddress, portNumber);
Console.WriteLine("Starting server with local IP {0}", ipAddress);
var listener = new TcpListener(localEndPoint);
listener.Start(maxConnectionsNumber);
Console.WriteLine();
Console.WriteLine("Server started...");
Console.WriteLine();
while (true)
{
var socket = listener.AcceptSocket();
Task.Factory.StartNew(() =>
{
ProcessSocket(socket);
});
}
}
private static async void ProcessSocket(Socket socket)
{
try
{
using (var stream = new NetworkStream(socket))
using (var reader = new StreamReader(stream))
using (var writer = new StreamWriter(stream))
{
writer.AutoFlush = true;
var received = await reader.ReadToEndAsync();
Console.WriteLine("Received: " + received);
}
socket.Close();
socket.Dispose();
}
catch (Exception exception)
{
Console.WriteLine("There was an error processing a message.");
Console.WriteLine(exception);
}
}
}
}
Seeing the above code running:
For the test application:
using System;
using System.IO;
using System.Net;
using System.Net.Sockets;
namespace TcpConsoleClient
{
class Program
{
static void Main(string[] args)
{
var ipHostInfo = Dns.GetHostEntry("localhost");
var ipAddress = ipHostInfo.AddressList[0];
var remoteEndPoint = new IPEndPoint(ipAddress, 3245);
var client = new TcpClient(remoteEndPoint);
using (var stream = client.GetStream())
using (var reader = new StreamReader(stream))
using (var writer = new StreamWriter(stream))
{
writer.AutoFlush = true;
string input;
while((input = Console.ReadLine()) != "exit")
{
writer.WriteLine(input);
}
}
}
}
}
A TCP/IP connection has a local IP address and port, as well as a remote IP address and port.
Generally, a port number can only be assigned to one socket at a time. The error message indicates that an attempt was made to associate more than one socket with the same port number.
The reason why can be found in the client code:
var client = new TcpClient(remoteEndPoint);
This overload of the TcpClient constructor accepts an IPEndPoint specifying the local endpoint. That is, when the TcpClient is constructed, it will get bound to the port number specified by remoteEndPoint, which fails, because that port number is already in use by the server application.
To fix this, use the parameter-less TcpClient constructor, and instead pass remoteEndPoint to the Connect call:
var client = new TcpClient();
client.Connect(remoteEndPoint);

C# Receive Data from Multiple TCP clients on same server and display it in GUI

I am trying to develop a C# based GUI program to receive the data from multiple TCP clients on a single server. All the clients should listen to the same port on the server and the server accepts the data from multiple clients, divide the receive data and display it in GUI.
I tried this console based program to receive the data from multiple clients on port 4000 on server. But i am not able to connect to the clients. For a single client using the specific ip address and port binding, its working fine. It just waiting for the multiple clients, and do not receive the data from the clients. Can you tell me the specific solution how to tackle this problem?
Here is my code:
using System;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Threading;
public class ThreadedTcpSrvr
{
private TcpListener client;
public ThreadedTcpSrvr()
{
client = new TcpListener(4000);
client.Start();
while (true)
{
while (!client.Pending())
{
Thread.Sleep(100);
}
ConnectionThread newconnection = new ConnectionThread();
newconnection.threadListener = this.client;
Thread newthread = new Thread(new
ThreadStart(newconnection.HandleConnection));
newthread.Start();}
}
public static void Main()
{
ThreadedTcpSrvr server = new ThreadedTcpSrvr();
}
}
class ConnectionThread
{
public TcpListener threadListener;
private static int connections = 0;
public void HandleConnection()
{
int recv;
byte[] data = new byte[1024];
TcpClient client = threadListener.AcceptTcpClient();
NetworkStream ns = client.GetStream();
connections++;
Console.WriteLine("New client accepted: {0} active connections",
connections);
string welcome = "Welcome to the Server";
data = Encoding.ASCII.GetBytes(welcome);
ns.Write(data, 0, data.Length);
while (true)
{
data = new byte[1024];
recv = ns.Read(data, 0, data.Length);
if (recv == 0)
break;
ns.Write(data, 0, recv);
}
ns.Close();
client.Close();
connections--;
Console.WriteLine("Client disconnected: {0} active connections",
connections); }
}
P.S. I tried to capture the data through wireshark and i am able to capture the data.

C# TCP Client to Server messages

I wrote a C# TCP Server that runs on my desktop, while I have a client running on my windows phone. It works great, the client can connect to the server. But I am trying to make it so the server can receive messages from the client. When I run it, the server just receives a number when I am sending a string.
Here is my server code.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Net.Sockets;
using System.Net;
using System.IO;
namespace TCPServer
{
class Server
{
private TcpListener tcpListener;
private Thread listenThread;
public Server()
{
this.tcpListener = new TcpListener(IPAddress.Any, 80);
this.listenThread = new Thread(new ThreadStart(ListenForClients));
this.listenThread.Start();
}
private void ListenForClients()
{
this.tcpListener.Start();
while (true)
{
TcpClient client = this.tcpListener.AcceptTcpClient();
Thread clientThread = new Thread(new ParameterizedThreadStart(HandleClientComm));
clientThread.Start(client);
}
}
private void HandleClientComm(object client)
{
TcpClient tcpClient = (TcpClient)client;
NetworkStream clientStream = tcpClient.GetStream();
Console.WriteLine("Got connection");
StreamReader clientStreamReader = new StreamReader(clientStream);
Console.WriteLine(clientStreamReader.Read());
}
}
}
Here is the client code:
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Threading;
namespace NetworkingTesting
{
class Client
{
Socket socket = null;
static ManualResetEvent clientDone = new ManualResetEvent(false);
const int TIMEOUT_MILLISECONDS = 5000;
const int MAX_BUFFER_SIZE = 2048;
DnsEndPoint hostEntry;
public string Connect(string hostName, int portNumber)
{
string result = string.Empty;
hostEntry = new DnsEndPoint(hostName, portNumber);
socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
SocketAsyncEventArgs socketEventArg = new SocketAsyncEventArgs();
socketEventArg.RemoteEndPoint = hostEntry;
socketEventArg.Completed += new EventHandler<SocketAsyncEventArgs>(delegate(object s, SocketAsyncEventArgs e)
{
result = e.SocketError.ToString();
clientDone.Set();
});
clientDone.Reset();
socket.ConnectAsync(socketEventArg);
clientDone.WaitOne(TIMEOUT_MILLISECONDS);
return result;
}
public void SendToServer(string message)
{
SocketAsyncEventArgs asyncEvent = new SocketAsyncEventArgs { RemoteEndPoint = hostEntry};
Byte[] buffer = Encoding.UTF8.GetBytes(message + Environment.NewLine);
asyncEvent.SetBuffer(buffer, 0, buffer.Length);
socket.SendAsync(asyncEvent);
}
}
}
In my main client class, I have: client.SendToServer("hello!");
When I run the server and run the client the server detects the client but receives "104" instead of "Hello". Could anybody explain why this is happening and maybe provide a solution to the problem?
When you're doing clientStreamReader.Read() you're just reading one char as int from the stream. Check the doc here.
That's why you get only a number.
You need a delimeter to each message to know where it ends, \r\n is often used.
Here a sample to make your server receive your hello! String :
In your client Code
client.SendToServer("hello!" + "\r\n");
In your server Code
Console.WriteLine(clientStreamReader.ReadLine()); // Which should print hello!

Categories