How can you avoid servers and get back to coding? Platform-as-a-service (PaaS) makes deployment easy. But which PaaS do you choose and how do you get started? This talk will examine several of the leading PaaS providers and discuss their pros/cons. We'll also give examples for how to deploy the same app to each of them to see the differences.
3. 2010-2011
• Nothing equivalent to Heroku for Django developers
• Built my own PaaS (“How hard can it be?”)
• Shut down last year. Increased competition from big corps
meant a race to the bottom
Sunday, March 17, 13 3
5. AGENDA
• Why should I care?
• What is a PaaS? What are the advantages?
• Which PaaS should I use?
• When might I not want to use a PaaS?
Sunday, March 17, 13 5
6. WHERE ARE YOU
DEPLOYING/HOSTING
TODAY?
• Shared hosting (i.e. Webfaction)
• Running your own servers (co-located)?
• Using an IaaS provider (i.e. AWS or Rackspace)
• Already using a platform-as-a-service (PaaS)
Sunday, March 17, 13 6
9. CONFIGURING A SERVER
• deciding what size to get (memory, disk)
• getting all the dependencies installed on it
• SSHing into the machine to deploy stuff
(feels dirty, but he’s under time pressure)
1 day 1 day
Sunday, March 17, 13 9
10. MAINTAINING THE
SERVER
1 day 1 day 1 day
Sunday, March 17, 13 10
11. SECURITY
1 day 1 day 1 day 1 day
Sunday, March 17, 13 11
12. SCALING
1 day 1 day 1 day 1 day 1 day
Sunday, March 17, 13 12
16. PaaS
Is it the promised land?
Sunday, March 17, 13 16
17. WHAT IS A PAAS?
Platform-as-a-Service
enables developers to create
innovative applications without
operational overhead around
configuration, deployment and
management.
Sunday, March 17, 13 17
18. LAYERS OF
INFRASTRUCTURE
Source: EngineYard “PaaS - State of the Market Survey” May 2012 - http://venturebeat.com/2012/07/05/engine-yard-paas-infographic/
Sunday, March 17, 13 18
19. Source: EngineYard “PaaS - State of the Market Survey” May 2012 - http://venturebeat.com/2012/07/05/engine-yard-paas-infographic/
Sunday, March 17, 13 19
20. Source: EngineYard “PaaS - State of the Market Survey” May 2012 - http://venturebeat.com/2012/07/05/engine-yard-paas-infographic/
Sunday, March 17, 13 20
21. Source: EngineYard “PaaS - State of the Market Survey” May 2012 - http://venturebeat.com/2012/07/05/engine-yard-paas-infographic/
Sunday, March 17, 13 21
22. Source: AppFog “Evolution of the Cloud: Toward a NoOps World” Jan 2012
http://gigaom.com/cloud/why-2013-is-the-year-of-noops-for-programmers-infographic/
Sunday, March 17, 13 22
23. EFFICIENT, ELASTIC, SECURE
• Lots of applications co-located on a few servers
• Drastically reduces resources
• Add/remove capacity depending on load
• All secured using SELinux or LXC
Sunday, March 17, 13 23
24. LET THEM DO
THE BORING STUFF
• Patches and updates
• Migrating applications
• Backups / snapshots
• Configuring everything (web servers, load balancers,
modules, databases)
Sunday, March 17, 13 24
39. ANATOMY OF A
DJANGO APP
ON HEROKU
customized settings.py for Heroku
if not using S3, must configure static serve
Procfile to configure process
requirements.txt to define dependencies
Sunday, March 17, 13 39
40. INSTALL THE HEROKU
TOOLBELT
Download the Heroku Toolbelt
http://toolbelt.herokuapp.com/osx/download
$ heroku login
Enter your Heroku credentials.
Email: someone@example.com
Password: ******
Could not find an existing public key.
Would you like to generate one? [Yn]
Generating new SSH public key.
Uploading ssh public key /Users/someone/.ssh/id_rsa.pub
Sunday, March 17, 13 40
41. CREATE APP AND DB
$ heroku create paasbakeoff
Creating paasbakeoff... done, stack is cedar
http://paasbakeoff.herokuapp.com/ | git@heroku.com:paasbakeoff.git
Git remote heroku added
$ heroku addons:add heroku-postgresql:dev
Adding heroku-postgresql:dev on paasbakeoff... done, v3 (free)
Attached as HEROKU_POSTGRESQL_GREEN_URL
Database has been created and is available
Use `heroku addons:docs heroku-postgresql:dev` to view documentation.
$ heroku pg:info
=== HEROKU_POSTGRESQL_GREEN_URL
Plan: Dev
Status: available
Sunday, March 17, 13 41
42. SET DB ENV VARIABLES
$ heroku config
=== paasbakeoff Config Vars
HEROKU_POSTGRESQL_GREEN_URL: postgres://x:y@z.com:5432/d2b3c9ichbauv0
$ heroku pg:promote HEROKU_POSTGRESQL_GREEN
Promoting HEROKU_POSTGRESQL_GREEN_URL to DATABASE_URL... done
$ heroku config
=== paasbakeoff Config Vars
DATABASE_URL: postgres://x:y@z.com:5432/d2b3c9ichbauv0
Sunday, March 17, 13 42
43. ADD TO SETTINGS.PY
Set the RACK_ENV environment variable to production
$ heroku config:set RACK_ENV=production
Sunday, March 17, 13 43
44. USE S3 FOR SERVING STATIC
AND MEDIA FILES
And Sendgrid for sending emails
Sunday, March 17, 13 44
46. $ git push heroku master
Counting objects: 8, done.
DEPLOY WITH GIT PUSH
Delta compression using up to 2 threads.
Compressing objects: 100% (6/6), done.
Writing objects: 100% (6/6), 616 bytes, done.
Total 6 (delta 3), reused 0 (delta 0)
-----> Heroku receiving push
-----> Python/Django app detected
-----> Preparing Python interpreter (2.7.2)
-----> Creating Virtualenv version 1.7.2
New python executable in .heroku/venv/bin/python2.7
...
Running virtualenv with interpreter /usr/local/bin/python2.7
-----> Activating virtualenv
-----> Installing dependencies using pip version 1.1
Downloading/unpacking Django==1.4.2 (from -r requirements.txt (line 1))
...
Cleaning up...
-----> Collecting static files
Sunday, March 17, 13 46
47. ANATOMY OF A
DJANGO APP
ON HEROKU
customized settings.py for Heroku
Procfile to configure process
requirements.txt to define dependencies
Sunday, March 17, 13 47
48. MORE HEROKU RESOURCES
• Getting Started with Django on Heroku
https://devcenter.heroku.com/articles/django
• Heroku Hackers Guide ($10 eBook)
http://theherokuhackersguide.com
• Developers Guide to Running Django Applications on Heroku
http://kencochrane.net/blog/2011/11/developers-guide-for-running-django-apps-on-heroku/
• django-skel
http://django-skel.readthedocs.org
Sunday, March 17, 13 48
49. DOTCLOUD
polyglot from the start, very flexible, most Python centric
Sunday, March 17, 13 49
52. ANATOMY OF A
DJANGO APP
ON
DOTCLOUD
customized settings.py for Dotcloud
createdb.py to create the database
dotcloud.yml to store config info
mkadmin.py to make the admin user
nginx.conf to config URL rewriting
postinstall to run syncdb, collectstatic
wsgi.py to serve using uWSGI
Sunday, March 17, 13 52
53. INSTALL THE DOTCLOUD
CLIENT
$ sudo pip install dotcloud
$ dotcloud setup
dotCloud username or email: natea@jazkarta.com
Password:
==> dotCloud authentication is complete!
You are recommended to run `dotcloud check` now.
Sunday, March 17, 13 53
54. CREATE AND PUSH AN
APP
$ dotcloud create mezz
==> Creating a sandbox application named "mezz"
==> Application "mezz" created.
Connect the current directory to "mezz"? [Y/n]:
==> Connecting with the application "mezz"
==> Connected with default push options: --rsync
$ dotcloud push
==> Pushing code with rsync from "./" to application mezz
building file list ... done
14:17:51: [www.0] Migrating stateful data located in ~/data
14:18:05: [www.0] Launching...
14:18:07: [www.0] Re-routing traffic to the new build...
14:18:08: [www.0] Successfully installed build revision rsync instance #0
Sunday, March 17, 13 54
55. ANATOMY OF A
DJANGO APP
ON
DOTCLOUD
customized settings.py for Dotcloud
createdb.py to create the database
dotcloud.yml to store config info
mkadmin.py to make the admin user
nginx.conf to config URL rewriting
postinstall to run syncdb, collectstatic
wsgi.py to serve using uWSGI
Sunday, March 17, 13 55
63. STACKATO
by ActiveState
Python 3, Run anywhere, New Relic integration
http://appsembler.com/blog/django-deployment-using-stackato/
Sunday, March 17, 13 63
72. STACKATO FOR DJANGO
1.Download the Stackato client
http://www.activestate.com/stackato/download_client
2.Create a wsgi.py file
3.Create a requirements.txt file
(if you don’t already have one)
4.Edit the DATABASES and MEDIA_ROOT settings in
settings.py file
5.Create a stackato.yml file to persist the
Sunday, March 17, 13 72
74. REQUIREMENTS.TXT
Django==1.4.2
psycopg2==2.4.5
-e git+git@github.com:yourname/django-awesome.git#egg=django-awesome
Or you can just reference another
requirements file in your repo
-r requirements/project.txt
Sunday, March 17, 13 74
77. TARGET AND LOGIN
$ stackato target api.appsembler.net
$ stackato login --email user@domain.com
Attempting to login to [https://api.appsembler.net]
Password: ********
Successfully logged into [https://api.appsembler.net]
Sunday, March 17, 13 77
78. INITIAL PUSH
$ stackato push
Would you like to deploy from the current directory ? [Yn]:
Would you like to use 'paasbakeoff' as application name ? [Yn]:
Detected a Python Application, is this correct ? [Yn]:
Framework: python
Runtime: <framework-specific default>
Application Deployed URL [paasbakeoff.appsembler.net]:
Application Url: paasbakeoff.appsembler.net
Enter Memory Reservation [128M]:
Sunday, March 17, 13 78
79. BIND SERVICES
What kind of service ?
1. filesystem
2. memcached
3. mongodb
4. mysql
5. postgresql
6. rabbitmq
7. redis
Choose: 5
Specify the name of the service [postgresql-cf691]:
Creating Service: OK
Binding Service: OK
Create another ? [yN]:
Would you like to save this configuration? [yN]: y
Uploading Application [paasbakeoff]:
Sunday, March 17, 13 79
80. AUTO-GENERATED
STACKATO.YML FILE
name: paasbakeoff
instances: 1
framework:
type: python
mem: 128
Let’s add some other requirements to be installed
requirements: requirements:
pypm: pypm:
- pillow -OR- - pillow
- psycopg2 pip:
- psycopg2
Sunday, March 17, 13 80
82. HANDLING STATIC
ASSETS
$ stackato run python mywebsite/manage.py collectstatic --noinput
...
Copying '/app/python/lib/python2.7/site-packages/django/contrib/admin/static/admin/css/rtl.css'
Copying '/app/python/lib/python2.7/site-packages/django/contrib/admin/static/admin/css/ie.css'
Copying '/app/python/lib/python2.7/site-packages/django/contrib/admin/static/admin/css/forms.css'
Make sure they were copied to the right place
framework:
type: python
home-dir: app
processes:
web: $STACKATO_UWSGI --static-map /static=$HOME/mywebsite/static
Sunday, March 17, 13 82
83. RUN MANAGEMENT
COMMANDS
hooks:
post-staging:
- python mywebsite/manage.py syncdb --noinput
- python mywebsite/manage.py collectstatic --noinput
- python mywebsite/manage.py migrate --noinput
Make sure you add South to the requirements
requirements:
pypm:
- pillow
- psycopg2
- south
Sunday, March 17, 13 83
84. PERSISTED FILESYSTEM FOR
FILE UPLOADS
services:
postgresql-cf691: postgresql
filesystem-paasbakeoff: filesystem
Remember to set the MEDIA_ROOT in settings.py:
MEDIA_ROOT = os.environ['STACKATO_FILESYSTEM']
Sunday, March 17, 13 84
87. OPENSHIFT
by Redhat
Open source, Auto-scaling, Jenkins builds
http://appsembler.com/blog/django-deployment-using-openshift/
Sunday, March 17, 13 87
89. Action hooks for running commands
during build, deploy, post-deploy, etc.
/data/ dir to store uploaded media files
ANATOMY OF AN
OPENSHIFT REPO
.htaccess to serve up static files
application inside of wsgi dir
setup.py instead of requirements.txt
Sunday, March 17, 13 89
90. INSTALL THE RHC CLIENT
$ sudo gem install rhc
$ rhc setup
...
$ rhc domain status
7 tests, 12 assertions, 0 failures, 0 errors, 0 pendings, 0 omissions, 0 notifications
100% passed
You may need to add the SSH key and start the SSH agent
$ ssh-add ~/.ssh/id_rsa
$ ssh-agent
Sunday, March 17, 13 90
91. QUICK ‘N DIRTY
INSTRUCTIONS
$ rhc app create -a mezzanineopenshift -t python 2.6
$ rhc cartridge add -c mysql-5.1 -a mezzanineopenshift
$ cd mezzanineopenshift
$ git remote add paasbakeoff git://github.com/appsembler/paasbakeoff.git
$ git fetch paasbakeoff
$ git merge paasbakeoff/openshift
Sunday, March 17, 13 91
92. Action hooks for running commands
during build, deploy, post-deploy, etc.
/data/ dir to store uploaded media files
ANATOMY OF AN
OPENSHIFT REPO
.htaccess to serve up static files
application inside of wsgi dir
setup.py instead of requirements.txt
Sunday, March 17, 13 92
98. .OPENSHIFT/
ACTION_HOOKS/DEPLOY
Sunday, March 17, 13 98
99. .OPENSHIFT/
ACTION_HOOKS/BUILD
Sunday, March 17, 13 99
100. CREATE AND BIND THE
DATABASE
$ rhc cartridge add -c mysql-5.1 -a mezz
Password: ******
Adding 'mysql-5.1' to application 'mezz'
Success
mysql-5.1
=========
Properties
==========
Similar for PostgreSQL
$ rhc cartridge add -c postgresql-8.4 -a mezz
Sunday, March 17, 13 100
101. $ git push
GIT PUSH TO DEPLOY
Counting objects: 5, done.
Delta compression using up to 2 threads.
Compressing objects: 100% (3/3), done.
Writing objects: 100% (3/3), 498 bytes, done.
Total 3 (delta 1), reused 0 (delta 0)
remote: restart_on_add=false
remote: Waiting for stop to finish
remote: Done
remote: restart_on_add=false
remote: ~/git/mezz.git ~/git/mezz.git
remote: ~/git/mezz.git
remote: Running .openshift/action_hooks/pre_build
remote: setup.py found. Setting up virtualenv
remote: New python executable in /var/lib/openshift/x/python-2.6/virtenv/bin/python
remote: Installing setuptools............done.
remote: Installing pip...............done.
...
Sunday, March 17, 13 101
102. MORE RESOURCES
• Getting started with Django on OpenShift
https://openshift.redhat.com/community/get-started/django
• openshift-django-example
https://bitbucket.org/mdoglio/openshift-django-sample
• Rapid Python and Django app deployment
https://openshift.redhat.com/community/blogs/rapid-python-and-django-app-
deployment-to-the-cloud-with-a-paas
Sunday, March 17, 13 102
103. ELASTIC BEANSTALK
by Amazon Web Services
Leverages EC2 and S3, Auto-scaling
Sunday, March 17, 13 103
109. ANATOMY OF GAE
lib directory needed since GAE can’t
pip install -r requirements.txt
modified settings file: add lib dir to
python path and DB settings
config file which defines libraries
and static files mappings
Sunday, March 17, 13 109
113. Stackato postinstall
OpenShift .openshift/action_hooks/deploy
Sunday, March 17, 13 113
114. Stackato OpenShift Dotcloud Heroku
Python 2.7, 3.2 2.6 (2.7) 2.6.5, 2.7.2, 2.7.2
stackato runtimes
3.1.2, 3.2.2
PostgreSQL 9.1 8.4 9.0 9.1.6
MySQL 5.5 5.1 5.1 (Yes, via RDS)
Persisted FS Yes Yes Yes (Yes, via S3)
Redis Yes, 2.4 No Yes, 2.4.11 (Yes, via addon)
MongoDB Yes, 2.0 Yes, 2.2 Yes, 2.2.1 (Yes, via addon)
Memcached Yes, 1.4 No Yes (Yes, via addon)
RabbitMQ Yes, 2.4 No Yes, 2.8.5 (Yes, via addon)
Solr No No Yes, 3.4.0 (Yes, via Websolr)
Cron Yes Yes Yes Yes
Extensible Yes, apt-get install Yes, DIY cartridge Yes, custom service Yes, buildpacks
WebSockets Yes Yes Yes Yes, via Pusher add-on
Sunday, March 17, 13 114
115. Google App Engine Elastic Beanstalk
Python 2.7 2.6
PostgreSQL No No
MySQL 5.5 via Cloud SQL Yes, via RDS
Persisted FS Yes, via Blob storage Yes, via S3
Redis No No
MongoDB No No
Memcached Yes Yes, ElasticCache
RabbitMQ No (SQS)
Solr No (CloudSearch)
Cron Yes, via Task Queues No
Extensible No Yes, via AMI
WebSockets Yes, via Channel API No
Sunday, March 17, 13 115
116. WHY NOT PAAS?
• Already invested in your own infrastructure.
• Need to run on servers outside U.S.
• Special requirements not met by PaaS services
Sunday, March 17, 13 116