How to create a Google Chrome extension

Creating an extension for Google Chrome is incredibly simple. With the knowledge of basic HTML and JavaScript, you can start building useful plugins in a matter of minutes.

This article will focus on creating the extension, and not on building the application. We will be using the todo list app I created in a previous tutorial. Read the tutorial here, and see the demo here.

The first step in creating an extension is to create a manifest file that will contain the details of your extension. Create a directory for your extension and create a file manifest.json there. Enter the following code into the file:

{
  "name": "Todo List",
  "version": "1.0",
  "description": "A simple todo list.",
  "browser_action": {
    "default_icon": "todo.jpg"
  }
}

You will need to add an image to the folder and change the value corresponding to “default_icon” to the name of that file.

In Chrome, go to Options > Tools > Extension and then enable the developer mode. Click on “Load unpacked extension” button and select the folder that contains your manifest.json file. You will now be able to see your app’s icon in the top right, next to the wrench icon.

The next thing to do is to add the application. Get the code for the todo app from github, and save it as index.html. Now add "popup": "index.html" after the line containing default_icon in the manifest file and click on the reload link for this extension in Chrome’s extensions tab. The code should look like this now:

{
  "name": "Todo List",
  "version": "1.0",
  "description": "A simple todo list.",
  "browser_action": {
    "default_icon": "todo.jpg",
    "popup": "index.html"
  }
}

Clicking on the icon will now open a small popup right below the icon with the Todo app. You can now add tasks to the todo list and they will be available when you reopen the browser later. Here’s what it will look like:

Todo App - Google Chrome extension

Todo App - Google Chrome extension

This was a quick introduction to show you how to create a simple Chrome extension. Take a look at Google Chrome extensions page, go through the documentation and start creating awesome extensions.

Git How-to – Installing git and pushing repo to github

In this post, I will describe the steps to install git on a windows machine, create a local repository, and then push that repo to your github account. This is a beginner level tutorial for those using windows, but except for the part about installation, it is common for all OSes.

Installation and set up

Download and install msysgit from http://code.google.com/p/msysgit. Msysgit comes with a GUI tool and a command line version.

Next you have to set up your name and email into git configuration. For this, open git bash and use the following commands:

$ git config --global user.name "Nithin Bekal"
$ git config --global user.email me@myemail.com

Creating the first repo

Now that the installation and configuration steps are done, let’s create our first repository. Create a folder called my_project and add some files to it. I created a rails project using rails my_poject since that automatically generates many files and folders.

Go to the project directory

$ cd my_project

Initialize a git repository for the project:

$ git init

Add all the files in the project to the repository:

$ git add .

Make the first commit.

git commit -m "First commit."

This commits all the changes (all the files in this case, because we have a new repo here) to the repository along with the message “First commit”.

Pushing the repo to github

The next step is to push this repository to github. First of all, you need to sign up for an account (if you don’t already have one) on github. Once you’ve created the account, create a new repository called my_project.

Before you can start pushing to github, you need to create an ssh key for your computer and copy the public key to your github account.

Create ssh key:

$ cd ~
$ mkdir .ssh
$ cd .ssh
$ ssh-keygen -t rsa -C "you@yourmail.com"

Now in giithub, go to Account settings > Add SSH keys > Add another public key and copy the contents of the id_rsa.pub file there. You will have to create an ssh key and add it to github for each computer from which you want to push repos to github.

To push the local repository to github:

$ git remote add origin git@github.com:<username>/my_project.git
$git push origin master

(Use your username instead of <username>.)

Now if you open the page for the repository on your browser, you can see the files of your project visible there. If you have a readme file in your project folder, the contents of that file will also be displayed. That’s it! Now you have the git repository available on github.

Rails: Avoid multiple level nested resource routes

While generating RESTful routes in rails, it is easy to get carried away and generate many levels of nested resources for every level of has_many associations. For instance, I recently wrote something like this in my routes file:

  # in config/routes.rb
  map.resources :first_resources do |first|
    first.resources :second_resources do |second|
      second.resources :third_resources
    end
  end

