python의 소켓 recv 메서드에 타임아웃을 설정하는 방법은 무엇입니까?
python의 socket recv 메서드에 타임아웃을 설정해야 합니다.어떻게 하는 거지?
일반적인 접근 방식은 select()를 사용하여 데이터를 사용할 수 있을 때까지 또는 시간 초과가 발생할 때까지 기다리는 것입니다.통화만recv()
데이터를 실제로 사용할 수 있는 경우.안전을 위해 소켓을 논블로킹 모드로 설정하여 다음을 보장합니다.recv()
무기한 차단하지 않습니다. select()
한 번에 둘 이상의 소켓에서 대기하는 데도 사용할 수 있습니다.
import select
mysocket.setblocking(0)
ready = select.select([mysocket], [], [], timeout_in_seconds)
if ready[0]:
data = mysocket.recv(4096)
열려 있는 파일 설명자가 많은 경우, poll()이 보다 효율적인 대안입니다.select()
.
다른 옵션은 다음을 사용하여 소켓의 모든 작업에 대한 시간 초과를 설정하는 것입니다.socket.settimeout()
하지만 당신은 다른 답변에서 그 해결책을 분명히 거부한 것으로 보입니다.
가 있습니다
두 가지 모두 언급한 바와 같이 작동할 것입니다.
전화해야 할 수도 있습니다.settimeout
예를 들어, 필요에 따라 두 번.
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.bind(("",0))
sock.listen(1)
# accept can throw socket.timeout
sock.settimeout(5.0)
conn, addr = sock.accept()
# recv can throw socket.timeout
conn.settimeout(5.0)
conn.recv(1024)
응답을 수신하기 전 및 응답을 수신한 후 시간 초과를 없음으로 다시 설정할 수 있습니다.
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.settimeout(5.0)
data = sock.recv(1024)
sock.settimeout(None)
서버 측을 구현하는 경우, 찾으려는 시간 제한은 기본 소켓의 시간 제한이 아니라 연결 소켓의 시간 제한입니다.즉, 연결 소켓 개체에 대한 다른 시간 초과가 있으며, 이는 다음의 출력입니다.socket.accept()
방법.따라서:
sock.listen(1)
connection, client_address = sock.accept()
connection.settimeout(5) # This is the one that affects recv() method.
connection.gettimeout() # This should result 5
sock.gettimeout() # This outputs None when not set previously, if I remember correctly.
당신이 클라이언트 쪽을 구현한다면, 그것은 단순할 것입니다.
sock.connect(server_address)
sock.settimeout(3)
상위 답변과 약간 혼동이 와서 더 잘 이해하기 위해 예를 들어 작은 요지를 작성했습니다.
옵션 #1 -socket.settimeout()
다음과 같은 경우에 예외를 제기합니다.sock.recv()
정의된 시간 초과를 기다립니다.
import socket
sock = socket.create_connection(('neverssl.com', 80))
timeout_seconds = 2
sock.settimeout(timeout_seconds)
sock.send(b'GET / HTTP/1.1\r\nHost: neverssl.com\r\n\r\n')
data = sock.recv(4096)
data = sock.recv(4096) # <- will raise a socket.timeout exception here
옵션 #2 -select.select()
시간 초과에 도달할 때까지 데이터가 전송될 때까지 기다립니다.다니엘의 답변을 수정하여 예외를 발생시킵니다.
import select
import socket
def recv_timeout(sock, bytes_to_read, timeout_seconds):
sock.setblocking(0)
ready = select.select([sock], [], [], timeout_seconds)
if ready[0]:
return sock.recv(bytes_to_read)
raise socket.timeout()
sock = socket.create_connection(('neverssl.com', 80))
timeout_seconds = 2
sock.send(b'GET / HTTP/1.1\r\nHost: neverssl.com\r\n\r\n')
data = recv_timeout(sock, 4096, timeout_seconds)
data = recv_timeout(sock, 4096, timeout_seconds) # <- will raise a socket.timeout exception here
사용할 수 있습니다.socket.settimeout()
초 수를 나타내는 정수 인수를 사용할 수 있습니다.예를들면,socket.settimeout(1)
시간 초과를 1초로 설정합니다.
이것을 시도해 보세요. 그것은 기본적인 C를 사용합니다.
timeval = struct.pack('ll', 2, 100)
s.setsockopt(socket.SOL_SOCKET, socket.SO_RCVTIMEO, timeval)
이전 답변에서 언급했듯이 다음과 같은 것을 사용할 수 있습니다..settimeout()
예:
import socket
s = socket.socket()
s.settimeout(1) # Sets the socket to timeout after 1 second of no activity
host, port = "somehost", 4444
s.connect((host, port))
s.send("Hello World!\r\n")
try:
rec = s.recv(100) # try to receive 100 bytes
except socket.timeout: # fail after 1 second of no activity
print("Didn't receive data! [Timeout]")
finally:
s.close()
이것이 도움이 되길 바랍니다!!
#! /usr/bin/python3.6
# -*- coding: utf-8 -*-
import socket
import time
s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
s.setsockopt(socket.SOL_SOCKET, socket.SO_BROADCAST, 1)
s.settimeout(5)
PORT = 10801
s.bind(('', PORT))
print('Listening for broadcast at ', s.getsockname())
BUFFER_SIZE = 4096
while True:
try:
data, address = s.recvfrom(BUFFER_SIZE)
except socket.timeout:
print("Didn't receive data! [Timeout 5s]")
continue
다음을 외칩니다: https://boltons.readthedocs.io/en/latest/socketutils.html
버퍼링된 소켓을 제공하며 다음과 같은 매우 유용한 기능을 제공합니다.
.recv_until() #recv until occurrence of bytes
.recv_closed() #recv until close
.peek() #peek at buffer but don't pop values
.settimeout() #configure timeout (including recv timeout)
언급URL : https://stackoverflow.com/questions/2719017/how-to-set-timeout-on-pythons-socket-recv-method
'programing' 카테고리의 다른 글
R 도움말 페이지에서 "실행되지 않음"은 무엇을 의미합니까? (0) | 2023.06.17 |
---|---|
단독 데이터 분석가를 위한 Rand 버전 제어 (0) | 2023.06.17 |
COUNTIF에서 비연속 범위를 정의하는 방법 (0) | 2023.06.17 |
VBA: 여러 작업을 포함하는 단일 행 if 문 (0) | 2023.06.17 |
Playstore에 게시한 후 Google 로그인이 작동하지 않음 (0) | 2023.06.17 |