I’m using Python Flask to run Python for web through FCGI with nginx. My fcgi backend is set up like this:
#!/usr/bin/env python
import argparse, daemon, os
from flup.server.fcgi import WSGIServer
from fwd_msg import app
SOCKET_LOCATION = '/tmp/fingerprinter-fcgi.sock'
if __name__ == '__main__':
# arg parse (and daemonize)
arg_parser = argparse.ArgumentParser()
arg_parser.add_argument('--daemon', action='store_true', default=False, help='Run as daemon')
arg_parser.add_argument('--cwd', action='store', default='/',
help='Full path of the working directory to which the process should change on daemon start.')
arg_parser.add_argument('--uid', action='store', type=int, default=os.getuid(),
help='The user ID ("UID") value and group ID ("GID") value to switch the process to on daemon start.')
args = vars(arg_parser.parse_args())
if args['daemon']:
context = daemon.DaemonContext(working_directory=args['cwd'], uid=args['uid'])
with context:
WSGIServer(app, bindAddress=SOCKET_LOCATION).run()
else:
WSGIServer(app, bindAddress=SOCKET_LOCATION).run()
If I run the WSGIServer without daemon argument, it works fine.
But if I run it with the daemon argument I get this error in the nginx log, while any requests to the server end with “502 BAD GATEWAY”:
2012/05/09 12:16:00 [error] 30895#0: *30 upstream sent unsupported FastCGI protocol version: 91 while reading response header from upstream, client: XXX.XXX.XXX.XXX, server: localhost, request: "POST / HTTP/1.1", upstream: "fastcgi://unix:/tmp/fingerprinter-fcgi.sock:", host: "XXX.XXX.XXX.XXX"
Any ideas why is this happening and how to prevent it?
It turns out that DaemonContext closes any opened file descriptors, so basically there should be a function, that instantiates WSGIServer, together with app аnd everything that could open a file descriptor INSIDE the DaemonContext.
Also make sure the working directory is such that is owned by the user or at least has permissions allowing the user with given UID to write there (not recommended).
Example: