fix whitespaces

This commit is contained in:
benoitc 2012-02-19 11:27:46 +01:00
parent 8bf793d2e5
commit f168a21dae
28 changed files with 319 additions and 319 deletions

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
import errno
@ -20,7 +20,7 @@ class Application(object):
An application interface for configuring and loading
the various necessities for any given web framework.
"""
def __init__(self, usage=None):
self.usage = usage
self.cfg = None
@ -35,23 +35,23 @@ class Application(object):
sys.stderr.write("\nError: %s\n" % str(e))
sys.stderr.flush()
sys.exit(1)
def load_config(self):
# init configuration
self.cfg = Config(self.usage)
# parse console args
parser = self.cfg.parser()
opts, args = parser.parse_args()
# optional settings from apps
cfg = self.init(parser, opts, args)
# Load up the any app specific configuration
if cfg and cfg is not None:
for k, v in cfg.items():
self.cfg.set(k.lower(), v)
# Load up the config file if its found.
if opts.config and os.path.exists(opts.config):
cfg = {
@ -67,7 +67,7 @@ class Application(object):
print "Failed to read config file: %s" % opts.config
traceback.print_exc()
sys.exit(1)
for k, v in cfg.items():
# Ignore unknown names
if k not in self.cfg.settings:
@ -77,17 +77,17 @@ class Application(object):
except:
sys.stderr.write("Invalid value for %s: %s\n\n" % (k, v))
raise
# Lastly, update the configuration with any command line
# settings.
for k, v in opts.__dict__.items():
if v is None:
continue
self.cfg.set(k.lower(), v)
def init(self, parser, opts, args):
raise NotImplementedError
def load(self):
raise NotImplementedError
@ -95,12 +95,12 @@ class Application(object):
self.do_load_config()
if self.cfg.spew:
debug.spew()
def wsgi(self):
if self.callable is None:
self.callable = self.load()
return self.callable
def run(self):
if self.cfg.spew:
debug.spew()
@ -111,11 +111,11 @@ class Application(object):
os.setpgrp()
except OSError, e:
if e[0] != errno.EPERM:
raise
raise
try:
Arbiter(self).run()
except RuntimeError, e:
sys.stderr.write("\nError: %s\n\n" % e)
sys.stderr.flush()
sys.exit(1)

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
import imp
@ -17,7 +17,7 @@ from gunicorn.app.base import Application
ENVIRONMENT_VARIABLE = 'DJANGO_SETTINGS_MODULE'
class DjangoApplication(Application):
def init(self, parser, opts, args):
self.global_settings_path = None
self.project_path = None
@ -25,7 +25,7 @@ class DjangoApplication(Application):
self.global_settings_path = args[0]
if not os.path.exists(os.path.abspath(args[0])):
self.no_settings(args[0])
def get_settings_modname(self):
from django.conf import ENVIRONMENT_VARIABLE
@ -69,7 +69,7 @@ class DjangoApplication(Application):
os.pardir)))
return settings_modname
def setup_environ(self, settings_modname):
from django.core.management import setup_environ
@ -82,7 +82,7 @@ class DjangoApplication(Application):
path = os.path.dirname(os.path.abspath(
os.path.normpath(settings_mod.__file__)))
sys.path.append(path)
for part in parts[1:]:
for part in parts[1:]:
settings_mod = getattr(settings_mod, part)
setup_environ(settings_mod)
except ImportError:
@ -101,9 +101,9 @@ class DjangoApplication(Application):
from django.conf import settings
from django.utils import translation
translation.activate(settings.LANGUAGE_CODE)
def validate(self):
""" Validate models. This also ensures that all models are
""" Validate models. This also ensures that all models are
imported in case of import-time side effects."""
from django.core.management.base import CommandError
from django.core.management.validation import get_validation_errors
@ -123,14 +123,14 @@ class DjangoApplication(Application):
def load(self):
from django.core.handlers.wsgi import WSGIHandler
self.setup_environ(self.get_settings_modname())
self.validate()
self.activate_translation()
return WSGIHandler()
class DjangoApplicationCommand(DjangoApplication):
def __init__(self, options, admin_media_path):
self.usage = None
self.cfg = None
@ -139,16 +139,16 @@ class DjangoApplicationCommand(DjangoApplication):
self.admin_media_path = admin_media_path
self.callable = None
self.project_path = None
self.do_load_config()
for k, v in self.options.items():
if k.lower() in self.cfg.settings and v is not None:
self.cfg.set(k.lower(), v)
def load_config(self):
self.cfg = Config()
if self.config_file and os.path.exists(self.config_file):
cfg = {
"__builtins__": __builtins__,
@ -164,7 +164,7 @@ class DjangoApplicationCommand(DjangoApplication):
print "Failed to read config file: %s" % self.config_file
traceback.print_exc()
sys.exit(1)
for k, v in cfg.items():
# Ignore unknown names
if k not in self.cfg.settings:
@ -174,7 +174,7 @@ class DjangoApplicationCommand(DjangoApplication):
except:
sys.stderr.write("Invalid value for %s: %s\n\n" % (k, v))
raise
for k, v in self.options.items():
if k.lower() in self.cfg.settings and v is not None:
self.cfg.set(k.lower(), v)
@ -191,7 +191,7 @@ class DjangoApplicationCommand(DjangoApplication):
settings_path = os.path.join(project_path, "settings.py")
if not os.path.exists(settings_path):
return self.no_settings(settings_path)
if not settings_modname:
project_name = os.path.split(project_path)[-1]
settings_name, ext = os.path.splitext(
@ -220,7 +220,7 @@ class DjangoApplicationCommand(DjangoApplication):
def reload_django_settings(self, settings_modname):
from django.conf import settings
from django.utils import importlib
mod = importlib.import_module(settings_modname)
# reload module
@ -283,14 +283,14 @@ class DjangoApplicationCommand(DjangoApplication):
def load(self):
from django.core.handlers.wsgi import WSGIHandler
# reload django settings and setup environ
self.setup_environ(self.get_settings_modname())
# validate models and activate translation
self.validate()
self.validate()
self.activate_translation()
from django.core.servers.basehttp import AdminMediaHandler, WSGIServerException
try:
@ -308,7 +308,7 @@ class DjangoApplicationCommand(DjangoApplication):
error_text = str(e)
sys.stderr.write(self.style.ERROR("Error: %s" % error_text) + '\n')
sys.exit(1)
def run():
"""\
The ``gunicorn_django`` command line runner for launching Django

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
import os
@ -20,7 +20,7 @@ class PasterBaseApplication(Application):
cx = loadwsgi.loadcontext(SERVER, self.cfgurl, relative_to=self.relpath)
gc, lc = cx.global_conf.copy(), cx.local_conf.copy()
cfg = {}
host, port = lc.pop('host', ''), lc.pop('port', '')
if host and port:
cfg['bind'] = '%s:%s' % (host, port)
@ -61,11 +61,11 @@ class PasterBaseApplication(Application):
config_file = os.path.abspath(self.cfgfname)
fileConfig(config_file, dict(__file__=config_file,
here=os.path.dirname(config_file)))
class PasterApplication(PasterBaseApplication):
def init(self, parser, opts, args):
if len(args) != 1:
parser.error("No application name specified.")
@ -81,14 +81,14 @@ class PasterApplication(PasterBaseApplication):
sys.path.insert(0, self.relpath)
pkg_resources.working_set.add_entry(self.relpath)
return self.app_config()
def load(self):
return loadapp(self.cfgurl, relative_to=self.relpath)
class PasterServerApplication(PasterBaseApplication):
def __init__(self, app, gcfg=None, host="127.0.0.1", port=None, *args, **kwargs):
self.cfg = Config()
self.app = app
@ -127,7 +127,7 @@ class PasterServerApplication(PasterBaseApplication):
def load_config(self):
if not hasattr(self, "cfgfname"):
return
cfg = self.app_config()
for k,v in cfg.items():
try:
@ -153,14 +153,14 @@ def run():
def paste_server(app, gcfg=None, host="127.0.0.1", port=None, *args, **kwargs):
"""\
A paster server.
Then entry point in your paster ini file should looks like this:
[server:main]
use = egg:gunicorn#main
host = 127.0.0.1
port = 5000
"""
from gunicorn.app.pasterapp import PasterServerApplication
PasterServerApplication(app, gcfg=gcfg, host=host, port=port, *args, **kwargs).run()

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
import os
@ -10,7 +10,7 @@ from gunicorn import util
from gunicorn.app.base import Application
class WSGIApplication(Application):
def init(self, parser, opts, args):
if len(args) != 1:
parser.error("No application module specified.")
@ -29,4 +29,4 @@ def run():
generic WSGI applications.
"""
from gunicorn.app.wsgiapp import WSGIApplication
WSGIApplication("%prog [OPTIONS] APP_MODULE").run()
WSGIApplication("%prog [OPTIONS] APP_MODULE").run()

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
from __future__ import with_statement
@ -34,9 +34,9 @@ class Arbiter(object):
WORKER_BOOT_ERROR = 3
START_CTX = {}
LISTENER = None
WORKERS = {}
WORKERS = {}
PIPE = []
# I love dynamic languages
@ -49,17 +49,17 @@ class Arbiter(object):
(getattr(signal, name), name[3:].lower()) for name in dir(signal)
if name[:3] == "SIG" and name[3] != "_"
)
def __init__(self, app):
os.environ["SERVER_SOFTWARE"] = SERVER_SOFTWARE
self.setup(app)
self.pidfile = None
self.worker_age = 0
self.reexec_pid = 0
self.master_name = "Master"
# get current path, try to use PWD env first
try:
a = os.stat(os.environ['PWD'])
@ -70,7 +70,7 @@ class Arbiter(object):
cwd = os.getcwd()
except:
cwd = os.getcwd()
args = sys.argv[:]
args.insert(0, sys.executable)
@ -80,27 +80,27 @@ class Arbiter(object):
"cwd": cwd,
0: sys.executable
}
def setup(self, app):
self.app = app
self.cfg = app.cfg
self.log = self.cfg.logger_class(app.cfg)
if 'GUNICORN_FD' in os.environ:
self.log.reopen_files()
self.address = self.cfg.address
self.num_workers = self.cfg.workers
self.debug = self.cfg.debug
self.timeout = self.cfg.timeout
self.proc_name = self.cfg.proc_name
self.worker_class = self.cfg.worker_class
if self.cfg.debug:
self.log.debug("Current configuration:")
for config, value in sorted(self.cfg.settings.iteritems()):
self.log.debug(" %s: %s", config, value.value)
if self.cfg.preload_app:
if not self.cfg.debug:
self.app.wsgi()
@ -117,7 +117,7 @@ class Arbiter(object):
self.init_signals()
if not self.LISTENER:
self.LISTENER = create_socket(self.cfg, self.log)
if self.cfg.pidfile is not None:
self.pidfile = Pidfile(self.cfg.pidfile)
self.pidfile.create(self.pid)
@ -128,7 +128,7 @@ class Arbiter(object):
self.cfg.settings['worker_class'].get())
self.cfg.when_ready(self)
def init_signals(self):
"""\
Initialize master signal handling. Most of the signals
@ -152,7 +152,7 @@ class Arbiter(object):
"Main master loop."
self.start()
util._setproctitle("master [%s]" % self.proc_name)
self.manage_workers()
while True:
try:
@ -163,18 +163,18 @@ class Arbiter(object):
self.murder_workers()
self.manage_workers()
continue
if sig not in self.SIG_NAMES:
self.log.info("Ignoring unknown signal: %s", sig)
continue
signame = self.SIG_NAMES.get(sig)
handler = getattr(self, "handle_%s" % signame, None)
if not handler:
self.log.error("Unhandled signal: %s", signame)
continue
self.log.info("Handling signal: %s", signame)
handler()
handler()
self.wakeup()
except StopIteration:
self.halt()
@ -185,7 +185,7 @@ class Arbiter(object):
except SystemExit:
raise
except Exception:
self.log.info("Unhandled exception in main loop:\n%s",
self.log.info("Unhandled exception in main loop:\n%s",
traceback.format_exc())
self.stop(False)
if self.pidfile is not None:
@ -195,7 +195,7 @@ class Arbiter(object):
def handle_chld(self, sig, frame):
"SIGCHLD handling"
self.wakeup()
def handle_hup(self):
"""\
HUP handling.
@ -205,16 +205,16 @@ class Arbiter(object):
"""
self.log.info("Hang up: %s", self.master_name)
self.reload()
def handle_quit(self):
"SIGQUIT handling"
raise StopIteration
def handle_int(self):
"SIGINT handling"
self.stop(False)
raise StopIteration
def handle_term(self):
"SIGTERM handling"
self.stop(False)
@ -227,7 +227,7 @@ class Arbiter(object):
"""
self.num_workers += 1
self.manage_workers()
def handle_ttou(self):
"""\
SIGTTOU handling.
@ -245,7 +245,7 @@ class Arbiter(object):
"""
self.kill_workers(signal.SIGUSR1)
self.log.reopen_files()
def handle_usr2(self):
"""\
SIGUSR2 handling.
@ -254,7 +254,7 @@ class Arbiter(object):
deployment with the ability to backout a change.
"""
self.reexec()
def handle_winch(self):
"SIGWINCH handling"
if os.getppid() == 1 or os.getpgrp() != os.getpid():
@ -263,7 +263,7 @@ class Arbiter(object):
self.kill_workers(signal.SIGQUIT)
else:
self.log.info("SIGWINCH ignored. Not daemonized")
def wakeup(self):
"""\
Wake up the arbiter by writing to the PIPE
@ -273,7 +273,7 @@ class Arbiter(object):
except IOError, e:
if e.errno not in [errno.EAGAIN, errno.EINTR]:
raise
def halt(self, reason=None, exit_status=0):
""" halt arbiter """
self.stop()
@ -283,7 +283,7 @@ class Arbiter(object):
if self.pidfile is not None:
self.pidfile.unlink()
sys.exit(exit_status)
def sleep(self):
"""\
Sleep until PIPE is readable or we timeout.
@ -303,12 +303,12 @@ class Arbiter(object):
raise
except KeyboardInterrupt:
sys.exit()
def stop(self, graceful=True):
"""\
Stop workers
:attr graceful: boolean, If True (the default) workers will be
killed gracefully (ie. trying to wait for the current connection)
"""
@ -357,11 +357,11 @@ class Arbiter(object):
if old_address != self.cfg.address:
self.LISTENER.close()
self.LISTENER = create_socket(self.cfg, self.log)
self.log.info("Listening at: %s", self.LISTENER)
self.log.info("Listening at: %s", self.LISTENER)
# spawn new workers with new app & conf
self.cfg.on_reload(self)
# unlink pidfile
if self.pidfile is not None:
self.pidfile.unlink()
@ -370,15 +370,15 @@ class Arbiter(object):
if self.cfg.pidfile is not None:
self.pidfile = Pidfile(self.cfg.pidfile)
self.pidfile.create(self.pid)
# set new proc_name
util._setproctitle("master [%s]" % self.proc_name)
# manage workers
self.log.reopen_files()
self.manage_workers()
self.manage_workers()
def murder_workers(self):
"""\
Kill unused/idle workers
@ -392,7 +392,7 @@ class Arbiter(object):
self.log.critical("WORKER TIMEOUT (pid:%s)", pid)
self.kill_worker(pid, signal.SIGKILL)
def reap_workers(self):
"""\
Reap workers to avoid zombie processes
@ -418,7 +418,7 @@ class Arbiter(object):
except OSError, e:
if e.errno == errno.ECHILD:
pass
def manage_workers(self):
"""\
Maintain the number of workers by spawning or killing
@ -432,7 +432,7 @@ class Arbiter(object):
while len(workers) > self.num_workers:
(pid, _) = workers.pop(0)
self.kill_worker(pid, signal.SIGQUIT)
def spawn_worker(self):
self.worker_age += 1
worker = self.worker_class(self.worker_age, self.pid, self.LISTENER,
@ -470,11 +470,11 @@ class Arbiter(object):
def spawn_workers(self):
"""\
Spawn new workers as needed.
This is where a worker process leaves the main loop
of the master process.
"""
for i in range(self.num_workers - len(self.WORKERS.keys())):
self.spawn_worker()
@ -485,11 +485,11 @@ class Arbiter(object):
"""
for pid in self.WORKERS.keys():
self.kill_worker(pid, sig)
def kill_worker(self, pid, sig):
"""\
Kill a worker
:attr pid: int, worker pid
:attr sig: `signal.SIG*` value
"""
@ -504,4 +504,4 @@ class Arbiter(object):
return
except (KeyError, OSError):
return
raise
raise

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
import copy
@ -34,21 +34,21 @@ def make_settings(ignore=None):
return settings
class Config(object):
def __init__(self, usage=None):
self.settings = make_settings()
self.usage = usage
def __getattr__(self, name):
if name not in self.settings:
raise AttributeError("No configuration setting for: %s" % name)
return self.settings[name].get()
def __setattr__(self, name, value):
if name != "settings" and name in self.settings:
raise AttributeError("Invalid access!")
super(Config, self).__setattr__(name, value)
def set(self, name, value):
if name not in self.settings:
raise AttributeError("No configuration setting for: %s" % name)
@ -77,7 +77,7 @@ class Config(object):
worker_class.setup()
return worker_class
@property
@property
def workers(self):
return self.settings['workers'].get()
@ -85,15 +85,15 @@ class Config(object):
def address(self):
bind = self.settings['bind'].get()
return util.parse_address(util.to_bytestring(bind))
@property
def uid(self):
return self.settings['user'].get()
@property
def gid(self):
return self.settings['group'].get()
@property
def proc_name(self):
pn = self.settings['proc_name'].get()
@ -112,17 +112,17 @@ class Config(object):
logger_class.install()
return logger_class
class SettingMeta(type):
def __new__(cls, name, bases, attrs):
super_new = super(SettingMeta, cls).__new__
parents = [b for b in bases if isinstance(b, SettingMeta)]
if not parents:
return super_new(cls, name, bases, attrs)
attrs["order"] = len(KNOWN_SETTINGS)
attrs["validator"] = wrap_method(attrs["validator"])
new_class = super_new(cls, name, bases, attrs)
new_class.fmt_desc(attrs.get("desc", ""))
KNOWN_SETTINGS.append(new_class)
@ -135,7 +135,7 @@ class SettingMeta(type):
class Setting(object):
__metaclass__ = SettingMeta
name = None
value = None
section = None
@ -147,11 +147,11 @@ class Setting(object):
default = None
short = None
desc = None
def __init__(self):
if self.default is not None:
self.set(self.default)
self.set(self.default)
def add_option(self, parser):
if not self.cli:
return
@ -167,13 +167,13 @@ class Setting(object):
if kwargs["action"] != "store":
kwargs.pop("type")
parser.add_option(*args, **kwargs)
def copy(self):
return copy.copy(self)
def get(self):
return self.value
def set(self, val):
assert callable(self.validator), "Invalid validator: %s" % self.name
self.value = self.validator(val)
@ -256,7 +256,7 @@ def validate_post_request(val):
def _wrapped(instance, req, environ):
return fun(instance, req)
return _wrapped
if not callable(val):
raise TypeError("Value isn't a callable: %s" % val)
@ -279,9 +279,9 @@ class ConfigFile(Setting):
default = None
desc = """\
The path to a Gunicorn config file.
Only has an effect when specified on the command line or as part of an
application specific configuration.
application specific configuration.
"""
class Bind(Setting):
@ -293,11 +293,11 @@ class Bind(Setting):
default = "127.0.0.1:8000"
desc = """\
The socket to bind.
A string of the form: 'HOST', 'HOST:PORT', 'unix:PATH'. An IP is a valid
HOST.
"""
class Backlog(Setting):
name = "backlog"
section = "Server Socket"
@ -307,14 +307,14 @@ class Backlog(Setting):
type = "int"
default = 2048
desc = """\
The maximum number of pending connections.
The maximum number of pending connections.
This refers to the number of clients that can be waiting to be served.
Exceeding this number results in the client getting an error when
attempting to connect. It should only affect servers under significant
load.
Must be a positive integer. Generally set in the 64-2048 range.
Must be a positive integer. Generally set in the 64-2048 range.
"""
class Workers(Setting):
@ -327,7 +327,7 @@ class Workers(Setting):
default = 1
desc = """\
The number of worker process for handling requests.
A positive integer generally in the 2-4 x $(NUM_CORES) range. You'll
want to vary this a bit to find the best for your particular
application's work load.
@ -342,18 +342,18 @@ class WorkerClass(Setting):
default = "sync"
desc = """\
The type of workers to use.
The default class (sync) should handle most 'normal' types of workloads.
You'll want to read http://gunicorn.org/design.html for information on
when you might want to choose one of the other worker classes.
A string referring to one of the following bundled classes:
* ``sync``
* ``eventlet`` - Requires eventlet >= 0.9.7
* ``gevent`` - Requires gevent >= 0.12.2 (?)
* ``tornado`` - Requires tornado >= 0.2
Optionally, you can provide your own worker by giving gunicorn a
python path to a subclass of gunicorn.workers.base.Worker. This
alternative syntax will load the gevent class:
@ -371,7 +371,7 @@ class WorkerConnections(Setting):
default = 1000
desc = """\
The maximum number of simultaneous clients.
This setting only affects the Eventlet and Gevent worker types.
"""
@ -385,11 +385,11 @@ class MaxRequests(Setting):
default = 0
desc = """\
The maximum number of requests a worker will process before restarting.
Any value greater than zero will limit the number of requests a work
will process before automatically restarting. This is a simple method
to help limit the damage of memory leaks.
If this is set to zero (the default) then the automatic worker
restarts are disabled.
"""
@ -404,7 +404,7 @@ class Timeout(Setting):
default = 30
desc = """\
Workers silent for more than this many seconds are killed and restarted.
Generally set to thirty seconds. Only set this noticeably higher if
you're sure of the repercussions for sync workers. For the non sync
workers it just means that the worker process is still communicating and
@ -421,8 +421,8 @@ class Keepalive(Setting):
default = 2
desc = """\
The number of seconds to wait for requests on a Keep-Alive connection.
Generally set in the 1-5 seconds range.
Generally set in the 1-5 seconds range.
"""
class Debug(Setting):
@ -434,7 +434,7 @@ class Debug(Setting):
default = False
desc = """\
Turn on debugging in the server.
This limits the number of worker processes to 1 and changes some error
handling that's sent to clients.
"""
@ -448,8 +448,8 @@ class Spew(Setting):
default = False
desc = """\
Install a trace function that spews every line executed by the server.
This is the nuclear option.
This is the nuclear option.
"""
class PreloadApp(Setting):
@ -461,7 +461,7 @@ class PreloadApp(Setting):
default = False
desc = """\
Load application code before the worker processes are forked.
By preloading an application you can save some RAM resources as well as
speed up server boot times. Although, if you defer application loading
to each worker process, you can reload your application code easily by
@ -477,7 +477,7 @@ class Daemon(Setting):
default = False
desc = """\
Daemonize the Gunicorn process.
Detaches the server from the controlling terminal and enters the
background.
"""
@ -491,7 +491,7 @@ class Pidfile(Setting):
default = None
desc = """\
A filename to use for the PID file.
If not set, no PID file will be written.
"""
@ -504,7 +504,7 @@ class User(Setting):
default = os.geteuid()
desc = """\
Switch worker processes to run as this user.
A valid user id (as an integer) or the name of a user that can be
retrieved with a call to pwd.getpwnam(value) or None to not change
the worker process user.
@ -519,7 +519,7 @@ class Group(Setting):
default = os.getegid()
desc = """\
Switch worker process to run as this group.
A valid group id (as an integer) or the name of a user that can be
retrieved with a call to pwd.getgrnam(value) or None to not change
the worker processes group.
@ -535,9 +535,9 @@ class Umask(Setting):
default = 0
desc = """\
A bit mask for the file mode on files written by Gunicorn.
Note that this affects unix socket permissions.
A valid value for the os.umask(mode) call or a string compatible with
int(value, 0) (0 means Python guesses the base, so values like "0",
"0xFF", "0022" are valid for decimal, hex, and octal representations)
@ -551,9 +551,9 @@ class TmpUploadDir(Setting):
default = None
desc = """\
Directory to store temporary request data as they are read.
This may disappear in the near future.
This path should be writable by the process permissions set for Gunicorn
workers. If not specified, Gunicorn will choose a system generated
temporary directory.
@ -599,10 +599,10 @@ class AccessLog(Setting):
cli = ["--access-logfile"]
meta = "FILE"
validator = validate_string
default = None
default = None
desc = """\
The Access log file to write to.
"-" means log to stdout.
"""
@ -612,7 +612,7 @@ class AccessLogFormat(Setting):
cli = ["--access-logformat"]
meta = "STRING"
validator = validate_string
default = '%(h)s %(l)s %(u)s %(t)s "%(r)s" %(s)s %(b)s "%(f)s" "%(a)s"'
default = '%(h)s %(l)s %(u)s %(t)s "%(r)s" %(s)s %(b)s "%(f)s" "%(a)s"'
desc = """\
The Access log format .
@ -631,7 +631,7 @@ class AccessLogFormat(Setting):
T: request time in seconds
D: request time in microseconds
You can also pass any WSGI request header as a parameter.
You can also pass any WSGI request header as a parameter.
(ex '%(HTTP_HOST)s').
"""
@ -644,7 +644,7 @@ class ErrorLog(Setting):
default = "-"
desc = """\
The Error log file to write to.
"-" means log to stdout.
"""
@ -657,9 +657,9 @@ class Loglevel(Setting):
default = "info"
desc = """\
The granularity of Error log outputs.
Valid level names are:
* debug
* info
* warning
@ -681,8 +681,8 @@ class LoggerClass(Setting):
normal usages in logging. It provides error and access logging.
You can provide your own worker by giving gunicorn a
python path to a subclass like gunicorn.glogging.Logger.
Alternatively the syntax can also load the Logger class
python path to a subclass like gunicorn.glogging.Logger.
Alternatively the syntax can also load the Logger class
with `egg:gunicorn#simple`
"""
@ -695,12 +695,12 @@ class Procname(Setting):
default = None
desc = """\
A base to use with setproctitle for process naming.
This affects things like ``ps`` and ``top``. If you're going to be
running more than one instance of Gunicorn you'll probably want to set a
name to tell them apart. This requires that you install the setproctitle
module.
It defaults to 'gunicorn'.
"""
@ -723,7 +723,7 @@ class OnStarting(Setting):
default = staticmethod(on_starting)
desc = """\
Called just before the master process is initialized.
The callable needs to accept a single instance variable for the Arbiter.
"""
@ -752,7 +752,7 @@ class WhenReady(Setting):
default = staticmethod(start_server)
desc = """\
Called just after the server is started.
The callable needs to accept a single instance variable for the Arbiter.
"""
@ -766,11 +766,11 @@ class Prefork(Setting):
default = staticmethod(pre_fork)
desc = """\
Called just before a worker is forked.
The callable needs to accept two instance variables for the Arbiter and
new Worker.
"""
class Postfork(Setting):
name = "post_fork"
section = "Server Hooks"
@ -781,7 +781,7 @@ class Postfork(Setting):
default = staticmethod(post_fork)
desc = """\
Called just after a worker has been forked.
The callable needs to accept two instance variables for the Arbiter and
new Worker.
"""
@ -796,7 +796,7 @@ class PreExec(Setting):
default = staticmethod(pre_exec)
desc = """\
Called just before a new master process is forked.
The callable needs to accept a single instance variable for the Arbiter.
"""
@ -810,7 +810,7 @@ class PreRequest(Setting):
default = staticmethod(pre_request)
desc = """\
Called just before a worker processes the request.
The callable needs to accept two instance variables for the Worker and
the Request.
"""

