On Thu, Aug 2, 2012 at 8:04 AM, Matt Spitz <
matt...@gmail.com> wrote:
> # parallel requests to external services
> sub_requests = [ gevent.spawn(fetch_something_from_db),
> gevent.spawn(fetch_something_from_cache), gevent.spawn(fetch_external_url) ]
> gevent.joinall(sub_requests)
>
> db_result, cache_result, external_url_result = [ g.value for g in
> sub_requests ]
> ... continue processing
>
> It seems wasteful to me to spawn 3 new greenlets with each request. I don't
wasteful how? creating greenlets is cheap, switching is more
expensive. The gevent.pool.Pool class, for example, does not re-use
greenlets for this reason, it only maintains the limit on the total
number of working greenlets.
The thing you need to worry is too many connections to a single service.
> think it's wise to use the pool that we used to create the StreamServer, as
> that would limit the number of potential worker connections (and potentially
> create deadlock). The only other solution I'd think of is to have a
> separate pool of greenlets used for these sub-requests, but that could
> create a bottleneck, as well.
>
> What's the best practice here? Is it actually wasteful to spawn new
> greenlets?
The way you do it with spawn+joinall is fine, provided
fetch_something_from_db and fetch_something_from_cache ensure that
your webapp does not spam the db/cache with too many connections.
Here's how you can do it for database:
https://bitbucket.org/denis/gevent/src/tip/examples/psycopg2_pool.py