Flowdock

Recent notes

RSS feed
February 9, 2010
0 thanks

Options

What are all the options here please?…

February 5, 2010
2 thanks

the :order parameter is not sanitized

The :order parameter is not sanitized, so doing something like Person.find( :first , :order => params[:order] ) could get you in trouble.

February 5, 2010
2 thanks

An alternate way to have a string ID as a primary key

You can disable automatically created primary key and add it to manually with mysql:

The migration file:

def self.up

  create_table( :my_special_table, :id => false ) do |t|
    t.string :id, :limit => 5, :null => :no
  end

  execute "ALTER TABLE my_special_table ADD PRIMARY KEY (id)"

end

Then in a before_save filter you can generate the primary key for yourself.

Use a transaction and be aware of uniqueness!

February 5, 2010
3 thanks

Rmoving preceding 0's

In most *nix system, adding a - after the % will remove preceding 0s.

So %-d for a single digit day, or %-I for a single digit hour, etc.

February 4, 2010 - (>= v2.1.0)
1 thank

All dates in the database are stored in UTC and all dates in Ruby are in a local timezone

With the timezone support introduced in Rails 2.1 the idea is that all dates in the database are stored in UTC and all dates in Ruby are in a local timezone.

Time.zone.now == Time.now # => false

as Peter Marklund lights up this in his blog:

http://marklunds.com/articles/one/402

“They will only be converted to UTC for you if they are ActiveSupport::TimeWithZone objects, not if they are Time objects. This means that you are fine if you use Time.zone.now, 1.days.ago, or Time.parse(”2008-12-23“).utc, but not if you use Time.now or Time.parse(”2008-12-23“)”

February 4, 2010
1 thank

Warning! Be aware of Active Record TimeZone

With the timezone support introduced in Rails 2.1 the idea is that all dates in the database are stored in UTC and all dates in Ruby are in a local timezone.

Time.zone.now == Time.now # => false

http://marklunds.com/articles/one/402

January 30, 2010
3 thanks

Paying attention to query parameters

Standard action caching ignores query parameters, which means you’d get the same results for a URL with and without query parameters if it was action cached. You can make it pay attention to them by using a custom cache path like so:

caches_action :my_action, :cache_path => Proc.new { |c| c.params }

Or, maybe you want some of the query parameters, but not all to factor into different versions of that action’s cache:

:cache_path => Proc.new { |c| c.params.delete_if { |k,v| k.starts_with?('utm_') } }

Beware of things like pagination if you use expires_in to expire the cache, as pages could get out of sync.

January 29, 2010
1 thank

Passing html options (Ruby hash parameters)

When you have two default hash parameters at the end of a function call, you need to use it as the following:

options = { :include_blank => true, :default => @my_object.my_method }

date_select :my_object, :my_method, options, :class => 'my_css_class'

You can try it for yourself on this example:

def test_funct a = {}, b = {}
  puts "a: #{a.inspect}"
  puts "b: #{b.inspect}"
end

test_funct :x => 'x', :y => 'y'  # all the parameters are collected for the hash a
January 27, 2010
1 thank

File name without the extension

To get the file name without the extension you can use File.extname in combination with File.basename

File.basename("test.rb", File.extname("test.rb"))             #=> "test"
File.basename("a/b/d/test.rb", File.extname("a/b/d/test.rb")) #=> "test"
File.basename("test", File.extname("test"))                   #=> "test"
File.basename(".profile", File.extname(".profile"))           #=> ".profile"
January 27, 2010
3 thanks
January 27, 2010
1 thank

Alternative hostname generation method

Instead of using a random number to generate the hostname for the single asset, I prefer using source.hash.modulo, so that a given file is always served from the same host. This makes the content more cacheable by browsers and proxies.

ActionController::Base.asset_host = Proc.new { |source|
  "http://assets#{ source.hash.modulo(9) }.example.com"
}

I didn’t benchmark how long it takes, but String#hash should be reasonably fast.

January 26, 2010 - (>= v2.3.2)
1 thank

is now a subclass of Hash that preserves order (or _is_ a Hash if running Ruby 1.9 or greater)

You might not realize it preserves order because it delegates inspect to its super-class, Hash, which doesn’t preserve order. But you will see that order is preserved if you iterate or use the keys or values methods:

