Peter Marklund

Peter Marklund's Home

Peter on Rails

Lessons Learned in Ruby on Rails and related technologies. Subscribe

Wed December 27, 2006
Programming

New Rails Plugin for HTML Validation: Html Test

Update on 2009-04-16: The source code has been moved from Google Code to GitHub

Update on 2007-12-12: I have renamed the plugin from "Http Test" to "Html Test" and moved it to a new home at Google Code. Sorry about the inconvenience that this may cause those of you who have the plugin installed and want to update it. The change is essentially a namespace change from Http:: to Html:: so it should be manageable. Thanks.

As I wrote earlier I like to monitor my production sites with HTTP tests that validate their HTML and check for broken links and images. I think that serves as a good baseline check, a smoke test if you like, that the site is not fundamentally broken.

It used to be that my HTTP tests were implemented in Perl using WWW::Mechanize. Now that we have the wonderful Ruby and Ruby on Rails at our fingertips that felt like a real shame. I decided to implement my HTTP tests in Ruby and once I had gotten that far, going the extra mile to package my scripts as a Rails plugin seemed natural. The plugin is called http_test and it's available at Google Code.

Read More | 7 Comments

Tue December 12, 2006
The IT Business, Programming

Hype and the Rise and Fall of Programming Languages

Steve Yegge has written an article on Ruby as a competitor to Python, the Rails hype, and the rise and fall of programming languages. The article touched me deeply. Thanks to Olle Jonsson for sending the link. The article is almost a year old but should still be relevant. I especially like the last section on Ruby:

"The worldwide Ruby culture is the warmest and friendliest I've seen in my long history with programming languages. And Ruby is a sweet language. Other people seem to agree, and are taking steps to market it, which is getting them labeled as "hyper-enthusiasts" by the Sour Grapes camp. It appears to me that Ruby is doing what I wanted Python to do a few years ago, so I've finally learned Ruby and have switched most of my development over to it.

Read More

Fri December 08, 2006
Programming

MySQL Gotchas and a Deadly Sin

Coming from mostly a PostgreSQL and Oracle background I experienced some major friction working with MySQL today.

The first obstacle to overcome was the syntax for foreign keys. I started out using

  create table test (
    service_id integer NOT NULL references services(id) on delete cascade
  );

Read More | 3 Comments

Sun December 03, 2006
Programming, Usability

Usability on the Web and Embracing Simplicity

I just booked flight tickets for the christmas holiday and it got me thinking of usability. People depend on websites so much these days and it's a shame to let them suffer from poor usability. Of course, usability has improved quite a bit over the last couple of years. Indeed SEB finally uses a date widget, and I think even suggests a sensible default (the next working day), when you do payments through their online bank. For the longest time they left the user with a bare bones YYYYMMDD text input widget.

Booking tickets on the web is often a series of frustrations for me. This is in spite of the fact that I am a skilled web user. For example a form won't submit and the validation error is hardly visible. The user is left wondering if the form submitted at all, if there was a validation error, and if so, where?

Read More | 1 Comment

Mon November 27, 2006
Salsa, Experiences

Third Place in Salsa Competition

There is a quote by Woody Allen that rings more and more true to me:

Eighty percent of success is showing up

Last friday me and my girlfriend Janne were able to win third price at a Salsa competition at La Isla here in Stockholm. Thanks to the encouragement of Pilar and Ociel at Stockholm Salsa dance we decided to give the competition a try and it was great fun! My friends Håkan and Mimmis won the silver, and a very professional and choreographed couple from Uppsala took home the gold. We were very pleased to walk home with the trophies and 1000 SEK though...

There is a huge difference between social dancing and show dancing, and as my friend Håkan said, if you want to be a successful show dancer you need to learn to dance outwards (with the audience) rather than inwards (with yourself and your partner and the music).

2 Comments

Thu November 16, 2006
Programming

Teaching Rails at Great Works

