Blog
what did i learn today
Uncategorized ruby arrrrcamp ruby on rails
Arrrrcamp 29/10/2010

The fourth and most international of all arrrrcamp editions. Also the first paying edition. As i said in mypost about the previous edition, i have been to all editions, and it is awesome to see how it has grown. The schedule was amazing, with an amazing array of international speakers, of which for me especially Yehuda Katz i looked forward to. The biggest problem i had was that two of my collegues gave a talk at the same time, both of which i wanted to see. Choices choices choices :) Let me give a quick impression of the talks i did see:

Keynote by Carl Lerche:

To be frank, i had totally no idea who Carl was. But his talk was very nice, talking about the speed improvements Rails does, under the covers, unknown at least to me, to get your site visible as soon as possible. Also the speed improvements they will take in the next version 3.1 and 3.2 to improve this even further. In short, they look for ways to serve the HTML so that a browser can download the page and all the assets quicker. Very new to me, touched some very interesting subjects as automatic spriting, the cache manifest ... But in the end, there is one thing that Rails can't solve: latency. That is the core time it takes to reach a server and get back to the client. A mere ping. If you want to reduce latency, you either make sure your servers are really close to all clients, ... or ... you work in a different way, and let your client handle more stuff. In short: using a minimal HTML which is only downloaded once, using the cache manifest and lots of javascript: back to client side code? Hold that thought, we'll come back to that later.

Escaping the Sludgy Swamp of Slow Tests by Joseph Wilk

This is a problem we are getting into at work. We try to solve that by running our tests in parallel. Joseph explains the routes they had taken in their team.

  • First off: use a lot of EC2 instances to reduce time. They went from 4hours build time to 11minutes, cheering developers, but very angry boss :) EC2 is not cheap!
  • So then they introduced some kind of low-level caching, which will cache sequences of SQL commands and returned a cached result. This sounds very interesting as that is what you see most in tests: a lot of similar db-setup to actually test something small.
  • Thirdly a great idea was to divide your tests into different sets, and only run those that are most likely to fail. Those that always succeed you only run nightly, and the ones that sometimes fail you also seperate so you can more easily test those, check loggings, and hopefully fix them. I also remembered the suggestions to use capybara together with env.jsto be able to test your javascript pages quicker. Good tips, and i especially like the graphics (and humour) on the slides :D

Refactoring++ : Refactor Everything A.T.F.T by Alain Ravet

