Elevate Your PHP to the Cloud

Elevate Your PHP to the Cloud

Tutorial Details

This article will walk you through cloud hosting for your PHP application with Pagoda Box. It’ll detail how to handle PHP dependencies, get your MySQL databases up and running (and debug locally), and customise various aspects of PHP with ease.


Introduction

As a developer who has been playing around with PHP since the age of 11, it’s hard to remember many things that have absolutely changed the way I develop. In 2007, I picked up CodeIgniter, which made me rethink how I structure my code and use OOP to get things done. In 2010, I began working with Git and Git Flow for teamwork and branching, but, recently, the biggest thing to change my development workflow has been one “Platform as a Service,” called Pagoda Box.

You might be a rockstar developer who knows how to set up a LAMP stack, but how much of your potential development time do you waste setting it up, optimizing it, securing things, locking it down, scaling resources and monitoring traffic.

Every day, I spot a developer battling to defend his server from some group of hackers or script kiddies, getting port flooded, having trouble getting some random security patch working, struggling to migrate to larger more powerful servers, getting mad trying to set up Capistrano, the list goes on. Services like Pagoda Box can help you skip all of that; so let’s see how.


Step 1 - Register With Pagoda Box

The first step is to grab yourself an account. It’s free, so go ahead.

Register

Step 2 - Create Your Application

Each application needs to have a unique name, as they are also used for preview URLs. You can call this application whatever you wish, as you will be hiding it behind a domain shortly, but call it something obvious and memorable.

SSH Key form

Step 3 - Set Up Git

Git is an extremely useful version management system. Right now, it is massively popular thanks to sites like GitHub who allow for free social code hosting, but it is also great for deploying your code.

If you are new to Git then try the crash course.

If you haven’t already, set up Git. Their documentation will help you get started. Windows users will find it a little more difficult than OSX or Linux users, so if you have a Virtual Machine of Ubuntu lying around, now would be a great time to fire it up.


Step 4 - Create Your SSH Key

To push your code to Pagoda Box you need to authorize your computer to have push access to applications on your account. Create an SSH key and paste it here.

SSH Key form

Step 5 - Deploy Your Code

First, set up a folder for your application and set the Git remotes. Remotes are essentially nicknames for a repository URL. By setting up this remote, we’re letting our local Git repo know how to push code to Pagoda Box.

	$ mkdir my-awesome-app && cd my-awesome-app
	$ git init
	Initialized empty Git repository in /Users/phil/Sites/my-awesome-app/.git/
	$ git remote add pagoda git@git.pagodabox.com:my-awesome-app.git

Now with all of this account and environment setup done, we can start deploying code. For now, we’ll deploy a simple Hello World app:

	$ echo '<?php echo "Hello World!";?>' > index.php

This is a little command line trick to put some text into a file. You could alternatively create this file with your favorite text editor or IDE.

	$ git add index.php 
	$ git commit -m "OH HAI"
	[master (root-commit) 6aa23f4] OH HAI
	 1 files changed, 1 insertions(+), 0 deletions(-)
	 create mode 100644 index.php

So far, we have made a new folder for our website, initialized Git, added a remote which tells Git where the Pagoda Box app lives, and added a new index.php file, which will simply say Hello World!. Next:

	$ git push pagoda master
	Counting objects: 3, done.
	Writing objects: 100% (3/3), 244 bytes, done.
	Total 3 (delta 0), reused 0 (delta 0)
	
	:: Auto deploy enabled for 'master'
	 +> to change, visit https://dashboard.pagodabox.com/apps/my-awesome-app/admin
	:: Deploying to 6aa23f4 on master
	:: Parsing Boxfile
	:: Executing deploy
	 +> Init submodules
	 +> Booting web1.1
	  - [22-Feb-2012 20:38:41] NOTICE: fpm is running, pid 54
	  - [22-Feb-2012 20:38:41] NOTICE: ready to handle connections
	 +> Propagating network updates
	:: Cleaning up
	
	To git@git.pagodabox.com:my-awesome-app.git
	 * [new branch]  master -> master

