Ubuntu 安装 Django(Python) with Nginx, Gunicorn, virtualenv, supervisor and PostgreSQL

2016年11月8日

django 部署,gunicorn、virtualenv、nginx

 

1. Update Your System

 

  1. apt-get update
  2. apt-get upgrade
  3. apt-get  install  aptitude

 

2. Install and create application database  这个我没有测试我使用的是 mysql

 

  1. apt-get install postgresql postgresql-contrib
  2. su – postgres
  3. postgres@django:~$createuser –interactive -P
  4. Enter name of role to add: hello_django
  5. Enter password for new role:
  6. Enter it again:
  7. Shall the new role be a superuser? (y/n) n
  8. Shall the new role be allowed to create databases? (y/n) n
  9. Shall the new role be allowed to create more new roles? (y/n) n
  10. postgres@django:~$createdb –owner hello_django hello
  11. postgres@django:~$logout

 

3. Create Application User

 

  1. groupadd webapps
  2. useradd -g webapps -s /bin/bash -d /webapps/hello_django hello
  3. useradd -g webapps -s /bin/bash -d /webapps/goodbye_django goodbye

 

4. Install Virtualenv and create environment for your application

 

  1. apt-get install python-virtualenv libmysqlclient-dev
  2. apt-get install python-dev build-essential libssl-dev libffi-dev libxml2-dev libxslt1-dev zlib1g-dev  g++ libpq-dev
  3. mkdir -p /webapps/hello_django/
  4. mkdir -p /webapps/goodbye_django/
  5. chown hello:webapps /webapps/hello_django/
  6. chown goodbye:webapps /webapps/goodbye_django/
  7. As the application user create a virtual Python environment in the application directory:
  8. su – hello
  9. hello@django:~$ cd /webapps/hello_django/
  10. hello@django:~$ virtualenv .
  11. New python executable in hello_django/bin/python
  12. Installing distribute…………..done.
  13. Installing pip…………………done.
  14. hello@django:~$ source bin/activate
  15. (hello_django)hello@django:~$
  16. Your environment is now activated and you can proceed to install Django inside it.
  17. (hello_django)hello@django:~$ pip install django
  18. Downloading/unpacking django
  19. (…)
  20. Installing collected packages: django
  21. (…)
  22. Successfully installed django
  23. Cleaning up…
  24. Your environment with Django should be ready to use. Go ahead and create an empty Django project.
  25. (hello_django)hello@django:~$ django-admin.py startproject hello
  26. You can test it by running the development server:
  27. (hello_django)hello@django:~$ cd hello
  28. (hello_django)hello@django:~$ python manage.py runserver 0.0.0.0:8000 (或者使用IP)
  29. Validating models…
  30. 0 errors found
  31. June 09, 2013 – 06:12:00
  32. Django version 1.5.1, using settings 'hello.settings'
  33. Development server is running at http://0.0.0.0:8000/
  34. Quit the server with CONTROL-C.
  35. You should now be able to access your development server from http://IP:8000

 

5. Allowing other users write access to the application directory

Your application will run as the user hello, who owns the entire application directory. If you want regular user to be able to change application files, you can set the group owner of the directory to users and give the group write permissions.

  1. chown -R hello:users /webapps/hello_django
  2. chmod -R g+w /webapps/hello_django
  3. If you're not a member of users, you can add yourself to the group with this command:
  4. usermod -a -G users `whoami`

6. Configure PostgreSQL to work with Django

 

  1. apt-get install libpq-dev python-dev
  2. Install psycopg2 database adapter:
  3. (hello_django)hello@django:~$ pip install psycopg2
  4. You can now configure the databases section in your settings.py. Change it to:
  5. DATABASES = {
  6. 'default': {
  7. 'ENGINE': 'django.db.backends.postgresql_psycopg2′,
  8. 'NAME': 'hello',
  9. 'USER': 'hello_django',
  10. 'PASSWORD': 'password',
  11. 'HOST': 'localhost',
  12. 'PORT':
  13. ”,                      # Set to empty string for default.
  14. }
  15. }
  16. And finally build the initial database for Django:
  17. (hello_django)hello@django:~$ python manage.py syncdb

 

  1. mysql_tzinfo_to_sql /usr/share/zoneinfo | mysql -u root -p mysql

7. Install and configure Gunicorn

 

  1. (hello_django)hello@django:~$ pip install gunicorn
  2. Now that you have gunicorn, you can test whether it can serve your Django application by running the following command:
  3. (hello_django)hello@django:~$ gunicorn hello.wsgi:application -–bind 0.0.0.0:8001
  4. You should now be able to access the Gunicorn server from http://0.0.0.0:8001 . I intentionally changed port 8000 to 8001 to force your browser to establish a new connection.
  5. Gunicorn is installed and ready to serve your app. Let's set some configuration options to make it more useful. I like to set a number of parameters, so let's put them all into a small BASH script, which I save as bin/gunicorn_start