A talk by a collegue of mine (had to miss Elise's talk, bummmmer, but her talk is recorded so i hope to see that later). I know most of his refactoring tips, because we have paired extensively and i have learned a lot by doing that. Alain took a small piece of code from the internet, an example to solve the Towers of Hanoi: the code was small and compact and seemed to be ok. But then Alain was able to find and show a lot of improvements. That was great. Aside from the standard refactorings (from the book) Alain also stressed the scanability of the code. This is also a pet-pieve of mine. Code has to be formatted nicely and correctly. In teams it is preferred that classes follow a bit the same structure, e.g. inside rails it is easy to make agreements where to expect the filters, constructors, public methods, ... Also Alain stressed the point to know your tools and your language. Ruby is a very expressive and compact language: use that to your benefit! Know the tool you are using, whether it is Rubymine, Textmate or VIM. And practice. Do code kata's, download some code and refactor-refactor-refactor.

Making it an Anti-Pattern is Not Enough by Timothy Payton and Sebastian Roebke :

I saw these guys last time, and i was very impressed by them at that time. Probably because what they said struck a chord, and matched my own experiences. This time, i found them less persuasive. I think maybe because my expectations were too high, they re-iterated a lot they said last time (or so it felt), the title was not explained anywhere (or i missed that), and i guess they were also having troubles with the single microphone (being two speakers) that made them more uncomfortable. Still a very nice talk, and Xing seems to be a very nice place to work.

Lightning Talks

  • Friendly attributes: apparently, in mysql, adding a columns is a very expensive operation. So this guy looked for alternatives, and came up with friendly attributes. This could be a very nice tool for someone if you are forced to use MySql (e.g. by your hosting provider). Otherwise i would suggest to use Postgresql.
  • A postgres textsearch without any extra server: this seemed very interesting and promising, but also very non-existant at the moment. He was in the process of turning it into a gem. Wait and see.
  • Yehuda's 10 minutes about concurrency in MRI: inspired by Elise's talk about concurrency, Yehuda dug a bit deeper into MRI threads and possible advantages. Unfortunately none of the big servers (passenger or unicorn) make any use of that. Only thin --threaded would profit from that. This really was a lightning talk! A lot of information in a short span, very interesting!
  • @Defv's recipe for a good rails rumble: after his third Rails Rumble Jan gave us the recipe: 1) a knock-out idea but simple enough so any visitor/judge would get it, simple enough to implement in 48 hours, and 2) good design. With the next emphasis being: simple! simple! simple! Reminds me a bit of what 37signals always says.
  • Wicegrid: i have used this grid in a few big projects i did, and really liked it. Nice that Yuri showed it, hope some more people start using it.
  • Restart of BRUG: this was nice news too. I have seen that amsterdam.rb and rotterdam.rb exist, and was wondering why we don't have such a "working" thing in Belgium. But the guys from Openminds offered to revive it, they will support the first three sessions, and then other sponsors would need take over (volunteers from the public immediately jumped in). Meetings would take place in different cities, so i am very curious how this would work out. That would be very nice ;)

Closing Keynote by Yehuda Katz:

Yehuda recently switched jobs, and together with Carl Lerche they are now both actively working on a framework called Sproutcore. In short, Sproutcore (or SC) is a javascript MVC framework. So, MVC on the client. In the talk from Carl we learned that the big problem is latency, so one way to improve or remove that, is instead of developing your web-application in the Rails way, is to use a more client-centric way. Yehuda then showed us a few moving parts of Sproutcore, which he intends to extract in seperate libraries so you could use them more easily. They also stressed that Carl and Yehuda are aiming for a very tight integration with Rails in the future. Altough it is not entirely sure what or how that will be be. You would be using Rails to just serve json-data. Rails still has its very strong points to be used in the backend for something like that. His talk left me a bit baffled, to be honest. The big advantage for me of the Rails framework is that there is one language, one platform to develop in, to cover both server and client side. That is a big advantage. It is also a big advantage compared to using AIR or Silverlight on the client, because you remove the duplication of all the models on both sides (in Rails you only need them on server side). That said, i do believe the future lies in heavier clients, like gmail and twitter shows us. The bindings that Yehuda showed, reminded my very much of the bindings offered in WPF and Silverlight. Possible advantages of Silverlight: with Ironruby you have the option to run ruby in the client as well. But, as the video-section of arrrrcamp themselves show: Silverlight it is not ready for all platforms. It does not work on my ubuntu 10.10. I am thinking now would be a good time to revive the idea of a ruby vm on javascript. In no specific order:

  • Hotruby was very promising but seems dead. With the speed improvements in current javascript vm's it would seem awesome to get some ruby on javascript too.
  • rubyjs: compiles ruby to javascript to be run in the browser
  • Js.class could be an alternative approach: use the classes and paradigms of ruby in javascript.
  • red: writes like ruby and runs like javascript
  • coffeescript: not quite ruby, that compiles into javascript I will dig into these alternatives in a later post :) The biggest advantage of sproutcore over extjs, AIR or Silverlight is that sproutcore is truly open source. Exciting times ahead :)

To conclude

As usual I really enjoyed arrrrcamp, the organisation was great, i enjoyed seeing and talking to a lot like-minded people, and the talks were really though-provoking this year. Setting sail to the next edition!

More ...
Uncategorized ruby gemsets rvm rails3 ruby on rails
rails 2 and 3 simultaneously: gemsets to the rescue

I am developing several rails projects. Some are still rails 2.3.9, and some are rails3. But using those at the same time, on the same machine can cause some trouble. I use bundles for all my projects, so the gem dependencies are managed. But still, somehow, when running my tests, i get into trouble. If i run spec, it complains that it is deprecated. Rubymine doesn't support running tests in my rails 2 project. The solution? Use gemsets! Gemsets are a feature from rvm, the Ruby Version Manager. But with gemsets rvm does more than just manage your ruby version! A gemset is a set of gems, which you can switch at will. So i am using a gemset per project. Creating a gemset is easy: [ruby] rvm gemset create some_name [/ruby] Using a gemset is equally simple: [ruby] rvm gemset use some_name [/ruby] Showing which gemset is in use: [ruby] rvm gemset name [/ruby] Showing the list of possible gemsets [ruby] rvm gemset list [/ruby] By default, you are using an unnamed gemset, which contains all the gems for your ruby-version. Per project you can create a new gemset. Per gemset you have to re-install your gems, but luckily, using bundler, that is as simple as doing bundle install. Now comes the good part:

  • Rubymine supports using gemsets, so you can select your gemset to work with, and each time your project is opened, it uses the correct gemset and the correct corresponding scripts (e.g. spec)
  • If you place a .rvmrc file in your project-folder containing rvm default@projecta, every time you cd into that folder it will select the default ruby and the projecta gemset. Awesome!
