[Tutor] Closing BaseHTTPServer...

lawrence wang levity at gmail.com
Sat Jul 16 16:41:00 CEST 2005


Here's some more detail about how I've got things set up. I left a
bunch of things out of my original email; sorry about that, I was
rushed for time. I don't have access to the verbatim code right now,
but here's the gist. I've subclassed threading.Thread like this:

class ServerThread(threading.Thread):
    def __init__(self):
        self.httpd = BaseHTTPServer(....)

    def run(self):
        self.httpd.serve_forever()

    def close(self):
        self.httpd.server_close()
        del self.httpd

I was expecting server_close() to stop serve_forever(), but this
doesn't seem to be the case, since the threads still stick around
after I run close() (that is, the extra python instances still show up
in the list of processes). When I try to use the port again after
closing, I get socket.error,'address already in use' or something like
that.

I'm running Python 2.4 on Debian Linux, btw.

On 7/15/05, Danny Yoo <dyoo at hkn.eecs.berkeley.edu> wrote:
> 
> 
> > I've been using BaseHTTPServer (and subclassing BaseHTTPRequestHandler,
> > of course) for a project at work. However, I can't seem to close my
> > connections completely once I'm done with the server. I've tried:
> >
> > server.server_close()
> > del server
> >
> > but when I try to use the same port again, it complains that it's
> > already bound; what's more, the interpreter hangs when I try to exit.
> > Thanks in advance for any help you can offer!
> 
> 
> Hi Lawrence,
> 
> I'm not exactly sure if this is the issue you're running into; if you can
> show us code, that'll help.  Are you sure nothing's running as a daemon
> afterwards?  You may want to try the unix utility 'telnet' and just make
> double-check that the server port is closed.
> 
> 
> If everything is truly closed, then it still usually takes a moment
> between restarts before the socket is available for use again. If we want
> to force the issue, we can use the socket.SO_REUSEADDR attribute.  For a
> general idea of what common problem is, see:
> 
>     http://www.unixguide.net/network/socketfaq/4.5.shtml
> 
> 
> Concretely, before binding the server's socket to a port, we may need to
> set a few socket parameters to reuse a port that's still in cooldown.  If
> we have a socket object that hasn't been bound yet, then we can do
> something like this:
> 
> ######
> socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
> socket.bind(server_address)
> ######
> 
> We shouldn't have to do this either if we're using BaseHTTPServer, since
> the mechanism for calling SO_REUSEADDR already exists in
> SocketServer.TCPServer.server_bind.
> 
> 
> The thing that bothers me is that this should already be happening for
> you, since by default, allow_reuse_address is set to true for subclasses
> of HTTPServer.  At least, this appears to be true in Python 2.3, according
> to this code snippet in the BaseHTTPServer code:
> 
> ### BaseHTTPServer.py ###
> class HTTPServer(SocketServer.TCPServer):
> 
>     allow_reuse_address = 1    # Seems to make sense in testing environment
> 
>     def server_bind(self):
>         """Override server_bind to store the server name."""
>         SocketServer.TCPServer.server_bind(self)
>         host, port = self.socket.getsockname()[:2]
>         self.server_name = socket.getfqdn(host)
>         self.server_port = port
> ######
> 
> 
> So I think we need some more information before we nail down what's really
> happening.  Show us some error messages, and some code, and we might be
> able to get a better idea of the situation.
> 
> 
> Good luck!
> 
>


More information about the Tutor mailing list