This is where the magic happens. You will push to a Git remote like any other repository, but then you will see the output of Pagoda Box taking over and creating a deployment. This will fire up a new instance each time and switch over from the live instance to this new instance instantaneously, meaning immediate updates – unlike slow FTP-based file deployment systems. Also unlike some similar services, all of your temporary files (cache, logs, image uploads, etc) will be there after any resize or re-deployment. Awesome!

Now if you refresh the Pagoda Box page, you will see a Dashboard with all sorts of options.


Step 6 - Creating a Boxfile

Pagoda Box has a special config file: Boxfile. This goes in the root of your application. An advanced example may look something like this:

web1:

  ################################################
  ## GENERAL SETTINGS
  ################################################
  shared_writable_dirs: [/system/cms/cache, /system/cms/logs, /uploads, /addons]

  ################################################
  ## WEB SPECIFIC SETTINGS
  ################################################
  index_list: [index.php]

  ################################################
  ## PHP SPECIFIC SETTINGS
  ################################################
  php_version: 5.3.8
  php_extensions: [mysqli, curl, gd, mbstring]
  php_date_timezone: Europe/London
  php_max_execution_time: 30
  php_max_input_time: 60
  php_post_max_size: 25M
  php_file_uploads: On
  php_upload_max_filesize: 20M
  php_max_file_uploads: 20

This example gives you the chance to create writable folders, set your index_list (which is index.php by default) and change all sorts of PHP settings that would normally be in a php.ini file.

The most important line here is:

	php_extensions: [mysqli, curl, gd, mbstring]

Pagoda Box allows you to list your applications dependencies. The “mysqli” driver is “MySQL Improved” which you should start using, as “mysql” is going to be deprecated in PHP 5.4. “curl” and “gd” are fairly standard and “mbstring” helps you work with UTF-8 code.

It’s good to know they are available – along with plenty of others – but for this tutorial we’ll only need the following:

	php_extensions: [pdo, pdo_mysql]

So let’s make our new Boxfile and save it:

web1:	
  php_extensions: [pdo, pdo_mysql]

We’ll be using this later on.


Step 7 - Create a Database

At the time of this writing, Pagoda Box only supports MySQL databases, which is fine as that is what the majority of developers use.

We can fire up as many small database instances as we like for free; we only start paying when they get bigger, so you won’t get surprised by a massive bill just for building a website. Just like the web instances, they can also be scaled to grow with your website.

New Database

To make a new one, click the + icon and give it a name. You’ll see a progress bar up top while it builds; then the page will refresh.


Step 8 - Connecting From Your App

Connecting via PHP is a cinch. You are given multiple $_SERVER variables, which contain credentials for each database you have. This means you can keep hard-coded passwords out of your application – which is very useful if you don’t want all of your developers to see live passwords, or if you have your complete website on GitHub, like some people are beginning to do.

$db = new PDO(sprintf('mysql:host=%s;dbname=%s;port=%s', $_SERVER['DB1_HOST'], $_SERVER['DB1_NAME'], $_SERVER['DB1_PORT']), $_SERVER['DB1_USER'], $_SERVER['DB1_PASS']);

This is a basic example of the variables in use – connecting to your MySQL database via the PDO extension. If you’re using a framework, such as CodeIgniter, you can shove those variables into your database.php config files.


Step 9 - Connecting Remotely

Some web servers – especially those run-of-the-mill cPanel set-ups – have phpMyAdmin installed and can be configured to allow remote access to the MySQL databases.

Instead of this approach, Pagoda Box uses Ruby Gem for – amongst other things – creating a temporary secure SSH tunnel. This means your MySQL databases are locked down behind a firewall and are only accessible via this secure SSH connection.

So, to install the gem run:

	$ sudo gem install pagoda

Then to create the tunnel, simply run:

	$ pagoda tunnel db1