>> names = ['Amy Irving', 'Jane Doe', 'John Doe', 'John Updike', 'Susan Anthony']
>> ordered = names.group_by { |name| name.split.first }
=> #<OrderedHash {"John"=>["John Doe", "John Updike"], "Amy"=>["Amy Irving"], "Susan"=>["Susan Anthony"], "Jane"=>["Jane Doe"]}>

>> ordered.keys
=> ["Amy", "Jane", "John", "Susan"]

>> ordered.each { |first, full| puts first; full.each { |name| puts "  "+name } }
Amy
  Amy Irving
Jane
  Jane Doe
John
  John Doe
  John Updike
Susan
  Susan Anthony
January 26, 2010 - (>= v2.3.2)
2 thanks

returns an ActiveSupport::OrderedHash

Returns an ActiveSupport::OrderedHash, which is a subclass of Hash that preserves order. If you’re running Ruby 1.9, it is simply an alias for Hash. Surprisingly, you might not realize that OrderedHash is preserving order since it delegates its inspect method to Hash. More at ActiveSupport::OrderedHash.

January 25, 2010
2 thanks

custom uniq method

Build hash from elements of your Array using attribute as key and the element as value and return values of Hash:

Hash[*ary.map {|obj| [obj.name, obj]}.flatten].values
January 22, 2010
1 thank

Interesting usage for polymorphic asset model :)

…to automatically define default scopes of inherited classes.

 class Asset < ActiveRecord::Base

  belongs_to :resource, :polymorphic => true
  before_save :set_asset_type

  def set_asset_type
   self.asset_type = self.class.name
  end

  def self.inherited(subclass)
    super
    subclass.send(:default_scope, :conditions => "asset_type='#{subclass.name}'")
  end
end
January 21, 2010
3 thanks

W3CDTF Format

Here is the formatted string for the W3CDTF datetime format (http://www.w3.org/TR/NOTE-datetime). It has a semicolon in the timezone part, therefore you cannot use ‘%z’:

Time::DATE_FORMATS[:w3cdtf] = lambda { |time| time.strftime("%Y-%m-%dT%H:%M:%S#{time.formatted_offset}") }
January 20, 2010
4 thanks

Using html text instead of default response

If you have a string containing html and want to assert_select against it, as the doc states you have to pass in an element (HTML::Node) as the first argument. You can do something like this:

doc = HTML::Document.new('<p><span>example</span></p>')
assert_select doc.root, 'span'
January 20, 2010
2 thanks

Escape brackets in selector

If you need to escape brackets in a selector, this is the way to do it:

assert_select "input[type=hidden][name='user[role_ids][]']"
January 20, 2010
3 thanks
January 19, 2010
2 thanks

Argument Accepted

Accepts a single argument record_separator which is the character or string to chomp.

Why isn’t this shown in the method def at the top?

January 19, 2010
2 thanks

Argument Accepted

Accepts a single argument sep_string

January 18, 2010
1 thank

Undeprecated version

The undeprecated version of this function is here: ActionView::Helpers::PrototypeHelper#link_to_remote

January 16, 2010 - (>= v2.2.1)
8 thanks

Pretty way to test for current environment

You can check your current Rails environment using nice methods such as:

Rails.env.development?
Rails.env.test?
Rails.env.production?
Rails.env.your_custom_environment?
January 15, 2010
3 thanks

Use this in controllers

Sometimes you’re gonna need this in controllers. Just put this in the controller:

include ActionView::Helpers::NumberHelper
January 14, 2010
0 thanks

:find takes more keys than written

The documentation says that the :find keywords “may include the :conditions, :joins, :include, :offset, :limit, and :readonly options”. Note that this does not mean that only those options are supported. :sort also works like it should, for example.

January 14, 2010
1 thank

Will this method get rid of existing data?

Will this method get rid of existing data?

January 11, 2010 - (>= v2.2.1)
2 thanks

Default fallback

You can specifly :default option which is useful when the translation is not found. For example:

t(:this_translation_doesnt_exist, :default => 'Ooops!')
# => Ooops!

Or even any number of “fallbacks” - the first not nil is returned:

t(:missing, :default => [:missing_too, :existing, 'Sad panda'])
# => :existing translation

Good introduction to Rails I18n is http://guides.rubyonrails.org/i18n.html

January 11, 2010
2 thanks
January 11, 2010
0 thanks

Includes all ancestors

May be helpful to know that this returns true if B is any ancestor of A, not just a direct one. As an example:

class Foo; end
class Bar < Foo; end
class Baz < Bar; end

Foo >= Bar #=> true
Foo >= Baz #=> true