Here FirstResouce has_many SecondResources and SecondResource has_many ThirdResources. Now imagine how you would get the path to edit the third level resource. You’d have to write something like this:

edit_first_resource_second_resource_third_resource_path(@first_resource, \
    @second_resource, @third_resource)

Yes, that’s how bad it would look when the routes are written for the innermost resource in the routes.

When I found myself doing something similar a few days ago, I decided to look for a better way to do this, and it amazes me how I missed this simple (and universally used) approach to writing nested resource routes.

Let’s take the example of a school where each course would have many batches, and each batch would have many exams.

# app/models/course.rb
class Course < ActiveRecord::Base
  has_many :batches
end

# app/models/batch.rb
class Batch < ActiveRecord::Base
  belongs_to :course
  has_many :exams
end

# exam.rb
class Exam < ActiveRecord::Base
  belongs_to :batch
end

Writing the routes with two levels of nesting would give me something like this:

  # config/routes.rb
  map.resources :courses do |course|
    course.resources :batches do |batch|
      batch.resources :exams
    end
  end

The route to edit an exam object @exam (belonging to batch @batch which in turn belongs to course @course) would look like this:

edit_course_batch_exam_path(@course, @batch, @exam)

This is way too long and rather than make it easy to understand the path, it is going to make it even more confusing when somebody tries to understand the path. The url is going to be something like http://domain.com/courses/1/batches/1/exams/1/edit.

