Deploying web applications using Juju on EC2 (Part 1/3)
Canonical
on 26 September 2013
Tags: Tutorial
The goal of this tutorial series is to demonstrate the power of Juju service orchestration for deploying web applications and infrastructure services in the cloud, in this case on Amazon EC2.
Juju is a service orchestration framework that is designed to make it very easy for application designers to deploy their applications in an easy, repeatable and logical manner without all that tedious mucking about with custom configuration files and logging in to servers.
The key differentiation with Juju is that it focuses on “Services” and their “Relationships”, not on individual servers or configurations, like a typical configuration management tool would.
Setting up Juju-core
Juju-core is now the latest version of Juju that is recommended for testing and development and is fast approaching its 2.0 release. Currently (September 2013) we are on release version 1.13.3 and most of the functionality is available for deploying to EC2 and Openstack clouds.
I will assume that you already have access to an Ubuntu Desktop or Server machine running the latest version of Ubuntu 13.04, the Raring Ringtail release. Although, the same steps can be carried out on any release from 12.04 LTS onwards.
So, let’s set up our Juju environment for Amazon EC2.
On your Ubuntu Desktop or Server run the following commands at the terminal:
sudo apt-get -y install python-software-properties sudo add-apt-repository ppa:juju/stable sudo apt-get update && sudo apt-get install juju-core
To generate an initial config file, you simply need to run:
juju init
This command will cause a file to be written to your ~/.juju directory if an environments.yaml file does not already exist. It will also create the ~./juju directory if that does not exist.
The contents of this file will look something like this:
## https://juju.ubuntu.com/get-started/amazon/ amazon: type: ec2 admin-secret: 989b97c439357947449d994720 # globally unique S3 bucket name control-bucket: juju-a28403f89d8245543d3cab01f1ca4a3e # override if your machine is on a different series than what you're deploying # default-series: precise # region defaults to us-east-1, override if required # region: us-east-1 # Usually set via the env variable AWS_ACCESS_KEY_ID, but can be specified here # access-key: # Can be set via the env variable AWS_SECRET_ACCESS_KEY, or specified here # secret-key:
Values for the default setting can be changed simply by editing this file, uncommenting the relevant lines and adding your own settings. All you need to do to get this configuration to work is to either set the AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY via environment variables, or uncomment and add the values to the configuration file.
You also want to create your own admin-secret as this is used to gain access to your environment on EC2 and so it should be a strong password of your own. The control bucket needs to be globally unique, so you should not use this one, but also create your own unique name.
You can retrieve your AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY easily from your AWS Management Console at http://console.aws.amazon.com. Click on your name in the top-right and then the “Security Credentials” link from the drop down menu.
Under the “Access Keys” heading click the “Create New Root Key” button. You will be prompted to “Download Key File” which by default is named rootkey.csv. Open this file to get the access-key and secret-key for the environments.yaml configuration file.
You must also have an SSH key installed under the current users ~/.ssh/ directory. If you haven’t already got an SSH key, then generate one with:
ssh-keygen -t rsa -b 2048
If you are on an Ubuntu version that is not Precise Pangolin (i.e. 12.04 LTS) then uncomment the default-series value.
Then bootstrap the Juju environment, this starts the first Juju server that will have a state server of your entire Juju environment and will be responsible for deploying other juju services.
You will have to wait for this server instance to start and it normally takes approximately 10 minutes to complete on Amazon EC2.
Once completed you will be able to check with:
juju status
The status output should be something like this:
environment: amazon machines: "0": agent-state: pending dns-name: ec2-54-221-34-86.compute-1.amazonaws.com instance-id: i-5a1fe130 instance-state: running series: precise hardware: arch=amd64 cpu-cores=1 cpu-power=100 mem=1740M root-disk=8192M services: {}
Deploying Juju Gui
First we want to deploy the Juju GUI. When deploying new services Juju defaults to installing each new service on a separate server.
But, we can also tell Juju to co-locate a service on an already deployed server using the following syntax:
juju deploy juju-gui –to 0
This deploys the Juju-gui service to the server 0, which is the Juju bootstrap node.
During deployment you can check the status using:
juju status
Which should look something like this:
environment: amazon machines: "0": agent-state: started agent-version: 1.13.3 dns-name: ec2-54-221-34-86.compute-1.amazonaws.com instance-id: i-5a1fe130 instance-state: running series: precise hardware: arch=amd64 cpu-cores=1 cpu-power=100 mem=1740M root-disk=8192M services: juju-gui: charm: cs:precise/juju-gui-76 exposed: false units: juju-gui/0: agent-state: pending agent-version: 1.13.3 machine: "0" public-address: ec2-54-221-34-86.compute-1.amazonaws.com
We also need to make the security group allow connection to the Juju gui on the web port, 80.
We do this by exposing the service as follows:
juju expose juju-gui
Once deployment is completed juju status should look something like this:
environment: amazon machines: "0": agent-state: started agent-version: 1.13.3 dns-name: ec2-54-221-34-86.compute-1.amazonaws.com instance-id: i-5a1fe130 instance-state: running series: precise hardware: arch=amd64 cpu-cores=1 cpu-power=100 mem=1740M root-disk=8192M services: juju-gui: charm: cs:precise/juju-gui-76 exposed: true units: juju-gui/0: agent-state: started agent-version: 1.13.3 machine: "0" open-ports: - 80/tcp - 443/tcp public-address: ec2-54-221-34-86.compute-1.amazonaws.com
Now you can connect to Juju-gui using your web browser by connecting to the public-address.
You will be presented with a login screen for Juju-gui.
The username is “admin” and the password is the same as your ~/.juju/environments.yaml “admin-secret” entry.
Once you have logged in you will see a Juju-gui screen that looks like this:
Deploy Nagios Monitoring Service
Our first infrastructure service is going to be Nagios monitoring server, so we can monitor the state of our deployed services.
So, let’s deploy the server.
From the command line, it is as simple as:
juju deploy nagios
You should now see the Nagios monitoring server deployed in the Juju Gui with an icon and a yellow bar showing it is pending.
Once it is deployed the bar will turn green.
Then we need to expose the service, to open the security group to allow connection on port 80.
juju expose nagios
Juju status should now look like this:
environment: amazon machines: "0": agent-state: started agent-version: 1.13.3 dns-name: ec2-54-221-34-86.compute-1.amazonaws.com instance-id: i-5a1fe130 instance-state: running series: precise hardware: arch=amd64 cpu-cores=1 cpu-power=100 mem=1740M root-disk=8192M "1": agent-state: started agent-version: 1.13.3 dns-name: ec2-54-211-5-1.compute-1.amazonaws.com instance-id: i-764a2e13 instance-state: running series: precise hardware: arch=amd64 cpu-cores=1 cpu-power=100 mem=1740M root-disk=8192M services: juju-gui: charm: cs:precise/juju-gui-76 exposed: true units: juju-gui/0: agent-state: started agent-version: 1.13.3 machine: "0" open-ports: - 80/tcp - 443/tcp public-address: ec2-54-221-34-86.compute-1.amazonaws.com nagios: charm: cs:precise/nagios-4 exposed: true units: nagios/0: agent-state: started agent-version: 1.13.3 machine: "1" open-ports: - 80/tcp public-address: ec2-54-211-5-1.compute-1.amazonaws.com
We will also need to retrieve the automatically configured password to connect.
You can do this by running the following command:
juju ssh nagios/0 sudo cat /var/lib/juju/nagios.passwd
This will print the password to your terminal window.
You can now connect to the Nagios web interface using the public-address from juju status above and the username “nagiosadmin” with the password you retrieved in the terminal window.
Nagios should display only 1 host, localhost, and associated services.
Deploying our First Web Application
So, now we have a monitoring server to monitor the services we deploy, let’s start by deploying a simple web application, like the ever popular, wordpress.
The services required to run a WordPress blog are:
-
SQL database
-
WordPress Application Server
We will use MySQL as the database server, so let’s deploy it.
This time rather than using the command line let’s use the Juju Gui to deploy the MySQL server.
First search for MySQL using the Search bar on the left hand side.
Then click on the MySQL server in the list.
Click on “Add to my Canvas”.
This will bring up a list of parameters you can modify on the right hand side.
Just click on “Confirm” to confirm the deployment.
Again, you will see a yellow bar when the service is “pending” and a green bar when it is “started”.
We also want to deploy the wordpress application server, so again using the Gui search for wordpress and deploy it.
Once both services are deployed and the bars are green, you can start adding our first relationships.
Adding Relationships
Services are only really useful once they are aware of each other and that is where relationships come in.
We add relationships to make a service work with another service.
So, first we should add a relationship between our WordPress application server and the MySQL database, so that the WordPress blog has somewhere to store all its data.
We can do this from the command line using the command:
juju add-relation mysql wordpress
Alternatively, to do it from the Gui, click on the WordPress Icon and then select “Build relation” and join it to the Mysql Icon.
This will set up a Database relationship between the WordPress Application server and the MySQL database.
It will then configure the database for WordPress, set a user and password and configure the tables required, all automatically.
Now all we need to do is expose the WordPress Server so we can connect to it.
From the Gui click on the WordPress icon and select “view”.
Now click on the “Expose” slider on the top right of the screen.
Now click on the unit box to bring up the unit details screen.
This shows you the public address to connect to.
Copy and paste the address into your browser to access the new WordPress Blog.
Now you can access your new WordPress blog and configure the details, such as the name, e-mail address and password for the admin user.
Do this now and make sure you set a reasonable password.
Monitoring your new blog
Now we have a working WordPress Blog it is time to add the monitoring so that the monitoring server tests the services are available and detects any failures.
To do this we simply add a relation to the nagios monitoring server.
At the command line we would run the command:
juju add-relation mysql nagios juju add-relation wordpress nagios
Or just add the relations using the gui like before, click the icon, select build relation and join the relationship.
Once this is done your screenshot should look like this:
Now if we wait for the relationships to build and then check the Nagios server, we should find that the MySQL server and WordPress server are now being monitored by Nagios.
Deploy NRPE Subordinate Service
Now lets move on to the next service we need to deploy, NRPE.
NRPE is the Nagios Remote Plugin Executor and it is an agent that you install on each monitored server.
The purpose of the agent is to allow tests to run on the monitored server on request from the monitoring server.
So, for example, a local disk test to check for free space is run from NRPE when the Nagios server requests it, so that you can see when the disk is filling up and you need to take action. It allows for more detailed tests to be carried out on each monitored server.
Now, as the NRPE service is installed on the monitored server and not as a service itself, it is known as a Subordinate Service.
A Juju Subordinate Service is a service which is installed on a server in addition to its primary service and so it allows for units of different services to be deployed into the same container and to have knowledge of each other.
To deploy a subordinate service, first you deploy the service (which just sets up it’s configuration) and then you relate it to each service where you actually want to install it.
In this case, we first deploy the NRPE service, then relate it to the nagios server itself.
juju deploy nrpe juju add-relation nrpe:monitors nagios:monitors
Now we add relationships to the monitored services:
juju add-relation nrpe:local-monitors mysql:local-monitors juju add-relation nrpe wordpress
If we now go and check the nagios monitoring server we should now find extra NRPE tests are added for the MySQL and WordPress services.
Summary
In this tutorial, you learnt how to deploy a Juju environment, how to deploy the Juju web gui and how to deploy the Nagios monitoring server and your first web application, a wordpress blog.
Next time we will add some more infrastructure services, such as logging and graphing and show you how to scale your web application under load.
Darryl Weaver
EMEA Cloud Sales Engineer, Canonical
Part 2
In part 2 we will set up the rsyslog log server, munin graphing server and landscape-client for managing packages. Then add relationships to the mysql and wordpress services so they are logged, graphed and managed.
Ubuntu cloud
Ubuntu offers all the training, software infrastructure, tools, services and support you need for your public and private clouds.
Newsletter signup
Related posts
DIY chiselled Ubuntu: crafting your own chiselled Ubuntu base image
In a previous post, I explained how we made our Ubuntu image 15 times smaller by chiselling a specific slice of Ubuntu for .NET developers. In this blog, I...
Open source cloud platform: meet OpenStack
Are you looking for an open source cloud platform and you don’t know where to start? Are you getting lost in all the independent rankings and cloud platform...
Let’s build a snap together – a complex snapcraft.yaml walkthrough
It has been a while since we talked about how to build snaps. In the past, we went through a number of detailed examples, focused on different programming...