I've started teaching Ruby on Rails at Great Works and I'm very excited about it! It's a three evening course given to a small group of up to 10 people. We use a lot of hands on excercise rather than lecturing and the goal is to build a small Rails application. The course participants are designers rather than programmers so we needed to lay down some object orientation and programming basics before we could take on Rails. Despite of this obstacle we were able to make a lot of progress by using Locomotive for installation and scaffolding for UI generation. You can check out the slides here.

I genuinely enjoy teaching and am now looking for more opportunities to help companies learn and get started with Rails quickly. Get in touch if this sounds interesting.

Make a Comment

Wed November 15, 2006
Programming

Stockholm Rails Meetup Tonight was Awesome

We had a fantastic turnout and great atmosphere at the Rails Meetup at Valtech here in Stockholm tonight. There was a great presentation by Ola Bini on web services and Rails, and one by Christian and Albert at Adocca about caching and a bunch of plugins that they have realeased at RubyForge. All very exciting.

I gave a presentation on the Media Contact Manager system that I have built for Green Media Toolshed.

Make a Comment

Tue November 14, 2006
Programming

Rails: File Uploading and Storage

File uploading and storage is no big deal, right? I mean with Ruby it can be as easy as:

  def create
    File.open("/Users/db/_dev/rails/videos/swing.mov", "w") do |f|
      f.write(@params["video"].read)
    end
  end

Don't forget to set :multipart => true on your form though. The easiest (and most naive?) approach to uploading files is probably to use the File Column plugin. The Rails Wiki has a good page that discusses file uploads in more depth. The file system base storage approach that I've used in my Rails app is similar to what's described here. I use the after_save and after_destroy callbacks to create and delete the file in the file system - an approach also described in this Rails manual. Johan Sorensen has some code for doing buffered file uploads that might be useful for huge files.

This page is quite impressive. It has everything you ever wanted to know about the input type="file" form widget, including why browsers will ignore the value attribute if you try to set it. An annoyance is that if the user gets validation errors on a form containing a file_field widget she will have to re-select the file to upload.

The classic controversy is whether to store files in the database or in the filesystem. If you store them in the database you have a more unified and consistent storage solution. You keep all your data in one place, in one format, and the only data you need to back up is your database. On the other hand, putting files in the file system could potentially offload your database and make the database dumps smaller. Also, databases were not really intended to store files, that's what file systems are for. Personally I'm ambivalent on this issue, but due to some incidents with file system storage recently I'm now leaning more in favor of storing files in the database.

2 Comments

Sat November 11, 2006
Programming

Rails script/console - Did you know it could do all this?

Yesterday someone pointed out some features of the Rails console that I had missed out on. Here are some objects and commands to be aware of:

4 Comments

Thu November 09, 2006
Programming

Rails Patch: Rake :test should not fail silently

Swallowing exceptions and failing silently has to be one of the worst sins you can commit as a programmer and I was surprised to run into that issue with the Rake :test task. The Rake :test task (the default task) will in turn invoke the tasks test:units, test:functionals, and test:integration. Any exceptions raised within these sub tasks are not exposed directly but are merely noted as an overall test failure - obscuring the root cause of the failure. This is obviously not very debugging friendly if you have an exception raised somewhere deep down in the Rake task dependency hierarchy. I submitted a patch to remedy the problem.

3 Comments

Thu November 09, 2006
Programming

Rails QA: Watch Out for Duplication in your Fixtures

I had a long debugging session due to duplicated record keys in one of my fixture files. It turns out the YAML parser will not complain if you have duplicated record keys (the keys on the top level) or duplicated column keys. Eventhough the YAML specification says that map keys should be unique the YAML parser will happily overwrite any existing value for a key if it encounters that key again.

Under the motto of crashing early and avoiding silent failures I came up with the following unit test:

Read More | 2 Comments

Thu August 24, 2006
Programming

Rails Recipe: Checking for Broken Links in Integration Tests

Having a way to automatically check for broken links in your application can be quite valuable and there is a simple way to do that with integration tests. Here is the DSL methods that I used for that purpose along with some sample usage:

Read More | 3 Comments

Wed August 23, 2006
Programming

Rails Workaround: Preserving Nested Hash Params With List Values Across Requests

