Welcome to my public account [Python programming and Practice] to learn more

Flask’s built-in WSGI, as anyone who has used the Python Web framework knows, is low in performance and does not support high concurrency. Nginx + Gunicorn is only suitable for your development and debugging, so generally use Nginx + Gunicorn online to get better performance and higher security!

Gunicorn is a Python Wsgi HTTP server that runs only on Unix systems.

1. Gunicorn installation

Note that Gunicorn cannot be used in Windows

pip install gunicorn

Let’s say we have a py file for the following app

from flask import Flask  
  
app = Flask(__name__)  

  
@app.route('/')  
def index(a):  
    return 'hello world! ' 

if __name__ == '__main__':  
    app.run()   
Copy the code

So how do we start with Gunicorn in Flask’s project directory? The command is as follows:

gunicorn -w 4 -b 0.0. 0. 0:8000 app:app
Copy the code

Where: the first app refers to the app.py file; Flask(name) = flask (name)

2. Gunicorn parameter description

Gunicorn -h has a lot of configuration items. I have listed them for your reference:

-c CONFIG: CONFIG, which is the path of the configuration file. Production environment use; -b ADDRESS: ADDRESS, where IP and port are bound to the running host. -w INT, --workers INT Specifies the number of workers to process. The value is a positive integer. The default value is 1. -k STRTING, --worker-class STRTING Specifies the working mode to use, which defaults to sync asynchronously. You can download eventlet and gEvent and specify --threads INT: Number of worker threads that process requests, using a specified number of threads to run each worker. Is a positive integer. The default value is 1. --worker-connections INT: maximum number of concurrent clients. By default, this value is 1000. Backlog int: The maximum number of pending connections, i.e. the number of customers waiting for service. The default value is 2048. -p FILE, --pid FILE: specifies the FILE name of the PID FILE. If this parameter is not set, the PID FILE will not be created. --access-logfile FILE: specifies the access log directory to be written. Access log format to be written --error-logfile FILE, --log-file FILE: directory to which error logs are to be written. --log-level level: indicates the output level of error logs. --limit-request-line INT: specifies the maximum size of HTTP header lines. This parameter is used to limit the allowed size of HTTP request lines. By default, the value is 4094. The value ranges from 0 to 8190. --limit-request-fields INT: limits the number of request header fields in an HTTP request. This field is used to limit the number of request header fields to prevent DDOS attacks. By default, this value is 100 and cannot exceed 32768 --limit-request-field-size INT: limits the size of request headers in HTTP requests. By default, this value is 8190 bytes. -t INT, --timeout INT: After this number of seconds, the work will be killed and restarted. Generally set to 30 seconds; --daemon: whether to start as a daemon. Default is false. --chdir: switch directory before loading the application; --graceful-timeout INT: By default, this value is 30. Any work that is still alive after a timeout (since the restart signal is received) is forcibly killed. Generally use the default; --keep-alive INT: number of seconds to wait for a request on a keep-alive connection. Default value is 2. Generally set between 1 and 5 seconds. --reload: The default is False. This setting is used for development and causes work to restart whenever an application changes. --spew: prints every statement executed by the server. The default is False. This selection is atomic, that is, print all or none; --check-config: displays the current configuration. The default value is False, that is, display. -e ENV, -- ENV ENV: Sets environment variables.Copy the code

Do you think gunicorn has a lot of metrics? Typing such a large number of commands during deployment can be a mistake even for someone familiar with the parameters! So, is there a more convenient way? That, of course, is to boot as a configuration file!

3. Start as a configuration file

The configuration file is gunicorn.conf.py. The code is as follows:

# Number of parallel working processes
workers = 4

# number of threads per worker
threads = 2

# port 5000
bind = '0.0.0.0:5000'

Set up the supervisor to manage the process
daemon = 'false'

# Work mode coroutine
worker_class = 'gevent'

# set maximum concurrency
worker_connections = 2000

Set the process file directory
pidfile = '/var/run/gunicorn.pid'

Set access log and error log paths
accesslog = "log/access.log"
errorlog = "log/debug.log"
loglevel = "debug"

Set the logging level
loglevel = 'warning'
Copy the code

The comments in the code are quite detailed, but there are a few points to note:

1. Log

The output directory of log files is specified in the configuration file. Note the following:

  • The log directory is required to exist. If it does not exist, the startup will report an error
  • Accesslogs are access logs that can be formatted using access_log_format
  • Loglevel Controls the errorLog information level

However, the logging module is recommended for logging management

2. workers

  • Worker_class refers to the mode type of each worker process started. The default is sync mode, which uses gEvent mode, a highly concurrent library in Python
  • Workers refers to the number of parallel working processes. In the above configuration file, it refers to the number of cpus on the server. It is important to note that this number is not as high as possible, because we also need to pay attention to the performance of the deployment machine and can not open unlimited. It is generally determined according to the number of CPU cores of the server!
workers = multiprocessing * cpu_count() * 2 + 1
Copy the code

With the configuration file in place, the startup command is simple. The gunicorn command is as follows

gunicorn -c gunicorn.conf app:app
Copy the code

Thank you for your attention!