2

Sorry for bad English ))

I have an array of ids in my ruby code.

Example:

[[10], [], [10, 1, 3], []]

Can I load User model from MySQL table users in one query by saving grouping?

Example:

[[#<User id=10>], [], [#<User id=10>, #<User id=1>, #<User id=3>], []]

Environment: Ruby 2.5.1 | Rails 5 | MySQL

One of found solution:

I can flat my array of ids and load my model by that array into hash:

hash = User.where(id: array.flatten).index_by(&:id)

Then, during iterating, through array I can load my objects from hash in the right order like that:

array.each do |ids|
  users = ids.map { |id| hash[id] }
  # do smth
end
korotindev
  • 81
  • 6
  • 1
    what is your criteria for grouping? I think active record only returns arrays, but you can use ruby to create the grouping you want. – Sean Gregory Apr 19 '18 at 15:30
  • Your example input and output don't match. – Stefan Apr 19 '18 at 15:43
  • I think you need to scan the main array at least and make a call to database for each element using [like this](https://stackoverflow.com/a/1441835/5239030) – iGian Apr 19 '18 at 15:50

1 Answers1

0

This is simple: use flatten method for array:

ids = [[123], [], [123, 1, 3, 4], [70, 80]]
user_ids = ids.flatten.reject(&:blank?).uniq
users = User.where(id: user_ids)

edited: not optimal (recursive) method for your need:

def map_users_by_id(ids_array:, users:)
  result = []
  ids_array.each do |array_element|
    if (array_element).is_a? Array
      result << map_users_by_id(ids_array: array_element, users: users)
    else
      result << users[array_element]
    end
  end
  return result
end

ids = [[123], [], [123, 1, 3, 4], [70, 80]]
user_ids = ids.flatten.reject(&:blank?).uniq
users = Hash[User.where(id: user_ids).map{|user|[user.id, user]}]
result = map_users_by_id(ids_array: ids, users: users)
Sergio Belevskij
  • 2,478
  • 25
  • 24
  • Thanks for your answer! But I need to save my grouping like that: ```[[#], [], [<#User id=123>, #], [<#User id=3>, ...]]``` In your example I will get just uniq array of my model. – korotindev Apr 23 '18 at 18:26