123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190 |
- # -*- coding: utf-8 -
- #
- # This file is part of gunicorn released under the MIT license.
- # See the NOTICE for more information.
- # Please remember to run "make -C docs html" after update "desc" attributes.
- import argparse
- import copy
- import grp
- import inspect
- import os
- import pwd
- import re
- import shlex
- import ssl
- import sys
- import textwrap
- from gunicorn import __version__, util
- from gunicorn.errors import ConfigError
- from gunicorn.reloader import reloader_engines
- KNOWN_SETTINGS = []
- PLATFORM = sys.platform
- def make_settings(ignore=None):
- settings = {}
- ignore = ignore or ()
- for s in KNOWN_SETTINGS:
- setting = s()
- if setting.name in ignore:
- continue
- settings[setting.name] = setting.copy()
- return settings
- def auto_int(_, x):
- # for compatible with octal numbers in python3
- if re.match(r'0(\d)', x, re.IGNORECASE):
- x = x.replace('0', '0o', 1)
- return int(x, 0)
- class Config(object):
- def __init__(self, usage=None, prog=None):
- self.settings = make_settings()
- self.usage = usage
- self.prog = prog or os.path.basename(sys.argv[0])
- self.env_orig = os.environ.copy()
- def __str__(self):
- lines = []
- kmax = max(len(k) for k in self.settings)
- for k in sorted(self.settings):
- v = self.settings[k].value
- if callable(v):
- v = "<{}()>".format(v.__qualname__)
- lines.append("{k:{kmax}} = {v}".format(k=k, v=v, kmax=kmax))
- return "\n".join(lines)
- 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().__setattr__(name, value)
- def set(self, name, value):
- if name not in self.settings:
- raise AttributeError("No configuration setting for: %s" % name)
- self.settings[name].set(value)
- def get_cmd_args_from_env(self):
- if 'GUNICORN_CMD_ARGS' in self.env_orig:
- return shlex.split(self.env_orig['GUNICORN_CMD_ARGS'])
- return []
- def parser(self):
- kwargs = {
- "usage": self.usage,
- "prog": self.prog
- }
- parser = argparse.ArgumentParser(**kwargs)
- parser.add_argument("-v", "--version",
- action="version", default=argparse.SUPPRESS,
- version="%(prog)s (version " + __version__ + ")\n",
- help="show program's version number and exit")
- parser.add_argument("args", nargs="*", help=argparse.SUPPRESS)
- keys = sorted(self.settings, key=self.settings.__getitem__)
- for k in keys:
- self.settings[k].add_option(parser)
- return parser
- @property
- def worker_class_str(self):
- uri = self.settings['worker_class'].get()
- # are we using a threaded worker?
- is_sync = uri.endswith('SyncWorker') or uri == 'sync'
- if is_sync and self.threads > 1:
- return "gthread"
- return uri
- @property
- def worker_class(self):
- uri = self.settings['worker_class'].get()
- # are we using a threaded worker?
- is_sync = uri.endswith('SyncWorker') or uri == 'sync'
- if is_sync and self.threads > 1:
- uri = "gunicorn.workers.gthread.ThreadWorker"
- worker_class = util.load_class(uri)
- if hasattr(worker_class, "setup"):
- worker_class.setup()
- return worker_class
- @property
- def address(self):
- s = self.settings['bind'].get()
- return [util.parse_address(util.bytes_to_str(bind)) for bind in s]
- @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()
- if pn is not None:
- return pn
- else:
- return self.settings['default_proc_name'].get()
- @property
- def logger_class(self):
- uri = self.settings['logger_class'].get()
- if uri == "simple":
- # support the default
- uri = LoggerClass.default
- # if default logger is in use, and statsd is on, automagically switch
- # to the statsd logger
- if uri == LoggerClass.default:
- if 'statsd_host' in self.settings and self.settings['statsd_host'].value is not None:
- uri = "gunicorn.instrument.statsd.Statsd"
- logger_class = util.load_class(
- uri,
- default="gunicorn.glogging.Logger",
- section="gunicorn.loggers")
- if hasattr(logger_class, "install"):
- logger_class.install()
- return logger_class
- @property
- def is_ssl(self):
- return self.certfile or self.keyfile
- @property
- def ssl_options(self):
- opts = {}
- for name, value in self.settings.items():
- if value.section == 'SSL':
- opts[name] = value.get()
- return opts
- @property
- def env(self):
- raw_env = self.settings['raw_env'].get()
- env = {}
- if not raw_env:
- return env
- for e in raw_env:
- s = util.bytes_to_str(e)
- try:
- k, v = s.split('=', 1)
- except ValueError:
- raise RuntimeError("environment setting %r invalid" % s)
- env[k] = v
- return env
- @property
- def sendfile(self):
- if self.settings['sendfile'].get() is not None:
- return False
- if 'SENDFILE' in os.environ:
- sendfile = os.environ['SENDFILE'].lower()
- return sendfile in ['y', '1', 'yes', 'true']
- return True
- @property
- def reuse_port(self):
- return self.settings['reuse_port'].get()
- @property
- def paste_global_conf(self):
- raw_global_conf = self.settings['raw_paste_global_conf'].get()
- if raw_global_conf is None:
- return None
- global_conf = {}
- for e in raw_global_conf:
- s = util.bytes_to_str(e)
- try:
- k, v = re.split(r'(?<!\\)=', s, 1)
- except ValueError:
- raise RuntimeError("environment setting %r invalid" % s)
- k = k.replace('\\=', '=')
- v = v.replace('\\=', '=')
- global_conf[k] = v
- return global_conf
- class SettingMeta(type):
- def __new__(cls, name, bases, attrs):
- super_new = super().__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"] = staticmethod(attrs["validator"])
- new_class = super_new(cls, name, bases, attrs)
- new_class.fmt_desc(attrs.get("desc", ""))
- KNOWN_SETTINGS.append(new_class)
- return new_class
- def fmt_desc(cls, desc):
- desc = textwrap.dedent(desc).strip()
- setattr(cls, "desc", desc)
- setattr(cls, "short", desc.splitlines()[0])
- class Setting(object):
- name = None
- value = None
- section = None
- cli = None
- validator = None
- type = None
- meta = None
- action = None
- default = None
- short = None
- desc = None
- nargs = None
- const = None
- def __init__(self):
- if self.default is not None:
- self.set(self.default)
- def add_option(self, parser):
- if not self.cli:
- return
- args = tuple(self.cli)
- help_txt = "%s [%s]" % (self.short, self.default)
- help_txt = help_txt.replace("%", "%%")
- kwargs = {
- "dest": self.name,
- "action": self.action or "store",
- "type": self.type or str,
- "default": None,
- "help": help_txt
- }
- if self.meta is not None:
- kwargs['metavar'] = self.meta
- if kwargs["action"] != "store":
- kwargs.pop("type")
- if self.nargs is not None:
- kwargs["nargs"] = self.nargs
- if self.const is not None:
- kwargs["const"] = self.const
- parser.add_argument(*args, **kwargs)
- def copy(self):
- return copy.copy(self)
- def get(self):
- return self.value
- def set(self, val):
- if not callable(self.validator):
- raise TypeError('Invalid validator: %s' % self.name)
- self.value = self.validator(val)
- def __lt__(self, other):
- return (self.section == other.section and
- self.order < other.order)
- __cmp__ = __lt__
- def __repr__(self):
- return "<%s.%s object at %x with value %r>" % (
- self.__class__.__module__,
- self.__class__.__name__,
- id(self),
- self.value,
- )
- Setting = SettingMeta('Setting', (Setting,), {})
- def validate_bool(val):
- if val is None:
- return
- if isinstance(val, bool):
- return val
- if not isinstance(val, str):
- raise TypeError("Invalid type for casting: %s" % val)
- if val.lower().strip() == "true":
- return True
- elif val.lower().strip() == "false":
- return False
- else:
- raise ValueError("Invalid boolean: %s" % val)
- def validate_dict(val):
- if not isinstance(val, dict):
- raise TypeError("Value is not a dictionary: %s " % val)
- return val
- def validate_pos_int(val):
- if not isinstance(val, int):
- val = int(val, 0)
- else:
- # Booleans are ints!
- val = int(val)
- if val < 0:
- raise ValueError("Value must be positive: %s" % val)
- return val
- def validate_ssl_version(val):
- ssl_versions = {}
- for protocol in [p for p in dir(ssl) if p.startswith("PROTOCOL_")]:
- ssl_versions[protocol[9:]] = getattr(ssl, protocol)
- if val in ssl_versions:
- # string matching PROTOCOL_...
- return ssl_versions[val]
- try:
- intval = validate_pos_int(val)
- if intval in ssl_versions.values():
- # positive int matching a protocol int constant
- return intval
- except (ValueError, TypeError):
- # negative integer or not an integer
- # drop this in favour of the more descriptive ValueError below
- pass
- raise ValueError("Invalid ssl_version: %s. Valid options: %s"
- % (val, ', '.join(ssl_versions)))
- def validate_string(val):
- if val is None:
- return None
- if not isinstance(val, str):
- raise TypeError("Not a string: %s" % val)
- return val.strip()
- def validate_file_exists(val):
- if val is None:
- return None
- if not os.path.exists(val):
- raise ValueError("File %s does not exists." % val)
- return val
- def validate_list_string(val):
- if not val:
- return []
- # legacy syntax
- if isinstance(val, str):
- val = [val]
- return [validate_string(v) for v in val]
- def validate_list_of_existing_files(val):
- return [validate_file_exists(v) for v in validate_list_string(val)]
- def validate_string_to_list(val):
- val = validate_string(val)
- if not val:
- return []
- return [v.strip() for v in val.split(",") if v]
- def validate_class(val):
- if inspect.isfunction(val) or inspect.ismethod(val):
- val = val()
- if inspect.isclass(val):
- return val
- return validate_string(val)
- def validate_callable(arity):
- def _validate_callable(val):
- if isinstance(val, str):
- try:
- mod_name, obj_name = val.rsplit(".", 1)
- except ValueError:
- raise TypeError("Value '%s' is not import string. "
- "Format: module[.submodules...].object" % val)
- try:
- mod = __import__(mod_name, fromlist=[obj_name])
- val = getattr(mod, obj_name)
- except ImportError as e:
- raise TypeError(str(e))
- except AttributeError:
- raise TypeError("Can not load '%s' from '%s'"
- "" % (obj_name, mod_name))
- if not callable(val):
- raise TypeError("Value is not callable: %s" % val)
- if arity != -1 and arity != util.get_arity(val):
- raise TypeError("Value must have an arity of: %s" % arity)
- return val
- return _validate_callable
- def validate_user(val):
- if val is None:
- return os.geteuid()
- if isinstance(val, int):
- return val
- elif val.isdigit():
- return int(val)
- else:
- try:
- return pwd.getpwnam(val).pw_uid
- except KeyError:
- raise ConfigError("No such user: '%s'" % val)
- def validate_group(val):
- if val is None:
- return os.getegid()
- if isinstance(val, int):
- return val
- elif val.isdigit():
- return int(val)
- else:
- try:
- return grp.getgrnam(val).gr_gid
- except KeyError:
- raise ConfigError("No such group: '%s'" % val)
- def validate_post_request(val):
- val = validate_callable(-1)(val)
- largs = util.get_arity(val)
- if largs == 4:
- return val
- elif largs == 3:
- return lambda worker, req, env, _r: val(worker, req, env)
- elif largs == 2:
- return lambda worker, req, _e, _r: val(worker, req)
- else:
- raise TypeError("Value must have an arity of: 4")
- def validate_chdir(val):
- # valid if the value is a string
- val = validate_string(val)
- # transform relative paths
- path = os.path.abspath(os.path.normpath(os.path.join(util.getcwd(), val)))
- # test if the path exists
- if not os.path.exists(path):
- raise ConfigError("can't chdir to %r" % val)
- return path
- def validate_hostport(val):
- val = validate_string(val)
- if val is None:
- return None
- elements = val.split(":")
- if len(elements) == 2:
- return (elements[0], int(elements[1]))
- else:
- raise TypeError("Value must consist of: hostname:port")
- def validate_reload_engine(val):
- if val not in reloader_engines:
- raise ConfigError("Invalid reload_engine: %r" % val)
- return val
- def get_default_config_file():
- config_path = os.path.join(os.path.abspath(os.getcwd()),
- 'gunicorn.conf.py')
- if os.path.exists(config_path):
- return config_path
- return None
- class ConfigFile(Setting):
- name = "config"
- section = "Config File"
- cli = ["-c", "--config"]
- meta = "CONFIG"
- validator = validate_string
- default = "./gunicorn.conf.py"
- desc = """\
- The Gunicorn config file.
- A string of the form ``PATH``, ``file:PATH``, or ``python:MODULE_NAME``.
- Only has an effect when specified on the command line or as part of an
- application specific configuration.
- By default, a file named ``gunicorn.conf.py`` will be read from the same
- directory where gunicorn is being run.
- .. versionchanged:: 19.4
- Loading the config from a Python module requires the ``python:``
- prefix.
- """
- class WSGIApp(Setting):
- name = "wsgi_app"
- section = "Config File"
- meta = "STRING"
- validator = validate_string
- default = None
- desc = """\
- A WSGI application path in pattern ``$(MODULE_NAME):$(VARIABLE_NAME)``.
- .. versionadded:: 20.1.0
- """
- class Bind(Setting):
- name = "bind"
- action = "append"
- section = "Server Socket"
- cli = ["-b", "--bind"]
- meta = "ADDRESS"
- validator = validate_list_string
- if 'PORT' in os.environ:
- default = ['0.0.0.0:{0}'.format(os.environ.get('PORT'))]
- else:
- default = ['127.0.0.1:8000']
- desc = """\
- The socket to bind.
- A string of the form: ``HOST``, ``HOST:PORT``, ``unix:PATH``,
- ``fd://FD``. An IP is a valid ``HOST``.
- .. versionchanged:: 20.0
- Support for ``fd://FD`` got added.
- Multiple addresses can be bound. ex.::
- $ gunicorn -b 127.0.0.1:8000 -b [::1]:8000 test:app
- will bind the `test:app` application on localhost both on ipv6
- and ipv4 interfaces.
- If the ``PORT`` environment variable is defined, the default
- is ``['0.0.0.0:$PORT']``. If it is not defined, the default
- is ``['127.0.0.1:8000']``.
- """
- class Backlog(Setting):
- name = "backlog"
- section = "Server Socket"
- cli = ["--backlog"]
- meta = "INT"
- validator = validate_pos_int
- type = int
- default = 2048
- desc = """\
- 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.
- """
- class Workers(Setting):
- name = "workers"
- section = "Worker Processes"
- cli = ["-w", "--workers"]
- meta = "INT"
- validator = validate_pos_int
- type = int
- default = int(os.environ.get("WEB_CONCURRENCY", 1))
- desc = """\
- The number of worker processes 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.
- By default, the value of the ``WEB_CONCURRENCY`` environment variable,
- which is set by some Platform-as-a-Service providers such as Heroku. If
- it is not defined, the default is ``1``.
- """
- class WorkerClass(Setting):
- name = "worker_class"
- section = "Worker Processes"
- cli = ["-k", "--worker-class"]
- meta = "STRING"
- validator = validate_class
- 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 :doc:`design` for information on when
- you might want to choose one of the other worker classes. Required
- libraries may be installed using setuptools' ``extras_require`` feature.
- A string referring to one of the following bundled classes:
- * ``sync``
- * ``eventlet`` - Requires eventlet >= 0.24.1 (or install it via
- ``pip install gunicorn[eventlet]``)
- * ``gevent`` - Requires gevent >= 1.4 (or install it via
- ``pip install gunicorn[gevent]``)
- * ``tornado`` - Requires tornado >= 0.2 (or install it via
- ``pip install gunicorn[tornado]``)
- * ``gthread`` - Python 2 requires the futures package to be installed
- (or install it via ``pip install gunicorn[gthread]``)
- 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:
- ``gunicorn.workers.ggevent.GeventWorker``.
- """
- class WorkerThreads(Setting):
- name = "threads"
- section = "Worker Processes"
- cli = ["--threads"]
- meta = "INT"
- validator = validate_pos_int
- type = int
- default = 1
- desc = """\
- The number of worker threads for handling requests.
- Run each worker with the specified number of threads.
- 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.
- If it is not defined, the default is ``1``.
- This setting only affects the Gthread worker type.
- .. note::
- If you try to use the ``sync`` worker type and set the ``threads``
- setting to more than 1, the ``gthread`` worker type will be used
- instead.
- """
- class WorkerConnections(Setting):
- name = "worker_connections"
- section = "Worker Processes"
- cli = ["--worker-connections"]
- meta = "INT"
- validator = validate_pos_int
- type = int
- default = 1000
- desc = """\
- The maximum number of simultaneous clients.
- This setting only affects the Eventlet and Gevent worker types.
- """
- class MaxRequests(Setting):
- name = "max_requests"
- section = "Worker Processes"
- cli = ["--max-requests"]
- meta = "INT"
- validator = validate_pos_int
- type = int
- 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 worker
- 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.
- """
- class MaxRequestsJitter(Setting):
- name = "max_requests_jitter"
- section = "Worker Processes"
- cli = ["--max-requests-jitter"]
- meta = "INT"
- validator = validate_pos_int
- type = int
- default = 0
- desc = """\
- The maximum jitter to add to the *max_requests* setting.
- The jitter causes the restart per worker to be randomized by
- ``randint(0, max_requests_jitter)``. This is intended to stagger worker
- restarts to avoid all workers restarting at the same time.
- .. versionadded:: 19.2
- """
- class Timeout(Setting):
- name = "timeout"
- section = "Worker Processes"
- cli = ["-t", "--timeout"]
- meta = "INT"
- validator = validate_pos_int
- type = int
- default = 30
- desc = """\
- Workers silent for more than this many seconds are killed and restarted.
- Value is a positive number or 0. Setting it to 0 has the effect of
- infinite timeouts by disabling timeouts for all workers entirely.
- Generally, the default of thirty seconds should suffice. 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 is not tied to the length of time required to handle a
- single request.
- """
- class GracefulTimeout(Setting):
- name = "graceful_timeout"
- section = "Worker Processes"
- cli = ["--graceful-timeout"]
- meta = "INT"
- validator = validate_pos_int
- type = int
- default = 30
- desc = """\
- Timeout for graceful workers restart.
- After receiving a restart signal, workers have this much time to finish
- serving requests. Workers still alive after the timeout (starting from
- the receipt of the restart signal) are force killed.
- """
- class Keepalive(Setting):
- name = "keepalive"
- section = "Worker Processes"
- cli = ["--keep-alive"]
- meta = "INT"
- validator = validate_pos_int
- type = int
- default = 2
- desc = """\
- The number of seconds to wait for requests on a Keep-Alive connection.
- Generally set in the 1-5 seconds range for servers with direct connection
- to the client (e.g. when you don't have separate load balancer). When
- Gunicorn is deployed behind a load balancer, it often makes sense to
- set this to a higher value.
- .. note::
- ``sync`` worker does not support persistent connections and will
- ignore this option.
- """
- class LimitRequestLine(Setting):
- name = "limit_request_line"
- section = "Security"
- cli = ["--limit-request-line"]
- meta = "INT"
- validator = validate_pos_int
- type = int
- default = 4094
- desc = """\
- The maximum size of HTTP request line in bytes.
- This parameter is used to limit the allowed size of a client's
- HTTP request-line. Since the request-line consists of the HTTP
- method, URI, and protocol version, this directive places a
- restriction on the length of a request-URI allowed for a request
- on the server. A server needs this value to be large enough to
- hold any of its resource names, including any information that
- might be passed in the query part of a GET request. Value is a number
- from 0 (unlimited) to 8190.
- This parameter can be used to prevent any DDOS attack.
- """
- class LimitRequestFields(Setting):
- name = "limit_request_fields"
- section = "Security"
- cli = ["--limit-request-fields"]
- meta = "INT"
- validator = validate_pos_int
- type = int
- default = 100
- desc = """\
- Limit the number of HTTP headers fields in a request.
- This parameter is used to limit the number of headers in a request to
- prevent DDOS attack. Used with the *limit_request_field_size* it allows
- more safety. By default this value is 100 and can't be larger than
- 32768.
- """
- class LimitRequestFieldSize(Setting):
- name = "limit_request_field_size"
- section = "Security"
- cli = ["--limit-request-field_size"]
- meta = "INT"
- validator = validate_pos_int
- type = int
- default = 8190
- desc = """\
- Limit the allowed size of an HTTP request header field.
- Value is a positive number or 0. Setting it to 0 will allow unlimited
- header field sizes.
- .. warning::
- Setting this parameter to a very high or unlimited value can open
- up for DDOS attacks.
- """
- class Reload(Setting):
- name = "reload"
- section = 'Debugging'
- cli = ['--reload']
- validator = validate_bool
- action = 'store_true'
- default = False
- desc = '''\
- Restart workers when code changes.
- This setting is intended for development. It will cause workers to be
- restarted whenever application code changes.
- The reloader is incompatible with application preloading. When using a
- paste configuration be sure that the server block does not import any
- application code or the reload will not work as designed.
- The default behavior is to attempt inotify with a fallback to file
- system polling. Generally, inotify should be preferred if available
- because it consumes less system resources.
- .. note::
- In order to use the inotify reloader, you must have the ``inotify``
- package installed.
- '''
- class ReloadEngine(Setting):
- name = "reload_engine"
- section = "Debugging"
- cli = ["--reload-engine"]
- meta = "STRING"
- validator = validate_reload_engine
- default = "auto"
- desc = """\
- The implementation that should be used to power :ref:`reload`.
- Valid engines are:
- * ``'auto'``
- * ``'poll'``
- * ``'inotify'`` (requires inotify)
- .. versionadded:: 19.7
- """
- class ReloadExtraFiles(Setting):
- name = "reload_extra_files"
- action = "append"
- section = "Debugging"
- cli = ["--reload-extra-file"]
- meta = "FILES"
- validator = validate_list_of_existing_files
- default = []
- desc = """\
- Extends :ref:`reload` option to also watch and reload on additional files
- (e.g., templates, configurations, specifications, etc.).
- .. versionadded:: 19.8
- """
- class Spew(Setting):
- name = "spew"
- section = "Debugging"
- cli = ["--spew"]
- validator = validate_bool
- action = "store_true"
- default = False
- desc = """\
- Install a trace function that spews every line executed by the server.
- This is the nuclear option.
- """
- class ConfigCheck(Setting):
- name = "check_config"
- section = "Debugging"
- cli = ["--check-config"]
- validator = validate_bool
- action = "store_true"
- default = False
- desc = """\
- Check the configuration and exit. The exit status is 0 if the
- configuration is correct, and 1 if the configuration is incorrect.
- """
- class PrintConfig(Setting):
- name = "print_config"
- section = "Debugging"
- cli = ["--print-config"]
- validator = validate_bool
- action = "store_true"
- default = False
- desc = """\
- Print the configuration settings as fully resolved. Implies :ref:`check-config`.
- """
- class PreloadApp(Setting):
- name = "preload_app"
- section = "Server Mechanics"
- cli = ["--preload"]
- validator = validate_bool
- action = "store_true"
- 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
- restarting workers.
- """
- class Sendfile(Setting):
- name = "sendfile"
- section = "Server Mechanics"
- cli = ["--no-sendfile"]
- validator = validate_bool
- action = "store_const"
- const = False
- desc = """\
- Disables the use of ``sendfile()``.
- If not set, the value of the ``SENDFILE`` environment variable is used
- to enable or disable its usage.
- .. versionadded:: 19.2
- .. versionchanged:: 19.4
- Swapped ``--sendfile`` with ``--no-sendfile`` to actually allow
- disabling.
- .. versionchanged:: 19.6
- added support for the ``SENDFILE`` environment variable
- """
- class ReusePort(Setting):
- name = "reuse_port"
- section = "Server Mechanics"
- cli = ["--reuse-port"]
- validator = validate_bool
- action = "store_true"
- default = False
- desc = """\
- Set the ``SO_REUSEPORT`` flag on the listening socket.
- .. versionadded:: 19.8
- """
- class Chdir(Setting):
- name = "chdir"
- section = "Server Mechanics"
- cli = ["--chdir"]
- validator = validate_chdir
- default = util.getcwd()
- desc = """\
- Change directory to specified directory before loading apps.
- """
- class Daemon(Setting):
- name = "daemon"
- section = "Server Mechanics"
- cli = ["-D", "--daemon"]
- validator = validate_bool
- action = "store_true"
- default = False
- desc = """\
- Daemonize the Gunicorn process.
- Detaches the server from the controlling terminal and enters the
- background.
- """
- class Env(Setting):
- name = "raw_env"
- action = "append"
- section = "Server Mechanics"
- cli = ["-e", "--env"]
- meta = "ENV"
- validator = validate_list_string
- default = []
- desc = """\
- Set environment variables in the execution environment.
- Should be a list of strings in the ``key=value`` format.
- For example on the command line:
- .. code-block:: console
- $ gunicorn -b 127.0.0.1:8000 --env FOO=1 test:app
- Or in the configuration file:
- .. code-block:: python
- raw_env = ["FOO=1"]
- """
- class Pidfile(Setting):
- name = "pidfile"
- section = "Server Mechanics"
- cli = ["-p", "--pid"]
- meta = "FILE"
- validator = validate_string
- default = None
- desc = """\
- A filename to use for the PID file.
- If not set, no PID file will be written.
- """
- class WorkerTmpDir(Setting):
- name = "worker_tmp_dir"
- section = "Server Mechanics"
- cli = ["--worker-tmp-dir"]
- meta = "DIR"
- validator = validate_string
- default = None
- desc = """\
- A directory to use for the worker heartbeat temporary file.
- If not set, the default temporary directory will be used.
- .. note::
- The current heartbeat system involves calling ``os.fchmod`` on
- temporary file handlers and may block a worker for arbitrary time
- if the directory is on a disk-backed filesystem.
- See :ref:`blocking-os-fchmod` for more detailed information
- and a solution for avoiding this problem.
- """
- class User(Setting):
- name = "user"
- section = "Server Mechanics"
- cli = ["-u", "--user"]
- meta = "USER"
- validator = validate_user
- 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.
- """
- class Group(Setting):
- name = "group"
- section = "Server Mechanics"
- cli = ["-g", "--group"]
- meta = "GROUP"
- validator = validate_group
- 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.
- """
- class Umask(Setting):
- name = "umask"
- section = "Server Mechanics"
- cli = ["-m", "--umask"]
- meta = "INT"
- validator = validate_pos_int
- type = auto_int
- 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)
- """
- class Initgroups(Setting):
- name = "initgroups"
- section = "Server Mechanics"
- cli = ["--initgroups"]
- validator = validate_bool
- action = 'store_true'
- default = False
- desc = """\
- If true, set the worker process's group access list with all of the
- groups of which the specified username is a member, plus the specified
- group id.
- .. versionadded:: 19.7
- """
- class TmpUploadDir(Setting):
- name = "tmp_upload_dir"
- section = "Server Mechanics"
- meta = "DIR"
- validator = validate_string
- 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.
- """
- class SecureSchemeHeader(Setting):
- name = "secure_scheme_headers"
- section = "Server Mechanics"
- validator = validate_dict
- default = {
- "X-FORWARDED-PROTOCOL": "ssl",
- "X-FORWARDED-PROTO": "https",
- "X-FORWARDED-SSL": "on"
- }
- desc = """\
- A dictionary containing headers and values that the front-end proxy
- uses to indicate HTTPS requests. If the source IP is permitted by
- ``forwarded-allow-ips`` (below), *and* at least one request header matches
- a key-value pair listed in this dictionary, then Gunicorn will set
- ``wsgi.url_scheme`` to ``https``, so your application can tell that the
- request is secure.
- If the other headers listed in this dictionary are not present in the request, they will be ignored,
- but if the other headers are present and do not match the provided values, then
- the request will fail to parse. See the note below for more detailed examples of this behaviour.
- The dictionary should map upper-case header names to exact string
- values. The value comparisons are case-sensitive, unlike the header
- names, so make sure they're exactly what your front-end proxy sends
- when handling HTTPS requests.
- It is important that your front-end proxy configuration ensures that
- the headers defined here can not be passed directly from the client.
- """
- class ForwardedAllowIPS(Setting):
- name = "forwarded_allow_ips"
- section = "Server Mechanics"
- cli = ["--forwarded-allow-ips"]
- meta = "STRING"
- validator = validate_string_to_list
- default = os.environ.get("FORWARDED_ALLOW_IPS", "127.0.0.1")
- desc = """\
- Front-end's IPs from which allowed to handle set secure headers.
- (comma separate).
- Set to ``*`` to disable checking of Front-end IPs (useful for setups
- where you don't know in advance the IP address of Front-end, but
- you still trust the environment).
- By default, the value of the ``FORWARDED_ALLOW_IPS`` environment
- variable. If it is not defined, the default is ``"127.0.0.1"``.
-
- .. note::
-
- The interplay between the request headers, the value of ``forwarded_allow_ips``, and the value of
- ``secure_scheme_headers`` is complex. Various scenarios are documented below to further elaborate. In each case, we
- have a request from the remote address 134.213.44.18, and the default value of ``secure_scheme_headers``:
-
- .. code::
-
- secure_scheme_headers = {
- 'X-FORWARDED-PROTOCOL': 'ssl',
- 'X-FORWARDED-PROTO': 'https',
- 'X-FORWARDED-SSL': 'on'
- }
-
-
- .. list-table::
- :header-rows: 1
- :align: center
- :widths: auto
-
- * - ``forwarded-allow-ips``
- - Secure Request Headers
- - Result
- - Explanation
- * - .. code::
-
- ["127.0.0.1"]
- - .. code::
-
- X-Forwarded-Proto: https
- - .. code::
-
- wsgi.url_scheme = "http"
- - IP address was not allowed
- * - .. code::
-
- "*"
- - <none>
- - .. code::
-
- wsgi.url_scheme = "http"
- - IP address allowed, but no secure headers provided
- * - .. code::
-
- "*"
- - .. code::
-
- X-Forwarded-Proto: https
- - .. code::
-
- wsgi.url_scheme = "https"
- - IP address allowed, one request header matched
- * - .. code::
-
- ["134.213.44.18"]
- - .. code::
-
- X-Forwarded-Ssl: on
- X-Forwarded-Proto: http
- - ``InvalidSchemeHeaders()`` raised
- - IP address allowed, but the two secure headers disagreed on if HTTPS was used
-
- """
- class AccessLog(Setting):
- name = "accesslog"
- section = "Logging"
- cli = ["--access-logfile"]
- meta = "FILE"
- validator = validate_string
- default = None
- desc = """\
- The Access log file to write to.
- ``'-'`` means log to stdout.
- """
- class DisableRedirectAccessToSyslog(Setting):
- name = "disable_redirect_access_to_syslog"
- section = "Logging"
- cli = ["--disable-redirect-access-to-syslog"]
- validator = validate_bool
- action = 'store_true'
- default = False
- desc = """\
- Disable redirect access logs to syslog.
- .. versionadded:: 19.8
- """
- class AccessLogFormat(Setting):
- name = "access_log_format"
- section = "Logging"
- 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"'
- desc = """\
- The access log format.
- =========== ===========
- Identifier Description
- =========== ===========
- h remote address
- l ``'-'``
- u user name
- t date of the request
- r status line (e.g. ``GET / HTTP/1.1``)
- m request method
- U URL path without query string
- q query string
- H protocol
- s status
- B response length
- b response length or ``'-'`` (CLF format)
- f referer
- a user agent
- T request time in seconds
- M request time in milliseconds
- D request time in microseconds
- L request time in decimal seconds
- p process ID
- {header}i request header
- {header}o response header
- {variable}e environment variable
- =========== ===========
- Use lowercase for header and environment variable names, and put
- ``{...}x`` names inside ``%(...)s``. For example::
- %({x-forwarded-for}i)s
- """
- class ErrorLog(Setting):
- name = "errorlog"
- section = "Logging"
- cli = ["--error-logfile", "--log-file"]
- meta = "FILE"
- validator = validate_string
- default = '-'
- desc = """\
- The Error log file to write to.
- Using ``'-'`` for FILE makes gunicorn log to stderr.
- .. versionchanged:: 19.2
- Log to stderr by default.
- """
- class Loglevel(Setting):
- name = "loglevel"
- section = "Logging"
- cli = ["--log-level"]
- meta = "LEVEL"
- validator = validate_string
- default = "info"
- desc = """\
- The granularity of Error log outputs.
- Valid level names are:
- * ``'debug'``
- * ``'info'``
- * ``'warning'``
- * ``'error'``
- * ``'critical'``
- """
- class CaptureOutput(Setting):
- name = "capture_output"
- section = "Logging"
- cli = ["--capture-output"]
- validator = validate_bool
- action = 'store_true'
- default = False
- desc = """\
- Redirect stdout/stderr to specified file in :ref:`errorlog`.
- .. versionadded:: 19.6
- """
- class LoggerClass(Setting):
- name = "logger_class"
- section = "Logging"
- cli = ["--logger-class"]
- meta = "STRING"
- validator = validate_class
- default = "gunicorn.glogging.Logger"
- desc = """\
- The logger you want to use to log events in Gunicorn.
- The default class (``gunicorn.glogging.Logger``) handles most
- normal usages in logging. It provides error and access logging.
- You can provide your own logger by giving Gunicorn a Python path to a
- class that quacks like ``gunicorn.glogging.Logger``.
- """
- class LogConfig(Setting):
- name = "logconfig"
- section = "Logging"
- cli = ["--log-config"]
- meta = "FILE"
- validator = validate_string
- default = None
- desc = """\
- The log config file to use.
- Gunicorn uses the standard Python logging module's Configuration
- file format.
- """
- class LogConfigDict(Setting):
- name = "logconfig_dict"
- section = "Logging"
- validator = validate_dict
- default = {}
- desc = """\
- The log config dictionary to use, using the standard Python
- logging module's dictionary configuration format. This option
- takes precedence over the :ref:`logconfig` option, which uses the
- older file configuration format.
- Format: https://docs.python.org/3/library/logging.config.html#logging.config.dictConfig
- .. versionadded:: 19.8
- """
- class SyslogTo(Setting):
- name = "syslog_addr"
- section = "Logging"
- cli = ["--log-syslog-to"]
- meta = "SYSLOG_ADDR"
- validator = validate_string
- if PLATFORM == "darwin":
- default = "unix:///var/run/syslog"
- elif PLATFORM in ('freebsd', 'dragonfly', ):
- default = "unix:///var/run/log"
- elif PLATFORM == "openbsd":
- default = "unix:///dev/log"
- else:
- default = "udp://localhost:514"
- desc = """\
- Address to send syslog messages.
- Address is a string of the form:
- * ``unix://PATH#TYPE`` : for unix domain socket. ``TYPE`` can be ``stream``
- for the stream driver or ``dgram`` for the dgram driver.
- ``stream`` is the default.
- * ``udp://HOST:PORT`` : for UDP sockets
- * ``tcp://HOST:PORT`` : for TCP sockets
- """
- class Syslog(Setting):
- name = "syslog"
- section = "Logging"
- cli = ["--log-syslog"]
- validator = validate_bool
- action = 'store_true'
- default = False
- desc = """\
- Send *Gunicorn* logs to syslog.
- .. versionchanged:: 19.8
- You can now disable sending access logs by using the
- :ref:`disable-redirect-access-to-syslog` setting.
- """
- class SyslogPrefix(Setting):
- name = "syslog_prefix"
- section = "Logging"
- cli = ["--log-syslog-prefix"]
- meta = "SYSLOG_PREFIX"
- validator = validate_string
- default = None
- desc = """\
- Makes Gunicorn use the parameter as program-name in the syslog entries.
- All entries will be prefixed by ``gunicorn.<prefix>``. By default the
- program name is the name of the process.
- """
- class SyslogFacility(Setting):
- name = "syslog_facility"
- section = "Logging"
- cli = ["--log-syslog-facility"]
- meta = "SYSLOG_FACILITY"
- validator = validate_string
- default = "user"
- desc = """\
- Syslog facility name
- """
- class EnableStdioInheritance(Setting):
- name = "enable_stdio_inheritance"
- section = "Logging"
- cli = ["-R", "--enable-stdio-inheritance"]
- validator = validate_bool
- default = False
- action = "store_true"
- desc = """\
- Enable stdio inheritance.
- Enable inheritance for stdio file descriptors in daemon mode.
- Note: To disable the Python stdout buffering, you can to set the user
- environment variable ``PYTHONUNBUFFERED`` .
- """
- # statsD monitoring
- class StatsdHost(Setting):
- name = "statsd_host"
- section = "Logging"
- cli = ["--statsd-host"]
- meta = "STATSD_ADDR"
- default = None
- validator = validate_hostport
- desc = """\
- ``host:port`` of the statsd server to log to.
- .. versionadded:: 19.1
- """
- # Datadog Statsd (dogstatsd) tags. https://docs.datadoghq.com/developers/dogstatsd/
- class DogstatsdTags(Setting):
- name = "dogstatsd_tags"
- section = "Logging"
- cli = ["--dogstatsd-tags"]
- meta = "DOGSTATSD_TAGS"
- default = ""
- validator = validate_string
- desc = """\
- A comma-delimited list of datadog statsd (dogstatsd) tags to append to
- statsd metrics.
- .. versionadded:: 20
- """
- class StatsdPrefix(Setting):
- name = "statsd_prefix"
- section = "Logging"
- cli = ["--statsd-prefix"]
- meta = "STATSD_PREFIX"
- default = ""
- validator = validate_string
- desc = """\
- Prefix to use when emitting statsd metrics (a trailing ``.`` is added,
- if not provided).
- .. versionadded:: 19.2
- """
- class Procname(Setting):
- name = "proc_name"
- section = "Process Naming"
- cli = ["-n", "--name"]
- meta = "STRING"
- validator = validate_string
- 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.
- If not set, the *default_proc_name* setting will be used.
- """
- class DefaultProcName(Setting):
- name = "default_proc_name"
- section = "Process Naming"
- validator = validate_string
- default = "gunicorn"
- desc = """\
- Internal setting that is adjusted for each type of application.
- """
- class PythonPath(Setting):
- name = "pythonpath"
- section = "Server Mechanics"
- cli = ["--pythonpath"]
- meta = "STRING"
- validator = validate_string
- default = None
- desc = """\
- A comma-separated list of directories to add to the Python path.
- e.g.
- ``'/home/djangoprojects/myproject,/home/python/mylibrary'``.
- """
- class Paste(Setting):
- name = "paste"
- section = "Server Mechanics"
- cli = ["--paste", "--paster"]
- meta = "STRING"
- validator = validate_string
- default = None
- desc = """\
- Load a PasteDeploy config file. The argument may contain a ``#``
- symbol followed by the name of an app section from the config file,
- e.g. ``production.ini#admin``.
- At this time, using alternate server blocks is not supported. Use the
- command line arguments to control server configuration instead.
- """
- class OnStarting(Setting):
- name = "on_starting"
- section = "Server Hooks"
- validator = validate_callable(1)
- type = callable
- def on_starting(server):
- pass
- 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.
- """
- class OnReload(Setting):
- name = "on_reload"
- section = "Server Hooks"
- validator = validate_callable(1)
- type = callable
- def on_reload(server):
- pass
- default = staticmethod(on_reload)
- desc = """\
- Called to recycle workers during a reload via SIGHUP.
- The callable needs to accept a single instance variable for the Arbiter.
- """
- class WhenReady(Setting):
- name = "when_ready"
- section = "Server Hooks"
- validator = validate_callable(1)
- type = callable
- def when_ready(server):
- pass
- default = staticmethod(when_ready)
- desc = """\
- Called just after the server is started.
- The callable needs to accept a single instance variable for the Arbiter.
- """
- class Prefork(Setting):
- name = "pre_fork"
- section = "Server Hooks"
- validator = validate_callable(2)
- type = callable
- def pre_fork(server, worker):
- pass
- 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"
- validator = validate_callable(2)
- type = callable
- def post_fork(server, worker):
- pass
- 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.
- """
- class PostWorkerInit(Setting):
- name = "post_worker_init"
- section = "Server Hooks"
- validator = validate_callable(1)
- type = callable
- def post_worker_init(worker):
- pass
- default = staticmethod(post_worker_init)
- desc = """\
- Called just after a worker has initialized the application.
- The callable needs to accept one instance variable for the initialized
- Worker.
- """
- class WorkerInt(Setting):
- name = "worker_int"
- section = "Server Hooks"
- validator = validate_callable(1)
- type = callable
- def worker_int(worker):
- pass
- default = staticmethod(worker_int)
- desc = """\
- Called just after a worker exited on SIGINT or SIGQUIT.
- The callable needs to accept one instance variable for the initialized
- Worker.
- """
- class WorkerAbort(Setting):
- name = "worker_abort"
- section = "Server Hooks"
- validator = validate_callable(1)
- type = callable
- def worker_abort(worker):
- pass
- default = staticmethod(worker_abort)
- desc = """\
- Called when a worker received the SIGABRT signal.
- This call generally happens on timeout.
- The callable needs to accept one instance variable for the initialized
- Worker.
- """
- class PreExec(Setting):
- name = "pre_exec"
- section = "Server Hooks"
- validator = validate_callable(1)
- type = callable
- def pre_exec(server):
- pass
- 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.
- """
- class PreRequest(Setting):
- name = "pre_request"
- section = "Server Hooks"
- validator = validate_callable(2)
- type = callable
- def pre_request(worker, req):
- worker.log.debug("%s %s" % (req.method, req.path))
- 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.
- """
- class PostRequest(Setting):
- name = "post_request"
- section = "Server Hooks"
- validator = validate_post_request
- type = callable
- def post_request(worker, req, environ, resp):
- pass
- default = staticmethod(post_request)
- desc = """\
- Called after a worker processes the request.
- The callable needs to accept two instance variables for the Worker and
- the Request.
- """
- class ChildExit(Setting):
- name = "child_exit"
- section = "Server Hooks"
- validator = validate_callable(2)
- type = callable
- def child_exit(server, worker):
- pass
- default = staticmethod(child_exit)
- desc = """\
- Called just after a worker has been exited, in the master process.
- The callable needs to accept two instance variables for the Arbiter and
- the just-exited Worker.
- .. versionadded:: 19.7
- """
- class WorkerExit(Setting):
- name = "worker_exit"
- section = "Server Hooks"
- validator = validate_callable(2)
- type = callable
- def worker_exit(server, worker):
- pass
- default = staticmethod(worker_exit)
- desc = """\
- Called just after a worker has been exited, in the worker process.
- The callable needs to accept two instance variables for the Arbiter and
- the just-exited Worker.
- """
- class NumWorkersChanged(Setting):
- name = "nworkers_changed"
- section = "Server Hooks"
- validator = validate_callable(3)
- type = callable
- def nworkers_changed(server, new_value, old_value):
- pass
- default = staticmethod(nworkers_changed)
- desc = """\
- Called just after *num_workers* has been changed.
- The callable needs to accept an instance variable of the Arbiter and
- two integers of number of workers after and before change.
- If the number of workers is set for the first time, *old_value* would
- be ``None``.
- """
- class OnExit(Setting):
- name = "on_exit"
- section = "Server Hooks"
- validator = validate_callable(1)
- def on_exit(server):
- pass
- default = staticmethod(on_exit)
- desc = """\
- Called just before exiting Gunicorn.
- The callable needs to accept a single instance variable for the Arbiter.
- """
- class ProxyProtocol(Setting):
- name = "proxy_protocol"
- section = "Server Mechanics"
- cli = ["--proxy-protocol"]
- validator = validate_bool
- default = False
- action = "store_true"
- desc = """\
- Enable detect PROXY protocol (PROXY mode).
- Allow using HTTP and Proxy together. It may be useful for work with
- stunnel as HTTPS frontend and Gunicorn as HTTP server.
- PROXY protocol: http://haproxy.1wt.eu/download/1.5/doc/proxy-protocol.txt
- Example for stunnel config::
- [https]
- protocol = proxy
- accept = 443
- connect = 80
- cert = /etc/ssl/certs/stunnel.pem
- key = /etc/ssl/certs/stunnel.key
- """
- class ProxyAllowFrom(Setting):
- name = "proxy_allow_ips"
- section = "Server Mechanics"
- cli = ["--proxy-allow-from"]
- validator = validate_string_to_list
- default = "127.0.0.1"
- desc = """\
- Front-end's IPs from which allowed accept proxy requests (comma separate).
- Set to ``*`` to disable checking of Front-end IPs (useful for setups
- where you don't know in advance the IP address of Front-end, but
- you still trust the environment)
- """
- class KeyFile(Setting):
- name = "keyfile"
- section = "SSL"
- cli = ["--keyfile"]
- meta = "FILE"
- validator = validate_string
- default = None
- desc = """\
- SSL key file
- """
- class CertFile(Setting):
- name = "certfile"
- section = "SSL"
- cli = ["--certfile"]
- meta = "FILE"
- validator = validate_string
- default = None
- desc = """\
- SSL certificate file
- """
- class SSLVersion(Setting):
- name = "ssl_version"
- section = "SSL"
- cli = ["--ssl-version"]
- validator = validate_ssl_version
- if hasattr(ssl, "PROTOCOL_TLS"):
- default = ssl.PROTOCOL_TLS
- else:
- default = ssl.PROTOCOL_SSLv23
- desc = """\
- SSL version to use (see stdlib ssl module's)
- .. versionchanged:: 20.0.1
- The default value has been changed from ``ssl.PROTOCOL_SSLv23`` to
- ``ssl.PROTOCOL_TLS`` when Python >= 3.6 .
- """
- default = ssl.PROTOCOL_SSLv23
- desc = """\
- SSL version to use.
- ============= ============
- --ssl-version Description
- ============= ============
- SSLv3 SSLv3 is not-secure and is strongly discouraged.
- SSLv23 Alias for TLS. Deprecated in Python 3.6, use TLS.
- TLS Negotiate highest possible version between client/server.
- Can yield SSL. (Python 3.6+)
- TLSv1 TLS 1.0
- TLSv1_1 TLS 1.1 (Python 3.4+)
- TLSv1_2 TLS 1.2 (Python 3.4+)
- TLS_SERVER Auto-negotiate the highest protocol version like TLS,
- but only support server-side SSLSocket connections.
- (Python 3.6+)
- ============= ============
- .. versionchanged:: 19.7
- The default value has been changed from ``ssl.PROTOCOL_TLSv1`` to
- ``ssl.PROTOCOL_SSLv23``.
- .. versionchanged:: 20.0
- This setting now accepts string names based on ``ssl.PROTOCOL_``
- constants.
- """
- class CertReqs(Setting):
- name = "cert_reqs"
- section = "SSL"
- cli = ["--cert-reqs"]
- validator = validate_pos_int
- default = ssl.CERT_NONE
- desc = """\
- Whether client certificate is required (see stdlib ssl module's)
- """
- class CACerts(Setting):
- name = "ca_certs"
- section = "SSL"
- cli = ["--ca-certs"]
- meta = "FILE"
- validator = validate_string
- default = None
- desc = """\
- CA certificates file
- """
- class SuppressRaggedEOFs(Setting):
- name = "suppress_ragged_eofs"
- section = "SSL"
- cli = ["--suppress-ragged-eofs"]
- action = "store_true"
- default = True
- validator = validate_bool
- desc = """\
- Suppress ragged EOFs (see stdlib ssl module's)
- """
- class DoHandshakeOnConnect(Setting):
- name = "do_handshake_on_connect"
- section = "SSL"
- cli = ["--do-handshake-on-connect"]
- validator = validate_bool
- action = "store_true"
- default = False
- desc = """\
- Whether to perform SSL handshake on socket connect (see stdlib ssl module's)
- """
- class Ciphers(Setting):
- name = "ciphers"
- section = "SSL"
- cli = ["--ciphers"]
- validator = validate_string
- default = None
- desc = """\
- SSL Cipher suite to use, in the format of an OpenSSL cipher list.
- By default we use the default cipher list from Python's ``ssl`` module,
- which contains ciphers considered strong at the time of each Python
- release.
- As a recommended alternative, the Open Web App Security Project (OWASP)
- offers `a vetted set of strong cipher strings rated A+ to C-
- <https://www.owasp.org/index.php/TLS_Cipher_String_Cheat_Sheet>`_.
- OWASP provides details on user-agent compatibility at each security level.
- See the `OpenSSL Cipher List Format Documentation
- <https://www.openssl.org/docs/manmaster/man1/ciphers.html#CIPHER-LIST-FORMAT>`_
- for details on the format of an OpenSSL cipher list.
- """
- class PasteGlobalConf(Setting):
- name = "raw_paste_global_conf"
- action = "append"
- section = "Server Mechanics"
- cli = ["--paste-global"]
- meta = "CONF"
- validator = validate_list_string
- default = []
- desc = """\
- Set a PasteDeploy global config variable in ``key=value`` form.
- The option can be specified multiple times.
- The variables are passed to the the PasteDeploy entrypoint. Example::
- $ gunicorn -b 127.0.0.1:8000 --paste development.ini --paste-global FOO=1 --paste-global BAR=2
- .. versionadded:: 19.7
- """
- class StripHeaderSpaces(Setting):
- name = "strip_header_spaces"
- section = "Server Mechanics"
- cli = ["--strip-header-spaces"]
- validator = validate_bool
- action = "store_true"
- default = False
- desc = """\
- Strip spaces present between the header name and the the ``:``.
- This is known to induce vulnerabilities and is not compliant with the HTTP/1.1 standard.
- See https://portswigger.net/research/http-desync-attacks-request-smuggling-reborn.
- Use with care and only if necessary.
- """
|