Suppose you have an HTML search form with a multi-valued select with the name "person[personal][interests][]". The trailing brackets are there to indicate to rails that this HTTP parameter should be converted to a Ruby list. Now, suppose the form submits to the search action in the contacts controller. Our params hash will then contain:

    params = {
      :controller => 'contacts',
      :action => 'search',
      :person => {
        :personal => {
          :interests => ['music', 'chess']
        }
      }
    }

Read More | 6 Comments

Fri August 18, 2006
Programming

Rails Recipe: HTML Validation

In this howto I'll show a simple approach to HTML validation that I use in my current Rails application. For me, HTML validation is a way to achieve wide browser compatibility, and to do a baseline check for correct rendering and UI brokenness. By putting ampersands and less-than signs in my test fixtures I can use HTML validation tests to check that I haven't forgotten any HTML quoting in my templates, i.e. that I haven't forgotten to use the following constructs:

<%=h some_variable %>
<%= link_to h(some_variable) ... %>

Read More | 7 Comments

Thu August 17, 2006
Programming

Rails Custom Validation

Suppose you have validation code for a certain type of data that you want to reuse across your ActiveRecord models. What is the best approach to doing this in Rails? As you probably know, Rails comes with a number of validation macros such as validates_presence_of, validates_format_of, and validates_uniqueness_of etc. One approach is to write your own validation macro that wraps one of the Rails validation macros. The validates_as_email plugin shows us how:

module ActiveRecord
  module Validations
    module ClassMethods
      def validates_as_email(*attr_names)
        configuration = {
          :message   => 'is an invalid email',
          :with      => RFC822::EmailAddress,
          :allow_nil => true }
        configuration.update(attr_names.pop) if attr_names.last.is_a?(Hash)

        validates_format_of attr_names, configuration
      end
    end
  end
end

Read More | 18 Comments

Wed August 16, 2006
Programming

Rails Recipe: A Timezone Aware Datetime Picker

NOTE! Only follow this recipe if you are using an earlier version of Rails than 2.1. As of Rails 2.1 timezone support is built into Rails in a way that makes it much easier to create timezone aware applications.

Quite often in web applications we display dates and times and also have users input them and store them in our databases. If your users are spread across the globe you really want to be able display times in the users own timezone. How do we accomplish this with Rails?

First off, as Scott Baron has pointed out, you want to grab a copy of the TZInfo Ruby timezone library. We need TZInfo since it can deal with daylight savings time (summer/winter hourly adjustments), something that the Timezone library that ships with Rails is not able to do. Installation is as simple as downloading the latest tgz file from RubyForge, extracting it into vendor/tzinfo, and requiring the library from config/environment.rb. We also add some new settings:

Read More | 124 Comments

Wed August 16, 2006
Programming

Rails Recipe: CSV Export

A common requirement from customers is the ability to export tabular data to a CSV file that can be imported into Excel. Ruby on Rails uses the standard Ruby CSV library to import test fixtures that are in CSV format. However, there is a runner up CSV library called FasterCSV which as the name suggests is faster and also has a much cleaner API. I was hesitant to use FasterCSV in production since it is still in Beta but after finding the discussion about including FasterCSV in the Ruby standard library I decided to give it a try.

Read More | 15 Comments

Wed July 19, 2006
Politics, Sweden

This Might Cost You a Little...

I just received an invoice from my dentist for 900 SEK (about a 100 EUR) for some unspecified service. I called them and it turned out I was paying 900 SEK for being 15 minutes late. What happened was I over slept and four minutes into the appointment when I was rushing out of my apartment to get on my bike my dentist calls (from Folktandvården, Eastmaninstitutet). I apologize and tell her I can be at her clinic in 7 minutes on my bike. She says nah, I'm not sure it's worth you coming in now that you're late, we better schedule a new time for you. I say ok, given that I didn't seem to have a choice. We book a new time and then at the end of the conversation she mentions that "oh, this might cost you a little" (the exact words in swedish were "det här kommer kanske att kosta lite").

