I decided to try HAML today, rather than the standard ERB templates. The jury is still out on if it is better or worse, but like many things Rails, it is better to just dive in and try it.
I have a little project (not yet released) which I’m converting over to use HAML. Since I also use rspec for testing, along with Cucumber and Webrat, I thought I had a long day ahead of me.
It turns out most of it can be made close to automatic, with just a little cleanup afterwards.
Using the rake task below, you can issue these two commands to convert your existing .html.erb views into.html.haml. The second target will convert the rspec view tests to expect haml. Renaming the spec tests is not required, but I like sanity.
$ rake haml:convert:html
$ rake haml:convert:spec
If you use a SCM (I still like Subversion best) you’ll want to remove the old files and add the new ones. For Subversion, I do:
$ svn rm app/views/*/*.html.erb spec/views/*/*.html.erb_spec.rb
$ svn add app/views/*/*.html.haml spec/views/*/*.html.haml_spec.rb
The main problems were that not all of the templates were properly indented, and “- end” lines appeared in the HAML templates. Fixing this was fast, as I really don’t have much in my templates yet as this is a new project. This step too could probably be done in an automated way. However, the indentation is probably going to require a bit of manual work.
While there, I also fixed up multi-line constructs generated with a much nicer compact format:
1 %h1
2 Title
3 %tr
4 %th
5 Heading
6 %th
7 Heading
8 ...
Compare with this:
1 %h1 Title
2
3 %tr
4 %th Heading
5 %th Heading
6 ...
And now for the rake task:
1 # RAILS_ROOT/lib/tasks/haml_convert.rake
2
3 require 'haml'
4 require 'haml/exec'
5
6 namespace :haml do
7 namespace :convert do
8 desc "Convert all *.html.erb files to *.html.haml"
9 task :html do
10 Dir.glob("app/views/**/*.html.erb").each do |html|
11 puts html + "..."
12 Haml::Exec::HTML2Haml.new([html, html.gsub(".html.erb", ".html.haml")]).process_result
13 File.delete(html)
14 end
15 end
16
17 desc "Convert all *.html.erb_spec.rb files to *.html.haml_spec.rb"
18 task :spec do
19 Dir.glob("spec/views/**/*.html.erb_spec.rb").each do |oldname|
20 puts oldname + "..."
21 newname = oldname.gsub(".html.erb", ".html.haml")
22 nf = File.open(newname, "w")
23 File.open(oldname) do |of|
24 of.each_line do |line|
25 nf.puts line.gsub(".html.erb", ".html.haml")
26 end
27 end
28 nf.close
29 #File.delete(oldname)
30 end
31 end
32 end
33 end