tornadoweb / tornado

Tornado is a Python web framework and asynchronous networking library, originally developed at FriendFeed.
http://www.tornadoweb.org/
Apache License 2.0
21.72k stars 5.5k forks source link

tornado server close connection actively #2657

Closed lxgithub24 closed 4 years ago

lxgithub24 commented 5 years ago

i have a question here. could u please help me?@bdarnell https://github.com/tornadoweb/tornado/issues/1200 below is detail of this question:

It was a fairly arbitrary choice; I don't know how long browsers keep connections open. If the client closes its connection then Tornado should notice immediately; the hour timeout is the longest Tornado will wait for any client who doesn't close its connection. It's conservative because there was no limit before and so we didn't want to cut off connections prematurely for anyone who may be relying on this.

Also note that the default limits for file descriptors are quite low and there's no harm in increasing them significantly for Tornado servers - I generally set the limit to 50K on the servers I'm responsible for.

I have two question: 1.how to set the fd(file descriptors) count? is it a parameter tornado? 2.the idle_connection_timeout default is 3600 second. In my tornado server, i set it to 31536000000(1000 years).

considering the second one, it seems that i don't understand this parameter. i understand it a parameter that if the client don't request for anything after 'idle_connection_timeout' seconds, the server will close the connection directly. in that way, whether the client know that the server has already close the connection if the connection itself is a long connection. i asked for this because my company runs application online, but something beyond my expectation happens. my application runs behind a gateway service(zuul: a springcloud Dalston.SR2 service), and zuul send request to me with a keep alive connection. But sometimes the tornado server can't get the zuul request, when i read the tcp message (use tools: tcpdump and wireshark), i found that the client send request with an old connection that server almost close, so tornado server response the client with tcp.flags.reset==1, and zuul regard this as tornado server timeout. I was confused by this question for as long as a month. if there is something wrong i was doing, tell me. below is some code of my application:

async def main():
    await eureka.register()
    app = tornado.web.Application(handlers=rest_apis_handler, template_path=os.path.join(os.path.dirname(__file__),"cangjie_gateway/utils/templates"))
    server = tornado.httpserver.HTTPServer(app, idle_connection_timeout=31536000000)
    server.listen(port)
    prerequest.smooth_reload(server)
    while True:
        await asyncio.sleep(60)
        await eureka.renew()

it confused me. hope for your reply!! @bdarnell

ploxiln commented 5 years ago

The typical way to set the file descriptor limit is for the shell that starts the tornado process to first run ulimit -n 50000. For example:

#!/bin/sh
ulimit -n 50000
exec python mytornadoapp.py

If you happen to use a "systemd unit file" to start your service, it also has an option LimitNOFILE=50000

Finally, it is possible to set this limit from the python application itself (e.g. first thing in main()): resource.setrlimit(resource.RLIMIT_NOFILE, (50000, 50000)) https://docs.python.org/3.5/library/resource.html#resource.setrlimit

ploxiln commented 5 years ago

It sounds like, these connections are not ones that the tornado server almost closed, but rather connections that were already closed, for some other reason.

1000 years is a somewhat unreasonably long time, maybe things break down at a conversion somewhere - I suggest 30 days. But also, I've seen cases in some networks, for example in amazon EC2 "security groups", where some firewall needs to do connection tracking, and it loses track of connections after a few days. In this case, you actually want shorter timeouts, not longer - so that both sides of the connection know when the connection will no longer work.

lxgithub24 commented 4 years ago

It sounds like, these connections are not ones that the tornado server almost closed, but rather connections that were already closed, for some other reason.

1000 years is a somewhat unreasonably long time, maybe things break down at a conversion somewhere - I suggest 30 days. But also, I've seen cases in some networks, for example in amazon EC2 "security groups", where some firewall needs to do connection tracking, and it loses track of connections after a few days. In this case, you actually want shorter timeouts, not longer - so that both sides of the connection know when the connection will no longer work.

Thanks! Though I don't solve the problem at last, I hide my service under a Spring service and everything go right. THAT'S MY SOLUTION. (PERBABLY I HAVE NO CHANCE TO TRY WHAT YOU SAY ABOVE)