gevent.spawn()
プロセスではなくグリーンレットを作成します(さらに:すべてのグリーンレットは単一のOSスレッドで実行されます)。したがってmultiprocessing.JoinableQueue
、ここでは適切ではありません。
gevent
協調マルチタスクに基づいています。つまり、gevent
のイベントループに切り替わるブロッキング関数を呼び出すまで、他のグリーンレットは実行されません。たとえば、conn
以下では、他のグリーンレットがサイトからの応答を待っている間に実行できるようにするgeventソケットメソッドのパッチを使用しています。そしてそれがなけれpool.join()
ば、イベントループを実行するグリーンレットへの制御を放棄し、接続は確立されません。
複数のサイトにリクエストを送信する際の同時実行を制限するには、次を使用できますgevent.pool.Pool
。
#!/usr/bin/env python
from gevent.pool import Pool
from gevent import monkey; monkey.patch_socket()
import httplib # now it can be used from multiple greenlets
import logging
info = logging.getLogger().info
def process(site):
"""Make HEAD request to the `site`."""
conn = httplib.HTTPConnection(site)
try:
conn.request("HEAD", "/")
res = conn.getresponse()
except IOError, e:
info("error %s reason: %s" % (site, e))
else:
info("%s %s %s" % (site, res.status, res.reason))
finally:
conn.close()
def main():
logging.basicConfig(level=logging.INFO, format="%(asctime)s %(msg)s")
num_worker_threads = 2
pool = Pool(num_worker_threads)
sites = ["google.com", "bing.com", "duckduckgo.com", "stackoverflow.com"]*3
for site in sites:
pool.apply_async(process, args=(site,))
pool.join()
if __name__=="__main__":
main()