【问题标题】:cherrypy not closing the sockets樱桃不关闭套接字
【发布时间】:2010-09-18 08:59:21
【问题描述】:

我使用cherrypy 作为网络服务器。它为我的应用程序提供了良好的性能,但它存在一个非常大的问题。几个小时后,cherrypy 崩溃,说明由于打开的文件太多,它无法创建套接字:

[21/Oct/2008:12:44:25] ENGINE HTTP Server 
cherrypy._cpwsgi_server.CPWSGIServer(('0.0.0.0', 8080)) shut down    
[21/Oct/2008:12:44:25] ENGINE Stopped thread '_TimeoutMonitor'.    
[21/Oct/2008:12:44:25] ENGINE Stopped thread 'Autoreloader'.    
[21/Oct/2008:12:44:25] ENGINE Bus STOPPED    
[21/Oct/2008:12:44:25] ENGINE Bus EXITING    
[21/Oct/2008:12:44:25] ENGINE Bus EXITED    
Exception in thread HTTPServer Thread-3:    
Traceback (most recent call last):    
  File "/usr/lib/python2.3/threading.py", line 436, in __bootstrap    
    self.run()    
  File "/usr/lib/python2.3/threading.py", line 416, in run   
    self.__target(*self.__args, **self.__kwargs)    
  File "/usr/lib/python2.3/site-packages/cherrypy/process/servers.py", line 73, in 
_start_http_thread    
    self.httpserver.start()    
  File "/usr/lib/python2.3/site-packages/cherrypy/wsgiserver/__init__.py", line 1388, in start
    self.tick()    
  File "/usr/lib/python2.3/site-packages/cherrypy/wsgiserver/__init__.py", line 1417, in tick    
    s, addr = self.socket.accept()    
  File "/usr/lib/python2.3/socket.py", line 167, in accept    
    sock, addr = self._sock.accept()    
error: (24, 'Too many open files')    
[21/Oct/2008:12:44:25] ENGINE Waiting for child threads to terminate..

我试图弄清楚发生了什么。我的应用程序没有打开任何文件或任何套接字等。我的文件只打开了几个 berkeley dbs。我进一步调查了这个问题。我在 /proc/4536/fd/ 中看到了 id 为 4536 的cherrypy 进程使用的文件描述符 最初创建并正确清理了新的套接字,但一个小时后我发现它有大约 509 个未清理的套接字。所有套接字都处于 CLOSE_WAIT 状态。我使用以下命令获得了这些信息:

netstat -ap | grep "4536" | grep CLOSE_WAIT | wc -l

CLOSE_WAIT 状态意味着远程客户端已经关闭了连接。为什么cherrypy然后不关闭套接字并释放文件描述符?我能做些什么来解决这个问题?

我尝试玩以下游戏:

cherrypy.config.update({'server.socketQueueSize': '10'})

我认为这会将任何时候打开的套接字数量限制为 10,但它根本没有效果。这是我设置的唯一配置,因此,其余配置保持其默认值。

有人能解释一下吗?你认为它是cherrypy中的一个错误吗?我该如何解决?有什么方法可以让我自己关闭这些套接字?

以下是我的系统信息:

CherryPy-3.1.0

python 2.3.4

红帽企业 Linux ES 第 4 版(Nahant 更新 7)

提前致谢!

【问题讨论】:

  • 如果您可以构建并发布一个最小的复制器,那将很有用;除非我们可以在自己的环境中重现,否则任何建议都是猜测。

标签: python sockets cherrypy


【解决方案1】:

我想您正在(内存中)存储一些引用套接字的数据;例如,如果您将请求对象存储在任何地方,则可能会这样做。

套接字关闭的最后机会是当它们被垃圾收集时;如果您正在做任何会阻止垃圾收集到达它们的事情,那就是您的问题。我建议你尝试用 CherryPy 编写的 Hello World 程序来重现;如果你不能在那里重现,你知道它在你的代码中——寻找你保存可以(直接或以其他方式)引用套接字的信息的地方。

【讨论】:

  • 不,我没有保留任何信息。事实上,我的服务器是只读服务器。除了套接字之外,没有发生任何写操作。插座最初收集得很好。这个问题随着时间的推移而出现。
  • 再次——你能用 Hello World 重现它吗?
  • 顺便说一句,当我说“保留任何信息”时,我的意思是在内存中,而不是在磁盘或数据库存储中。
  • 再次——你能用 Hello World 重现它吗? (有一个网站是我在几年前使用 CherryPy 建立的一家初创公司;它仅从脚本进程中就获得了 lot 的点击量,而 AFAIK 他们从未遇到过这个问题) .
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2011-01-02
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-12-07
  • 2012-07-06
  • 2011-12-06
相关资源
最近更新 更多