Skip to main content

Posts

Showing posts from 2012

Poor person's guide to managing Ruby versions

Understanding the guts of Ruby Version Management by rolling your own I've been tinkering with a fresh install of Ubuntu 12.10, setting up a nice clean development environment. One of the first things to do, of course, is implement some sort of Ruby version management. RVM and rbenv seem to be the clear winners in this arena, though there are a lot of tools out there that do a similar job . Writing your own version management for your Rubies isn't actually all that difficult. At it's core, we need need two things: A way to segregate the executables of the various versions A way to call the versions at will Segregating versions is trivial - working with files and folders, we can put the various versions into named directories. Actually executing our different versions is not all that difficult either. One way would be to create aliases with version numbers and explicitly call those when we want to use them. The more popular way, however, is to manipulate our PATH ...

Rails 3.2, MiniTest Spec and Capybara

What do you do when you love your spec testing with Capybara but you want to veer off the beaten path of Rspec and forge ahead into MiniTest waters? Follow along, and you'll have not one, but two working solutions. The setup Quickly now, let's throw together an app to test this out. I'm on rails 3.2.9. $ rails new minicap Edit the Gemfile to include a test and development block group :development, :test do gem 'capybara' gem 'database_cleaner' end Note the inclusion of database_cleaner as per the capybara documentation And bundle: $ bundle We will, of course, need something to test against, so for the sake of it, lets throw together a scaffold, migrate our database and prepare our test database all in one big lump. If you are unclear on any of this, go read the guides . $ rails g scaffold Book name:string author:string $ rake db:migrate $ rake db:test:prepare Make it minitest To make rails use minitest , we simply add a require ...

Ruby, facemash and the Elo rating system via BDD

Reproducing the Elo rating algorithm in Ruby is a little challenge that I took upon myself recently for a small hack. The same Elo rating system that was scrawled upon the glass in "The Social Network" as the algorithm that Mark Zuckerberg used on rank people on FaceMash. As an exercise, here's a pass at it with a little BDD thrown in for good measure. A new file - elo.rb: require 'minitest/spec' require 'minitest/autorun' describe "result" do describe "when both players start with rating of 100 and k factor of 30" do it "must return 115 for the winner" do new_rating.must_equal 115 end end end Starting a new algorithm is always tricky. We know that the Elo rating system is essentially concerned with assigning ratings to players based on the outcome of their games or matches. In fact, it is widely used as a chess ranking algorithm. At a first glance then, I thought I might want to jump in and start mo...

Overriding equality and Test Driven Development

Ruby has, at its root, an Object. Methods available in Object are available to every class because every class in Ruby inherits from Object somewhere in its own class hierarchy. Of course, you can override methods in subclasses, changing the functionality of a root method. You might stumble on to this idea if you work through Test Driven Development By Example by Kent Beck, translating the Java code into Ruby as you go. At some point pretty early on, he overrides the equality method on the Currency class to better test if two instances are equal. I'm going to do the same here, working with Instruments instead of Currency. Equality Equality in Ruby can be expressed using any of the following three methods object == other equal?(other) eql?(other) These methods are defined on the base Object. The default implementation of equality will only return true if both objects are exactly the same. The interesting thing is that although these three methods start out functioning the...

Rails Callbacks and Boolean Values

Rails has a lovely feature as part of ActiveRecord - Callbacks; to wit: Callbacks are hooks into the life cycle of an Active Record object that allow you to trigger logic before or after an alteration of the object state Basically, that means that you can instruct Rails to execute your own code throughout the process of creating, updating and destroying objects/records. You can, for example, use them to set some default values on create, or perhaps do some last minute validation, or even fire an event just after you've saved a record. The available callbacks are: after_initialize after_find after_touch before_validation after_validation before_save around_save after_save before_create around_create after_create before_update around_update after_update :before_destroy around_destroy after_destroy after_commit after_rollback At the same time, Ruby methods have the concept of implicit return values. That is to say, any method will return the value of the la...

Install or update gems behind corporate firewall or proxy server

