The Gevent loop engine (0.9.9-dev)
Gevent ( http://www.gevent.org) is an amazing non-blocking python network library built on top of libev (libevent on older release) and greenlet.
Even if uWSGI supports greenlet as suspend/resume|greenthread|coroutine library, it requires a lot of effort and code modifications to work with gevent.
So, starting from 0.9.9-dev a gevent LoopEngine has been added.
The gevent plugin requires gevent 1.0.0 (still not released as august 2011 but available on bitbucket) and async mode.
Bulding the plugin
It is now built by default.
You can obviously build the gevent plugin as an external plugin
python uwsgiconfig --plugin plugins/gevent
Running uWSGI in gevent mode
If you have embedded the gevent plugin simply do
uwsgi --socket :3031 --module myapp --gevent 100
or if it is an external plugin:
uwsgi --plugins gevent --socket :3031 --gevent 100 --module myapp
Set the --async value to the maximum number of concurrent connections you want to accept.
A crazy example
This example shows how to sleep in a request, how to make async-network requests and how to continue doing logic after a request has been closed.
import gevent import gevent.socket def bg_task(): for i in range(1,10): print "background task", i gevent.sleep(2) def long_task(): for i in range(1,10): print i gevent.sleep() def application(e, sr): sr('200 OK', [('Content-Type','text/html')]) t = gevent.spawn(long_task) t.join() yield "sleeping for 3 seconds...<br/>" gevent.sleep(3) yield "done<br>" yield "getting some ips...<br/>" urls = ['www.google.com', 'www.example.com', 'www.python.org', 'projects.unbit.it'] jobs = [gevent.spawn(gevent.socket.gethostbyname, url) for url in urls] gevent.joinall(jobs, timeout=2) for j in jobs: yield "ip = %s<br/>" % j.value # this task will goes on after request end gevent.spawn(bg_task)
The Signal Framework
The SignalFramework is fully working. Each handler will be executed in a dedicated greenlet. Look at the http://projects.unbit.it/uwsgi/browser/tests/ugevent.py example.
Testing with curl
If you're testing a wsgi application that generates a stream of data, you should know that curl by default buffers data until a newline. So make sure you either disable curl buffering with -N or have regular newlines in your output.
stream of data with nginx
If you are using nginx as a frontend to uwsgi and you have an app that generates a stream of data, you'll probably want to disable nginx buffering. In that can you need to set:
uWSGI multithread mode is not working (and probably will never work as it makes little sense in gevent) but running python threads in your apps is supported.
Mixing uWSGI async api with gevent one is EXPLICITLY FORBIDDEN
Currently you cannot run uWSGI+gevent on more than one socket. If you need multiple sockets simply spawn additional uWSGI instances.
Both Mongrel2 and its protocol handler are currently not supported