Interesting points of comparison here is that once before when I missed an apointment I paid 300 SEK. My mom says she has never had to pay for missed appointments at her dentist. Last time I visited the dentist and they examined my teeth I paid 500 SEK, which right now seems pretty cheap, especially given that that time they actually performed a service for me.

Make a Comment

Tue July 04, 2006
Experiences

The Weepies Make me Weep with Joy

I just came home from a concert with The Weepies (a folk/pop duo from the US) at Debaser here in an exceptionally warm and sunny Stockholm.

The Weepies made me all misty eyed, showering beautiful harmonies of vocals and guitars over a small audience in an intimate concert setting. I loved the fact that about half of the songs were new to me since they were drawn from the solo CDs of Deb Talan and Steve Tannen that preceeded The Weepies. They also played a new song about an "Old Coyote" to be released soon on Itunes...

Read More

Thu June 08, 2006
Programming

Rails Code Generation Considered Useful

I just checked out Ryan Daigle's excellent What's New in Rails blog. There are a lot of great findings there for anyone like me who hasn't monitored closely the changes to the Ruby on Rails source code. In the post about the observer generator Ryan writes:

"On a side note, I feel like the generator utility has been getting a bad rap recently from people that frown upon auto-generation of code. Fair enough, but think of them more as best practices templates and learning tools rather than some sort of coding robot. They're really great tools for seeing how things should be done, and how things are expected to be done. If you don't want to use them, don't - but if you're not quite sure how to go about creating an observer, or controller, or model they're of great help."

Ryan puts it very well and I couldn't agree more. I've found the scaffold generator very useful in the project I'm working on now, and it's not for prototyping I'm using it, but for providing a skeleton for the production code I'm going to write.

Another advantage of the code generation in Rails is that if you use it your code will probably follow conventions (naming of controller actions for example) more closely and this will make the code easier to read and maintain for other developers. The generated code also contains best practices (such as the verify :method => :post for certain actions in controllers) that an average Rails programmer (or even a good Rails programmer) may not know about or may forget to use otherwise.

Make a Comment

Wed May 10, 2006
Programming

Presentations from the Rails Recipes Meetup

The Rails Recipes Meetup yesterday was a great success with over 20 participants and four interesting presentations. I would like to thank Xlent for hosting us and all the people who showed up and contributed to making the evening so nice.

If you are interested in coming to the next meetup (scheduled to happen in June or July), please signup for the swedish Rails mailing list at rails.se. Please also suggest presentation topics on that mailing list.

Here are two of the presentations from the meetup:

See you at the next meetup!

1 Comment

Sat April 29, 2006
Programming

Ruby on Rails Tips and Tricks

I've started a wiki page with some Ruby on Rails tips and tricks that I pick up from various weblogs and books. Hope it might be useful to others as well.

Make a Comment

Wed April 26, 2006
The IT Business, Programming

Starting a Startup - Hard but Doable

Here are some encouraging words from Paul Graham's How to Start a Startup article (which will make you scroll through eternity):

"You need three things to create a successful startup: to start with good people, to make something customers actually want, and to spend as little money as possible. Most startups that fail do it because they fail at one of these. A startup that does all three will probably succeed.

And that's kind of exciting, when you think about it, because all three are doable. Hard, but doable. And since a startup that succeeds ordinarily makes its founders rich, that implies getting rich is doable too. Hard, but doable."

Interesting to see the Web 2.0 Startup Toplist as well for a list of successful startups.

From Paul Graham's Y Combinator:

"Y Combinator relies on certain premises: that open-source software and falling hardware prices means that tech start-ups are cheap to finance; that large companies are no longer at the forefront of innovation; and that mature technology companies find it cheaper to buy than to build."

Make a Comment

Wed April 26, 2006
Programming

Rails Recipes Meetup in Stockholm

Each presentation is up to 20 minutes long followed by a 10 minute discussion. The presentations should be in the Rails tradition of "show don't tell". We prefer short presentations with code samples from recipes applied to real problems over the traditional type lengthy and theoretical Powerpoint presentations.

