我需要檢查主機是否快速啟動或關閉。為此,我在建立連接之前添加了套接字超時,但套接字超時似乎不起作用。為什么?
這是我的代碼:
import socket
def test_hostname(hostname, port):
s = socket.socket(socket.AF_INET,socket.SOCK_STREAM)
s.settimeout(1.0) # timeout
try:
s.connect((hostname, port))
except (socket.timeout, socket.gaierror):
return False
else:
return True
finally:
s.close()
result = test_hostname("001.com",80) # 001.com is down
print(result)
我需要大約 10-20 秒而不是指定的超時時間(1 秒)。
uj5u.com熱心網友回復:
發生這種情況是因為 Python 套接字的超時不會限制 DNS 查找所花費的時間。由于您使用的域名需要決議為 IP,因此您s.connect((hostname, port))首先需要對 進行 DNS 查詢hostname,然后才能使用 DNS 服務器回傳的其中一個 IP 創建連接(如果任何)。
該域001.com似乎無法決議為任何 IP 地址,因此您的系統可能需要幾秒鐘才能回傳故障。發生這種情況時,Python 將退出,連接將失敗,但超時時間已過長。
如果您知道要訪問的主機的 IP 地址,請使用它而不是主機名。如果沒有,您將不得不使用 DNS 決議庫來超時 DNS 決議,例如dnspython:
import socket
import dns.resolver
def test_hostname(hostname, port):
resolver = dns.resolver.Resolver()
resolver.timeout = resolver.lifetime = 1
try:
answer = resolver.resolve(hostname, 'A')
except dns.exception.Timeout:
return False
if not answer.rrset:
return False
addr = next(iter(answer.rrset)).to_text()
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.settimeout(1)
try:
s.connect((addr, port))
except (socket.timeout, socket.gaierror):
return False
else:
return True
finally:
s.close()
轉載請註明出處,本文鏈接:https://www.uj5u.com/caozuo/416583.html
標籤:
上一篇:如何定位特定行程的unix套接字
下一篇:非活動期后關閉與客戶端的連接