cat bin/gunicorn_start

  1. #!/bin/bash
  2.  
  3. NAME="hello_app"                                  # Name of the application
  4. DJANGODIR=/webapps/hello_django/hello                        # Django project directory
  5. SOCKFILE=/webapps/hello_django/run/gunicorn.sock          # we will communicte using this unix socket
  6. USER=hello                                        # the user to run as
  7. GROUP=webapps                                       # the group to run as
  8. NUM_WORKERS=3                                # how many worker processes should Gunicorn spawn
  9. TIMEOUT=600
  10. DJANGO_SETTINGS_MODULE=hello.settings             # which settings file should Django use
  11. DJANGO_WSGI_MODULE=hello.wsgi                     # WSGI module name
  12.  
  13. PORT=8000
  14. SERVER_NAME=0.0.0.0
  15. echo "Starting $NAME as `whoami`"
  16. # Activate the virtual environment
  17. cd $DJANGODIR
  18. source ../bin/activate
  19. export DJANGO_SETTINGS_MODULE=$DJANGO_SETTINGS_MODULE
  20. export PYTHONPATH=$DJANGODIR:$PYTHONPATH
  21. # Create the run directory if it doesn't exist
  22. RUNDIR=$(dirname $SOCKFILE)
  23. test -d $RUNDIR || mkdir -p $RUNDIR
  24. # Start your Django Unicorn
  25. # Programs meant to be run under supervisor should not daemonize themselves (do not use --daemon)
  26. exec ../bin/gunicorn ${DJANGO_WSGI_MODULE}:application \
  27. --name $NAME \
  28. --workers $NUM_WORKERS \
  29. --timeout $TIMEOUT \
  30. --user=$USER --group=$GROUP \
  31. --log-level=debug \
  32. --bind=unix:$SOCKFILE

#如果你需要直接用 IP:port 这样的方式访问查看 那么就这么写 ,主要是测试是否可以访问  用上面的,不可以直接在浏览器中查看需要借助 nginx 等 反向代理的方法看。 配置 在 9 , 安装nginx 中。 在没有安装Nginx前注释  --bind=unix:$SOCKFILE  有了Nginx后注释 #--bind=$SERVER_NAME:$PORT
当前也可以就用--bind=$SERVER_NAME:$PORT 的方式;

Set the executable bit on the gunicorn_start script:chmod u+x bin/gunicorn_start

You can test your gunicorn_start script by running it as the user hello.

su – hello

hello@django:~$ bin/gunicorn_start

In order for the –name argument to have an effect you need to install a Python module called setproctitle. To build this native extension pip needs to have access to C header files for Python. You can add them to your system with the python-dev package and then install setproctitle.

(hello_django)hello@django:~$ pip install setproctitle

Now when you list processes, you should see which gunicorn belongs to which application.

ps aux
USER       PID %CPU %MEM    VSZ   RSS TTY      STAT START   TIME COMMAND
.....

hello    12977 12643  0 04:26 pts/1    00:00:00 /webapps/hello_django/bin/python /webapps/hello_django/hello/../bin/gunicorn hello.wsgi:application --name hello_app --workers 3 --timeout 600 --user=hello --group=webapps --log-level=debug --bind=0.0.0.0:8000
hello    12988 12977  0 04:26 pts/1    00:00:00 /webapps/hello_django/bin/python /webapps/hello_django/hello/../bin/gunicorn hello.wsgi:application --name hello_app --workers 3 --timeout 600 --user=hello --group=webapps --log-level=debug --bind=0.0.0.0:8000
hello    12989 12977  0 04:26 pts/1    00:00:00 /webapps/hello_django/bin/python /webapps/hello_django/hello/../bin/gunicorn hello.wsgi:application --name hello_app --workers 3 --timeout 600 --user=hello --group=webapps --log-level=debug --bind=0.0.0.0:8000
hello    12990 12977  0 04:26 pts/1    00:00:00 /webapps/hello_django/bin/python /webapps/hello_django/hello/../bin/gunicorn hello.wsgi:application --name hello_app --workers 3 --timeout 600 --user=hello --group=webapps --log-level=debug --bind=0.0.0.0:8000
root     13019  9050  0 04:27 pts/2    00:00:00 grep --color=auto gunicorn

8. Configure Monitoring using Supervisor