More ...
Uncategorized rspec2 rcov rails3 ruby on rails
getting rcov working with rspec 2.0.0.rc

I had troubles to get rcov working with the latest rspec2 release (since beta23 and now 2.0.0.rc). I got the same error every time: [bash] require': no such file to load -- spec\_helper (LoadError) [/bash] But luckily, somebody [found the problem](http://github.com/rspec/rspec-core/issues/issue/172) and it is extremely easy to fix. Just add -Ispecto your rcov task. Therake spec:rcovdoes not work for me (as it needs to be fixed). So i added my own task (add this code to the end ofRakefileor add in a seperate filercov.rakeinsidelib/tasks`) : [ruby] desc "Run all specs with rcov" RSpec::Core::RakeTask.new("test_cov") do |t| t.rcov = true t.rcov_opts = %w{--rails --include views -Ispec --exclude gems/,spec/,features/,seeds/} end [/ruby] and then you can run the task by typing [bash] > rake test_cov [/bash] in your rails root folder.

More ...
Uncategorized haml jquery rails3 ruby on rails
rails 3 and haml and unobtrusive javascript

I have created a Rails3 application, started with Haml/Sass and finding it awesome. I am also trying to do unobtrusive javascript. Before, in Rails 2.3, I would have expected a remote-form to have an :update attribute, where you could specify a selector where the response of the remote method would be rendered. Now it needs to be done differently: my controller function will render a ".js" view, which will do the necessary actions itself. This makes it more library agnostic, and i prefer jquery. So for instance i have a controller action "search", and i have a corresponding "search.js.erb" as follows: [ruby] $('.grid').replaceWith('<%= escape_javascript(render :partial => 'list') %>') [/ruby] This works. It will replace the html of the element with a class grid with the html from my rendered partial. I started out trying to achieve that in HAML, and failed at first. So first i created the above ERB code which worked. Now my task seemed simpler: translate this seemingly simple line to HAML. My first naive approach was to do the following: [ruby] = "$('.grid').replaceWith('#{escape_javascript(render :partial => 'list')}')" [/ruby] But this just places the html as a readable string inside my page. Even i do something simple like [ruby] = "$('.grid').replaceWith('<h3>Text</h3>') [/ruby] i see the actual characters [ruby] <h3>Text</h3> [/ruby] and not the markup. But i need to contain the javascript inside the double-quotes or haml will not recognise it, and can not interpolate my ruby there. After looking through the HAML reference, actually the solution was incredible simple. Once more. [ruby] != "$('.grid').replaceWith('#{escape_javascript(render :partial => 'list')}')" [/ruby] The != unescapes HTML (as opposed to the standard =). This is exactly what we need of course.

More ...
Uncategorized ruby on rails rspec
skipping slow tests in rspec2

For Test::Unit there is a module called skippy, that allows you to skip for instance slow tests. I was looking for a way to achieve the same in Rspec. I am currently developing against Rails 3.0.0.rc, and using rspec 2.0.0.beta.19 and could not find anything. So i asked on the rspec mailing list and got a great answer! It is actually present in rspec2, right out of the box, as a feature they needed for their own tests. Read the description by David himself here. He shows a lot of very good examples, even filtering tests based on ruby-version is now possible. Awesome. In short, you would do something like : [ruby] describe "something", :slow => true do it "should be blabla" end describe "something else" do it "should be a slow test", :slow => true do ... end it "should be a fast test" do .. end end [/ruby] then you can write the following to skip the slow tests : [ruby] # in spec/spec_helper.rb RSpec.configure do |c| c.filter_run_excluding :slow => true end [/ruby] and to run only the slow tests: [ruby] # in spec/spec_helper.rb RSpec.configure do |c| c.filter_run :slow => true end [/ruby] and to filter on slow tests, and run all tests if no slow tests are available: [ruby] # in spec/spec_helper.rb RSpec.configure do |c| c.filter_run :slow => true c.run_all_when_everything_filtered = true end [/ruby] Awesome! :) For the moment there is no command-line support, but in the spec/spec_helper.rb you could also check for any environment variables to do the slow or fast test-set. What i personally needed, was something that would either run all tests, or run all tests excluding a few (i have a test-suite for an sms-gateway and do not want to send sms-es all the time). So i handled that like this: [ruby] # in spec/spec_helper.rb RSpec.configure do |config| if ENV['SEND_REAL_SMS'] != "true" config.filter_run_excluding :send_sms => true end end [/ruby]

