]> granicus.if.org Git - python/commitdiff
Added timout parameter to telnetlib.Telnet. Also created
authorFacundo Batista <facundobatista@gmail.com>
Thu, 29 Mar 2007 18:22:35 +0000 (18:22 +0000)
committerFacundo Batista <facundobatista@gmail.com>
Thu, 29 Mar 2007 18:22:35 +0000 (18:22 +0000)
test_telnetlib.py with a basic test and timeout ones.
Docs are also updated.

Doc/lib/libtelnetlib.tex
Lib/telnetlib.py
Lib/test/test_telnetlib.py [new file with mode: 0644]
Misc/NEWS

index c7a4226dccdc018a1c7b4b9272d285a1878c1cb5..d2364984b1b16c3c5c46f06b3c4c868dd29d49b6 100644 (file)
@@ -23,13 +23,16 @@ Mark), BRK (Break), IP (Interrupt process), AO (Abort output), AYT
 SB (Subnegotiation Begin).
 
 
-\begin{classdesc}{Telnet}{\optional{host\optional{, port}}}
+\begin{classdesc}{Telnet}{\optional{host\optional{, port\optional{, timeout}}}}
 \class{Telnet} represents a connection to a Telnet server. The
 instance is initially not connected by default; the \method{open()}
 method must be used to establish a connection.  Alternatively, the
 host name and optional port number can be passed to the constructor,
 to, in which case the connection to the server will be established
 before the constructor returns.
+The optional \var{timeout} parameter specifies a timeout in seconds for the
+connection attempt (if not specified, or passed as None, the global default
+timeout setting will be used).
 
 Do not reopen an already connected instance.
 
@@ -111,10 +114,13 @@ The callback should access these data when it was invoked with a
 \versionadded{2.3}
 \end{methoddesc}
 
-\begin{methoddesc}{open}{host\optional{, port}}
+\begin{methoddesc}{open}{host\optional{, port\optional{, timeout}}}
 Connect to a host.
 The optional second argument is the port number, which
 defaults to the standard Telnet port (23).
+The optional \var{timeout} parameter specifies a timeout in seconds for the
+connection attempt (if not specified, or passed as None, the global default
+timeout setting will be used).
 
 Do not try to reopen an already connected instance.
 \end{methoddesc}
index a13e85cc9863542fd520e12a9131c3157375a703..f4c01e428cbabe6413b68d462666f825307d9aed 100644 (file)
@@ -184,7 +184,7 @@ class Telnet:
 
     """
 
-    def __init__(self, host=None, port=0):
+    def __init__(self, host=None, port=0, timeout=None):
         """Constructor.
 
         When called without arguments, create an unconnected instance.
@@ -195,6 +195,7 @@ class Telnet:
         self.debuglevel = DEBUGLEVEL
         self.host = host
         self.port = port
+        self.timeout = timeout
         self.sock = None
         self.rawq = ''
         self.irawq = 0
@@ -205,9 +206,9 @@ class Telnet:
         self.sbdataq = ''
         self.option_callback = None
         if host is not None:
-            self.open(host, port)
+            self.open(host, port, timeout)
 
-    def open(self, host, port=0):
+    def open(self, host, port=0, timeout=None):
         """Connect to a host.
 
         The optional second argument is the port number, which
@@ -221,20 +222,9 @@ class Telnet:
             port = TELNET_PORT
         self.host = host
         self.port = port
-        msg = "getaddrinfo returns an empty list"
-        for res in socket.getaddrinfo(host, port, 0, socket.SOCK_STREAM):
-            af, socktype, proto, canonname, sa = res
-            try:
-                self.sock = socket.socket(af, socktype, proto)
-                self.sock.connect(sa)
-            except socket.error, msg:
-                if self.sock:
-                    self.sock.close()
-                self.sock = None
-                continue
-            break
-        if not self.sock:
-            raise socket.error, msg
+        if timeout is not None:
+            self.timeout = timeout
+        self.sock = socket.create_connection((host, port), self.timeout)
 
     def __del__(self):
         """Destructor -- close the connection."""
@@ -661,7 +651,7 @@ def test():
             port = socket.getservbyname(portstr, 'tcp')
     tn = Telnet()
     tn.set_debuglevel(debuglevel)
-    tn.open(host, port)
+    tn.open(host, port, timeout=0.5)
     tn.interact()
     tn.close()
 
diff --git a/Lib/test/test_telnetlib.py b/Lib/test/test_telnetlib.py
new file mode 100644 (file)
index 0000000..42ad20c
--- /dev/null
@@ -0,0 +1,74 @@
+import socket
+import threading
+import telnetlib
+import time
+
+from unittest import TestCase
+from test import test_support
+
+
+def server(evt):
+    serv = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
+    serv.settimeout(3)
+    serv.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
+    serv.bind(("", 9091))
+    serv.listen(5)
+    try:
+        conn, addr = serv.accept()
+    except socket.timeout:
+        pass
+    finally:
+        serv.close()
+        evt.set()
+
+class GeneralTests(TestCase):
+    
+    def setUp(self):
+        self.evt = threading.Event()
+        threading.Thread(target=server, args=(self.evt,)).start()
+        time.sleep(.1)
+
+    def tearDown(self):
+        self.evt.wait()
+
+    def testBasic(self):
+        # connects
+        telnet = telnetlib.Telnet("localhost", 9091)
+        telnet.sock.close()
+        
+    def testTimeoutDefault(self):
+        # default
+        telnet = telnetlib.Telnet("localhost", 9091)
+        self.assertTrue(telnet.sock.gettimeout() is None)
+        telnet.sock.close()
+    
+    def testTimeoutValue(self):
+        # a value
+        telnet = telnetlib.Telnet("localhost", 9091, timeout=30)
+        self.assertEqual(telnet.sock.gettimeout(), 30)
+        telnet.sock.close()
+
+    def testTimeoutDifferentOrder(self):
+        telnet = telnetlib.Telnet(timeout=30)
+        telnet.open("localhost", 9091)
+        self.assertEqual(telnet.sock.gettimeout(), 30)
+        telnet.sock.close()
+
+    def testTimeoutNone(self):
+        # None, having other default
+        previous = socket.getdefaulttimeout()
+        socket.setdefaulttimeout(30)
+        try:
+            telnet = telnetlib.Telnet("localhost", 9091, timeout=None)
+        finally:
+            socket.setdefaulttimeout(previous)
+        self.assertEqual(telnet.sock.gettimeout(), 30)
+        telnet.sock.close()
+
+
+
+def test_main(verbose=None):
+    test_support.run_unittest(GeneralTests)
+
+if __name__ == '__main__':
+    test_main()
index 3ebf16e8b30b15d5a7202dc41946d428e80aad5d..e3dd20d01fdc9d7b2054b2c5bf37b3d9a2eb74e9 100644 (file)
--- a/Misc/NEWS
+++ b/Misc/NEWS
@@ -200,6 +200,11 @@ Core and builtins
 Library
 -------
 
+- Added a timeout parameter to the constructor of other protocols
+  (telnetlib, ftplib, smtplib and poplib). This is second part of the
+  work started with create_connection() and timeout in httplib, and
+  closes patch #723312.
+
 - Patch #1676823: Added create_connection() to socket.py, which may be 
   called with a timeout, and use it from httplib (whose HTTPConnection 
   now accepts an optional timeout).