At re:Invent 2016, Amazon introduced Lightsail, the newest addition to the list of AWS Compute Services. It is a quick and easy way to launch a virtual private server within AWS.
As someone who moved into the AWS world from an application development background, this sounded pretty interesting to me. Getting started with deploying an app can be tricky, especially if you want to do it with code and scripting rather than going through the web console. CloudFormation is an incredible tool but I can’t be the only developer to look at the user guide for deploying an application and then decide that doing my demo from localhost wasn’t such a bad option. There is a lot to learn there and it can be frustrating because you just want to get your app up and running, but before you can even start working on that you have to figure how to create your VPC correctly.
Lightsail takes care of that for you. The required configuration is minimal, you pick a region, an allocation of compute resources (i.e. memory, CPU, and storage), and an image to start from. They even offer images dedicated to tailored to common developer setups so it is possible to just log in, download your source code, and you are off to the races.
No, you can’t use Lightsail to deploy a highly available load balanced application, but if you are new to working with AWS it is a great way to get a feel for what you can do without being overwhelmed by all the possibilities. Plus once you get the hang of it you have a better foundation for branching out to some of the more comprehensive solutions offered by Amazon.
Deploying a Node App From Github
Let’s look at a basic example. We have source code in Github, we want it deployed on the internet. Yes, this is the monumental kind of challenge that I like to tackle every day.
You will need:
- An AWS Account
- At this time Lightsail is only supported in us-east-1 so you will have to try it out there.
- The AWS Command Line Interface
- The Lightsail CLI commands are relatively new so please make sure you are updated to the latest version
- About 10 minutes
Step 1: Create an SSH Key
First of all let’s create an SSH key for connecting to our instance. This is not required, Lightsail has a default key that you can use, but it is generally better to avoid using shared keys.
aws lightsail create-key-pair \ --key-pair-name 'lightsail_demo' \ --query 'privateKeyBase64' \ --output text > 'demo.key' chmod 700 "demo.key"
Step 2: Create a User Data Script
The user data script is how you give instructions to AWS to tailor an instance to your needs. This can be as complex or simple as you want it to be. For this case we want our instance to run a Node application that is in Github. We are going to use Amazon Linux for our instance so we need to install Node and Git then pull down the app from Github.
Take the following snippet and save it as userdata.sh. Feel free to modify if you have a different app that you would like to try deploying.
readonly SOURCE_REPO='https://github.com/stelligent/chat-app' readonly APP_HOME='/opt' yum update -y yum install git -y echo 'Installing node' curl --silent --location https://rpm.nodesource.com/setup_6.x | bash - yum install nodejs -y i echo "Cloning $SOURCE_REPO in $APP_HOME" cd "$APP_HOME" || exit 1 git clone "$SOURCE_REPO" cd 'chat-app' || exit 1 npm install --no-optional npm run start
A user data script is not the only option here. Lightsail supports a variety of preconfigured images. For example, it has a WordPress image, so if you needed a wordpress server you wouldn’t have to do anything but launch it. It also supports creating an instance snapshot. So you could start an instance, log in, do any necessary configuration manually, and then save that snapshot for future use.
That being said once you start to move beyond what Lightsail provides you will find yourself working with instance user data for a variety of purposes and it is nice to get a feel for it with some basic examples
Step 3: Launch an Instance
Next we have to actually create the instance, we simply call create and refer to the key and userdata script we just made.
aws lightsail create-instances \ --instance-names 'LightsailDemo' \ --availability-zone 'us-east-1b' \ --blueprint-id 'amazon_linux_2016_09_0' \ --bundle-id 'micro_1_0' \ --user-data file://'userdata.sh' \ --key-pair-name 'lightsail_demo'
This command has several parameters so let’s run through them quickly:
- instance-names – Required: This is the name for your server.
- availability-zone – Required: An availability zones is an isolated datacenter in a region. Since Lightstail isn’t concerned with high availability deployments, we just have to choose one.
- blueprint-id – Required: The blueprint is the reference to the server image
- bundle-id – Required: The set of specs that describe your server
- [user-data-file] – Optional: This is the file we created above. If no script is specified your instance will have the functionality provided by the blueprint, but no capabilities tailored to your needs.
- [key-pair-name] – Optional: This is the private key that we will use to connect to the instance. If this is not specified there is a default key that is available through the Lightsail console.
It will take about a minute for your instance to be up and running. If you have the web console open you can see when it ready:
Once we are running it is time check out our application…
Step 4: Troubleshooting
Let’s log in and see where things went wrong. We will need the key we created in the first step and the IP address of our instance. You can get see that in the web console or through another cli command to pull the instance data.
# Full description of instance aws lightsail get-instance --instance-name 'LightsailDemo' # Return only the IP aws lightsail get-instance --instance-name 'LightsailDemo' --query 'instance.privateIpAddress' --output text # Connect ssh -i demo.key ec2-user@<IP_ADDRESS>
When you are troubleshooting any sort of AWS virtual server a good place to start is by checking out: /var/log/cloud-init-output.log
Cloud-init-output.log contains the output from the instance launch commands. That includes the commands run by Amazon to configure the instance as well as any commands from user data script. Let’s take a look…
Ok... that actually that looks like it started the app correctly. So what is the problem? Well if you looked at the application linked above and actually read the README (which, frankly, sounds exhausting) you probably already know…
If we take a look at our firewall settings for the instance networking:
Step 5: Update The Instance Firewall
We can fix this! AWS is managing the VPC that your instance is deployed in but you still have the ability to control the access. We just have to open the port that our application is listening on.
aws lightsail open-instance-public-ports \ --instance-name 'LightsailDemo' \ --port-info fromPort='3030',toPort='3030',protocol='tcp'
Then if we reload the page: Success!
That’s it, you are deployed! If you familiar with Heroku you are probably not particularly impressed right now, but if you tried to use AWS to script out a simple app deployment in the past and got fed up the third time your CloudFormation stack rolled back due to having your subnets configured incorrectly I encourage you to give Lightsail a shot.