Adding a console shell to your ruby apps

Using Rails Engines is a really nice way to introduce yourself to creating gems. It provides an environment to create and test code that is very similar to that used when creating a full rails app. There are couple of things to be aware of, such as that you run tests from the root (rake test), but run the test server and console (via rails s and rails c respectively) at test/dummy, but otherwise any rails developer should be able to get up to speed with engines reasonably quickly.

However, the more gems I write, the more I’m learning that keeping dependencies to a minimum is a really good idea. For example, do you really need a specialist HTTP gem like curb or typhoeus or can you manage with net/http. In a rails app, the simplicity and features that excellent gems like curb and typhoeus provide, often make them compelling. In a gem, the extra dependencies they add can be an issue. For example, what if a host rails app is already using a version of typhoeus, and that version clashes with the one your code uses.

A key rule with a gem is that you cannot predict the environment in which it is run, and therefore you should put some effort into reducing the gem’s dependencies.

Using engines to create gems, by definition, adds a dependency on rails, and all the baggage that comes with rails. If the gem is only ever going to be a rails plugin, and it adds its own controllers and views to the host app, dealing with this ‘baggage’ is well worth the effort. However, that is often not the case. With a little effort you can minimise the dependencies. For example, my most popular gem (array_logic) has no dependencies beyond the ruby standard library.

So as I have been creating more gems, I’ve started to identify strategies that allow me to minimise dependencies. For example, indulgence needed ActiveRecord, but by using standalone-migrations, I was able to create a nice test environment using ActiveRecord, without any other dependencies.

In fact, it is fairly easy to create a working test environment. I’m a great fan of test/unit and minitest, and as both are now part of ruby standard library, using them again reduces my gems’ dependencies.

What I’ve been missing is an easy way of getting to an equivalent of the rails development console. Today, I’ve had yet another ‘why didn’t I think of that before‘ moment. There is an easy way to create a console. I’ve added a console.sh file to my latest gem project (webdav_file_store) with this content:

#!/bin/bash

echo Opening Ruby shell with WebdavFileStore loaded
irb -r ./lib/webdav_file_store

The -r option of irb is doing all the work. It is loading the file that opens my WebdabFileStore namespace Module, along with the requirements it loads. This only works in a bash shell, and you have to make the file executable, but once that is done, all I do is run ./console.sh and I am in a console session with all my WebdavFileStore objects loaded.

So another technique I can add to my strategies to minimise my gem dependencies.

Update:

See this article on Ernie Miller’s blog for an alternative approach. That is, to create a rake task that opens the console with the gem loaded. The comments are well worth a look through. I think Ernie’s is probably a better technique to the one I describe above.

This entry was posted in Ruby. Bookmark the permalink.