Follow Along as I Stumble on the Path to Learning RoR

Posts tagged “amazon

Using CloudFront with S3 and Paperclip

I wanted to cache my S3 images for my Rails app, so I changed my app to serve images using AWS CloudFront, a CDN.

Doing this was pretty simple.

(1) Set-up a AWS CloudFront instance and your S3 bucket as your origin

(2) Change your Paperclip settings to use the new CloudFront instance.  I did this in production.rb (make sure neither the url or s3_host_alias values are being written by Paperclip settings in your model):

config.paperclip_defaults = {
storage: :s3,
:url => “:s3_alias_url”,
:s3_host_alias => “”,
:path => “:rails_env/:class/:attachment/:id/:style/:filename”,
:bucket => “your-bucket-name”,
s3_credentials: {
bucket: ENV[‘AWS_S3_BUCKET’],
access_key_id: ENV[‘AWS_ACCESS_KEY_ID’],
secret_access_key: ENV[‘AWS_SECRET_ACCESS_KEY’],

and that’s it!

Now, if you check the URL of your images, it should see that their source is prefaced with your CloudFront URL.

Setting Up SSL on AWS Bitnami Instance of Ruby on Rails (Apache)

Setting up SSL on the Bitnami instance of Ruby on Rails is easy.

  1. First, you’ll want to make sure that you’ve purchased your SSL certificates for your domain
  2. Next, log in to your EC2 instance
  3. place the .key and .crt files you have for your SSL certificate in your apps’s root directory
  4. go to your app’s root and move the files to the correct directory with

mv yourcrt.crt /opt/bitnami/apache2/conf/extra/yourcrt.crt

mv yourkey.key /opt/bitnami/apache2/conf/extra/yourkey.key

       5.  the httpd.conf file that the instance comes with already points to another file for the ssl configuration, so we’ll want to edit that file that is being used.

6.  enter “cd  /opt/bitnami/apache2/conf/extra”

7.  enter “pico httpd-ssl.conf” to edit the ssl configuration

8.  in the file (CNTL + X to save when you are done):

    • change the “DocumentRoot” to “home/bitnami/apps/yourapp/public” or where ever your app is
    • change the “ServerName” to
    • change the “ServerAdmin” to your email
    • change the “SSLCertificateFile” to “/opt/bitnami/apache2/conf/extra/yourcrt.crt”
    • change the “SSLCertificateKeyFile” to “/opt/bitnami/apache2/conf/extra/yourkey.key”

9.  stop and restart your server

apachectl -k stop

apachectl -k graceful

Your app should now be successfully set-up for SSL.

Running Ruby on Rails on EC2 with Bitnami

Bitnami makes it easy to get started with Rails with their Amazon Machine Image (AMI) which creates a server for your app with all of the software you need already installed.  For my apps, I’m using Apache and Passenger, but Nginx is also installed if you prefer that.

Here are some instructions for setting up Rails using Apache / Passenger / MySQL

(1) sign-up for your Amazon Web Services account

(2) log in, and go to your AWS Management console

(3) go to the EC2 section

(4) click on the security groups link

(5) change the default security group to allow inbound requests:

http, https and ssh access from ip

(this allows people to access your app over http or https and allows you shell access to the server)

(6) click on the key pairs link and create a key pair (you’ll need this to access your EC2 instance)

(7) click the instances link

(8) click the ‘launch instance’ button and then select to create an instance from the Amazon Marketplace.  In the search box, enter Ruby on Rails

(9) select the Bitnami Ruby on Rails image and then follow the steps to create the instance

(10) while your instance is getting created, you’ll want to create your MySQL database.  In the Console, off the top menu, click “Services” and then RDS (under databases)

(11) click the “launch a DB instance” button in RDS, click MySQL on the next screen

(12) on the next screen, select a class (based on how powerful the server you want running your DB), enter the other required fields and record or remember what you entered here as you’ll need them to access your database

(13) Click on the “DB Security Groups” link.  Click on the default group, and down below you should be able to alter the permissions.  If you want to be able to access your database from your PC, add one for CIDR/IP and then copy the CIDR detected (it will show as AWS’s best guess in small font once your select CIDR).  You will need to add one for “EC2 Security Group” and select the “Default” EC2 security group.  This does not mean that you are adopting the settings of the  EC2 security group – it means that you are allowing members of that group to access the DB – this way your EC2 server with the application can access the database.

(14) Next you’ll have to update your database.yml file to make sure it connects to your RDS.  Once your instance has finished creating (green light next to the instance), click on the DB Instances tab on the left, and then on the next screen click on your instance.  This should bring up the properties of the instance in the lower frame of the web page.  Note the “endpoint” as this is the host you will use in your database.yml.

In your database.yml, for production enter this:

adapter: mysql2
encoding: utf8
database: (your database name from step 12)
username: (your database user name from step 12)
password: (your database password from step 12)
host: (your endpoint)
port: 3306

(15)next you’ll want to log in to your EC2 instance, which should have been created by now to finish setting that up.  to log in, you can use the Putty program or you can use the Java shell client that AWS provides.  To use the the client AWS provides, go to Services > EC2 in the AWS management console.  Click on the Instances tab, and then right click your running instance and select “connect”.

(16) In the Java pop-up, change the user name from ubuntu to bitnami, and change the private key path to the path that the .pem file you downloaded to (in step 6), and then click “Launch SSH instance”.  If you are prompted to add the remote host, click ‘yes’.

(17) once you’re in, you can create a directory for your app, i put mine in /home/bitnami/apps/myappname

cd /home/bitnami/apps

sudo mkdir myappname

(18)  you can follow these steps to set-up git on your EC2 instance.  For my EC2 instance, I put my repo in: /home/bitnami/repo  (so you may want to change the directories in the set-up git link)

(19) we want to make sure your permissions are correct, otherwise your app will get 403 errors (Permission Denied) when accessing pages of your app.  Go to the directory above the one where you put your app.  For example, I used /home/bitnami/apps/myappname, so I would go to the /home/bitnami/apps folder:

cd /home/bitnami/apps

sudo chown -R bitnami:bitnami myappname

chmod -R 775 myappname

chmod -R 755 myappname

(20) after you’ve pushed your code, it should be in the directory you set-up for your app (in my example, /home/bitnami/apps/myappname).  run these three commands:

cd /home/bitnami/apps/myappname

bundle install

rake db:create

(21) with apache and passenger already installed, your app is ready to run.  the one last thing you have to do is to point Apache to your app.  to do that, go into your shell client and enter this command:

cd /opt/bitnami/apach2/conf

pico httpd.conf

(22) you should now be editing the httpd.conf file which is apache’s configuration for routing.  find this line and delete it:

DocumentRoot “/opt/bitnami/apache2/htdocs”

(23) paste (shift + insert key) in this (replace “myappname” with your app’s name):

<VirtualHost *:80>
DocumentRoot /home/bitnami/apps/myappname/public
<Directory /home/bitnami/apps/myappname/public>
Allow from all
Options -MultiViews

(24) exit and save (CNTL + x, then click enter when it asks you if you want to save)

(25) run these commands to stop and restart your server so the changes take effect:

sudo apachectl -k stop

sudo apachectl -k graceful

(26) go to the public IP for your EC2 instance (you can find this if you go into the AWS Management Console, then go to the EC2 section – Services > EC2 – and click on your running instance to see the attributes – it’s “Public DNS”)

You’re app should now be available on the web at this address.

Using SSL

Turning on SSL was a little more time consuming than I thought it would be – largely because of my naivete.  Here’s some of things I had to do to make it work.

  1. For Paperclip – for images from S3, I had to changes the parameters in has_attached_file to include ‘:s3_permissions => :private, ‘ .  This will give the S3 images a https in the url
  2. For the Recaptcha gem, add the option :ssl => true as an option to the recaptcha_tag, like so: <%= recaptcha_tags(:ssl => true) %>
  3. I had to change all external libraries I referenced for CSS or JS to https (in the url) or download a local copy and reference the local copy
  4. in each controller where a view that needed to be secured force_ssl :only => :new or force_ssl :only => [:new, :edit] for multiple actions

When you run into issues, maybe these tips will help:

  • if you’re using Chrome, Chrome will mark all pages insecure if you hit one that claims https, but has some insecure elements (so you may see a page that is secure, but it says insecure).  If you find this, pop open a new tab and paste the url in doubt
  • seek and destroy all elements that show in your source that are http instead https, except links
  • when a browser asks if you want to display insecure items, try saying no and see if you can see if there’s anything missing (in the case of it being javascript, you may not notice anything visually)