"Now, I know Rails well enough that over time I may have stumbled on some of the solutions, but that's not the point. With a collection of great recipes at hand - In-Place Form Editing, Live Search, RJS Templates, Polymorphic Associations, Tagging, Syndicate Your Site with RSS, and Sending Email with Attachments to name a few - I can quickly give my app the functionality today's web users have come to expect, then move on to the features that really set it apart from the crowd."

Make a Comment

Fri April 07, 2006
Programming

Quote of the Day

Thanks Jarkko for highlighting the following nice quote from the article Two more reasons why so many tech docs suck which argues the case of getting your users excited and using use cases for technical documentation:

One of the best techniques for creating and keeping interest is to make non-reference docs use-case driven. That way, each topic is framed by a context that matches something the user really wants to do. That way, each little sub-topic shows up just-in-time, instead of appearing to be there just-in-case.

It makes a lot of sense to me to organize technical documentation by the readers goals, i.e. to use the howto or cookbook approach. The Perl Cookbook is a great example of how this approach can be successful. In that instance the use-cases are on a very low level such as "How do I iterate over an array" but the approach should also work on a higher level, i.e. "How do I setup a weblog". High level use-cases like that are probably best broken down into smaller use-cases.

Make a Comment

Fri March 31, 2006
Programming

Quote of the Day

I was catching up with a lot of Rails related posts in my RSS reader and found DHH's bashing of James McGovern which was pretty entertaining. I also like this quote in the comments:

First they ignore you
Then they laugh at you
Then they compete with you
Then you win

I also learned today that Dreamhost upgraded to Rails 1.1. Apparently my homepage survived that upgrade. I still don't have Rails in the vendor directory but I do have web tests set up so I don't have to worry too much.

Make a Comment

Tue March 21, 2006

Rails Meetup @ Akkurat

The Akkurat pub

Tonight a bunch of hardcore geeks here in Stockholm met up at the excellent Akkurat pub to chat about Ruby and Rails. More than Rails though, the conversation seemed to drift towards ABC 80, Atari, and Amiga nostalgia which was great fun. I am very positively surprised by the atmosphere and service at Akkurat by the way and I now consider it to be my favorite pub here in Stockholm. The next time I need to try their special "Heaven" and "Hell" beers.

I've thoroughly enjoyed both the Rails meetups that we've had so far. The first one was held at The Dancing Dingo, the second one tonight at Akkurat, and the third one we are planning to have in a couple of weeks at Saddle and Sabre. To signup for notifications about future meetups in Stockholm make sure to get on the swedish Rails mailing list which you'll find at rails.se.

Make a Comment

Sun March 19, 2006

Sunday Brunch with a Touch of Flair

Stylish lobby of Hotel Amaranten

I enjoyed an exotic brunch today with my girlfriend at the flairful Amaranten hotel here on Kugsholmen in Stockholm. As you can see, the hotel lobby and restaurant is stylish and has a nice ambience. The buffet is offered at 160 SEK and is high quality with a good selection of meat such as chicken wings, spare ribs, bacon, and a number of more exotic dishes that I don't even know the name of :-) Some of the Cajun specialties didn't particularly speak to our taste but all in all it was quite good. On the minus side was the fact that the place was almost empty and one of the waitresses was not so service minded.

The atmosphere was enhanced by a house Jazz band - a trio on bass, drums, and piano. They performed professionally albeit somewhat uninspired, which is understandable given the lack of an engaged audience. We tried to cheer the band on by taking the initiative to applaud and I think this was appreciated.

I seem to have taken up an interest in luxury hotels lately - there is something fascinating about them. A couple of years ago I stayed with my girlfriend at the Grand hotel here in Stockholm - a very memorable and highly recommended experience. Recently I read in the paper about how the new Hotel Rival (owned by famed Benny Anderson of Abba) in Stockholm came in highest in scandinavia (at place ninety something) in a listing of the most luxurious hotels in the world. This sparked my interest and I have now booked a brunch there for the second of April and will spend the night with my girlfriend in one of their "de luxe" rooms. It's no exaggeration to say that I look forward to that...

Make a Comment

Tue March 07, 2006

Less is More - The 37Signals Mantra