The first time you run this (or any other pagoda gem command) you should be asked for a username and password. This is your Pagoda Box username and password, and is needed so that the gem can act on your behalf and is nothing to do with your database.

	$ pagoda tunnel db1
	it appears this is the first time you have used our client
	  Username: someguy
	  Password: 
	
	Tunnel Established!  Accepting connections on :
	-----------------------------------------------
	
	HOST : 127.0.0.1 (or localhost)
	PORT : 3307
	USER : (found in pagodabox dashboard)
	PASS : (found in pagodabox dashboard)
	
	-----------------------------------------------
	(note : ctrl-c To close this tunnel)

Go to your dashboard and click on the database, then click “Show Credentials” to see a info window like this:

Database Credentials

Use these credentials to connect. Don’t forget to specify which port; it is listed in the output from the gem above – not the green box. Remember, you are connecting to the local tunnel, not directly to the database.


Step 10 - Making a Blog

What sort of tutorial would this be if it didn’t involve making a blog in 20 minutes?

For all development you should really be building things locally using MAMP, XAMPP, WAMP, etc., then deploying code and database changes using some sort of “Migrations” or schema change tracking stuff, but we’ll do this the old fashioned way.

First connect to your database remotely via the tunnel, then run this query to build a new table:

CREATE TABLE posts (
  'id' int(11) NOT NULL AUTO_INCREMENT,
  'title' varchar(255) NOT NULL,
  'slug' varchar(255) NOT NULL,
  'summary' text NOT NULL,
  'body' text NOT NULL,
  'created_at' int(11) NOT NULL,
  'updated_at' int(11) NOT NULL,
  PRIMARY KEY (id)
) ENGINE=InnoDB;

INSERT INTO posts VALUES
('1', 'Women love guys who use FuelPHP', 'women-love-guys-who-use-fuelphp', 'It is a well proven fact that girls love developers, but things have never been so good for PHP developers. Everyone who starts using FuelPHP gets 150% more women within the first month. Fact.', 'It is a well proven fact that girls love developers, but things have never been so good for PHP developers. Everyone who starts using FuelPHP gets 150% more women within the first month. Fact.', '1322825332', '1322934052'),
('2', 'People who echo HTML from apps die younger', 'bad-practises', 'Scientists have proven that PHP developers who echo HTML directly our of PHP files die younger. Often it happens while the developer is in the office. While sat at their chairs they suffer multiple wounds, but apparently there are no witnesses, even though their colleagues were in the office \"refactoring bad code\" all day.', 'Important body text', '1322826479', '1322826479');

With some test posts in place we can create this index.php:

<?php 

	$db = new PDO(sprintf('mysql:host=%s;dbname=%s;port=%s', $_SERVER['DB1_HOST'], $_SERVER['DB1_NAME'], $_SERVER['DB1_PORT']), $_SERVER['DB1_USER'], $_SERVER['DB1_PASS']);
	
	$posts = array();
	foreach ($db->query('SELECT * from posts') as $row)
	{
		echo "<h2>{$row['title']}</h2>";
		echo "<p><em>Posted: ".date('l jS \of F Y', $row['created_at'])."</em><br />";  		echo $row['summary']."</p>";
	}

With that file saved, and our new Boxfile (from step 6) in place, we can deploy these new changes:

	$ git add Boxfile index.php
	$ git commit -m "Added Boxfile and deployed index.php changes"
	$ git push pagoda master

Go to “http://my-awesome-app.pagodabox.com” and see the output:

Database Credentials

This is clearly not something that you’ll want running on your website, but it does enough. You can see that your database content is being output to the browser, and your demo URL is working. You can replace this with your CMS of choice, or build something custom.


Step 11 - Use a Real Domain

There is no point having your wonderful new blog on a pagodabox.com subdomain; so let’s park a domain on top of it.

First, in the DNS/SSL tab of your dashboard, add in some entries for your domain:

Database Credentials