View File

@ -1,9 +1,9 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
"""The debug module contains utilities and functions for better
"""The debug module contains utilities and functions for better
debugging Gunicorn."""
import sys
@ -69,5 +69,5 @@ def unspew():
"""Remove the trace hook installed by spew.
"""
sys.settrace(None)

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
@ -8,7 +8,7 @@ class HaltServer(Exception):
def __init__(self, reason, exit_status=1):
self.reason = reason
self.exit_status = exit_status
def __str__(self):
return "<HaltServer %r %d>" % (self.reason, self.exit_status)

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
import datetime
@ -39,7 +39,7 @@ class Logger(object):
loglevel = self.LOG_LEVELS.get(cfg.loglevel.lower(), logging.INFO)
self.error_log.setLevel(loglevel)
# always info in access log
self.access_log.setLevel(logging.INFO)
@ -100,13 +100,13 @@ class Logger(object):
'D': str(request_time.microseconds)
}
# add WSGI request headers
# add WSGI request headers
atoms.update(dict([(k,v) for k, v in environ.items() \
if k.startswith('HTTP_')]))
for k, v in atoms.items():
atoms[k] = v.replace('"', '\\"')
try:
self.access_log.info(self.cfg.access_log_format % atoms)
except:
@ -138,12 +138,12 @@ class Logger(object):
util.close_on_exec(handler.stream.fileno())
handler.release()
def _get_gunicorn_handler(self, log):
for h in log.handlers:
if getattr(h, "_gunicorn", False) == True:
return h
def _set_handler(self, log, output, fmt):
# remove previous gunicorn log handler
h = self._get_gunicorn_handler(log)

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
import errno
@ -35,7 +35,7 @@ def sendfile(fdout, fdin, offset, nbytes):
ctypes.c_int]
_nbytes = ctypes.c_uint64(nbytes)
result = _sendfile(fdin, fdout, offset, _nbytes, None, 0)
if result == -1:
e = ctypes.get_errno()
if e == errno.EAGAIN and _nbytes.value is not None:
@ -60,7 +60,7 @@ def sendfile(fdout, fdin, offset, nbytes):
ctypes.POINTER(ctypes.c_uint64), ctypes.c_size_t]
_offset = ctypes.c_uint64(offset)
sent = _sendfile(fdout, fdin, _offset, nbytes)
sent = _sendfile(fdout, fdin, _offset, nbytes)
if sent == -1:
e = ctypes.get_errno()
raise OSError(e, os.strerror(e))

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
import sys
@ -18,7 +18,7 @@ class ChunkedReader(object):
self.req = req
self.parser = self.parse_chunked(unreader)
self.buf = StringIO()
def read(self, size):
if not isinstance(size, (int, long)):
raise TypeError("size must be an integral type")
@ -40,11 +40,11 @@ class ChunkedReader(object):
self.buf.truncate(0)
self.buf.write(rest)
return ret
def parse_trailers(self, unreader, data):
buf = StringIO()
buf.write(data)
idx = buf.getvalue().find("\r\n\r\n")
done = buf.getvalue()[:2] == "\r\n"
while idx < 0 and not done:
@ -73,7 +73,7 @@ class ChunkedReader(object):
rest += unreader.read()
if rest[:2] != '\r\n':
raise ChunkMissingTerminator(rest[:2])
(size, rest) = self.parse_chunk_size(unreader, data=rest[2:])
(size, rest) = self.parse_chunk_size(unreader, data=rest[2:])
def parse_chunk_size(self, unreader, data=None):
buf = StringIO()
@ -87,7 +87,7 @@ class ChunkedReader(object):
data = buf.getvalue()
line, rest_chunk = data[:idx], data[idx+2:]
chunk_size = line.split(";", 1)[0].strip()
try:
chunk_size = int(chunk_size, 16)
@ -112,18 +112,18 @@ class LengthReader(object):
def __init__(self, unreader, length):
self.unreader = unreader
self.length = length
def read(self, size):
if not isinstance(size, (int, long)):
raise TypeError("size must be an integral type")
size = min(self.length, size)
if size < 0:
raise ValueError("Size must be positive.")
if size == 0:
return ""
buf = StringIO()
data = self.unreader.read()
while data:
@ -131,7 +131,7 @@ class LengthReader(object):
if buf.tell() >= size:
break
data = self.unreader.read()
buf = buf.getvalue()
ret, rest = buf[:size], buf[size:]
self.unreader.unread(rest)
@ -143,7 +143,7 @@ class EOFReader(object):
self.unreader = unreader
self.buf = StringIO()
self.finished = False
def read(self, size):
if not isinstance(size, (int, long)):
raise TypeError("size must be an integral type")
@ -151,7 +151,7 @@ class EOFReader(object):
raise ValueError("Size must be positive.")
if size == 0:
return ""
if self.finished:
data = self.buf.getvalue()
ret, rest = data[:size], data[size:]
@ -179,10 +179,10 @@ class Body(object):
def __init__(self, reader):
self.reader = reader
self.buf = StringIO()
def __iter__(self):
return self
def next(self):
ret = self.readline()
if not ret:
@ -197,7 +197,7 @@ class Body(object):
elif size < 0:
return sys.maxint
return size
def read(self, size=None):
size = self.getsize(size)
if size == 0:
@ -221,12 +221,12 @@ class Body(object):
self.buf.truncate(0)
self.buf.write(rest)
return ret
def readline(self, size=None):
size = self.getsize(size)
if size == 0:
return ""
line = self.buf.getvalue()
idx = line.find("\n")
if idx >= 0:
@ -234,7 +234,7 @@ class Body(object):
self.buf.truncate(0)
self.buf.write(line[idx+1:])
return ret
self.buf.truncate(0)
ch = ""
buf = [line]
@ -246,7 +246,7 @@ class Body(object):
lsize += 1
buf.append(ch)
return "".join(buf)
def readlines(self, size=None):
ret = []
data = self.read()

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
class ParseException(Exception):
@ -26,18 +26,18 @@ class InvalidRequestMethod(ParseException):
def __str__(self):
return "Invalid HTTP method: %r" % self.method
class InvalidHTTPVersion(ParseException):
def __init__(self, version):
self.version = version
def __str__(self):
return "Invalid HTTP Version: %s" % self.version
class InvalidHeader(ParseException):
def __init__(self, hdr):
self.hdr = hdr
def __str__(self):
return "Invalid HTTP Header: %r" % self.hdr
@ -51,13 +51,13 @@ class InvalidHeaderName(ParseException):
class InvalidChunkSize(ParseException):
def __init__(self, data):
self.data = data
def __str__(self):
return "Invalid chunk size: %r" % self.data
class ChunkMissingTerminator(ParseException):
def __init__(self, term):
self.term = term
def __str__(self):
return "Invalid chunk terminator is not '\\r\\n': %r" % self.term

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
import re
@ -28,7 +28,7 @@ class Message(object):
unused = self.parse(self.unreader)
self.unreader.unread(unused)
self.set_body_reader()
def parse(self):
raise NotImplementedError()
@ -50,12 +50,12 @@ class Message(object):
if self.hdrre.search(name):
raise InvalidHeaderName(name)
name, value = name.strip(), [value.lstrip()]
# Consume value continuation lines
while len(lines) and lines[0].startswith((" ", "\t")):
value.append(lines.pop(0))
value = ''.join(value).rstrip()
headers.append((name, value))
return headers
@ -99,7 +99,7 @@ class Request(Message):
def __init__(self, unreader):
self.methre = re.compile("[A-Z0-9$-_.]{3,20}")
self.versre = re.compile("HTTP/(\d+).(\d+)")
self.method = None
self.uri = None
self.scheme = None
@ -119,12 +119,12 @@ class Request(Message):
raise StopIteration()
raise NoMoreData(buf.getvalue())
buf.write(data)
def parse(self, unreader):
buf = StringIO()
self.get_data(unreader, buf, stop=True)
# Request line
idx = buf.getvalue().find("\r\n")
while idx < 0:
@ -134,8 +134,8 @@ class Request(Message):
rest = buf.getvalue()[idx+2:] # Skip \r\n
buf = StringIO()
buf.write(rest)
# Headers
idx = buf.getvalue().find("\r\n\r\n")
@ -144,7 +144,7 @@ class Request(Message):
self.get_data(unreader, buf)
idx = buf.getvalue().find("\r\n\r\n")
done = buf.getvalue()[:2] == "\r\n"
if done:
self.unreader.unread(buf.getvalue()[2:])
return ""
@ -154,7 +154,7 @@ class Request(Message):
ret = buf.getvalue()[idx+4:]
buf = StringIO()
return ret
def parse_request_line(self, line):
bits = line.split(None, 2)
if len(bits) != 3:

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
from gunicorn.http.message import Request
@ -17,18 +17,18 @@ class Parser(object):
def __iter__(self):
return self
def next(self):
# Stop if HTTP dictates a stop.
if self.mesg and self.mesg.should_close():
raise StopIteration()
# Discard any unread body of the previous message
if self.mesg:
data = self.mesg.body.read(8192)
while data:
data = self.mesg.body.read(8192)
# Parse the next request
self.mesg = self.mesg_class(self.unreader)
if not self.mesg:

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
import os
@ -16,10 +16,10 @@ except ImportError:
class Unreader(object):
def __init__(self):
self.buf = StringIO()
def chunk(self):
raise NotImplementedError()
def read(self, size=None):
if size is not None and not isinstance(size, (int, long)):
raise TypeError("size parameter must be an int or long.")
@ -48,7 +48,7 @@ class Unreader(object):
self.buf.truncate(0)
self.buf.write(data[size:])
return data[:size]
def unread(self, data):
self.buf.seek(0, os.SEEK_END)
self.buf.write(data)
@ -58,7 +58,7 @@ class SocketUnreader(Unreader):
super(SocketUnreader, self).__init__()
self.sock = sock
self.mxchunk = max_chunk
def chunk(self):
return self.sock.recv(self.mxchunk)

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
import logging
@ -59,7 +59,7 @@ def create(req, sock, client, server, cfg):
"CONTENT_TYPE": "",
"CONTENT_LENGTH": ""
}
# authors should be aware that REMOTE_HOST and REMOTE_ADDR
# may not qualify the remote addr:
# http://www.ietf.org/rfc/rfc3875
@ -98,7 +98,7 @@ def create(req, sock, client, server, cfg):
environ[key] = hdr_value
environ['wsgi.url_scheme'] = url_scheme
if isinstance(forward, basestring):
# we only took the last one
# http://en.wikipedia.org/wiki/X-Forwarded-For
@ -121,7 +121,7 @@ def create(req, sock, client, server, cfg):
remote = (host, port)
else:
remote = forward
remote = forward
environ['REMOTE_ADDR'] = remote[0]
environ['REMOTE_PORT'] = str(remote[1])

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
#
# Copyright 2001-2005 by Vinay Sajip. All Rights Reserved.

View File

@ -1,12 +1,12 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
from optparse import make_option
import sys
import django
from django.core.management.base import BaseCommand, CommandError
from django.conf import settings
@ -56,17 +56,17 @@ class Command(BaseCommand):
option_list = BaseCommand.option_list + GUNICORN_OPTIONS
help = "Starts a fully-functional Web server using gunicorn."
args = '[optional port number, or ipaddr:port or unix:/path/to/sockfile]'
# Validation is called explicitly each time the server is reloaded.
requires_model_validation = False
def handle(self, addrport=None, *args, **options):
if args:
raise CommandError('Usage is run_gunicorn %s' % self.args)
if addrport:
options['bind'] = addrport
options['default_proc_name'] = settings.SETTINGS_MODULE
admin_media_path = options.pop('admin_media_path', '')
@ -74,11 +74,11 @@ class Command(BaseCommand):
print "Validating models..."
self.validate(display_num_errors=True)
print "\nDjango version %s, using settings %r" % (django.get_version(),
print "\nDjango version %s, using settings %r" % (django.get_version(),
settings.SETTINGS_MODULE)
print "Server is running"
print "Quit the server with %s." % quit_command
# django.core.management.base forces the locale to en-us.
translation.activate(settings.LANGUAGE_CODE)
DjangoApplicationCommand(options, admin_media_path).run()

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
from __future__ import with_statement
@ -20,7 +20,7 @@ class Pidfile(object):
def __init__(self, fname):
self.fname = fname
self.pid = None
def create(self, pid):
oldpid = self.validate()
if oldpid:
@ -30,7 +30,7 @@ class Pidfile(object):
"(or pid file '%s' is stale)" % (os.getpid(), self.fname))
self.pid = pid
# Write pidfile
fdir = os.path.dirname(self.fname)
if fdir and not os.path.isdir(fdir):
@ -43,14 +43,14 @@ class Pidfile(object):
self.fname = fname
os.close(fd)
# set permissions to -rw-r--r--
# set permissions to -rw-r--r--
os.chmod(self.fname, 420)
def rename(self, path):
self.unlink()
self.fname = path
self.create(self.pid)
def unlink(self):
""" delete pidfile"""
try:
@ -61,7 +61,7 @@ class Pidfile(object):
os.unlink(self.fname)
except:
pass
def validate(self):
""" Validate pidfile and make it stale if needed"""
if not self.fname:

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
import errno
@ -14,7 +14,7 @@ from gunicorn import util
class BaseSocket(object):
def __init__(self, conf, log, fd=None):
self.log = log
self.conf = conf
@ -24,13 +24,13 @@ class BaseSocket(object):
else:
sock = socket.fromfd(fd, self.FAMILY, socket.SOCK_STREAM)
self.sock = self.set_options(sock, bound=(fd is not None))
def __str__(self, name):
return "<socket %d>" % self.sock.fileno()
def __getattr__(self, name):
return getattr(self.sock, name)
def set_options(self, sock, bound=False):
sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
if not bound:
@ -38,10 +38,10 @@ class BaseSocket(object):
sock.setblocking(0)
sock.listen(self.conf.backlog)
return sock
def bind(self, sock):
sock.bind(self.address)
def close(self):
try:
self.sock.close()
@ -51,12 +51,12 @@ class BaseSocket(object):
del self.sock
class TCPSocket(BaseSocket):
FAMILY = socket.AF_INET
def __str__(self):
return "http://%s:%d" % self.sock.getsockname()
def set_options(self, sock, bound=False):
sock.setsockopt(socket.IPPROTO_TCP, socket.TCP_NODELAY, 1)
return super(TCPSocket, self).set_options(sock, bound=bound)
@ -70,9 +70,9 @@ class TCP6Socket(TCPSocket):
return "http://[%s]:%d" % (host, port)
class UnixSocket(BaseSocket):
FAMILY = socket.AF_UNIX
def __init__(self, conf, log, fd=None):
if fd is None:
try:
@ -80,16 +80,16 @@ class UnixSocket(BaseSocket):
except OSError:
pass
super(UnixSocket, self).__init__(conf, log, fd=fd)
def __str__(self):
return "unix:%s" % self.address
def bind(self, sock):
old_umask = os.umask(self.conf.umask)
sock.bind(self.address)
util.chown(self.address, self.conf.uid, self.conf.gid)
os.umask(old_umask)
def close(self):
super(UnixSocket, self).close()
os.unlink(self.address)
@ -103,7 +103,7 @@ def create_socket(conf, log):
"""
# get it only once
addr = conf.address
if isinstance(addr, tuple):
if util.is_ipv6(addr[0]):
sock_type = TCP6Socket
@ -127,7 +127,7 @@ def create_socket(conf, log):
# If we fail to create a socket from GUNICORN_FD
# we fall through and try and open the socket
# normally.
for i in range(5):
try:
return sock_type(conf, log)
@ -140,6 +140,6 @@ def create_socket(conf, log):
if i < 5:
log.error("Retrying in 1 second.")
time.sleep(1)
log.error("Can't connect to %s", str(addr))
sys.exit(1)

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
@ -55,11 +55,11 @@ hop_headers = set("""
te trailers transfer-encoding upgrade
server date
""".split())
try:
from setproctitle import setproctitle
def _setproctitle(title):
setproctitle("gunicorn: %s" % title)
setproctitle("gunicorn: %s" % title)
except ImportError:
def _setproctitle(title):
return
@ -82,9 +82,9 @@ def load_class(uri, default="sync", section="gunicorn.workers"):
if uri.startswith("#"):
uri = uri[1:]
return pkg_resources.load_entry_point("gunicorn",
return pkg_resources.load_entry_point("gunicorn",
section, uri)
except ImportError:
except ImportError:
raise RuntimeError("class uri invalid or not found")
klass = components.pop(-1)
mod = __import__('.'.join(components))
@ -103,10 +103,10 @@ def set_owner_process(uid,gid):
# versions of python < 2.6.2 don't manage unsigned int for
# groups like on osx or fedora
os.setgid(-ctypes.c_int(-gid).value)
if uid:
os.setuid(uid)
def chown(path, uid, gid):
try:
os.chown(path, uid, gid)
@ -122,7 +122,7 @@ def is_ipv6(addr):
except socket.error: # not a valid address
return False
return True
def parse_address(netloc, default_port=8000):
if netloc.startswith("unix:"):
return netloc.split("unix:")[1]
@ -136,7 +136,7 @@ def parse_address(netloc, default_port=8000):
host = "0.0.0.0"
else:
host = netloc.lower()
#get port
netloc = netloc.split(']')[-1]
if ":" in netloc:
@ -145,9 +145,9 @@ def parse_address(netloc, default_port=8000):
raise RuntimeError("%r is not a valid port number." % port)
port = int(port)
else:
port = default_port
port = default_port
return (host, port)
def get_maxfd():
maxfd = resource.getrlimit(resource.RLIMIT_NOFILE)[1]
if (maxfd == resource.RLIM_INFINITY):
@ -158,7 +158,7 @@ def close_on_exec(fd):
flags = fcntl.fcntl(fd, fcntl.F_GETFD)
flags |= fcntl.FD_CLOEXEC
fcntl.fcntl(fd, fcntl.F_SETFD, flags)
def set_non_blocking(fd):
flags = fcntl.fcntl(fd, fcntl.F_GETFL) | os.O_NONBLOCK
fcntl.fcntl(fd, fcntl.F_SETFL, flags)
@ -183,7 +183,7 @@ except ImportError:
def write_chunk(sock, data):
chunk = "".join(("%X\r\n" % len(data), data, "\r\n"))
sock.sendall(chunk)
def write(sock, data, chunked=False):
if chunked:
return write_chunk(sock, data)
@ -199,7 +199,7 @@ def write_nonblock(sock, data, chunked=False):
sock.setblocking(1)
else:
return write(sock, data, chunked)
def writelines(sock, lines, chunked=False):
for line in list(lines):
write(sock, line, chunked)
@ -229,7 +229,7 @@ def write_error(sock, status_int, reason, mesg):
def normalize_name(name):
return "-".join([w.lower().capitalize() for w in name.split("-")])
def import_app(module):
parts = module.split(":", 1)
if len(parts) == 1:
@ -264,7 +264,7 @@ def http_date(timestamp=None):
day, monthname[month], year,
hh, mm, ss)
return s
def to_bytestring(s):
""" convert to bytestring an unicode """
if not isinstance(s, basestring):
@ -289,11 +289,11 @@ def daemonize():
if os.fork():
os._exit(0)
os.umask(0)
maxfd = get_maxfd()
closerange(0, maxfd)
os.open(REDIRECT_TO, os.O_RDWR)
os.dup2(0, 1)
os.dup2(0, 2)

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
from __future__ import with_statement
@ -21,7 +21,7 @@ class AsyncWorker(base.Worker):
def __init__(self, *args, **kwargs):
super(AsyncWorker, self).__init__(*args, **kwargs)
self.worker_connections = self.cfg.worker_connections
def timeout_ctx(self):
raise NotImplementedError()

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
@ -24,7 +24,7 @@ class Worker(object):
lambda x: getattr(signal, "SIG%s" % x),
"HUP QUIT INT TERM USR1 USR2 WINCH CHLD".split()
)
PIPE = []
def __init__(self, age, ppid, socket, app, timeout, cfg, log):
@ -47,11 +47,11 @@ class Worker(object):
self.log = log
self.debug = cfg.debug
self.address = self.socket.getsockname()
self.tmp = WorkerTmp(cfg)
self.tmp = WorkerTmp(cfg)
def __str__(self):
return "<Worker %s>" % self.pid
@property
def pid(self):
return os.getpid()
@ -88,7 +88,7 @@ class Worker(object):
self.PIPE = os.pipe()
map(util.set_non_blocking, self.PIPE)
map(util.close_on_exec, self.PIPE)
# Prevent fd inherientence
util.close_on_exec(self.socket)
util.close_on_exec(self.tmp.fileno())
@ -96,9 +96,9 @@ class Worker(object):
self.log.close_on_exec()
self.init_signals()
self.wsgi = self.app.wsgi()
# Enter main run loop
self.booted = True
self.run()
@ -118,7 +118,7 @@ class Worker(object):
def handle_usr1(self, sig, frame):
self.log.reopen_files()
def handle_quit(self, sig, frame):
self.alive = False
@ -135,10 +135,10 @@ class Worker(object):
if isinstance(exc, (InvalidRequestLine, InvalidRequestMethod,
InvalidHTTPVersion, InvalidHeader, InvalidHeaderName,)):
status_int = 400
reason = "Bad Request"
if isinstance(exc, InvalidRequestLine):
mesg = "<p>Invalid Request Line '%s'</p>" % str(exc)
elif isinstance(exc, InvalidRequestMethod):
@ -147,7 +147,7 @@ class Worker(object):
mesg = "<p>Invalid HTTP Version '%s'</p>" % str(exc)
elif isinstance(exc, (InvalidHeaderName, InvalidHeader,)):
mesg = "<p>Invalid Header '%s'</p>" % str(exc)
if self.debug:
tb = traceback.format_exc()
mesg += "<h2>Traceback:</h2>\n<pre>%s</pre>" % tb
@ -156,7 +156,7 @@ class Worker(object):
util.write_error(client, status_int, reason, mesg)
except:
self.log.warning("Failed to send error message.")
def handle_winch(self, sig, fname):
# Ignore SIGWINCH in worker. Fixes a crash on OpenBSD.
return

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
from __future__ import with_statement
@ -28,9 +28,9 @@ class EventletWorker(AsyncWorker):
def init_process(self):
hubs.use_hub()
super(EventletWorker, self).init_process()
def timeout_ctx(self):
return eventlet.Timeout(self.cfg.keepalive, False)
return eventlet.Timeout(self.cfg.keepalive, False)
def run(self):
self.socket = GreenSocket(family_or_realsock=self.socket.sock)

