Simplicity is the ultimate sophistication

Time is a tangled web. Try not to dwell on all the loose ends..

Prepare Flask Environment(EN)

Prepare Flask Environment

My test environment are using KVM, CentOS 7.

Prepare VMs under KVM

Here are some tips for the configuration:

  • First off all, make sure the network ready for host/guest, have a plan is better than anything.
  • Actually KVM Bridge is pretty need your time if you got no experience or umfamilier with it. Be patient, understand your environment before going to set it up. There are a lot information on Google, but make sure the post is similar to your environment.
  • In fact, you can feel that KVM is pretty conviencent, and got a lot information/help/guideline on internet.
  • Snapshot is your best friend. You can beat anything down with this tool, remember it!

Using VirtualBox

VirtualBox is free, sustaion by Oracle and started by Sun before. Here is PC Version, and also MAC version.

Snapshot is also a great tool. That’s feel good that me always have several VMs on my mahcine.

I think VMs actually is one kind of solution for malware. I have one VM specially for Bank Web. Also another VM for china web site, and another for the web site I think maybe got problem. By snapshot, I can using VMs to avoid compromise.

It’s same as setting VM on KVM, prepare the plan for network is most important thing. bridge network is a way to get the VM similar standalone machine. Just take care, some wifi environment is not allow this mode.

Install CentOS 7

  • Make sure you can have root permission, check it by sudo -v
  • Using ifconfig to check your network, if system don’t know this command, install it by sudo yum install -y net-tools to unstall net-tools
  • Following are the options for Flask deployment:

Following are some tips for installation:

  1. If your VM installed by minimal install ISO, suppose have to install some tools when the Operating System ready. I used nano for text editor, so I always run sudo yum install -y net-tools nano wget curl to install the basic tools, curl and wget are the great tools to access network. If failed on yum install, maybe you should check your network first.
  2. Check firewall. In CentOS 7 you can check it by sudo systemctl status firewalld, and config the port if the status is “active”
  3. Install pip, this is Python package management tool, you can using wget download get-pip.py by wget https://bootstrap.pypa.io/get-pip.py and install it by python sudo python get-pip.py.

WSGI Deployment

Here we are using Tornado as Web Server, install it by two line commands:

1
2
sudo pip install tornado
sudo pip install flask

First of all, we are going to verify the functionality of Tornado, Following is the Office Sample, I just changed port:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
mport tornado.ioloop
import tornado.web

class MainHandler(tornado.web.RequestHandler):
    def get(self):
        self.write("Hello, world")

application = tornado.web.Application([
    (r"/", MainHandler),
])

if __name__ == "__main__":
    application.listen(80)
    tornado.ioloop.IOLoop.instance().start()

Save it as index.py, then input sudo python index.py in the console, then we should see “Hello, world” on browser when connect to the web server.

If we want to conbine with Flask, bdarnell’s sample can show you how to do it. Using Tornado’s tornado.wsgi.WSGIContainer(wsgi_application) to run Flask.

But the design concept between Tornado and Flask are difference, Tornado is design for non-blocking, but Flask is non-async的framework. That’s why I stop here.

If we need Tornado for Realtime, and still want to have Flask, Serge Koval wroten a great post -Python Realtime, this post detail the concept and also provide a complete guideline for how to utilize them in the same time.

You can look Realtime as there is keeping a connection between client and Server. The connection is considered on HTTP Request’s Header cost, we can pnly relay on Comet) before the Websocket. But Websocket got browser support condition, if you want to implement it, please check your target customer/client’s Browser version before implmentation.

Deployment by uWSGI

Install VM for nginx

attached the repository by following command

sudo rpm -Uvh http://nginx.org/packages/centos/7/noarch/RPMS/nginx-release-centos-7-0.el7.ngx.noarch.rpm

install

sudo yum install nginx

start it up

sudo systemctl start nginx.service

and enable it when boot

sudo systemctl enable nginx.service

then we can check it by browser, please check the firewall if cannot see nginx page

Install web server VM

First, we are going to install uWSGI, uWSGI deployment required clangclang or gccgcc, and also header files and a static library for Python, so we install them before install uWSGI

sudo yum install -y gcc clang
sudo yum install -y python-devel

then install pip, and continue install uWSGI

sudo pip install uwsgi

we can verify the installation of uWSGI now, touch a file (I am using “testuwsgi.py”“), and write into following content:

def application(env, start_response):
    start_response('200 OK', [('Content-Type','text/html')])
    return ["Hello World"]

Using following command to run uWSGI on Console:

uwsgi --http :5000 --wsgi-file testuwsgi.py

We can install Flask if everything ok.

sudo pip install flask

creaet a new file (test.py) as following content

from datetime import datetime
from flask import Flask

app = Flask(__name__)

@app.route('/')
def index():
    return 'Hello from Flask! (%s)' % datetime.now().strftime('%Y-%m-%d %H:%M:%S')

run following command on console:

uwsgi --http 0.0.0.0:5000 --module test --callable app

“test” is the file name, callable object is point to “app” under Flask, and then uwsgi can utilize it.

Result should be:

Hello from Flask! (2015-02-03 23:33:44)

After verified, we can continue to setup nginx

Config Reverse Proxy in the VM installed nginx

The nginx confiuration file is under /etc/nginx/nginx.conf on CentOS 7, we append following content inside http content:

upstream flask {
    server FIRST.MACHIME.IP.ADDRESS:5000;
}

and

server {
    listen 80;
    server_name THIS.MACHINE.IP.ADDRESS;
    charset utf-8;
    location / {
        proxy_pass http://flask;
    }
}

Then we can check the web page on the VM installednginx , suppose the result should be the same.

Any issue/unexcepted result, we can check /var/log/nginx/error.log to see any error.

If got error as connect() to failed (13: Permission denied) while connecting to upstream, we can turn on the Selinux的httpd_can_network_connect as following command:

sudo setsebool httpd_can_network_connect=1

Deploy by Apache mod_wsgi

Install Apache

yum install -y httpd

Open the port

sudo firewall-cmd --zone=dmz --add-port=80/tcp --permanent
sudo firewall-cmd --reload

Start and enable Apache

sudo systemctl enable httpd.service
sudo systemctl start httpd.service

Install mod_wsgi

yum -y install mod_wsgi

Create YOURAPP.wsgi

import sys
sys.stdout = sys.stderr
sys.path.append("/Your/Application/Folder/")

Config Apache’s configuration by create one

nano /etc/httpd/conf.d/YourApplicationName.conf

Input following content(Please change the value by your environment):

<VirtualHost *>
    ServerName YOUR.MACHINE.IP.ADDRESS

    WSGIDaemonProcess YourAPPName user=apache group=apache threads=5
    WSGIScriptAlias /SUBPATH /Your/Application/Folder/YOURAPP.wsgi
    <Directory /Your/Application/Folder>
        WSGIProcessGroup YourAPPName
        WSGIApplicationGroup %{GLOBAL}
        Order deny,allow
        Allow from all
    </Directory>
</VirtualHost>

and then restart Apache and we can verify it.

Flask’s document is great, you can read it before any deployment.