More ...
Uncategorized actionmailer attachments windows ruby on rails
actionmailer attachments on windows

I have been having troubles sending e-mails using ActionMailer on windows. The simple code-sample: [ruby] my_filename="my_image.jpeg" attachment "image/jpeg" do |a| a.body = File.read(my_filename) a.filename = File.basename(my_filename) end [/ruby] did not work. I did find an attachment inside my e-mail, but it was corrupt. It took me a while to figure out it could be something related to my development platform, which unfortunately still is windows (not for long). On windows reading binary files is less obvious, apparently, so you need to write: [ruby] my_filename="my_image.jpeg" attachment "image/jpeg" do |a| a.body = File.open(my_filename,'rb') { |f| f.read} a.filename = File.basename(my_filename) end [/ruby] ... and this will work! :) I you have to combine normal e-mail content and one or more attachments, this then becomes something like: [ruby] # we send a mail to respond to a mention def mention_response(given_subject, addressee, pdf_attachment = nil) from APP_CONFIG["mail"]["from"] recipients addressee.to_a subject given_subject content_type "multipart/mixed" part "text/html" do |p| p.body = render_message("mention_response", :thr_name => thr_name) end attachment :content_type => "application/doc" do |a| a.filename File.basename(pdf_attachment) a.body File.open(pdf_attachment, "rb") { |f| f.read } end unless pdf_attachment.nil? end [/ruby] Nice :)

More ...
Uncategorized javascript observe_field ruby on rails
keeping observe_field and spinner in sync

I am using a lot of observe_fields in my views. I have two searches on my form, one with two fields one with four, and every time a user types something the observe_field is triggered and some search is executed via AJAX. To make sure the user knows what is going on, i use a spinner-image. [ruby] <%= observe_field 'querypeople', :frequency => 1, :update => 'people_to_link', :before => "Element.show('spinner2')", :loaded => "Element.hide('spinner2')", :complete => "Element.hide('spinner2')", :url => {:action => 'listpeople'}, :with => " 'querypeople=' +escape($('querypeople').value) + '&queryorganisation=' + escape($('queryorganisation').value)" %> <%= observe_field 'queryorganisation', :frequency => 1, :update => 'people_to_link', :before => "Element.show('spinner2')", :loaded => "Element.hide('spinner2')", :complete => "Element.hide('spinner2')", :url => {:action => 'listpeople'}, :with => " 'querypeople=' +escape($('querypeople').value) + '&queryorganisation=' + escape($('queryorganisation').value)" %> [/ruby] This works all fine and dandy, but when a user types multiple characters in a row, the spinner is hidden while another query is running. So i needed to improve that. I first introduced a little code to count how many times a certain spinner is shown: [ruby] <% javascript_tag do %> var spinner_counter=[0,0,0]; function show_spinner(itm) { spinner = (itm == 0) ? "spinner2" : "spinner" ; Element.show(spinner); spinner_counter[itm] = spinner_counter[itm] + 1; } function hide_spinner(itm) { spinner = (itm == 0) ? "spinner2" : "spinner" ; spinner_counter[itm] = spinner_counter[itm] - 1; if (spinner_counter[itm] <= 0) { Element.hide(spinner); spinner_counter[itm] = 0; } } <% end %> [/ruby] and then adapted the ruby-code as follows: [ruby] <%= observe_field 'querypeople', :frequency => 1, :update => 'people_to_link', :before => "show_spinner(0)", :complete => "hide_spinner(0)", :url => {:action => 'listpeople'}, :with => " 'querypeople=' +escape($('querypeople').value) + '&queryorganisation=' + escape($('queryorganisation').value)" %> <%= observe_field 'queryorganisation', :frequency => 1, :update => 'people_to_link', :before => "show_spinner(0)", :complete => "hide_spinner(0)", :url => {:action => 'listpeople'}, :with => " 'querypeople=' +escape($('querypeople').value) + '&queryorganisation=' + escape($('queryorganisation').value)" %> [/ruby] Do you know a better solution?