If you work with Ruby on Windows in a corporate environment, sooner or later, you will hit an error when you are trying to install or update Gems. In my case, I simply had to set a few environment variables and I was good to go. RubyGems uses the HTTP_PROXY, HTTP_PROXY_USER and HTTP_PASS by default so if you open up a command prompt and set these as follows, it will use them to find the proxy and authenticate you to your proxy server: set HTTP_PROXY=http://pr.oxy.ip:port set HTTP_PROXY_USER=domain\user.name set HTTP_PASS=sUp3rS3curepAs$w0rd Extra points: A reader sent me a comment that this will only work when the proxy is using basic authentication. If you're having trouble using this method then you can give ntlmaps a shot. It's basically a little bit of python magic that sets up a proxy on your localhost through which you can route traffic and it will handle the authentication with your proxy server for you.

Ruby on Rails - mapping a url to a resource

There are always times when you need to override the default RESTful routes in Rails. The most common case for this is mapping a /logout url to a session#destroy controller and action. However, this simple example doesn't really help when you want to achieve something a little more intricate - for example using a completely different url for a resource. Examples include a blog when you want your urls to add blog posts to be /add rather than blogs/new. Or what about a application with a Users model that has different types of users that can be added - perhaps it is a medical database and you have Doctors and Nurses - you want your urls to reflect the kind of person you are adding or editing - so doctor/new or nurse/new rather than users/new. Mapping urls like this is easy. However there is a little gotcha that you have to be aware of. Let's walk through an example and we'll see how to make it work New project We'll create a simple project for this example - a hypoth...

Getting started with Ruby on Rails 3.2 and MiniTest - a Tutorial

For fun, I thought I would start a new Ruby on Rails project and use MiniTest instead of Test::Unit. Why? Well MiniTest is Ruby 1.9s testing framework dejour, and I suspect we will see more and more new projects adopt it. It has a built in mocking framework and RSpec like contextual syntax. You can probably get away with fewer gems in your Gemfile because of that. Getting started is always the hardest part - let's jump in with a new rails project rails new tddforme --skip-test-unit Standard stuff. MiniTest sits nicely next to Test::Unit, so you can leave it in if you prefer. I've left it out just to keep things neat and tidy for now. Now we update the old Gemfile: group :development, :test do gem "minitest" end and of course, bundle it all up.....from the command line: $ bundle Note that if you start experiencing strange errors when we get in to the generators later on, make sure you read about rails not finding a JavaScript runtime . Fire up...

Javascript - Objects by ref

If any language should have been name after a snake, Javascript should have. It's a slippery little thing I tell you. It slithers and slides and wraps around you. And you have to work like a snake charmer to coax it out of its basket and make it play nicely without biting you. Take, for example the simple idea of passing a variable by ref or by val. Javascript's snakey little implementation means that if you are passing a variable then you'll never pass it by ref. However if you are passing an object, then, hey presto, by ref it is. Bear witness: var globalVar; var anObj = function() { this.value = "default value"; } function changeValue(arg){ arg.value = "Changed by function"; } function changeUp(arg) { arg = "Changed"; } globalVar = "global"; console.log(globalVar); changeUp(globalVar); console.log(globalVar); var myObj = new anObj()...

Ruby frameworks, Rails and Padrino

Some thoughts on the Padrino and Rails . For the past few weeks, I've been working on a small project that is using Padrino rather than Rails. The interesting thing was that the decision for the technology was based on the idea that the project was only going to have a few objects; at most five or six and as such, didn't need something as large, complex or weighty as Rails . However, something as barebones as Sinatra would not allow for some of the more rapid application development that you get from some of the baked in goodness of Rails - things like Sessions, Flash, Form helpers and generators all speed up development fairly considerably. With that in mind, Padrino was the framework of choice. Now Padrino is interesting. It's a great little framework, but, the temptation is to look at it's relative light-weightedness in comparison to Rails and think it will require less learning time or up-front knowledge for someone with little experience of the framework or of so...

Rails 3.2 Could not find a JavaScript runtime execjs

Running a fresh copy of Linux Mint and Rails lets you generate a new project with no problems, but you might start to hit issues as soon as you start trying to generate some scaffolding. So for example, if you try rails g scaffold User name:string email:string You'll get something like this: /home/x/.rvm/gems/ruby-1.9.3-p194@rails3.2/gems/execjs-1.4.0/lib/execjs/runtimes.rb:51 in 'autodetect': Could not find a JavaScript runtime. It will also tell you to visit https://github.com/sstephenson/execjs to see a list of available runtimes. Don't be shy now, head over there and take a look. Or, if you just want to hack it, add the following to your Gemfile: gem 'therubyracer' Run your bundle update and you should be good to go.

Triple boot Linux, Windows 7 and Windows 8 RTM

I wanted to have a triple boot computer - why? don't ask me why! Oh, ok, I'll tell you - I needed Windows 7 for some current work and didn't want to mess up the install. I wanted to install Windows 8 so I could play with the metro style app development that I've seen floating around and of course, I like my Linux system for my ruby web development . So - here's the rough steps without a specific walk through of each one, except for reinstalling grub, which is really the crucial step to getting everything to hum and purr along nicely. The caveat is that this worked for me, on my system, it might not work on yours - so take precautions, backup, verify backup, store a backup off-site - you know the drill, I shouldn't need to tell you.: 1) Install Windows 7 Easy enough, follow the prompts and pop Windows 7 on your machine. 2) Install Linux Choose your flavour - I've got Mint up and running, but go for Ubuntu if you prefer. Actually, go for pretty much whate...

Generate an absolute URL in padrino

Sometimes, you just need that absolute URL. Padrino gives you a great little helper to create your urls in th form of url_for. Unfortunately, Padrino's documentation seems to be written from the point of view of someone who is intimately familiar with Rails, which means the total noob trying to get into Padrino without any Rails experience can be left a little flummoxed. Anyway, it is important to realise that Padrino has Sinatra as its base and you can tap into all that goodness that Sinatra offers. Absolute urls are as simple as: value) %> Lovely.

Ruby LoadError: cannot load such file

So, you've set yourself up a lovely new app using, for example, Sinatra , and you're really chaffing at the bit to write some lovely code. But you keep getting bit by this: LoadError: cannot load such file -- sweetsweetcode You double check your config.ru but it is pretty standard stuff: require 'sweetsweetcode' run Sinatra::Application What can be wrong? Please tell me oh gods of Ruby. Is it Passenger? Is it Rack? Have I uncovered a great big bug in Ruby itself? Naaaa! Of course not you fool, it's just that you're on the very latest version of Ruby, probably 1.9.3 or something and the load path no longer includes the current path. So to fix it, just do this: require './sweetsweetcode' run Sinatra::Application And you should be singing again.

Adding an item to Linux Mint Cinnamon Menu

Last time I took you through installing Sublime Text 2 on Linux Mint . The trouble with doing the install the manual way as I showed and not using sudo apt-get is that you don't get the neat integration into the operating system so you wont find Sublime Text in your Menu and if you search it wont be there yet. Right click on the "Menu" in the bottom left and choose "Edit Menu". You should have something that looks like this: Excellent. On my install, Programming was not yet ticked, so I clicked the checkbox so that the Programming section would show up in my Applications menu. Then on the left hand side, you need to click Programming, or whichever other category you want to put Sublime Text into and then on the right, click the "New Item" and fill it in as follows: If you followed along when I installed Sublime Text, you aliased subl to launch Sublime Text. Clicking where the icon is will let you choose the icon location. I used the 48x48 icon...

Padrino, Datamapper, Rake, Uninitialized Constant

So, perhaps you've set up a fancy application using padrino , datamapper and sqlite and you are going great guns until padrino rake dm:migrate => Executing Rake dm:migrate ... rake aborted! uninitialized constant Text Or something similar - the datatype is probably not too important. The solution is to edit your migration and put the datatype into quotes....like this: column :description, "TEXT" There seems to be a bug with the use of datamapper and the migration. I'm not sure where the bug is, but this fixes it!

Installing Sublime Text 2 on Linux Mint

So, continuing on from installing RVM on Linux Mint and installing Ruby on Rails on Linux Mint , I want to give a brief rundown on installing Sublime Text 2 on Linux Mint, though in fact, this will work for pretty much any Linux version, so if you're running Ubuntu it will work as well. If you aren't using Sublime Text 2 , I suggest you download it and give it a go - it's an awesome editor, especially for Rails and Python development, bringing a Textmate elegance to Linux. It's cross platform too, so if you are jumping between OSX, Linux and Windows, it makes the perfect companion giving you a consistent interface across the various OSs. Don't trust me? Well take a look at what others think about it So, there are two routes here - you can install using the traditional apt-get on Mint. You'll have to add a repository. That's not really my preferred method though. It takes too long to get releases through to the repository so I like to do a manual insta...

Installing Rails on Linux Mint 13 with RVM and gemsets

Last time I did a quick RVM install guide for Linux Mint . This time I'm going to finish up by installing rails so we can rock some new development work. Nothing like a clean and humming system I tell you. Let's begin by making sure we have git - we are going to be using it anyway. Fire up your terminal (Ctrl-Alt-T) and type sudo apt-get install git Great - version control level unlocked. We should have rubygems installed already (if you followed along with the RVM install then this is all taken care of). Now, to make sure RVM functions well, see this https://rvm.io/integration/gnome-terminal/ . Or, if you prefer, just move the commands from .bash_login to .bash_profile. As I understand it, and I'm no Linux guru, .bash_login doesn't run if .bash_profile is present. I'm going to create a gemset to install rails 3, just for fun...and just in case I want to go back and work on some legacy apps. rvm gemset create rails3.2 And set it so it is the default gems...

Installing RVM on Linux Mint 13

Linux Mint has captured my imagination recently, and of course a fresh install means getting my dev environment up and running again. I'm using the cinnamon version and so far things are going well. Everything on my laptop is just working; suspend, all the various function keys. Support out of the box is good. I'm impressed. The experience is soooo much better than the last time I tried a more full featured distro and things got so bad with video drivers crashing and causing my fan to spin up constantly that I ended up going totally minimal with Arch and just a command line. I like arch, but I thought I would give Mint a go. So, now we need to get Ruby, RVM and Rails on the go so we can do some web development. Let's start with RVM. Next time I'll take a crack at installing Rails on Mint First things first - we need curl. My install didn't have it so.....fire up the terminal with Ctrl-Alt-T and type the following sudo apt-get install curl Next up, install RV...

Jekyll and ruby 1.9.3 site not regenerating

If you are trying to compile a site with Jekyll and ruby 1.9.3 and you have some dodgy yaml front matter in one of your posts, your site just won't regenerate. Step 1 is to edit your _config.yaml and set auto: false. If you leave auto:true then it won't report the errors at all. With that, if you run your jekyll --server command again, you could get an error to the effect of "did not find expected key while parsing a block mapping at line" blah blah blah. The error isn't particularly useful. However, help is at hand - see this pull request which you can manually apply to your gem if you want and you'll start to get meaningful error messages again. I monkey patched mine by editing my lib/jekyll/post.rb file to include the pull request's code. I guess you could use RVM and use an older ruby version, but this did the job for me

Creating flash messages bootstrap style

I'm on a twitter bootstrap binge at the moment, it fills my soul with glee to start a new project with a base template that looks better than the usual dog's breakfast. Anyway, there are days when you just need a piece of code to blast in to your templates so that you can get on with your work. This is one of those and slapping the tremendous bootstrap success, warning and info messages into our normal flash message stylings is just what the doctor ordered. Here then, for your delectation, a small snippet of code to pop into your application layout in place of your usual flash message code that will style things up the bootstrap way. If you prefer, pull this out into a helper.....if you think that's the rails way. Personally, for small projects, I don't bother.

Add css class to your label form helpers

Say, for example, you are using Twitter Bootstrap to style up a quick rails app and you want to throw in a label tag with the class set to "control-label" just like the bootstrap guys do.....how do you do it? And more importantly, since you don't want to specify the text of the label, how do you accomplish that? Fear not intrepid young but soon to be rails guru, behold the truth:

Nginx and Rails into development mode

If you are running a rails app with nginx serving it up and you want to put the whole shebang into development mode, open up your nginx.conf file and in the server section, add the following line: rails_env development; Remember though, it takes a ton more resource to do this so remove the line when you're done. Part of the fun of doing this is if you are hacking away on a project and you want to skip the precompiling of assets and such.

Redirect www to naked domain in nginx

Redirecting a www based domain to a non-www based or naked domain is pretty easy - in the nginx conf file, you'll need something like this: server { listen 80; server_name www.example.com; rewrite ^(.*) http://example.com$1 permanent; } server { listen 80; server_name example.com; ...rest of your conf } You might not want to do this though. Using naked domains is not always the best idea .

Installing a gem with no documentation

Often you will want to install a gem on your local system or server, but you don't require the documentation, you want to leave it out. This not only speeds up the install, but saves some space on your machine. Here's the script to run from the command line if, for example you were installing the rack_csrf gem: The reason for both "no-ri" and "no-rdoc" is because there are actually two types of documentation being installed - the RDoc is essentially embedded documentation generator for the Ruby language. It will analyze source code and create the documentation. the Ruby ri files are to all intents and purposes Ruby's version of man pages which give you documentation from the command line.