Deploying Flask app on EC2 for localhost access

I have finished up a simple Flask app that I am trying to host on an AWS EC2 instance with Apache2. I've been following this tutorial.

The only changes I've made from the development process (in which the app runs totally fine when I run it and then try to access it via localhost) are:

1) Moved all the code in to /var/www
2) Changed it so that 
        if __name__=='__main__':
            app.run(debug = False) #Now False instead of True
3) Added a app.wsgi file
4) Added file my_app to /etc/apache2/sites-available
5) Ran these commands:
    $ sudo a2dissite default
    $ sudo a2ensite sitename.com
    $ sudo /etc/init.d/apache2 restart

Here is the app.wsgi file:

import sys 
sys.path.insert(0, '/var/www/my_app')

from app import app as application

Here is the my_app file in /etc/apache2/sites-available:

<VirtualHost *:5000>
         WSGIDaemonProcess app 
     WSGIScriptAlias / /var/www/my_app/app.wsgi

     <Directory /var/www/my_app>
            WSGIProcessGroup app 
        WSGIApplicationGroup %{GLOBAL}
        Order deny,allow
        Allow from 127.0.0.1
     </Directory>
</VirtualHost>

As you can see from the above file, I only want the flask app to be available on localhost.

When I run apache and try to access the website at my_site.com:5000 I get an "Unable to connect error". I can't really figure out why. Any help would be appreciated.

Also, here is my directory structure for the Flask app itself if that's needed:

/var/www/my_app/
    app/
        __init__.py
        static/
            css/
                bootstrap.css
            favicon.ico
            js/
                bootstrap.js
        templates/
            base.html
            index.html
            search.html
        views.py
    app.wsgi
    flask/           #my virtualenv
        #Your typical virutalenv structure
    flask_util_js.py   #File that is a FLask entension for client-side generation of URLs
    requirements.txt
    run.py
    virtualenv.py    #Creates virutalenv flask

UPDATE:

So, I got the feeling that the way I had my code set up was being problematic. So I took everything in run.py, __init__.py, and views.py and made one big main.py. I've updated my app.wsgi to look like this:

app.wsgi

import sys 

activate_this = '/home/achumbley/flask/bin/activate_this.py'
execfile(activate_this, dict(__file__=activate_this))

sys.path.insert(0, '/home/achumbley/new_flask_app')

from main import app as application

And now, my /etc/apache2/sites-available/new_flask_app looks like:

<VirtualHost *>
  ServerName dev.east.appliedminds.com

  WSGIDaemonProcess app 
  WSGIScriptAlias / /var/www/app.wsgi

 <Directory /home/achumbley/new_flask_app>
   WSGIProcessGroup main
   WSGIScriptReloading On
   WSGIApplicationGroup %{GLOBAL}
   Order deny,allow
   Allow from all
 </Directory>

Finally, he is my newest directory structure:

/home/my_username/new_flask_app/
    logging.log
    flask_util_js.py
    main.py
    static/
    templates/

It still does not work. But, it's possible I don't understand how to run the whole thing. I should have to run a python main.py right? It should just be automatic, at least that is what I assumed.

Answers


Moved all the code in to /var/www

This is wrong. You need to post your code in a non-web accessible directory. Only post your static files to /var/www

Please see the official deployment guide on how to set it up with Apache and mod_wsgi. If you are having problems, you might consider this AMI image which has flask, nginx and uwsgi installed.

The nginx+uwsgi stack is also detailed in the documentation.

Here are the steps (simplified) that you need to follow:

Assume that your application is:

my_app/
   static/
      logo.gif
      style.css
   templates/
      index.html
   main.py

Then follow these instructions:

  1. Upload all your code into /home/youruser/
  2. Upload the app.wsgi file to /var/www/
  3. Upload the contents of the static directory to /var/www/static
  4. In the app.wsgi file:

    import sys
    sys.path.append(0, '/home/youruser/my_app')
    
    from main import app as application
    

Have you enabled mod_wsgi on apache?

a2enmod wsgi 
service apache2 restart

I would also try with a simple 'hello world' example, this would be the content of main.py under /home/ubuntu/new_flask_app:

from flask import Flask
app = Flask(__name__)

@app.route('/')
def hello_world():
    return 'Hello World!'

if __name__ == '__main__':
    app.run()

This is a sample flask apache config for my working example:

<VirtualHost *:80>
    ServerAdmin webmaster@localhost

    ServerName app.com

    WSGIDaemonProcess new_flash_app user=ubuntu group=ubuntu threads=5
    WSGIScriptAlias / /var/www/app/app.wsgi

    <Directory /var/www/app>
        WSGIProcessGroup new_flash_app
        WSGIApplicationGroup %{GLOBAL}
        Order deny,allow
        Allow from all
    </Directory>

</VirtualHost>

and this would be the content for app.wsi

import sys

activate_this = '/home/ubuntu/flask/bin/activate_this.py'
execfile(activate_this, dict(__file__=activate_this))

sys.path.insert(0, '/home/ubuntu/new_flask_app')

from main import app as application

Btw, your wsgi and main.py (or app file) don't need to be in the same directory, just make sure the configuration points to the right files.

You can test your server like this:

$ telnet localhost 80
Trying 127.0.0.1...
Connected to localhost.
Escape character is '^]'.
GET /
Hello World!Connection closed by foreign host.
$

I would also check for the apache logs /var/log/apache2/error.log

You can also try nginx just like (Burhan Khalid) mentioned.


Need Your Help

Activate wordpress theme remotely for a wordpress blog using ruby xmlrpc/client library

ruby wordpress xmlrpcclient

I need to activate theme for wordpress blogs which are present remotely. I thought I will do it with xmlrpc api of worpress http://core.svn.wordpress.org/trunk/wp-includes/class-wp-xmlrpc-server.ph...

About UNIX Resources Network

Original, collect and organize Developers related documents, information and materials, contains jQuery, Html, CSS, MySQL, .NET, ASP.NET, SQL, objective-c, iPhone, Ruby on Rails, C, SQL Server, Ruby, Arrays, Regex, ASP.NET MVC, WPF, XML, Ajax, DataBase, and so on.