I have a small rest api built in python using Falcon Framework and it runs in a virtual environment with gunicorn + gevent and pypy 2.3 (I successfully installed the pip packages from gevent@pypy-hacks and gevent-on-pypy/pypycore). I wanted to add a "supervisor" for my application so I first installed supervisord and followed the steps to get it up and running.
The first thing I did in the server was to test the command to start the api; it ran successfully and I could use the api without any issues. The command is:
/bin/bash -c 'cd /path/to/project/api && /path/to/project/env/bin/gunicorn -c settings.py my-api:my_api'
Note: in settings.py I set the parameter daemon=False
since I saw that supervisors require that the commands are run in the "foreground" and not daemonized.
Once that was working, I went ahead and created the app's /etc/supervisor/conf.d/my_api.conf
conf file with the "command" parameter set as the command above I ran successfully. When I tried to start the api through supervisord, it failed, and in the log of the api, the error was:
Traceback (most recent call last):
File "/path/to/project/env/site-packages/gunicorn/arbiter.py", line 507, in spawn_worker
worker.init_process()
File "/path/to/project/env/site-packages/gunicorn/workers/ggevent.py", line 185, in init_process
self.patch()
File "/path/to/project/env/site-packages/gunicorn/workers/ggevent.py", line 74, in patch
_sock=s))
File "/path/to/project/env/site-packages/gevent/socket.py", line 240, in __init__
self.hub = get_hub()
File "/path/to/project/env/site-packages/gevent/hub.py", line 169, in get_hub
hub = _threadlocal.hub = hubtype(*args, **kwargs)
File "/path/to/project/env/site-packages/gevent/hub.py", line 268, in __init__
loop_class = _import(self.loop_class)
File "/path/to/project/env/site-packages/gevent/hub.py", line 198, in _import
return _import(path[-1])
File "/path/to/project/env/site-packages/gevent/hub.py", line 210, in _import
x = __import__(module)
ImportError: No module named gevent.core
So, I was surprised that running the command manually did work, but when supervisor tried to run it, the above error was thrown.
After lots of trial and errors, I decided to install monit to see if it could monitor my api, and I did set it up successfully specifying the "start program" parameter as the aforementioned command.
I was surprised that monit throwed the exact same error. So, does this mean that the nature of my api (pypy + gunicorn + gevent) prevents itself from being monitored by any monitor software around there?
Is there something I'm doing wrong when configuring supervisord/monit?
Any help is greatly appreciated.
Turns out that I have the environment var GEVENT_LOOP already exported in my
/etc/environment
as follows:Since for running gevent on pypy some hacks are needed including the above export.
But I needed to export it manually in the 'start_program' command entry of Monit (at the end I sticked with Monit), so the resulting command is: