Get ready for the TextMate “Trundle to Rails 2.0 Bundle”

Posted by Dr Nic on January 31, 2008

logo_bundle.png

Have you noticed lately that the Rails TextMate git pull origin two_point_oohbundle (also installed with e - the Text Editor for Windows) isn’t quite as helpful as it once was - guiding and amplifying your rails app development.

Your resourceful/restful rails apps are now filled with named routes, but none of the helpers (link_to, redirect_to, etc) use them. The default view template was still rhtml for a long time (latest svn trunk fixes this to be html.erb, though Marc Jeanson is having a crack at supporting both through a per-project config file).

Or perhaps you were hoping for some snippets for new features of Rails 2.0: assert_difference (asd), assert_select (ass), respond_to (rst).

Or just maybe, you’ve been updating your local bundle to Rails 2.0 already? Please say yes, please say yes. If you are saying “yes”, read at the bottom for how/where to send me the patches. If you are saying “no”, read at the bottom for how/where to start creating patches and sending them to me.

Firstly, DHH didn’t write the Rails bundle

I didn’t know this - I just assumed the guy who created Rails and helped promote TextMate also created the Ruby on Rails TextMate bundle. Instead if was WWF’s “The Rock” himself Duane Johnson (figurines sold separately, and may look different to the real Duane Johnson who writes Rails code instead of prancing around in his underpants with other adult males in confined spaces).

The TextMate SVN logs say that it the bundle was first committed in Jan 2005. Its now Jan 2008. That’s three years of maintaining a suite of code that thousands of people take for granted every day writing Rails code. What a champion.

Like the Australian Cricket team’s wicketkeeper, Adam Gilchrist, he’s also retiring at the top of his game.

New Maintainer… me

Instead of maintaining my own projects, I’ve decided to maintain this one. I love the TextMate bundles. Before I had a Mac, I ported them across to RadRails and many RadRailers entered a golden era of snippet happiness.

My bundle-fu may not be the equivalent of Bruce Lee, but I’m keen to see my favourite Rails tool live on strong.

Bleeding edge bundle

Whilst the TextMate SVN administrators process the maintainer change request (Allan is on holidays somewhere and he took the house keys with him), you might think all is lost!

Never.

The straight-off-the-cow bleeding edge Rails bundle can be accessed via Git. Specifically the branch two_point_ooh.

So, let’s all do away with our pre-existing Rails bundle and live on the edge.

cd ~/"Library/Application Support/TextMate/Bundles/"
mv "Ruby on Rails.tmbundle" "RoR.tmbundle.orig"
git clone git://github.com/drnic/ruby-on-rails-tmbundle.git "Ruby on Rails.tmbundle"
cd "Ruby on Rails.tmbundle"
git checkout --track -b two_point_ooh origin/two_point_ooh
git pull

Now, back in TextMate, go to menu “Bundles” > “Bundle Editor” > “Reload Bundles”.

You, my friend, are sitting pretty.

Upgrading to when newer blood is on the bleeding edge

Coming back for more?

cd ~/"Library/Application Support/TextMate/Bundles/Ruby on Rails.tmbundle"
git checkout two_point_ooh  # optional; only if you changed to another branch etc
git pull

Now, back in TextMate, go to menu “Bundles” > “Bundle Editor” > “Reload Bundles”.

Bathe yourself in glory. Splash it all over yourself.

Submitting patches

If you go into TextMate, launch the Bundle Editor (Cmd+Alt+Ctrl+B) and change something in the Ruby on Rails bundle, then files will added/changed within your local git clone.

What I mean is, you can very simply submit patches now. [When I say "simply", I mean, "I think this is the best approach but I could be completely wrong here..."] Git is so cool that I don’t know what its doing most of the time; but let’s hang in there as a team.

cd ~/"Library/Application Support/TextMate/Bundles/Ruby on Rails.tmbundle"
git add .   # to add any new files/snippets/commands you created; TextMate uses one file per snippet
git commit -a -m "Useful message about this patch goes here"
git diff -p HEAD^ HEAD

[Theoretically] this creates a patch based on your most recent commit. So you can easily create patches for changes even if your repository and the remote/central/bleeding edge repository look different.

If your patch was created over several commits, then replace HEAD^ with HEAD~4, if there were 4 commits.

I think. God I could be wrong about this though.

Just try your best and if it works, let me know and I’ll remove all this “I don’t know what I’m talking about” text and future readers will think I know everything. Web 2.0 rocks.

Send patches to…

Me drnicwilliams@gmail.com [update] or via the new Google Group.

Want to fork the git repo? Use a free account at Gitorious or GitHub.

Google Groups
Ruby on Rails: TextMate
Visit this group

Trundle to Rails 2.0 Bundle

Arguably, we just keep patching the bundle forever and bleeding edges will continue to live happily within the blood and muck of said existence.

But, lots of other people want nicely zipped up bundles. No doubt “e - the Text Editor” will want a “released” version so they can clean it of all the ugly things they can’t yet replicate like Macros. And eventually I’ll push it all down to the SVN repo and it will be released with future TextMate upgrades.

So, there will be a “Rails 2.0 compatible” grand opening one day soon. Probably before 14th of March 2008, when I’m giving a “What’s new in Rails 2.0?” talk at QCON London. Showing off the new bundle will be sweet.

That gives us 6 wks to refactor this bundle to make it a shining example of all that is wonderful in Rails 2.0. Every patch helps.

[Please consider Rails 1.2.6 and before developers when conceiving of patches, and please consult your doctor if pain persists.]

Autotesting Javascript in Rails

Posted by Dr Nic on January 04, 2008

I used to love Javascript so much that it would scare me. Why? Because I used to never write any tests. No unit tests. No integration tests (e.g. Selenium). Why? I didn’t know how. Not properly. I didn’t know how to write Javascript unit tests with an autotesting tool, like ZenTest’s autotest command.

And now…

javascript-testing-intro.jpg

I am now free to write as much Javascript as I like knowing forever I’ll write Javascript tests first, and Javascript in libraries second. TDD for Javascript beckons!

Below is a “getting started” tutorial, a helpful autotesting plugin, and hints about a TextMate bundle for Javascript Unit Testing and a future Peepcode on Javascript Unit Testing.

Installation

Fundamentally, the ideas here are app server-neutral. We’re using the unittest.js library from scriptaculous. But here I’ll show/demo the Rails plugins that make this all uber easy to get started.

Firstly, create a blank rails app, or use an existing app. The tutorial should be non-invasive - just a few “demo” files to delete when you’re done. This tutorial is independent of your app.

ruby script/plugin install javascript_test
mkdir test/javascript
ln -s ../../vendor/plugins/javascript_test/assets/ test/javascript/assets

For Windows people copy vendor/plugins/javascript_test/assets into test/javascript/assets, as you don’t have symbolic links, which is sad.

At this stage, you can add and commit these files to your project. The rest of this article is destructible demo files and tests.

Creating javascript tests

Let’s say

$ ruby script/generate javascript_test maths
    exists  test/javascript
    exists  public/javascripts
    create  test/javascript/maths_test.html
    create  public/javascripts/maths.js

maths.js is just a blank javascript file. The important file is maths_test.html. Its packed with lots of “getting started” goodies.

Open test/javascript/maths_test.html and find the testTruth method.

testTruth: function() { with(this) {
  assert(true);
}}

This is an example of a javascript test method, with a sample assert call. It has the same api as the Ruby test::unit assert call. Thomas Fuchs’ presentation Adventures in JavaScript testing gives a good rundown of the available assert methods (and the BDD style syntax that is available). I’m also preparing a TextMate bundle to generate the assert calls, with the same “as”, “ase”, “asnn” tab completions as the Ruby bundle. It makes me happy when using it.

Running unit tests

The most holistic way to run your javascript unittests, is against all the browsers you have on your local machine. The javascript_test plugin comes with a rake task for this: test:javascripts

$ rake test:javascripts
(in /Users/nicwilliams/Documents/rails_apps/imindi_theme)
/test/javascript/maths_test.html on Safari: SUCCESS
/test/javascript/maths_test.html of Firefox: SUCCESS
Skipping Internet Explorer, not supported on this OS
Skipping Konqueror, not supported on this OS

In the browsers you’ll see:

javascript-unit-test-file.jpg

It runs all your tests on all browsers. That’s great for a Continuous Integration process, but for me, coming from the ZenTest world of autotest, I only want to run those tests for which something has changed.

I want continual feedback. Small change, run small test. autotest gives me that for Ruby, but rake test:javascript doesn’t.

Autotesting javascript tests

On my Mac, I’ve set up something as a starting point for autotesting javascript tests, based on the “small change, run small test” principle.

$ ruby script/plugin install http://drnicutilities.rubyforge.org/svn/plugins/javascript_test_autotest/
.
.
Edit config/javascript_test_autotest.yml for the browser(s) to use for autotesting.

Open config/javascript_test_autotest.yml and uncomment the browser(s) you want to autotest with. I autotest on Safari on the Mac, even though I develop/debug on Firefox, because it reloads each page in the same tab, which I like, and I’m having problems getting this to work into Firefox at all.

My yml file looks like:

browsers:
  safari: '/Applications/Safari.app/Contents/MacOS/Safari'

So, the current version is known to work for Mac OS X and Safari. If you get this plugin working on different O/S and browsers, let me know below or please submit a patch to http://groups.google.com/group/drnicutilities

From a command line:

$ script/js_autotest
Watching public/javascripts/controls.js, public/javascripts/application.js, test/javascript/maths_test.html, public/javascripts/effects.js, public/javascripts/dragdrop.js, public/javascripts/prototype.js

Files: 6

Let’s TDD with js_autotest

In test/javascript/maths_test.html, replace testTruth, with the following and save:

// Maths class should exist
testMathsClassShouldExist: function() { with(this) {
  assert(Maths, 'Where is Maths?');
}},

js_autotest will automatically load maths_test.html into your browser, and its tests executed.

javascript-testing-failure.jpg

Now, let’s fix the problem by creating the Maths javascript class. In public/javascripts/maths.js, add:

var Maths = Class.create();
Maths.prototype = {
  initialize: function() {

  }
}

js_autotest will again automatically reload maths_test.html into your browser, and its tests executed.

javascript-testing-success.jpg

Yay for TDD and Yay for “small change, run small test”.

Peepcode

I love Geoffrey’s Peepcodes. Geoffrey has all my money in Peepcode credits. More importantly, Geoffrey’s due to give birth this year to #1 child. Geoffrey, who works from home, is blissfully unaware that soon he’ll be a full-time father and part-time Peepcode author. This could mean fewer peepcodes on important peepcode-worthy topics.

I always wished there was a Peepcode on Javascript Unit Testing. It would take many blog posts to cover as much as can be covered in a single 60 minutes peepcode. So, we’re writing/videoing one.

As a Javascript developer [has anyone ever heard of a Javascript Users Group?] let me know what specifically you’d like covered in this video, so I don’t accidently miss something.

[optional] Install some patches

There was a section here about some patches that could be applied. These have now been applied, and javascript_test plugin has been updated with prototype 1.6.0.1. Life is good.

Find objects in IRB directly from browser URLs

Posted by Dr Nic on January 01, 2008

A long time ago, I tired of going into the irb/console and finding objects/models using the traditional ActiveRecord command Person.find(15) and now I’m sitting pretty: I can paste in URLs to fetch objects.

# No more of this:
=> Person.find(15)
# instead:
=> people/15

people/15 is something you’ll copy+paste directly from your browser: http://localhost:3000/people/15

Of course, the url is based on your routing + controllers, so the assumption here is that your routes/controllers map to your active record models. That is, your app is smothered in RESTful love and cuddles.

Not following this? Here’s a video:

How to make this work at home

Copy and paste the following into your .irbrc file:

Thanks goes to…

The some original code for this comes via Mike Clark, who had the idea for syntax activity(6). This was good.

I previously had another idea to support the syntax 6.to_activity using the RubyGem to_activerecord. I still like the id.to_class_name structure of this and still use it.

But if I have a perfectly nice looking url sitting in front of me, I can now paste the class_name/id part into irb and I’m off and running.

Happy New Year.

RubiGen meets the A-Team - live in Charlotte

Posted by Dr Nic on November 05, 2007

I previously posted the stunningly realistic teaser/trailer for my RubyConf talk in Charlotte.

The RubiGen talk has now been given. The highlight was definitely the opening 90 second video.

So now here is the full video that preceded my talk. DRM-free. Good-for-a-few-laughs. With special Ruby guest stars.

Two bonus announcements for RubiGen brethren:

  1. In addition to Merb, NewGem, RubyCocoa (via Rucola) and Airake, now Adhearsion has RubiGen in its trunk (to be included in impending 0.8.0 release).

    The Merb team have been enthusiastically adding and updating generators. For this reason, and many others, the up coming 0.4 release of Merb is going to be awesome!
  2. RubiGen will be renamed. During my 1hr talk I had to say out aloud the words “RubiGen”, “Gem”, “RubyGems”, “Generators” so many times that it was just becoming plain confusing.

    I’ll post my vote below in the comments. Vote below to name the ultimate Ruby generator!

I also want to reiterate my thanks to Jeremy Kemper, the original author of the code. Its uber sexy.

Everything you wanted to know about Ruby.NET

Posted by Dr Nic on October 29, 2007

Recently Wayne Kelly spoke at the Brisbane Ruby and Rails Brigade about Ruby.NET (code repository).

We figured he was some authority figure on the topic, as he wrote it, together with some other members of his QUT department, plus a growing number of Ruby.NET users and contributors.

Local Microsoft officialdom sponsored the show with pizza and then drinks afterwards. Ok, I’m understating that - Charles Sterling is an ex-.NET project manager, who is now in Oz for a Tour of Duty as an Evangelist. In his capacity as an evangelist, he giveth us thy pizza. Twas tasty too.

I believe Ruby.NET is in direct competition with IronRuby for the hearts and minds of Ruby/.NET/Windows developers.

Wayne starts the video below with a comparison of the two, plus a few other Ruby implementations (sorry Evan, Rubinius wasn’t mentioned).

Fortunately we were treated to a demo early in the show. Wayne had recently implemented Ruby code-behind for some of the drag-and-drop widgets that come with Visual Studio. It was very sexy to see all that Ruby being generated.

The video also includes lots of “why Ruby is hard to work with as a compiler writer”, and more importantly, there are lots of audience questions all throughout the talk. This might be why the talk is 1.45hrs long!! :)

Enjoy… (and the slides from Wayne)