Я пишу клиент-серверное приложение, используя TCP-сокеты. Сервер написан на C # с использованием Visual Studio 2010 (.NET 4.0). Сервер допускает несколько клиентских подключений одновременно, поэтому я использую Async. стиль. Сервер должен подключаться к базе данных (MySQL), и пока запущена серверная программа, мне нужно взаимодействовать с базой данных. По этой причине я использую BackgroundWorker для запуска бесконечного цикла прослушивания (который будет принимать клиентов), чтобы предотвратить зависание интерфейса и возможность доступа к базе данных из визуального интерфейса.
Все работает нормально, кроме случаев, когда программа сервера теряет фокус. Примеры потери фокуса: на компьютере, на котором запущена серверная программа, запускается заставка, вы нажимаете на часы на панели задач, чтобы увидеть время, вы открываете другую вдову (проводник окон, калькулятор ...). Если серверная программа теряет фокус и клиент пытается подключиться, сервер полностью закрывается! Если я запускаю сервер из Visual Studio, он не выдает никаких ошибок или исключений. Если у меня запущенная версия сервера, Microsoft Windows покажет диалоговое окно «Программирование не отвечает ...».
Вот как структурирован мой код:
Переменные в основном классе:
const int portNo = 12345;
static System.Net.IPAddress localAdd = System.Net.IPAddress.Parse("192.168.1.67");
static TcpListener tcpListenerReadWrite = new TcpListener(localAdd, portNo);
В основной форме кнопка запускает сервер:
private void button1_Click(object sender, EventArgs e)
{
tcpListenerReadWrite.Start();
backgroundWorker1.RunWorkerAsync();
}
Фоновая рабочая функция DoWork:
private void backgroundWorker1_DoWork(object sender, DoWorkEventArgs e)
{
while (true)
{
ChatClient clientRead = new ChatClient(tcpListenerReadWrite.AcceptTcpClient());
}
}
В классе сервера конструктор выглядит следующим образом:
public ChatClient(TcpClient client) //constructor
{
_client = client;
_clientIP = client.Client.RemoteEndPoint.ToString();
//start reading data from the client in a separate thread
data = new byte[_client.ReceiveBufferSize];
_client.GetStream().BeginRead(data, 0, Convert.ToInt32(_client.ReceiveBufferSize), ReceiveMessage, client);
}
При получении сообщения сервером:
public void ReceiveMessage(IAsyncResult asyncResult)
{
//read received message from client
}
Два заключительных замечания: (1) когда клиент подключается к серверу, первое, что он делает, - отправляет сообщение на сервер как сообщение Hello, (2) перед записью сервера в визуальном интерфейсе, в котором я тестировал его Консольный режим и этой проблемы не было, заставка запускалась и ничего не происходило. Конечно, в режиме консоли я не использовал BackgroundWorker.
Есть идеи, почему сервер падает?