Sepertinya semua kasus yang menyebabkan penundaan lama dapat diselesaikan banyak lebih cepat dengan mencoba koneksi soket langsung seperti ini:
foreach (string svrName in args)
{
try
{
System.Net.Sockets.TcpClient tcp = new System.Net.Sockets.TcpClient(svrName, 1433);
if (tcp.Connected)
Console.WriteLine("Opened connection to {0}", svrName);
else
Console.WriteLine("{0} not connected", svrName);
tcp.Close();
}
catch (Exception ex)
{
Console.WriteLine("Error connecting to {0}: {1}", svrName, ex.Message);
}
}
Saya akan menggunakan kode ini untuk memeriksa apakah server merespons pada port SQL Server, dan hanya mencoba membuka koneksi jika ya. Saya pikir (berdasarkan pengalaman orang lain) bahwa akan ada penundaan 30 detik bahkan pada level ini, tetapi saya mendapatkan pesan bahwa mesin "secara aktif menolak koneksi" pada ini segera.
Sunting: Dan jika mesin itu tidak ada, itu memberitahu saya segera juga. Tidak ada penundaan 30 detik yang dapat saya temukan.
Sunting: Mesin yang berada di jaringan tetapi tidak dimatikan masih membutuhkan waktu 30 detik untuk gagal, saya kira. Namun, mesin yang di-firewall gagal lebih cepat.
Sunting: Berikut kode yang diperbarui. Saya merasa lebih bersih untuk menutup soket daripada membatalkan utas:
static void TestConn(string server)
{
try
{
using (System.Net.Sockets.TcpClient tcpSocket = new System.Net.Sockets.TcpClient())
{
IAsyncResult async = tcpSocket.BeginConnect(server, 1433, ConnectCallback, null);
DateTime startTime = DateTime.Now;
do
{
System.Threading.Thread.Sleep(500);
if (async.IsCompleted) break;
} while (DateTime.Now.Subtract(startTime).TotalSeconds < 5);
if (async.IsCompleted)
{
tcpSocket.EndConnect(async);
Console.WriteLine("Connection succeeded");
}
tcpSocket.Close();
if (!async.IsCompleted)
{
Console.WriteLine("Server did not respond");
return;
}
}
}
catch(System.Net.Sockets.SocketException ex)
{
Console.WriteLine(ex.Message);
}
}