More ...
Uncategorized mongrel service thin windows ruby on rails
mongrel_service beta troubles with space

I am switching back from using thin inside a service to mongrel_service, because when my thin-process is killed somehow, the service stills seems to be running. Mongrel_service can cope with this much better: it also keeps a check on your ruby process and restarts it if needed (at least in the old version, i hope the 0.4.beta3 prerelease version behaves the same). When using the mongrel_service (gem install mongrel_service --pre) on ruby 1.8.7 you can no longer have a space inside the name. So if you run the following command: [bash] mongrel_rails service::install -N "Name with a space" -c c:\path\to\your\app -p 4000 -e production [/bash] there will be no output as to whether it succeeded or not on XP, on Windows Server 2008 a more appropriate error is shown; but the service will not be created. The trouble is the name: it contains a space, and apparently that is no longer allowed. On the old MRI and previous mongrel_service it was not a problem. The old version, however, does not work in ruby 1.8.7 from rubyinstaller.org, due to a dependency to some very specific Visual C++ code regarding service communication (and now the ruby is compiled using gcc). Luckily there is an easy fix, as suggested by Luis Lavena himself: [bash] mongrel_rails service::install -N name_without_space -D "Name with a space" -c c:\path\to\your\app -p 4000 -e production [/bash]

More ...
Uncategorized model mvc ruby on rails
accessing current_user in models

Up until now i was able to somehow circumvent the need to access the current-user in the model, by calling methods from the controllers and handing down the current-user. In the MVC pattern, the model should know as little as possible about things the controller handles. But now, i need a method that will check :before_save what has changed, and by whom, and will log that into another table (model). So i am going to create an Observerclass, that needs to access the model on the one hand, but needs to know the current-user on the other hand. First I found a very dirty but working solution. Put this in application.rb: [ruby] around_filter :you_dont_have_bloody_clue protected def you_dont_have_bloody_clue klasses = [ActiveRecord::Base, ActiveRecord::Base.class] methods = ["session", "cookies", "params", "request"] methods.each do |shenanigan| oops = instance_variable_get(:"@_#{shenanigan}") klasses.each do |klass| klass.send(:define_method, shenanigan, proc { oops }) end end yield methods.each do |shenanigan| klasses.each do |klass| klass.send :remove_method, shenanigan end end end [/ruby] This was credited to Pratik Naik, but at the same time highly NOT recommended by him. It seems a bit like a bulldozer approach. Actually it is nice to know such things are possible, and how to achieve it, but it (kind of) breaks the MVC pattern. So i looked further for a nicer solution. I found a really simple one here, and adapted it to my needs: [ruby] class User < ActiveRecord::Base cattr_accessor :current_user def self.current_user @current_user ||= User.new("dummy-user") end ... end class ApplicationController < ActionController::Base include AuthenticatedSystem before_filter { |c| User.current_user = session[:user] } end [/ruby] And now, inside each class, i can just use [ruby]User.current_user[/ruby]. I overwrite the current_user class method, so i don't have to set the user manually during tests (is that clean?). I am not sure if this is the best solution. I found a few more complicated ones, but this seems to fit me the best.

More ...
News ruby arrrrcamp ruby on rails
Arrrrcamp

