Changeset 391 for python/trunk/Doc/library/socketserver.rst
- Timestamp:
- Mar 19, 2014, 11:31:01 PM (11 years ago)
- Location:
- python/trunk
- Files:
-
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
python/trunk
-
Property svn:mergeinfo
set to
/python/vendor/Python-2.7.6 merged eligible /python/vendor/current merged eligible
-
Property svn:mergeinfo
set to
-
python/trunk/Doc/library/socketserver.rst
r2 r391 1 2 1 :mod:`SocketServer` --- A framework for network servers 3 2 ======================================================= … … 9 8 10 9 The :mod:`SocketServer` module has been renamed to :mod:`socketserver` in 11 Python 3.0. The :term:`2to3` tool will automatically adapt imports when 12 converting your sources to 3.0. 13 10 Python 3. The :term:`2to3` tool will automatically adapt imports when 11 converting your sources to Python 3. 12 13 **Source code:** :source:`Lib/SocketServer.py` 14 15 -------------- 14 16 15 17 The :mod:`SocketServer` module simplifies the task of writing network servers. … … 86 88 87 89 The mix-in class must come first, since it overrides a method defined in 88 :class:`UDPServer`. Setting the various member variables also changesthe90 :class:`UDPServer`. Setting the various attributes also change the 89 91 behavior of the underlying server mechanism. 90 92 … … 115 117 116 118 Another approach to handling multiple simultaneous requests in an environment 117 that supports neither threads nor :func:` fork` (or where these are too expensive118 or inappropriate for the service) is to maintain an explicit table of partially 119 finished requests and to use :func:`select` to decide which request to work on 120 next (or whether to handle a new incoming request). This is particularly 121 important for stream services where each client can potentially be connected for 122 a long time (if threads or subprocesses cannot be used). See :mod:`asyncore` for 123 another way to manage this.119 that supports neither threads nor :func:`~os.fork` (or where these are too 120 expensive or inappropriate for the service) is to maintain an explicit table of 121 partially finished requests and to use :func:`~select.select` to decide which 122 request to work on next (or whether to handle a new incoming request). This is 123 particularly important for stream services where each client can potentially be 124 connected for a long time (if threads or subprocesses cannot be used). See 125 :mod:`asyncore` for another way to manage this. 124 126 125 127 .. XXX should data and methods be intermingled, or separate? … … 157 159 .. method:: BaseServer.serve_forever(poll_interval=0.5) 158 160 159 Handle requests until an explicit :meth:`shutdown` request. Polls for 160 shutdown every *poll_interval* seconds. 161 Handle requests until an explicit :meth:`shutdown` request. 162 Poll for shutdown every *poll_interval* seconds. Ignores :attr:`self.timeout`. 163 If you need to do periodic tasks, do them in another thread. 161 164 162 165 163 166 .. method:: BaseServer.shutdown() 164 167 165 Tell s the :meth:`serve_forever` loop to stop and waitsuntil it does.168 Tell the :meth:`serve_forever` loop to stop and wait until it does. 166 169 167 170 .. versionadded:: 2.6 … … 304 307 305 308 Called after the :meth:`handle` method to perform any clean-up actions 306 required. The default implementation does nothing. If :meth:`setup` or307 :meth:`handle` raisean exception, this function will not be called.309 required. The default implementation does nothing. If :meth:`setup` 310 raises an exception, this function will not be called. 308 311 309 312 … … 355 358 # self.request is the TCP socket connected to the client 356 359 self.data = self.request.recv(1024).strip() 357 print " %s wrote:" % self.client_address[0]360 print "{} wrote:".format(self.client_address[0]) 358 361 print self.data 359 362 # just send back the same data, but upper-cased 360 self.request.send (self.data.upper())363 self.request.sendall(self.data.upper()) 361 364 362 365 if __name__ == "__main__": … … 379 382 # we can now use e.g. readline() instead of raw recv() calls 380 383 self.data = self.rfile.readline().strip() 381 print " %s wrote:" % self.client_address[0]384 print "{} wrote:".format(self.client_address[0]) 382 385 print self.data 383 386 # Likewise, self.wfile is a file-like object used to write back … … 388 391 ``recv()`` multiple times until it encounters a newline character, while the 389 392 single ``recv()`` call in the first handler will just return what has been sent 390 from the client in one ``send ()`` call.393 from the client in one ``sendall()`` call. 391 394 392 395 … … 402 405 sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 403 406 404 # Connect to server and send data 405 sock.connect((HOST, PORT)) 406 sock.send(data + "\n") 407 408 # Receive data from the server and shut down 409 received = sock.recv(1024) 410 sock.close() 411 412 print "Sent: %s" % data 413 print "Received: %s" % received 407 try: 408 # Connect to server and send data 409 sock.connect((HOST, PORT)) 410 sock.sendall(data + "\n") 411 412 # Receive data from the server and shut down 413 received = sock.recv(1024) 414 finally: 415 sock.close() 416 417 print "Sent: {}".format(data) 418 print "Received: {}".format(received) 414 419 415 420 … … 452 457 data = self.request[0].strip() 453 458 socket = self.request[1] 454 print " %s wrote:" % self.client_address[0]459 print "{} wrote:".format(self.client_address[0]) 455 460 print data 456 461 socket.sendto(data.upper(), self.client_address) 457 462 458 463 if __name__ == "__main__": 459 HOST, PORT = "localhost", 9999460 server = SocketServer.UDPServer((HOST, PORT), MyUDPHandler)461 server.serve_forever()464 HOST, PORT = "localhost", 9999 465 server = SocketServer.UDPServer((HOST, PORT), MyUDPHandler) 466 server.serve_forever() 462 467 463 468 This is the client side:: … … 477 482 received = sock.recv(1024) 478 483 479 print "Sent: %s" % data480 print "Received: %s" % received484 print "Sent: {}".format(data) 485 print "Received: {}".format(received) 481 486 482 487 The output of the example should look exactly like for the TCP server example. … … 499 504 def handle(self): 500 505 data = self.request.recv(1024) 501 cur_thread = threading.current Thread()502 response = " %s: %s" % (cur_thread.getName(), data)503 self.request.send (response)506 cur_thread = threading.current_thread() 507 response = "{}: {}".format(cur_thread.name, data) 508 self.request.sendall(response) 504 509 505 510 class ThreadedTCPServer(SocketServer.ThreadingMixIn, SocketServer.TCPServer): … … 509 514 sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 510 515 sock.connect((ip, port)) 511 sock.send(message) 512 response = sock.recv(1024) 513 print "Received: %s" % response 514 sock.close() 516 try: 517 sock.sendall(message) 518 response = sock.recv(1024) 519 print "Received: {}".format(response) 520 finally: 521 sock.close() 515 522 516 523 if __name__ == "__main__": … … 525 532 server_thread = threading.Thread(target=server.serve_forever) 526 533 # Exit the server thread when the main thread terminates 527 server_thread. setDaemon(True)534 server_thread.daemon = True 528 535 server_thread.start() 529 print "Server loop running in thread:", server_thread. getName()536 print "Server loop running in thread:", server_thread.name 530 537 531 538 client(ip, port, "Hello World 1") … … 534 541 535 542 server.shutdown() 543 536 544 537 545 The output of the example should look something like this::
Note:
See TracChangeset
for help on using the changeset viewer.