Reputation: 2079
I have the following code, which is self explanatory:
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect(host, port)
s.send("some data")
# don't close socket just yet...
# do some other stuff with the data (normal string operations)
if s.stillconnected() is true:
s.send("some more data")
if s.stillconnected() is false:
# recreate the socket and reconnect
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect(host, port)
s.send("some more data")
s.close()
How do I implement s.stillconnected()
I do not wish to recreate the socket blindly.
Upvotes: 19
Views: 114726
Reputation: 2317
I've had good results with this variant to check if a socket is closed (negate the result if you want to check if it's still connected):
import logging
import socket
logger = logging.getLogger(__name__)
def is_socket_closed(sock: socket.socket) -> bool:
try:
# this will try to read bytes without blocking and also without removing them from buffer (peek only)
data = sock.recv(16, socket.MSG_DONTWAIT | socket.MSG_PEEK)
if len(data) == 0:
return True
except BlockingIOError:
return False # socket is open and reading from it would block
except ConnectionResetError:
return True # socket was closed for some other reason
except Exception as e:
logger.exception("unexpected exception when checking if a socket is closed")
return False
return False
Upvotes: 28
Reputation: 1752
If the server connection is no longer alive, calling the send method will throw an exception, so you can use a try-exception block to attempt to send data, catch the exception if it's thrown, and reestablish the connection:
try:
s.send("some more data")
except:
# recreate the socket and reconnect
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect(host, port)
s.send("some more data")
EDIT: As per @Jean-Paul Calderone's comments, please consider using the sendall
method, which is a higher level method that sends all the data or throws an error, instead of send
, which is a lower level method that does not guarantee the transmission of all the data, OR use higher level modules like an HTTP library that can handle socket lifecycles.
Upvotes: 18