Went to arrrrcamp last friday (Arrrr as in _R_uby, _R_ails, _R_adiant and, of course, _R_hum!). It was the third edition of this unique ruby-on-rails event, and the third time i visited it ;) So i am a regular :) The first year i was just starting ruby and my then-collegue and me learned a lot. The second time i took some new collegues along hoping to get them infected with the ruby virus. This year i went alone (so you can guess how well the infection spread :), but one advantage of being alone in a croud is that it is way easier to mingle. There's even a picture to prove it :) I saw some very interesting talks:

  • Something Something Mongo: I alrready had read about Mongo, and was interested. This speech interested me more than Radiant. Just another NoSQL database. Some things were not entirely clear, like how you can query stuff if all things are in the same "database". But it seems like something i should investigate more. I think there are a lot of possible applications, and the presenter showed a very good example, where the database is entirely configurable by the end-user, which is dead-easy in Mongo and MongoMapper, because there is no schema! Ha! :) Opens up possibilities indeed ;)
  • jQuery on Rails: at the same time there was a talk about the new things in Rails3. So this was a hard choice. But i am already using jQuery, in combination with Prototype, and was hoping to get some tips to do it better. The talk was very quick, but also very informative. The presenter did a very cool job, where he showed the same site in Prototype (using helpers) and jQuery (using unobtrusive javascript). Very nice. I still write most of my javascript inline, and am gradually switching over. I am still struggling with one problem. In most of unobtrusive javascript examples, i always see that all code is placed in the application.js. But that is not good enough for me. I want a js file per erb-file. I found a blogpost by Yehuda Katz, where he does something even smarter: only include the js-files which include the selectors from the current page. But unfortunately it is so old, the source is nowhere to be found anymore. when i asked the presenter, after the session, he pointed me to this article about Jzip, but on second look it is not quite what i am looking for.
  • Railties: what, why & how?: a very interesting talk, but i must admit, since Rails 3 territory is still very unknown to me (and a lot has changed apparently) a lot of it was unclear. In short: the old way to create rails plugins is replaced by Railties. Plugins and engines are supported, dependencies are more explicit. Something i still need to look into, to convert the plugin we use at work.
  • Something something Rack: actually i did not want to see this one, but rather the 12 hours to rate a rails website by Elise Huard, but because @Atog was late those two talks had switched. She confided, however, that i would get a second change at RailsConf :) The something-something-rack talk was very basic, but also enlightning. Rack provides a minimal interface between webservers supporting Ruby and Ruby frameworks. Rack applications can be stacked. Since Rails is a Rack application, it is now very easy to put Rack-apps in front of Rails, for instance to redirect to different sites or pages if the visitor uses a mobile device (Rack::MobileDetect), add google analytics to your pages automatically (Rack::GoogleAnalytics), or to block unallowed access (Rack::Warden). Very interesting. Also allows for a clean seperation of concerns. One last Rack middleware I really want to mention: Rack::ChromeFrame! This middleware will make sure the Google Chrome frame is automatically enabled. Cool :)
  • Learning to smile at your code: a talk by two german guys, who both work at Xing, about refactoring and to learn to actually enjoy it. Xing is a very big website, coded for the largest part in Rails. They have 22 developers working in Rails. Sebastian and Tim, the presenters, had to add features to the job-postings page/code and encountered a lot of problems doing so. I really liked this talk because i found it very recognisable and also because it was a talk focusing on the programming of an application as a whole. They used a lot of humour to convey their message, with success. Really-really compressed their message was: 1) seeing a lot of old, incomprehensible code can be demotivating; 2) breathe and relax; 3) starting to refactor it anyway, despite the obvious unwillingness at first, will make you smile because you can create something beautiful. They gave some examples which i guess barely even scratched the surface of the complexity they had to deal with. Nice :) After that the lightning talks came (short talks of about 10 minutes). I will highlight a few:
  • failtale: a notification framework/website by the guys from Mr. Henry. Impressive, because not only does it capture ruby/rails exceptions, but also ActionScript (flash) and Javascript soon. I am going to try that out! :) I am currently using Exception Notifier myself, curious how it compares.
  • The guys from 10-forward did three talks. First a demo of their application, which was incredibly impressive. Wow! Blew me away. A lot of javascript and ajax to make the website feel like a real application. Very powerful. Then they discussed a gem of theirs, and rspec and cucumber.
  • wallsome: Sebastian and Tim from Xing, who also did the Learning to smile talk, here presented their pet-project, using Rails 3 and jQuery: a wall to arrange your tasks from Basecamp like in Scrum or Kanban. I am looking forward to the next edition on the 29th of october! :)
More ...
Uncategorized rjs javascript ruby on rails
observe_field in IE8: endless loop