View File

@ -1,11 +1,11 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
from datetime import datetime
from gunicorn.workers.ggevent import BASE_WSGI_ENV, GeventWorker
from gunicorn.workers.ggevent import BASE_WSGI_ENV, GeventWorker
from gevent import wsgi
@ -30,9 +30,9 @@ class WSGIHandler(wsgi.WSGIHandler):
self.time_start = datetime.now()
super(WSGIHandler, self).handle()
class WSGIServer(wsgi.WSGIServer):
base_env = BASE_WSGI_ENV
base_env = BASE_WSGI_ENV
class GeventWSGIWorker(GeventWorker):
"The Gevent StreamServer based workers."

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
import os
@ -19,7 +19,7 @@ from gunicorn.workers.base import Worker
from gunicorn import __version__ as gversion
class TornadoWorker(Worker):
@classmethod
def setup(cls):
web = sys.modules.pop("tornado.web")
@ -29,18 +29,18 @@ class TornadoWorker(Worker):
self._headers["Server"] += " (Gunicorn/%s)" % gversion
web.RequestHandler.clear = clear
sys.modules["tornado.web"] = web
def handle_quit(self, sig, frame):
super(TornadoWorker, self).handle_quit(sig, frame)
self.ioloop.stop()
def watchdog(self):
self.notify()
if self.ppid != os.getppid():
self.log.info("Parent changed, shutting down: %s", self)
self.ioloop.stop()
def run(self):
self.socket.setblocking(0)
self.ioloop = IOLoop.instance()

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
#
@ -16,7 +16,7 @@ import gunicorn.util as util
import gunicorn.workers.base as base
class SyncWorker(base.Worker):
def run(self):
# self.socket appears to lose its blocking status after
# we fork in the arbiter. Reset it here.
@ -24,7 +24,7 @@ class SyncWorker(base.Worker):
while self.alive:
self.notify()
# Accept a connection. If we get an error telling us
# that no connection is waiting we fall down to the
# select which is where we'll wait for a bit for new
@ -48,7 +48,7 @@ class SyncWorker(base.Worker):
if self.ppid != os.getppid():
self.log.info("Parent changed, shutting down: %s", self)
return
try:
self.notify()
ret = select.select([self.socket], [], self.PIPE, self.timeout)
@ -63,7 +63,7 @@ class SyncWorker(base.Worker):
else:
return
raise
def handle(self, client, addr):
try:
parser = http.RequestParser(client)
@ -78,7 +78,7 @@ class SyncWorker(base.Worker):
self.log.debug("Ignoring EPIPE")
except Exception, e:
self.handle_error(client, e)
finally:
finally:
util.close(client)
def handle_request(self, req, client, addr):
@ -113,7 +113,7 @@ class SyncWorker(base.Worker):
raise
except Exception, e:
# Only send back traceback in HTTP in debug mode.
self.handle_error(client, e)
self.handle_error(client, e)
return
finally:
try:

View File

@ -1,6 +1,6 @@
# -*- coding: utf-8 -
#
# This file is part of gunicorn released under the MIT license.
# This file is part of gunicorn released under the MIT license.
# See the NOTICE for more information.
import os
@ -13,7 +13,7 @@ class WorkerTmp(object):
def __init__(self, cfg):
old_umask = os.umask(cfg.umask)
fd, name = tempfile.mkstemp(prefix="wgunicorn-")
# allows the process to write to the file
util.chown(name, cfg.uid, cfg.gid)
os.umask(old_umask)
@ -28,7 +28,7 @@ class WorkerTmp(object):
self.spinner = 0
def notify(self):
def notify(self):
try:
self.spinner = (self.spinner+1) % 2
os.fchmod(self._tmp.fileno(), self.spinner)
@ -42,6 +42,6 @@ class WorkerTmp(object):
def fileno(self):
return self._tmp.fileno()
def close(self):
return self._tmp.close()