frx*_*frx 4 python xmlrpclib gevent
是否有可能使用python的标准库xmlrpclib与gevent?目前我尝试使用monkey.patch_all(),但没有成功.
from gevent import monkey
monkey.patch_all()
import gevent
import time
import xmlrpclib
from SimpleXMLRPCServer import SimpleXMLRPCServer
import urllib2
def fetch(url):
g = gevent.spawn(urllib2.urlopen, url)
return g.get().read()
def is_even(n):
return n%2 == 0
def req(url):
return fetch(url)
server = SimpleXMLRPCServer(("localhost", 8000))
print "Listening on port 8000..."
server.register_function(is_even, "is_even")
server.register_function(req, "req")
server.serve_forever()
Run Code Online (Sandbox Code Playgroud)
urllib2.urlopen阻止服务器.在我看来,monkey.patch_all没有修补socket,这就是它阻塞的原因.
套接字修补得很好,但代码还有其他问题.
首先,这个
def fetch(url):
g = gevent.spawn(urllib2.urlopen, url)
return g.get().read()
Run Code Online (Sandbox Code Playgroud)
是相同的
def fetch(url):
return urllib2.urlopen(url).read()
Run Code Online (Sandbox Code Playgroud)
你在这里产生一个新的greenlet,然后阻止当前的greenlet,直到新的greenlet完成.它不会使事情并发.它与刚刚运行urlopen并等待它完成相同.
其次,为了利用gevent,必须同时运行多个轻量级线程(greenlet).
但是,SimpleXMLRPCServer定义为
class SimpleXMLRPCServer(SocketServer.TCPServer,
SimpleXMLRPCDispatcher):
Run Code Online (Sandbox Code Playgroud)
这意味着它一次提供一个连接.
如果您创建自己的SimpleXMLRPCServer类,但使用ThreadingTCPServer而不是TCPServer,您应该能够在此处使用gevent.
monkey.patch_all()修补程序threading将成为基于greenlet的,因此这样的服务器将为每个新连接生成一个新的greenlet.