My users showed me the weirdest problem today. In my application is a select-box that allows users to select the classification. When the classification is changed, the div containing the icons for the actions (and the classification-select-box itself) is updated to reflect the new classification. So i use an observe_field to watch the select-box, and trigger some javascript to perform the magic. In Firefox this works perfectly. But my users tend to use IE8, for some obscure reason, and switching to FF or Chrome is ... difficult (What other browser?). The observe_field is written as follows: [ruby] <%= observe_field "mention_thm_classification", :frequency => 0.5, :update => "mention-actions", :with => "classification_id", :before => "Element.show('spinner_cl')", :loaded => "Element.hide('spinner_cl')", :complete => "Element.hide('spinner_cl')", :url => { :action => "set_classification", :id => mention } %> [/ruby] Pretty straightforward. The observe_field is contained inside the div that is updated. When in IE8 a new value is chosen, i get the correct value in my method first, and then i get a whole bunch of classification_id="null". I am guessing what happens is that when the html is updated, somehow also the select-box is emptied, and thus changed, and thus a new value is triggered. So i replace the html again, and the select-box is emptied again, and an endless loop is born. So, the easy solution should be: do not do the action of the observe_field if the value of the select-box is null, and that is actually really easy: [ruby highlight="3"] <%= observe_field "mention_thm_classification", :frequency => 0.5, :update => "mention-actions", :with => "classification_id", :condition => "value != null", :before => "Element.show('spinner_cl')", :loaded => "Element.hide('spinner_cl')", :complete => "Element.hide('spinner_cl')", :url => { :action => "set_classification", :id => mention } %> [/ruby] We add a :condition that checks just that! It still feels i am doing something wrong, that i should not have to do this, so i would be happy to hear any way to improve this.

More ...
Uncategorized javascript jquery ruby on rails
using content_for jquery on document ready