I remember seeing a presentation by Jason Fried of 37Signals at Reboot in Copenhagen a couple of years ago. The presentation was about defensive web design and it was very professional and convincing. It seems now though, Jason has become not only an authority on web design but also on the general process of how to successfully build websites. I listened to Jason's interview at IT conversations a while back and it really impressed me. I felt like listening to the speech several times and write down all the important points that Jason is making. However, 37Signals beat me to that task and for only $19 you can have the Getting Real book which essentially covers and expands on the same philosophy and guidelines that are in the speech. The book notwithstanding, here are my own sketchy notes from the IT conversations interview:

Reduce mass. Physics tells us that the higher the mass of a moving object the more difficult it is to change its direction. Mass can be too many people, hardware, software lockin, and long term contracts. Ability to change is very important in any product development.

Embrace constraints. Examples of constraints are hardware, people, and money. Constraints is where creativity happens. Let people use the product and look for real patterns. Start with less and your more with be a lot more clear down the road. The initial release should be half the product. Everything is beta these days but its time to have confidence, public is public. Keep iterating and make what you have rock solid, bullet proof, and great

Getting real. Use few documents, specs and diagrams. Build top down - build the interface first.

Managing debt. Feel the hurt. The people who built the product should support it. Chefs become waiters once in a while.

Finding people. Look for people who are:

Make a Comment

Tue March 07, 2006

My First Acoustic Instrument

I just had to post a picture of my nice new LP Bongo drums:

My Bongo Drums

It was in Copenhagen that I regularly started dancing salsa and through the dancing I developed an interest in the music. On the salsa mailing list in Copenhagen there came an invitation from Jakob Johansen to learn how to play in a salsa band. As a child I always wanted to play the drums but my dad wasn't happy about the idea of having drums in the house so that dream never materialized. However, in Copenhagen I jumped on the opportunity and by chance I ended up playing Timbales in the band. I was the only one in the band who was a total beginner but it worked out ok anyway and I throughly enjoyed it.

Once in Stockholm last year I was looking for the opportunity to continue playing in a salsa band. I found Pygge and Alternativa Musikskolan in Sollentuna where I took private lessons in Timbales. I decided to switch to conga drumming and pursued that for a while. Eventually I found a salsa band that I could play in. However, it turned out they alreay had a conga drummer so I had to learn the bongos instead. I find bongos easier to play than the congas and they are great for soloing. I think my new bongo drums look great - now I just have to learn how to play them...

2 Comments

Thu January 19, 2006

Financial Freedom vs Liking What you Do

Paul Graham writes that:

"Most people would say, I'd take that problem. Give me a million dollars and I'll figure out what to do. But it's harder than it looks. Constraints give your life shape. Remove them and most people have no idea what to do: look at what happens to those who win lotteries or inherit money. Much as everyone thinks they want financial security, the happiest people are not those who have it, but those who like what they do. So a plan that promises freedom at the expense of knowing what to do with it may not be as good as it seems."

Whichever route you take, expect a struggle. Finding work you love is very difficult. Most people fail. Even if you succeed, it's rare to be free to work on what you want till your thirties or forties. But if you have the destination in sight you'll be more likely to arrive at it. If you know you can love work, you're in the home stretch, and if you know what work you love, you're practically there.

Make a Comment

Sun January 01, 2006
Programming

Lessons from Adam Bosworth

Adam Bosworth's article Learning from THE WEB is well worth reading (thanks Branimir for pointing me to it). A surprising number of the lessons have to do with simplicity, for example the KISS one:

"KISS. Keep it (the design) simple and stupid. Complex systems tend to fail. They are hard to tune. They tend not to scale as well. They require smarter people to keep the wheels on the road. In short, they are a pain in the you-know-what. Conversely, simple systems tend to be easy to tune and debug and tend to fail less and scale better and are usually easier to operate. This isn't news. As I've argued before, spreadsheets and SQL and PHP all succeeded precisely because they are simple and stupid - and forgiving."

Other lessons such as "It is acceptable to be stale much of the time" and "The wisdom of crowds works amazingly well" ring very true to me. His critique of database vendors inability to learn from the web is thought provoking.

1 Comment