The best solution in this case is to nest the resources to just one level so that batches a nested within courses (e.g. http://domain.com/courses/1/batches) and exams are nested only within batches (e.g. http://domain.com/batches/1/exams). Using a rails shortcut to define nested routes, we could write the routes like this:

  # in config/routes.rb
  map.resources :courses, :has_many => :batches
  map.resources :batches, :has_many => :exams

Now if you wanted to edit an exam resource, you could just write edit_batch_exam(@batch, @exam) without having to worry about specifying the course object in the route. If you needed the course object within the exams controller, all you need to do is write a before filter that loads the batch and course as shown here:

# app/controllers/exams_controller.rb
class ExamsController < ApplicationController
  before_filter :load_batch_and_course

  # RESTful actions

  private
  def load_batch_and_course
    @batch = Batch.find(params[:batch_id])
    @course = @batch.course
  end
end

Since we can get the course_id from the batch, there is no need for us to have the course_id in the route. This makes the routes much easier to understand.

Have you come across any situation where nesting more than one level is absolutely necessary? (I couldn't imagine any such situation off the top of my head.) How many levels of nested resources are okay with you? Do leave a comment and tell me what you think.

How-to: Setting up Ubuntu 9.10 on Virtualbox

I’ve just been setting up Ubuntu as a virtual OS in my Windows machine using Sun Virtualbox. I did run into a couple of problems initially, so I’m listing out the steps involved in acse somebody else needs some help with the same.

Downlaod Virtualbox from here and install it. You will obviously need Ubuntu as well, and you can get the Ubuntu ISO from here.

Open Virtualbox and click on new to set up a new virtual machine. On clicking next, you will be prompted for the following details: operating system — Linux, version — Ubuntu, and name for the virtual machine, e.g. “ubuntu”.

In the next setting, set the base memory size. The recommended value will already be selected, but you can increase it a little if you have a lot of memory. (I set 512MB on my 2G machine.)

Now you’ll be prompted for a virtual hard disk, and since you haven’t already created one, select the option to created a new virtual hard disk. Set the storage type to “dynamically expanding”. Set the location, and the size to something like 8GB and click finish.

Now that you’ve created the VM and the virtual hard disk, you need to install Ubuntu. For this right click on the VM in the sidebar and go to settings. Here, in the storage tab, click on the CD/DVD icon and set the ubuntu installation CD ISO as the device. (Use your CD/DVD drive as the device if you’re installing from a CD and not from ISO.)

On starting the virtual machine, the CD gets booetd, and you can now install Ubuntu into the VM as you would do in case of a normal Ubuntu installation. Once installed, you can use this VM to boot into Ubuntu.

Since I work mostly on ruby, needed to install a ruby and rails environment on the virtual machine. I’m not going to post all the steps here, but there’s an awesome post on setting up a ruby and rails environment on Ubuntu on hackido.com.

Moving SVN repository to another server

I had to move an SVN repository for one of my projects from one hosting account to another today. I don’t know much about handling SVN and it took me a bit of searching before I was able to do it, so i’ve written the steps here for anyone else who might be in the same situation. You need to have SSH access on both servers to do this.

Go to ~/svn/ or wherever you have your SVN repos and dump the repo using the svnadmin dump command:

$ svnadmin dump myproject > myproject.dump
  Dumping revision 0
  Dumping revision 1
  ...
  Dumping revision 46

You now have the dump of the repo, which you can upload to the other server where you want to import the repository. Now, in the svn folder of that serer, do this:

$ mkdir myproject
$ svnadmin create myproject
$ svnadmin load myproject < myproject.dump

Importing the repository like this keeps all the revisions intact and you can continue using the repository at the new server.

Rails: Thinking Sphinx plugin for search

Just a couple of weeks into being a rails developer, I made the one really, really, really big blunder — I used a find_by_sql in a search page. (Oh, please… stop booing. I was a newbie then.) Now, I’ve realized that I might have to modify the search to add yet another column, and well… extending a find_by_sql query for a fourth column (yeah, it was searching 3 columns already) would be stupid and incredibly ugly.

I came across Thinking Sphinx plugin for full text search over MySQL and Postgres databases. It connects ActiveRecord to the Sphinx search engine and lets you perform searches over multiple columns and even multiple models easily.

Things went rather smoothly when I tried using the plugin and I managed to set it up and running within a few minutes. Here’s how I set up an example application and tested sphinx.

  1. Download sphinx from here. If you’re on windows, you just have to extract the exe files to ruby/bin directory. On, Linux/Mac, you’ll have to compile the source. (See instructions here.)
  2. Install the thinking_sphinx plugin like this:
    script/plugin install git://github.com/freelancing-god/thinking-sphinx.git

    You might run into trouble on Windows with the script/plugin install, so you can use this instead.

    ruby script/plugin install http://github.com/freelancing-god/thinking-sphinx.git/
  3. For this example, let’s quickly set up a Post model through scaffolding.
    ruby script/generate scaffold Post title:string body:text
  4. Now we’ll set up the indexes for the posts model like this:
      define_index do
        indexes title, body
      end
  5. In the index method in PostsController, change Post.all to this:
    Post.search(params[:search])
  6. Add a simple search form in articles/index.
    <% form_tag posts_path, :method => 'get' do %>
      <p>
        <%= text_field_tag :search, params[:search] %>
        <%= submit_tag "Search", :name => nil %>
      </p>
    <% end %>
    
  7. Now we have to run a couple of rake commands to get sphinx to work. To get sphinx to process the data, run this rake task:
    rake thinking_sphinx:index

    To start the sphinx server:

    rake thinking_sphinx:start
  8. Now if you search for something using the form, the page returns the posts matching your query.

It also allows you to search across multiple models that are related. For example, if a post has many comments, you could change define_index to search comments as well.

  define_index do
    indexes title, body
    indexes comments.body :as => :comments_body
  end

Sphinx also has support for delta indexing, which means that rather than index the entire table, it can index only those rows that have been added since the last index. You need to schedule the indexing according to your application’s requirement. There’s a nice little gem called whenever that will allow you to schedule the rake tasks in ruby.

What plugins have you used for full text search in rails? Have you tried Sphinx? Or ferret or solr? I’ve mostly heard people saying sphnx is better than solr or ferret. What do you think?

Update. I’ve put the source code for this example on github.

Rails: Importing data from spreadsheets into database

Recently I was trying to find ways to import data from excel spreadsheets into the database in a rails project. We needed to save the data from the client’s excel file into the database. Here’s how it can be done using a rake task.

Update (4 Apr 2012): Just realized that FasterCSV became a part of ruby in 1.9. This post is for ruby 1.8.7. See this discussion if you run into problems with ruby 1.9.

  1. The file will have to be in CSV format, so you’ll have to open it with any spreadsheet application like Microsoft Excel (or Google Docs in my case) and save it as CSV. Put the file in your project folder.
  2. FasterCSV is a ruby gem that lets you easily parse CSV files and is a faster alternative to ruby’s standard CSV library. Install it using the command:
    gem install fastercsv
    
  3. Create a rake task that reads the CSV file using the fastercsv gem and saves the data in the database. Your code should look something like this:
    namespace :db do
    
      desc "load user data from csv"
      task :load_csv_data  => :environment do
        require 'fastercsv'
    
        FasterCSV.foreach("data.csv") do |row|
          User.create(
            :user_name => row[0],
            :email => row[1],
            :password => row[2]
          )
        end
      end
    end
    

    You can replace the User model here with whatever model you’re importing from the CSV file.

  4. Save the task as a rake file in lib/tasks folder and name it import_csv_data.rake or something to that effect.
  5. Go to the shell and run the task by:
    rake db:load_csv_data
    

When I came across this problem, my first reaction was to look for a ruby library that reads spreadsheets directly. But that’s a challenge for another day. For this particular project we can manually save the spreadsheets as CSV.

I did find a library called roo (http://roo.rubyforge.org/) that can access the contents of a spreadsheet directly and it might be worth looking into if you need to read an uploaded spreadsheet directly.

Have you had to do something similar in your projects? What other method would you suggest to accomplish this task?

JavaScript: How to create a simple countdown timer

After yet another disappointing performance yesterday by the football (soccer, if you’re American) club I support, Liverpool, this was my tweet:

I’ve already started counting days until FIFA world cup. Football season seem practically over for Liverpool. :(

I actually did count the days, but being a web developer, I ended up writing javascript code to do the dirty work for me. ;-) I’ve never really done much with javascript date and time, so I’m not sure if there’s a better way to do this, but this works. Follow these steps to create a countdown timer for FIFA World Cup 2010. It’s easy to customize it for anything else.

First, we have to create a div with id as “worldcup_countdown_time” where you want to display the countdown timer. This div will be modified by our script to display the time remaining for the World Cup kick off.

<div id="worldcup_countdown_time"> </div>

Now let’s write the script that will calculate the number of days, hours, seconds and minutes left for kick off. We’ll write each of the steps first and then put it all in a function called updateWCTime().

First we have to calculate the time difference between the current time and the time of kickoff. Here, now is the current time, and kickoff is the kickoff time. We store the difference (which we get in milliseconds) in a variable called diff.

    now = new Date();
    kickoff = Date.parse("June 11, 2010 11:30:00");
    diff = kickoff - now;

We find the time left till kickoff in terms of days, minutes, hours and seconds as shown below. We use the Math.floor function to get the absolute values in the variables. It returns the highest integer that’s less then the floating point value.

    days  = Math.floor( diff / (1000*60*60*24) );
    hours = Math.floor( diff / (1000*60*60) );
    mins  = Math.floor( diff / (1000*60) );
    secs  = Math.floor( diff / 1000 );

Now these variables will give us the exact number of hours, minutes and seconds left, but that’s not exactly what we want. If the remaining time were a day and 7 hours, we would have the value 31 (24+7) in the minutes variable. But what we want is the value 1 in the day variable, and the value 7 in the hours. Let’s create another set of variables to do that.

    dd = days;
    hh = hours - days  * 24;
    mm = mins  - hours * 60;
    ss = secs  - mins  * 60;

Now that the time has been calculated, you have to update the div you created at the beginning.

    document.getElementById("worldcup_countdown_time")
        .innerHTML =
            dd + ' days ' +
            hh + ' hours ' +
            mm + ' minutes ' +
            ss + ' seconds';

Putting it all together

Now, to make the countdown timer work, let’s put it all together.

function updateWCTime() {
	now      = new Date();
	kickoff  = Date.parse("June 11, 2010 11:30:00");
	diff = kickoff - now;

	days  = Math.floor( diff / (1000*60*60*24) );
	hours = Math.floor( diff / (1000*60*60) );
	mins  = Math.floor( diff / (1000*60) );
	secs  = Math.floor( diff / 1000 );

	dd = days;
	hh = hours - days  * 24;
	mm = mins  - hours * 60;
	ss = secs  - mins  * 60;

        document.getElementById("worldcup_countdown_time")
            .innerHTML =
                dd + ' days ' +
                hh + ' hours ' +
                mm + ' minutes ' +
                ss + ' seconds';
}
setInterval('updateWCTime()', 1000 );

The last line in the above code creates a timer that calls the updateWCTime() every 1000ms to refresh the timer every second.

Put this script in a .js file and include it in your HTML page to turn the dv with id “worldcup_countdown_time” into a countdown timer that counts down to the world cup kickoff time. There you go, you have a working countdown timer ready now with something like the following diplayed in the div:

186 days 17 hours 12 minutes 14 seconds

To count down to some other event, you can easily change the value in the kickoff variable to the date that you want to use.

Update. I’ve put up the code on gihub where you can also download it as tar.gz.

How to use Notepad++ to edit files via FTP

For a few days now, I’ve been working on a wordpress based website where I have to edit quite a few files directly on the server. I used wordpress’ theme and plugin editors for the first day, but it soon became too difficult to edit the files that way and I had to look for an editor that would allow me to edit files live on the server.

Notepad++ has a great plugin called FTP_synchronize that allows you to edit your files directly on the server. With the plugin installed, editing files on the server doesn’t feel any different from editing files on the local machine.

Here’s a list of steps on how to set up Notepad++ to edit files through FTP.

  1. If you don’t already have Notapad++ installed, download the binaries from here and install.
  2. Download the FTP_synchronize plugin from here and install it by copying the DLL into Notepad++’s plugins folder. (You’ll have to restart Notepad++ to be able to use the plugin.)
  3. Open the FTP_Synchronize interface by clicking the “Show FTP folders” button or from the Plugins option in the menubar.

    npp_ftp1

  4. Click on settings on the FTP folders interface, and enter the login details. The address is your domain name, and the username is the one your hosting provider gives you. (In Bluehost, for instance, it’s usually (not always) the first 8 characters of your main domain’s name.) Set the port to 21.

    npp-ftp2

  5. Now click on the connect button and choose the FTP profile you’ve created. The folder you’ve selected in the settings gets loaded in the FTP synchronize sidebar, and you can edit the files on the server the same way you would use an IDE to edit a project stored locally. FTP Synchronize automatically syncs your files when you hit Ctrl+S.

It’s been working great for me so far, and unless you’re editing unusually large files, Ctrl+S synchronizes the file almost instantaneously. The only thing that irritated me about the plugin was that it wouldn’t alert me when the FTP connection gets disconnected, so more than once I’ve wondered why there was no change on the site when I changed some code.

How do you edit files on the server? Is there a better option I could use? I’ve heard that the feature’s been added to NetBeans, but haven’t really checked it out. Should I be trying it out?

How to create a simple datepicker using jQuery

jQuery allows you to easily create a datepicker and customize it according to your requirements. Here’s a quick look at how you can get started with using the jQuery datepicker.

The jQuery website has a nice application called Themeroller that lets you customize the interface for jQuery UI widgets. There are also plenty of themes available in the gallery that you can download and use directly. Copy the stylesheet, images, the jQuery file and the jQuery-UI files into the appropriate directories and link them in the header of your HTML file.

Now let’s create a simple form that contains the text field that you want to convert into a datepicker.

<form action="index" method="get">
  <input id="date-pick" name="date-pick" type="text" value="" />
  <input id="date-submit" name="date-submit" type="submit" value="Go!" />
</form>

To convert the input field with the id date-pick into a datepicker, write the following jQuery code in the head section of your HTML.

$(function(){
  $("#date-pick").datepicker();
});

That’s it! The input field that you created now works as a popup datepicker. A calendar showing the current month appears whenever you focus on the #date-pick field and the date you click on appears as text in the field.

There are tons of options to customize the datepicker, such as changing the date format sent to the server or using a different language for the calendar. You can explore these options in the jQuery UI documentation for the datepicker.