In my Rails application i use a generic application.rhtml for all my pages. Amongst others, this code contains some jQuery code to manipulate my page [javascript] var $j = jQuery.noConflict() $j(document).ready(function() { // remove all alt-tags $j("[alt]").removeAttr("alt"); // validate all forms $j("form").validate({ errorPlacement: function(error, element) { error.appendTo( element.parent() ); }}); }); [/javascript] The things i do in my document ready callback is simple: remove the alt attribute everywhere, so my tooltips will work on my links containing images, and if there is a form on the page i validate it. Now for one form, i need to add special code, so that when a user fills something in a field, a select-box looses some options. The ideal place to do this, is in the document ready. But not for all pages. How do i solve this in some elegant way, and not use a different layout for that page. I choose to use yield and content_for. Like this. Add the following line : [javascript] var $j = jQuery.noConflict() $j(document).ready(function() { // remove all alt-tags $j("[alt]").removeAttr("alt"); <%= yield :script %> // validate all forms $j("form").validate({ errorPlacement: function(error, element) { error.appendTo( element.parent() ); }}); }); [/javascript] and in my view i write: [ruby] <% content_for :script do %> var allOptions = $j('#mention_thm_classification option').clone(); $j('#mention_thm_reference_local').change(function() { var filter_txt = '.ref-'; if (!$j(this).val()) { filter_txt = filter_txt + 'empty'; } else { filter_txt = filter_txt + 'filled'; }; $j('#mention_thm_classification').html(allOptions.filter(filter_txt)); }); <% end %> [/ruby] So what i actually do is, check whether the value of a field changes. When it contains something a select-list with id mention_thm_classification is changed, and only the options with the correct class are kept. For completeness, my select is built as follows: [html] <select name="mention[thm_classification]" id="mention_thm_classification" > <option value='1' style='background-color: #b7f9e2' class="ref-empty " >Green</option> <option value='2' style='background-color: #ffdebb' class="ref-empty " >Orange</option> <option value='3' style='background-color: #ffbbc6' class="ref-empty ref-filled" selected="selected">Red</option></select> [/html] So i have described a nice way to add extra code to my document ready function without needing a special layout-page. And experienced for the umpteenth time how great jQuery is.

More ...
Uncategorized ruby win32 cucumber ruby on rails rspec
missing 'a' with rspec and cucumber

I am developing Ruby on Rails on Windows platforms mostly. But using Rspec and cucumber on windows has a very strange side-effect: all a's are missing as can be seen from the following screenshot: rspec-without-a-smallerLuckily, after some very extensive googling, i found a single blogpost with a fix! Apparently it has something to do with UTF-8 encoding, and the simple solution is that you need to change the encoding of the current command prompt. This can be achieved via a simple call before you start: [sourcecode] chcp 1252 [/sourcecode] The aforementioned post then proposes to adjust the cucumber.bat to not have to type this every time. This is all good for cucumber, but not for rspec, and anyhow, every new update of the cucumber i would need to apply this fix again. I was thinking that it might be possible to set the default codepage, which is 850 on my machine, to 1252 permanently. As this blogpost mentions, there are two different ways to achieve the wanted result.

Change the codepage system-wide

This can be done in the registry. [sourcecode] [HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Nls\CodePage] OEMCP=1252 [/sourcecode] But one commenter notes this is not without risk.

Only for command prompt

An alternative way is to put make sure that each time a console is opened (cmd.exe) the codepage is set automatically. [sourcecode] [HKEY_LOCAL_MACHINE\Software\Microsoft\Command Processor] Autorun=chcp 1252 [/sourcecode] This will only work for console windows in which you run cmd.exe, which is just what i needed.

More ...
Uncategorized i18n oracle ruby on rails
showing international or accented characters

I am now working in Ruby on Rails for about a month. I have done a few smaller things before, investigating, trying out; but now I am really building a full application site in Rails! It feels great :) But of course, just starting out in such a new environment, both ruby and rails, I encountered a lot of initial problems. One of them is showing international, accented characters, like é, è, ê ... from the database. Nor Rails nor irb could show the correct characters. I really needed to solve this problem, so this started an investigative journey.

The symptoms

When displaying a table of results from Rails in any browser, all accented characters were shown as white question marks inside a black rhombus (diamond?). When i tested this with irb i also got very weird results. When using TOAD the results of a query are displayed correctly. But maybe TOAD just does it very clever? If i use the GUI version of SQL*Plus (sqlplusw) the results are also shown correctly. But when i use the console (command-line) version of sqlplus, the characters were also distorted. So maybe the clue could be found there.

Oracle NLS-LANG

No matter what character-set the Oracle database uses to store the data (e.g. UTF-8, UTF-16) the data is always converted to the clients character set. This is truly an amazing feature. This depends on a setting called NLS_LANG. Not sure wat it quite stands for. NLS_LANG is built up as follows:NLS_LANG=language_territory.charsetThe NLS_LANG property is set by default in the registry to the correct Windows codepage.NLS_LANG="AMERICAN_AMERICA.WE8MSWIN1252"But why doesn't it work inside the command line console? Apparently because it used a different codepage. If you type chcp (requesting the codepage) at the DOS prompt, it would normally return 437 (it did on my machine). So you would need to enter`

set NLS_LANG=american_america.US8PC437 require 'oci8' OCI8.new('user','pw','db').exec('select * from emp') do |r| puts r.join('|'); end `in your irb and then all results would be displayed correctly. The crucial line being the correct setting of NLS_LANG. Wow! I got my results correctly in ruby! Now i was in the assumption that Rails would be a piece of cake, but that was wrong.

Fixing Rails

The easy idea would be to set NLS_LANG in Rails correct, before the oci8-library is required. My first approach was to set the NLS_LANG in the first line of the environment.rb with the following line:ENV["NLS_LANG"] = "AMERICAN_AMERICA.WE8MSWIN1252"But this didn't work. I am using NetBeans 6.5, and it took me a while to realise that if I edited a file to contain special characters (fixed text, e.g. on a menu) it would work. NetBeans (or Rails for that matter) standard works with UTF-8. So all files are encoded in that way. The easy solution would be to useENV["NLS_LANG"] = "AMERICAN_AMERICA.AL32UTF8"But that didn't work. I tried the alternative AMERICAN_AMERICA.UTF8 but that didn't work either. I am just guessing here, but i think somehow the NLS_LANG setting didn't get picked up in the Rails environment. It kept using the registry setting. So I tried to turn it around: make Rails use the windows codepage instead of utf-8. This took several steps:

  • change the default setting inside NetBeans to use the correct code-page instead of UTF-8. This in fact only affects the format of the files that are saved, but it is nevertheless important that all files being served are in the same format. Also convert all previously edited files from UTF-8 to standard ASCII. I used an editor to do that.

  • added the following to application_controller.rb:` before_filter :headers_iso

    def headers_iso

    make sure the charset matches the default Oracle NLS setting

    headers["content-type"]= "text/html; charset=windows-1252" end `

  • added the correct META-tag to application.rhtml in the HEAD-section:``Note: this meta-tag is not really needed, it has no real effect. And that finally worked! :)

More ...