apt-get install supervisor

When Supervisor is installed you can give it programs to start and watch by creating configuration files in the /etc/supervisor/conf.d directory. For our hello application we’ll create a file named /etc/supervisor/conf.d/hello.conf with this content:

vim /etc/supervisor/conf.d/hello.conf

  1. [program:hello]
  2. command = /webapps/hello_django/bin/gunicorn_start ; Command to start app
  3. user = hello ; User to run as
  4. stdout_logfile = /webapps/hello_django/logs/gunicorn_supervisor.log ; Where to write log
  5. messages
  6. redirect_stderr = true ; Save stderr in the same log
  7. environment=LANG=en_US.UTF-8,LC_ALL=en_US.UTF-8

 

Create the file to store your application’s log messages:hello@django:~$ mkdir -p /webapps/hello_django/logs/

hello@django:~$ touch /webapps/hello_django/logs/gunicorn_supervisor.log

After you save the configuration file for your program you can ask supervisor to reread configuration files and update (which will start your the newly registered app).

supervisorctl command [all]|[appname]   启动/关闭/重启 ..  指定/所有 supervisor 管理的程序进程

supervisorctl reread
hello: available

supervisorctl update
hello: added process group

You can also check the status of your app or start, stop or restart it using supervisor.

supervisorctl status hello
hello                            RUNNING    pid 18020, uptime 0:00:50

supervisorctl stop hello
hello: stopped

supervisorctl start hello
hello: started

supervisorctl restart hello
hello: stopped
hello: started

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

多个 gunicorn  需注意一点 supervisorctl 需要重新加载以及更新

Reread the configuration files and update Supervisor to start the apps:

supervisorctl reread
supervisorctl update例如: 上面建立的  goodbye_django  过程一致
su – goodbye
cd /webapps/goodbye_django/
goodbye@django:~$ virtualenv .
New python executable in goodbye_django/bin/python
Installing distribute…………..done.
Installing pip…………………done.goodbye@django:~$ source bin/activate
(goodbye_django)goodbye@django:~$
Your environment is now activated and you can proceed to install Django inside it.

 

 

 

(goodbye_django)goodbye@django:~$ pip install django
...
...
过程省略

(goodbye_django)goodbye@django:~$ django-admin.py startproject goodbye
(goodbye_django)goodbye@django:~$ cd goodbye
(goodbye_django)goodbye@django:~$ python manage.py runserver 0.0.0.0:8001
...  省略

You should now be able to access your development server from http://IP:8001
出现django 的It worked! 就成功了

安装 gunicorn (我采用的是单独的虚拟环境 virtualenv是Python中常用的虚拟环境。可以理解为属于Python的虚拟机 )
(goodbye_django)goodbye@django:~$ pip install gunicorn
....
....

vim bin/gunicorn_start

  1. #!/bin/bash
  2. NAME="goodbye_app"                                  # Name of the application
  3. DJANGODIR=/webapps/goodbye_django/goodbye                        # Django project directory
  4. SOCKFILE=/webapps/goodbye_django/run/gunicorn.sock          # we will communicte using this unix socket
  5. USER=goodbye                                        # the user to run as
  6. GROUP=webapps                                       # the group to run as
  7. NUM_WORKERS=3                                # how many worker processes should Gunicorn spawn
  8. TIMEOUT=600
  9. DJANGO_SETTINGS_MODULE=goodbye.settings             # which settings file should Django use
  10. DJANGO_WSGI_MODULE=goodbye.wsgi                     # WSGI module name
  11.  
  12. PORT=8001
  13. SERVER_NAME=0.0.0.0
  14. echo "Starting $NAME as `whoami`"
  15. # Activate the virtual environment
  16. cd $DJANGODIR
  17. source ../bin/activate
  18. export DJANGO_SETTINGS_MODULE=$DJANGO_SETTINGS_MODULE
  19. export PYTHONPATH=$DJANGODIR:$PYTHONPATH
  20.  
  21. # Create the run directory if it doesn't exist
  22. RUNDIR=$(dirname $SOCKFILE)
  23. test -d $RUNDIR || mkdir -p $RUNDIR
  24.  
  25. # Start your Django Unicorn
  26. # Programs meant to be run under supervisor should not daemonize themselves (do not use --daemon)
  27. exec ../bin/gunicorn ${DJANGO_WSGI_MODULE}:application \
  28. --name $NAME \
  29. --workers $NUM_WORKERS \
  30. --timeout $TIMEOUT \
  31. --user=$USER --group=$GROUP \
  32. --log-level=debug \
  33. --bind=unix:$SOCKFILE
  34. ###--bind=0.0.0.0:8001

 