Now that your application is ready to accept a domain you should head over to whoever handles the DNS for your domain. Go to the DNS management area and set an A record for "myawesomedomain.com" to be "50.97.141.37" – which is the IP address listed on the interface for your app. These IP addresses are not unique per application, but will not always be the same. Set a CNAME record for "www.myawesomedomain.com" to alias "myawesomedomain.com" and you should be all set.


Summary

This may all seem rather different from how you work at the moment, but start to think about how much work you are saving yourself in the long run. Using PaaS is the same reason we use jQuery over native JavaScript, or PHP frameworks over writing native PHP. Why mess around with minor details when you can instead focus on building an awesome app?

Other alternatives you might consider are PHPFog and Orchestr.io, which both offer similar services. Have fun, and thanks for reading!

Note: Want to add some source code? Type <pre><code> before it and </code></pre> after it. Find out more
  • ‘Neko

    Nice post, this will surely fuel my skils in php ;)

  • http://ozweegoville.com kcmerrill

    One thing that really interested me with pagoda box was it’s undo feature. So you can quickly revert changes if your push did end up breaking something.

    +1 for the article.

    • http://www.danharper.me Dan Harper

      You can rollback a commit with:

      git push -f phpfog df062ee:master

      That will force push commit SHA df062ff to the master branch on the phpfog remote.

  • http://www.danharper.me Dan Harper

    We’ve recently been using PHP Fog at work, and I’ve got to say that having moving everything to a Git-powered setup, working is just that much easier.

    I can’t quite believe I used to manually upload files through FTP, incredibly slowly. Deployment with Git is just the next logical step.

    • http://twitter.com/drale2k Drazen Mokić

      I totally agree and the next big thing i can’t believe is the absence of a task management tool for PHP, like “rake” for Ruby.

      I’ve seen something like “Phake” and i think Phil’s Fuel PHP framework has something like that but as far as i remember none of them is nearly as powerful and easy to use.

      I also would like to see some preprocessor for PHP, like coffee for js.

      Thanks for the tut!

      • http://blog.icambridge.me Iain Cambridge

        Drazen Mokić – Sounds like you need to check out phing. Which is a build tool based on ant. It’s extremely powerful and extremely easy to use and extend.

        However I have to disagree with a git deployment being the way forward as it has some major limitations. For one on platform such as PHPFog if your application creates files these files aren’t entered into the version control. Which means if you’re are using an application such as WordPress and use the plugin installer functionality from the admin dashboard you are unable to edit or modify the plugin files. With no FTP you are stuck with a very unclean application install. Also if you have it so that your application writes files such as css files based on CSS and you have your server pulling from github every time there is a change you can end up with conflicts and your day being ruined by constant merging and conflict fixes on your production server. Major pain in the ass.

        I’m not sure how Orchestra and pagodabox handle their deployments from github maybe they migrate away from these two issues by have a git “hub” server which handles pulling from the production server and then pulling from github and then pushing back to the production server. However I really do like the fact you can commit to github and it automatically deploys. I guess it really depends on what your application is doing, maybe the issues I’ve dealt with file creation won’t affect your application if not then git deployment rocks.

      • Nico Schneider

        Well, technically, PHP *is* a preprocessor, for hypertext:

        “While PHP originally stood for “Personal Home Page”, it is now said to stand for “PHP: Hypertext Preprocessor”, a recursive acronym.” – http://en.wikipedia.org/wiki/PHP

  • http://www.udgwebdev.com Caio Ribeiro Pereira

    Another PaaS for PHP who I enjoy so much is the new Red Hat OpenShift which support many programming languages like PHP, Ruby, Python… and databases like MySQL, MongoDB for free.

    You just need to use Git and the OpenShift CLI.

    I have two blogs using OpenShift Express (Free Version Cloud Host) using WordPress.
    http://www.udglinux.com and http://www.udgwebdev.com

    By the way I made a post explaining how to use WordPress for free on OpenShift.
    http://www.udgwebdev.com/hospedando-wordpress-no-cloud-openshift/

  • Smiti

    Nice post

  • http://maomuffy.blogspot.com Mfawa Alfred Onen

    Nice Article Phil!

  • Pagoda-Newb

    Sorry if these are really obvious questions but here goes:

    Using a normal server, I get a certain package for £X, but how do I work out the price for the same package on pagoda box? I know they have pricing, but they have ‘MB of RAM per instance’ where as on a normal server, you are given a set amount of webspace etc.

    Basically, if I want to move across a standard site with a few pages that will not require scaling – what do I pay.

    Also would Pagoda be classed as suitable for high level websites such as ecommerce etc… parking the domain over a sub domain seems a bit low level.

    • http://philsturgeon.co.uk Phil Sturgeon
      Author

      You are asking for definitive answers to vague questions with no metrics. Pagoda Box will take a big load without much cost. Free handles a lot, lowest options get a lot.

      It will also support ecommerce. “high level” doesn’t actually mean anything! :)

  • Guillermo

    How about DotCloud? Does anyone have use it for running PHP apps? Is there any good reviews?

  • Ali

    I am wondering if there are any drawbacks of using this or other paas for php.
    Sorry if I am missing the obvious here, but I am a complete noob.

    • http://philsturgeon.co.uk Phil Sturgeon
      Author

      The most obvious drawback is that you cannot install your own software, but that has not been a problem for me yet as most of my websites are built with PyroCMS which has very simple requirements.

      They have MySQL, Memcache, MongoDB – coming soon and most of the software you need. If you need more then stick with a VPS or fire up an EC2 instance.

  • Nathan

    Very interesting service, but what the hell is up with their pricing? $ 23 / month for a database with 200mb of ram?! How on earth do they justify that??

    • http://philsturgeon.co.uk Philip Sturgeon
      Author

      Amazon RDS charge $80 a month. Cloud things are different.

    • http://philsturgeon.co.uk Phil Sturgeon
      Author

      How does Amazon Web Services justify $80 a month for a small RDS instance? In comparison, Pagoda Box is cheap.

      When you compare the price of a PaaS it is not about “This is a MySQL database, I can install one of those for free”. You have to take everything into account:

      Support
      Security
      Monitoring and Statistics
      Potential to Scale

      None of those will happen on your own little MySQL instance, which could fall over when a link to your blog hits reddit for example. If that happens some PaaS can auto-scale (costing you more money) or I can just hit a slider and have a much bigger website within a few seconds.

      That – to me – is worth $23 a month.

      • Nathan

        Amazon’s small RDS instance has 1.7GB of RAM though, which if you calculate it means that Amazon charges you around 9 bucks for the same amount of RAM that Pagoda Box charges 23 dollar for.

        I have no doubt that they provide a fantastic service, and I’m all for paying a fair amount.. but 23 dollar for 200 mb of RAM just seems way too high, even with the added service they provide.

        You can’t really call “ability to scale” an added value that justifies a higher price, as the very act of scaling itself already has a pricetag attached to it.

        I’m simply wondering if I’m missing something though. Do they somehow manage to make far better use of that 200MB of RAM than a regular dedicated MySQL server would?

      • http://philsturgeon.co.uk Phil Sturgeon
        Author

        “Amazon’s small RDS instance has 1.7GB of RAM though”

        Which is way more than anyone needs for the average site.

        “which if you calculate it means that Amazon charges you around 9 bucks for the same amount of RAM that Pagoda Box charges 23 dollar for”

        Well no thats not how it works. If I want “A database” with RDS I am paying $80 straight off the bat, which is too much. Pagoda Box start smaller and make you pay less, which is great. If you start talking dollar-per-megabyte you can make all sorts of comparisons, and I have no doubt Amazon are cheaper at high level, but that doesn’t help Joe Bloggs get his Blog running for a reasonable amount.

        “You can’t really call “ability to scale” an added value”

        I certainly can. I can have 1x server for $9 a month with a DB instance on it, but if that takes me a few hours to scale, or even a day to set up proper replication for a smooth switchover then that has just cost me hundreds of dollars in potential income.

        The point is, if you’re farming out websites and farming out work, then why complain about a few dollars a month if you can get websites running on a secure environment twice as fast?

        This is literally the same argument the Ruby community has had – and got over – during the last few years with Heroku: Watch the pennies, or just pay a little more, get shit done and go for the big money.

        You decide.

      • Nathan

        We could keep going back and forth disputing what the other said, but I suppose it boils down to whether or not the service you get is worth the increased price. To me the service is definitely worth paying extra for, but the DB pricing just seems too excessive. I might use them for future projects with a medium to large scope, but not to host a simple blog that might catch on.

        Thanks for the review, I’ll definitely keep an eye on them.

  • http://imknight.net knight

    Could there be a comparison post among these PHP based paas ?

  • http://natetronn.com Natetronn

    Wow! Only 8 comments, what gives?

  • Pritesh Desai

    I’m getting an error

    C:\Users\Pritesh\my-blog>git push pagoda master
    ssh: connect to host git.pagoda.com port 22: Bad file number
    fatal: The remote end hung up unexpectedly

    I’m at step 5

  • Omar Hitter

    this is great, thanks dude ….. :)

  • Pierre Paul

    Spend my afternoon on it, and it works really well !

    But I am still very skeptical… It seems to be a young company, not sure if it’s reliable, no info about it. Also no big website seems to use it…. Not sure how fast is it under heavy load… And the server specifications seems light….

    I will launch a medium / big size website soon, I was going to rent a dedicated server but now I hesitate…. not sure what to do….

    I suppose PHP Paas is nice but has yet to prove itself…

    What do you think about that ?

    Good article ! cheers from France.

    • http://philsturgeon.co.uk Phil Sturgeon
      Author

      It absolutely depends on your definitions of “large”.

      I am handling 200,000 page views a month on pyrocms.com which is not large but is not small either. It only had some performance issues due to a badly written SQL query, nothing to do with PaaS.

      They have been around for over a year, they have got through most of the hard times (I’ve been there through all of them >.<) and they have come out the other site with a great service that scales well.

      Look at it like this: just because PaaS exists does not mean it is always right for everything. If you were going to get a dedicated server and look after it yourself, or you have a team of sysadmins to look after it then you obviously don't need PaaS.

      If you are a start-up company and you don't have that then you don't NEED to worry about that dedicated server for a year or two anyway.

      Deploying to Pagoda Box (or any of the other PaaS' mentioned) is rather easy. Put it on there for the start and let it grow as you grow. If you outgrow them then move away to a dedicated server – by that time I'd assume you have investment, more money, whatever, and can afford it anyway.

      It's a different way of thinking and can sometimes just be a temporary use case, it's not just "the new thing that replaces the old thing".

  • http://anarinfo.com/ Anaradam

    Great article. Its very nice. Thanks for sharing with us.

  • Jim

    Great article. I’ve been using PHPFog for about 4 months now. There service is stelllar and they respond quick to issues. It is annoying the DB is shared and not a dedicated instance. But that feature is coming soon and they had other platform priorities first. I use Xeround for my DB and have a dedicated AWS instance running redis. It all works like a charm.

  • http://www.peterbriers.be Peter Briers

    Just began playing with PagodaBox last month.
    Loving it for my apps!

  • dimon

    nice article but as for me i have local server and it’s just good for me right now.

    I really enjoyed “ur blog in 20 min” and would like to see article of creating some simple blog as u write with some comments module, readmore and some sort of admin page.

  • Tesh

    Philip, this is a great article and quite helpful – i was able to fix my problem and get rolling. Thanks!

  • Lucky

    Great article. I have been able to host my site on pagodabox using this. Just one thing, i don’t see an “email hosting” feature with pagodabox. I used to have this with my Godaddy account. Now how do i receive emails on domain email address? Thanks!