krn
krn

Reputation: 6815

Accepting either a hash or an array of hashes as arguments to a Ruby method

I have the method:

def self.store(params)
  params.each { }
end

It works perfectly, if I pass an Array of Hashes:

params = [ { key: 'value' }, { key: 'value' } ]

However, I might want to pass only a single Hash, instead of an Array of Hashes:

params = { key: 'value' }

What would be the cleanest Ruby way to convert a Hash into an Array of Hashes?

The Array() method a kind of ensures, that an array is always returned, but when the Hash is passed, it is converted into an Array itself.

Array({ key: 'value' }) => [[:key, 'value']]

What I need:

 { key: 'value' } => [ { key: 'value' } ]

Is there any nice way to implement this, or do I have to do a manual type checking with is_a?(Array) ?

Upvotes: 7

Views: 3463

Answers (3)

Slava Eremenko
Slava Eremenko

Reputation: 2506

I would do it like this:

def self.store(params)
  (params.is_a?(Array) ? params : [params]).each {|single_hash| }
end

Upvotes: 0

miguel.camba
miguel.camba

Reputation: 1827

For me, the best solution is to change the method to:

def self.store(*hashes)
  params = hashes.flatten
  puts params.inspect
end
  • If you pass a single hash, it will be an array
  • If you pass an array of hashes, it remains the same
  • If you pases N hashes, it compacts all parameters into a one dimensional array.

You can pass whatever you want.

self.store({:key => 'value'}) # => [{:key => 'value'}]
self.store({:key => 'value'}, {:foo => 'bar'}) # => [{:key => 'value'}, {:foo => 'bar'}]
self.store([{:key => 'value'}, {:foo => 'bar'}]) # => [{:key => 'value'}, {:foo => 'bar'}]

Upvotes: 9

Kulbir Saini
Kulbir Saini

Reputation: 3915

Try this

def self.store(params)
  params = [params].flatten
  ...
end

Upvotes: 3

Related Questions