root@django:~# chmod u+x bin/gunicorn_start
先杀掉之前启动的进程
(goodbye_django)goodbye@django:~$  bin/gunicorn_startcat  /etc/supervisor/conf.d/goodbye.conf[program:goodbye]
command = /webapps/goodbye_django/bin/gunicorn_start ; Command to start app
user = goodbye ; User to run as
autostart = true ; 在 supervisord 启动的时候也自动启动
startsecs = 5 ; 启动 5 秒后没有异常退出,就当作已经正常启动了
autorestart = true ; 程序异常退出后自动重启
redirect_stderr = true ; 把 stderr 重定向到 stdout,默认 false
stdout_logfile_maxbytes = 100MB ; stdout 日志文件大小,默认 50MB
stdout_logfile_backups = 20 ; stdout 日志文件备份数
stdout_logfile = /webapps/goodbye_django/logs/gunicorn_supervisor.log ; Where to write log messages
environment=LANG=en_US.UTF-8,LC_ALL=en_US.UTF-8

 

 

 

logfile 自定义如果不存在先创建  注意所属用户和组
mkdir -p  mkdir -p /webapps/hello_django/logs/

将任务添加到  supervisord
supervisorctl reread
goodbye: available

supervisorctl update
goodbye: added process group

 

9. Install and configure Nginx for web hosting

 

  1. aptitude install libpcre3 libpcre3-dev
  2. aptitude install  libssl-dev openssl
  3. aptitude install   libxslt-dev
  4. aptitude install  libgd2-xpm libgd2-xpm-dev
  5. aptitude install  libgeoip-dev
  6. aptitude install  pcre
  7. pcre-config --version
  8. cd /usr/local/src
  9. wget http://labs.frickle.com/files/ngx_cache_purge-2.3.tar.gz
  10. tar zxf ngx_cache_purge-2.3.tar.gz
  11. wget http://nginx.org/download/nginx-1.9.0.tar.gz
  12. tar zxf  nginx-1.9.0.tar.gz
  13. cd  nginx-1.9.0
  14. ./configure --prefix=/usr/local/nginx --with-http_ssl_module --with-http_gzip_static_module --with-http_stub_status_module --with-http_realip_module --add-module=/usr/local/src/ngx_cache_purge-2.3  --with-http_image_filter_module --with-http_dav_module --with-http_flv_module --with-http_random_index_module --with-http_secure_link_module --with-mail --with-mail_ssl_module --with-file-aio --with-ipv6 --with-http_spdy_module --with-http_gunzip_module --with-http_auth_request_module  --with-http_geoip_module
  15. make
  16. make  install
  17.  
  18. /usr/local/nginx/sbin/nginx -t
  19. nginx: the configuration file /usr/local/nginx/conf/nginx.conf syntax is ok
  20. nginx: configuration file /usr/local/nginx/conf/nginx.conf test is successful
  21.  
  22. 具体细节参照之前的debain nginx 安装 note.php?serial_number=203   nginx自启动 note.php?serial_number=236
  23.  
  24. upstream hello_app_server {
    # fail_timeout=0 means we always retry an upstream even if it failed
  25.         # to return a good HTTP response (in case the Unicorn master nukes a
  26.         # single worker for timing out).
  27.         server unix:/webapps/hello_django/run/gunicorn.sock fail_timeout=0;
  28.         #server 127.0.0.1:8000;
  29.   }
  30.  
  31. server {
  32.         listen 80;
  33.         server_name world_alive.com;
  34.         client_max_body_size 100M;
  35.         access_log /webapps/hello_django/logs/nginx-access.log;
  36.         error_log /webapps/hello_django/logs/nginx-error.log;
  37.         location /static/ {
  38.                 alias
  39. /webapps/hello_django/static/;
  40.         }
  41.         location /media/ {
  42.                 alias
  43. /webapps/hello_django/media/;
  44.         }
  45.  
  46.         location / {
  47.  
  48.                 proxy_set_header
  49. X-Forwarded-For $proxy_add_x_forwarded_for;
  50.  
  51.                 proxy_set_header Host $http_host;
  52.  
  53.                 proxy_redirect off;
  54.  
  55.                 if (!-f
  56. $request_filename) {
  57.                         proxy_pass http://hello_app_server;
  58.                         break;
  59.                 }
  60.         }
  61.         # Error pages
  62.         error_page 500 502 503 504 /500.html;
  63.         location = /500.html {
  64.                 root /webapps/hello_django/static/;
  65.         }
  66. }

没有评论

发表回复

您的电子邮箱地址不会被公开。 必填项已用 * 标注