Simple_Captcha with Restful_Authentication
April 27, 2008
Enabling Simple_Catpcha verification with Restful_Authentication for new user signups is quite easy. I found the answer on the Restful_Authentication “bells and whistles” thread on Rails Forum. The reason i needed this was because i did not want to use email activation for new users, i wanted them to be able to log in straight away, and i needed some sort of protection against spam bots.
Anyway, add the “show_simple_captcha” code to your new user signup form and include the parameter
bject => ‘user’. Then add the following to the user model – models/user.rb:
apply_simple_captcha :message => “The text does not match the image”, :add_to_base => true
attr_accessible :login, :email, :password, :password_confirmation, :identity_url, :profile, :captcha, :captcha_key
And finally change the user_controller.rb create action:
def create
cookies.delete :auth_token
@user = User.new(params[:user])
if @user.save_with_captcha
#Uncomment to have the user logged in after creating an account – Not Recommended
#self.current_user = @user
flash[:notice] = “Thanks for signing up!”
redirect_to login_path
else
flash[:error] = “There was a problem creating your account.”
render :action => ‘new’
end
end
That’s it.
Using GMail SMTP with ActionMailer
April 27, 2008
There are a number of solutions that have been posted around the net to get Rails’ ActionMailer to talk to GMail, allowing you to send email from your Rails app. From Googling around, it seems that many bloggers have quoted a post from Anatol Pomozov. However, this is now a dead link:
http://blog.pomozov.info/posts/how-to-send-actionmailer-mails-to-gmailcom.html
Stephen Chu talked about how to use GMail’s smtp server back in 2006:
http://www.stephenchu.com/2006/06/how-to-use-gmail-smtp-server-to-send.html
More recently, Preston Lee talks about the Anatol Pomozov approach here:
http://www.prestonlee.com/archives/63
And Daniel Fischer explains how to use the action_mailer_tls plugin – this method is also mentioned in the new Advanced Rails Recipes book:
http://www.danielfischer.com/2008/01/09/how-to-use-gmail-as-your-mail-server-for-rails/
However, there is another far easier solution that was posted originally to my knowledge by Tim Riendeau:
http://www.wanlord.com/articles/2007/11/29/sending-email-using-actionmailer-and-gmail
I will repeat the steps as they worked for me here…
1. Install the tlsmail gem
sudo gem install tlsmail
2. Add the following to the bottom of your environment.rb
require ‘tlsmail’
Net::SMTP.enable_tls(OpenSSL::SSL::VERIFY_NONE)
ActionMailer::Base.delivery_method = :smtp
ActionMailer::Base.smtp_settings = {
:address => ‘smtp.gmail.com’,
:tls => ‘true’,
:port => 587,
:domain => ‘mydomain.com’,
:authentication => :plain,
:user_name => ‘info@mydomain.com’,
:password => ‘mypassword’
}
3. To enable errors to show up if the mail does not get delivered, modify your development.rb and production.rb as shown below – it’s ok to make this true in devlopment, but i think most people say to set this to false in production:
development.rb
config.action_mailer.raise_delivery_errors = true
production.rb
config.action_mailer.raise_delivery_errors = false
And that’s it!
NOTE: “Timeout::Error (execution expired)”
I got this message quite a lot when i tried to send emails in development, and no one seems to know why this is the case. But when i switched to production things worked like a breeze. I am developing on a MacBook Pro with Leopard, if you have any idea why this happens please let me know.
NOTE: Internet Service Provider blocking ports
Another point to note is that some ISP’s block outgoing smtp mail on certain ports, eg port 25. Check with your ISP if they do any port filtering.
Automatic MySQL Database Backups to Amazon S3 with S3SYNC
April 19, 2008
I am running an Ubuntu Gutsy based Slicehost VPS, and have a Macbook Pro development machine. On my server i am logged in as a user with sudo privileges. What i’d like to document in this blog post is how to create automatic MySQL database backups to Amazon S3 with S3SYNC.
Now there are a lot of options available to achieve all this, this is the way that i found easy and that worked for me. To create the automatic mysql database dumps, there is the automysqlbackup script available from SourceForge:
http://sourceforge.net/projects/automysqlbackup/
I downloaded this onto my Macbook Pro and used ‘scp’ to copy back to my server. I suppose you could use ‘wget’ directly form the server too if you prefer. You can put the file anywhere on the server you like, i just keep it in my home directory for now (/home/user/) – but i will move it later. First thing is to rename the file, at the time of writing version 2.5 was available:
sudo mv automysqlbackup.sh.2.5 automysqlbackup.sh
Now create a directory in which you want your backups to go to, and one where the restored backups from S3 will be downloaded to, eg /home/user/mysqlbackups/ and /home/user/mysqlrestores/:
mkdir mysqlbackups
mkdir mysqlrestores
The automysqlbackup script is of course just one file, and you can open and view it in a text editor. In fact i suggest that you do that next as it has pretty good instructions as to what it does and what parameters you need to add. Move to the directory in which you have the script and open it up, i use the nano editor:
sudo nano automysqlbackup.sh
Basically you need to add the names of your databases, mysql user, and mysql password info. The script will do daily, weekly, and monthly backups of your database into the specified backup folder of your choice – you can even have emails sent to you! Here is an excerpt:
# Username to access the MySQL server e.g. dbuser
USERNAME=root
# Username to access the MySQL server e.g. password
PASSWORD=********
# Host name (or IP address) of MySQL server e.g localhost
DBHOST=localhost
# List of DBNAMES for Daily/Weekly Backup e.g. “DB1 DB2 DB3″
DBNAMES=”therailscoder_production”
# Backup directory location e.g /backups
BACKUPDIR=”/home/user/mysqlbackups”
Edit the files with your own settings, then save and exit!
Next edit the permissions on the script to give read, write, and execute permissions to the user, and not to to anyone else.
sudo chmod 700 automysqbackup.sh
You can test the script out manually as follows:
./automysqlbackup.sh
Move to your backups directory and you should see 3 sub-directories – daily, weekly, and monthly. In the daily directory you will find a gzipped sql file of you database backup! I will talk about how to actually automate this process a little later on…
Next we need to get the mysql backup’s over to Amazon S3. If you haven’t got an S3 account, sign up and get your Access Key ID and Secret Access Key ready:
http://www.amazon.com/s3
Next we need to setup s3sync:
http://s3sync.net
I want to credit John Eberly’s blog post from way back in 2006 for helping me set up s3sync. I have cheekily repeated most of his instructions in some of the steps below…
http://blog.eberly.org/2006/10/09/how-automate-your-backup-to-amazon-s3-using-s3sync/
s3sync requires ruby 1.8.4 or greater as well as libopenssl-ruby. I already had these setup on my server so i did not have to install them, if you don’t have these enter the command below to get them:
sudo aptitude install ruby libopenssl-ruby
In your /home/user/ directory download and install s3sync as follws:
wget http://s3.amazonaws.com/ServEdge_pub/s3sync/s3sync.tar.gz
tar xvzf s3sync.tar.gz
rm s3sync.tar.gz
You then need to create a directory for ssl certificates as well as download them. Move to the newly created s3sync folder and follow the commands below:
cd s3sync
mkdir certs
cd certs
wget http://mirbsd.mirsolutions.de/cvs.cgi/~checkout~/src/etc/ssl.certs.shar
Run this command form the certs directory:
sh ssl.certs.shar
Now go back to the main s3sync directory. You can create an S3 ‘bucket’ to store your database backup using s3sync eg:
ruby s3cmd.rb createbucket mysql.mydomain.com
Or use an GUI interface such as S3 Browser, Cockpit, or Jungle Disk:
http://people.no-distance.net/ol/software/s3/
http://jets3t.s3.amazonaws.com/applications/cockpit.html
http://www.jungledisk.com/
Next create your upload and download scripts, and edit them as follows with your own parameters. Note the ‘database’ is just a name i gave as a sub-directory or folder within the bucket – you can call it what you want:
sudo nano upload.sh
#!/bin/bash
# script to upload local directory upto s3
cd /home/user/s3sync/
export AWS_ACCESS_KEY_ID=yourS3accesskey
export AWS_SECRET_ACCESS_KEY=yourS3secretkey
export SSL_CERT_DIR=/home/user/s3sync/certs
ruby s3sync.rb -r –ssl –delete /home/user/mysqlbackups/ mysql.mydomain.com:/database
# copy and modify line above for each additional folder to be synced
sudo nano download.sh
#!/bin/bash
# script to download local directory upto s3
cd /home/user/s3sync/
export AWS_ACCESS_KEY_ID=yourS3accesskey
export AWS_SECRET_ACCESS_KEY=yourS3secretkey
export SSL_CERT_DIR=/home/user/s3sync/certs
ruby s3sync.rb -r –ssl –delete mysql.mydomain.com:/database/ /home/user/mysqlrestores
# copy and modify line above for each additional folder to be synced
Change the permissions on the files, and check the ownership – i had to change this to the current user (me):
sudo chmod 700 upload.sh
sudo chmod 700 download.sh
sudo chown user upload.sh
sudo chown user download.sh
Set up some S3 configuration:
mkdir /etc/s3conf
cp s3config.yml.example /etc/s3conf/s3config.yml
Edit s3config.yml with your S3 details and ssl cert path:
sudo nano /etc/s3conf/s3config.yml
In your s3sync directory, to run the upload and download scripts manually enter:
./upload.sh
./download.sh
To check the upload use ruby scmd.rb as shown below, or use your preferred GUI software:
ruby s3cmd.rb list mysql.mydomain.com
To check the download just go to your mysqlrestores directory. I found that when i tried the download, i needed to also create a sub-directory called ‘database’ (/home/user/mysqlrestores/database/).
What we now have is the ability to create mysql database backup files, as well as being able to upload and download these backup files to and from S3. But everything is being done manually! I’ll finish up by showing how this can become an automated process…
To get the automysqlbackup script to function automatically there are a couple of options. On Ubuntu and most other Linux distributions you should have the following ‘cron’ directories:
/etc/cron.daily/
/etc/cron.weekly/
/etc/cron.monthly/
You can move the script to any one of these directories, and the script will run automatically every day, week, or month! On Ubuntu the .sh extension does not need to be there.
sudo mv automysqlbackup.sh /etc/cron.daily/automysqlbackup
But i prefer not to do this! This is because there are other default scripts or processes that run on a daily basis, and these will be run at the same time as your database backups. The default on my setup is 0625 am! I prefer to have my database dumps run at a different time, when there are no other scripts or processes running, and when my website is likely to have less traffic. The same goes for uploads to S3. The easiest way to do this is to create your own ‘crontab’, here you can specify what time to run your scripts.
Before i do this, i like to move the automyslbackup script to the s3sync directory, where it’s friends ‘upload’ and ‘download’ live
!
sudo mv automysqlbackup.sh /home/user/s3sync/automysqlbackup.sh
Then from any directory open your own ‘crontab’:
crontab -e
Then paste in this code:
# m h dom mon dow command
0 1 * * * /home/user/s3sync/automysqlbackup.sh
30 1 * * * /home/user/s3sync/upload.sh
Save and exit. This will basically set things up so that the automysqlbackup script will run every day at 0100 am, and so that the s3sync uploads the backups to S3 at 0130 am every day! You might need to do a Google search on crontab to find out how to customize this to suit your own needs.
Done!
MySQL Data Backups
April 13, 2008
I have not figured out an easy or efficient way to do this yet, but this is what i am doing now.
Step 1.
On my Ubuntu Gutsy server, i create a mysqlbackups directory and then do a mysqldump into this directory:
mysqldump -u root -p databasename > databasebackup.sql
Step 2.
On my Macbook Pro, i create a mysqlbackups directory and the copy the databasebackup.sql file from the server to my local machine:
scp user@11.222.333.44:/home/user/mysqlbackups/databasebackup.sql /Users/user/mysqlbackups
Step 3.
Upload the databasebackup.sql file to an Amazon S3 bucket using S3 Browser (see my previous post for more info on this).
AND/OR
Backup to CD/DVD/USB/External Hard Disk.
This is obviously a manual process that could become quite tedious. If anyone has any suggestions as to how to backup MySQL databases to Amazon S3 that is more automated, please let me know how you would do this!
Using Amazon S3 with Attachment_Fu on Rails
April 12, 2008
If you’re using the attachment_fu Rails plugin to upload files (eg images, video, etc…), you will probably be aware that there is a built-in storage option to use Amazon’s Simple Storage Service (S3). The reason i opted to use S3 was that it would take some load of my own server, and i think in the long run it is more efficient than using the file system or db options. Many web startups are doing exactly the same thing.
So how do we implement it?
First create an Amazon Web Services account, and sign up to use S3:
https://aws.amazon.com
Note that you will have to give some credit card details as the service is not free, but it is damn cheap!!
You will be given an access key id and a secret access key. These are both very long strings.
Next step is to create a bucket. A bucket is like a folder that will hold all your files. The easiest way to do this is get an S3 GUI, just like CocoaMSQL(Mac)/HeidiSQL(Win) for MySQL. There are a number of options to consider, eg:
S3 Browser:
http://people.no-distance.net/ol/software/s3/
Cockpit:
http://jets3t.s3.amazonaws.com/applications/cockpit.html
JungleDisk
http://www.jungledisk.com/
As i am using a Macbook Pro, i opted to use the S3 Browser.
With the S3 Browser, you just need to create a New Connection by entering you access key id and secret access key. There will be a similar option for other S3 GUI’s. Once you’ve done this you will be connected to your S3 storage and can simply add and delete buckets as you wish! I think it is a good idea to have a separate bucket for the development, test, and production versions of your app (just like you do with databases). With the S3 Browser you can also view the contents of your buckets and delete files from the buckets as well.
Next step is to install the S3 gem, eg:
sudo gem install aws-s3
Now get back to your app. I use attachment_fu for photos. So in my Photo model, i have the following:
has_attachment :content_type => :image,
:storage => :s3,
:size => 0.megabyte..3.megabytes,
:resize_to => ’450×450>’,
:thumbnails => { :thumb => ’150×150>’ }validates_as_attachment
Go to your Rails app config directory and you should see the amazon_s3.yml file.
Edit it as follows. Basically you need to enter your access key id and secret access key’s plus specify the bucket names:
development:
bucket_name: photos_myproject_development
access_key_id: xxxxxxx
secret_access_key: xxxxxxxxxxxx
test:
bucket_name: photos_myproject_test
access_key_id: xxxxxx
secret_access_key: xxxxxxxxxxxx
production:
bucket_name: photos_myproject_production
access_key_id: xxxxxx
secret_access_key: xxxxxxxxxxxx
I am using Subversion for source control, but i do not check the amazon_s3.yml file into Subversion, in fact i treat it just like database.yml (there are different ways of dealing with this, i won’t be going into this right now).
That’s it. Pretty easy. Upload your files and then use your S3 browser to see that they are indeed on S3!
Google Apps for Email
April 11, 2008
I have been looking into how to setup and manage an email server on my VPS and came to the decision to outsource this to Google instead! It’s dead simple to setup and saves me the hassle of trying to do something that i don’t fully understand in the first place. Plus you get to use GMail
.You can sign up for free or go for the Premier version and pay $50/year.
http://www.google.com/a/
Simple_Captcha on Linux
April 5, 2008
If you’re using the brilliant simple_captcha plugin and are not seeing captcha images on your Linux production server, make sure you have ghostscript installed on your server. On my basic Ubuntu Gutsy install on Slicehost (slicehost.com) i did not have this.
sudo aptitude install ghostscript
That did the trick for me.
http://expressica.com/category/simple_captcha/
Rails Deployment
April 5, 2008
So today i succesfully deployed my development application to my server. When people say deployment isn’t easy, they are right. Thankfully i managed to wade myself through it.
My development machine is my new Macbook Pro running the Leopard OS. If you’ve read some of my previous posts, i was using a PC with Windows Vista before. I had a lot of trouble getting my app deployed from a Windows environment, in fact, i couldn’t do it. But, it turns out that i ended up getting to the exact same stumbling point when i was trying to deploy from my Mac/Leopard. As it turns out, it wasn’t really a PC/Windows issue that stopped me from making a successful deployment, rather a “wrong code” in the “wrong place” issue from me! In particular, getting Capistrano and Mongrel set up correctly on my server.
So Windows users don’t fret, you can still get by just fine. What i have also realised is that setting up a development environment was much easier and quicker for me on Windows using InstantRails, than it is on my Mac. Despite the fact that Mac is the preferred system for the Rails Core. So go figure that one out. Anyway, i got a great development and deployment environment going now, and have no regrets as everything is working just fine
.
I deployed with Capistrano to an Ubuntu Gutsy server running Ruby, Rails, MySQL, nginx, and mongrel_cluster. My host is slicehost.com, they have a great articles section which details how to get things set up on your server from scratch. I am also using remote subversion hosting through codespaces.com.