2014年10月21日 星期二

Deploy Django on CentOS 6.5 with Apache and mod_wsgi

今天試著在 CentOS 6.5 上佈署 Django 的開發環境,過程大致上和網路上能找到的教學差不多,會遇到的問題也都差不多,紀錄一下重新整理後的過程。

  • Install Python 2.7.X
    先從 Python 的官網下載 2.7.X 的原始碼下來編譯,configure 時記得加入"--enable-shared"。
    /* configure */
    $ ./configure --prefix=/usr/local --enable-shared
    /* make */
    $ make
    /* install */
    # make install

    因為開啟了"--enable-shared"的 flag,所以要新增一個系統變數 LD_LIBRARY_PATH,其路徑指向 /usr/local/lib,否則在執行 python2.7 時會出現找不到 libpython2.7.so.1.0 的錯誤。
    # echo "/usr/local/lib" > /etc/ld.so.conf.d/python2.7.conf

    (20141027 update)

    編譯時可以不需要開啟 --enable-shared,但要加入 -fPIC 的 CFLAGS,要不然在編譯 mod_wsgi 時會現錯誤訊息。若是使用此方式編譯,則不需要設定 LD_LIBRARY_PATH。

    (20141107 update)
    編譯時還是得開啟 --enable-shared,開啟 --enable-shared 後,flag PIC 就會一起加進去。
  • Install Apache
    在編譯 mod_wsgi 時會需要用到 apxs 指令,而 apxs 指令是包在 httpd-devel 裡,所以也一併安裝。
    # yum install httpd httpd-devel
  • Install mod_wsgi
    modwsgi 的網站下載原始碼回來編譯,因為 CentOS 6.5 預載的 python 版本為  2.6.6,而 mod_wsgi 需要 python 版本 2.7,所以在 configure 時要指定 python 的路徑。make 時則需要指定 LD_RUN_PATH,否則在 httpd 啟動時會出現 mod_wsgi.so 找不到 libpython2.7.so.1.0 的錯誤。
    /* configure */
    $ ./configure --with-python=/usr/local/bin/python2.7
    /* make */
    $ LD_RUN_PATH=/usr/local/lib make
    /* install */
    # make install


    (20141027 update)

    若是在編譯 python 時有加入 -fPIC,那編譯 mod_wsgi 時就不需要加任何額外的參數,直接 configure 就好。
  • Configure httpd
    新增 mod_wsgi.conf 至 /etc/httpd/conf.d/
    # touch mod_wsgi.conf /etc/httpd/conf.d/
    並將下列內容寫入 mod_wsgi.conf
    <IfModule !python_module>
        <IfModule !wsgi_module>
            LoadModule wsgi_module modules/mod_wsgi.so
        </IfModule>
    </IfModule>
  • Start httpd
    # service httpd start
    檢查 /var/log/httpd/error.log,如果有出現下列訊息,則表示安裝成功。
    Apache/2.2.15 (Unix) DAV/2 mod_wsgi/4.3.0 Python/2.7.8 mod_perl/2.0.4 Perl/v5.10.1 configured
  • Integrate Django and Apache
    Modify settings.py, and add the following setting.
    STATIC_ROOT = os.path.join(BASE_DIR, 'static')
    then, run the following command to collect static files.
    $ python manage.py collectstatic
    Copy entire project directory to /var/www, and change the directory mode to avoid "permission denied" isuue.
    $ sudo cp -rf MYSITE /var/www
    $ sudo chmod o+w /var/www/MYSITE

    Change mode of database to avoid the "database readonly" issue.
    $ sudo chmod o+w /var/www/MYSITE/db.sqlite3
    Follow the instruction from this document to configure the httpd.conf, and restart the httpd.
    $ sudo /etc/init.d/httpd restart

    /etc/httpd/conf/httpd.conf:
    Alias /static/ /var/www/food/static/

    <Directory /var/www/food/static>
    Order deny,allow
    Allow from all
    </Directory>

    WSGIScriptAlias / /var/www/food/food/wsgi.py
    WSGIPythonPath /var/www/food


    <Directory /var/www/food/food/>
    <Files wsgi.py>
    Order deny,allow
    Allow from all
    </Files>
    </Directory>


參考連結
[1] How to install Python 2.7 and Python 3.3 on CentOS 6 
[2] Installing Python 2.7.8 on CentOS 6.5 
[3] mod_wsgi.so: Cannot load mod_wsgi.so into server: libpython2.5.so.1.0: cannot open shared object file: No such file or directory 
[4] modwsgi Quick Installation Guide 
[5] How to install Django
[6] Django + Apache + mod_wsgi permission denied 
[7] Conference Presentations 
[8] PyCon AU 2010 - Getting Started With Apache/mod_wsgi.