简体   繁体   中英

rails: query has_many for a list of objects

I have a model City :

class City
 belongs_to :country
end

And a model Street:

//street has an attribute `Type` which can be 1, 2 or 3
class Street
  belongs_to City
end

I want all cities in Croatia including streets that are of type 2

So something like this:

cities = City.find_by_country("Croatie").include_streets_where(type: 2)

so I get something like this:

[
 {
   name: "Zagreb", 
   country: "Croatia",
   streets: [{name: "street1", type: 2},{name: "street2", type: 2}]
 },
 {
   name: "Split",
   country: "Croatia",
   streets: [{name: "street3", type: 2},{name: "street4", type: 2}]
 }
]

My solution is to first get the cities by country name and loop through each city to query it's streets. But I'm guessing there is a better way.

I'm assuming your City has_many :streets , and your Country class has an attribute name .

A 2-layered loop is not as efficient as an INNER JOIN, which you can assemble with this: (You can look at the SQL it generates by appending .to_sql to the end of it.)

cities = City.where(country: Country.find_by_name("Croatie"))
             .joins(:streets).where(streets: { type: 2 })

This will return a list of city objects matching your criteria. Now to get it to the format you specified, you have to do some formatting on the Ruby side since the default returned is not an Array type. This is assuming you want an array of hashes.

formatted_list = cities.map do |city|
  { name: city.name,
    country: city.country.name,
    streets: list_of_streets_with_type(city.streets) }
end

def list_of_streets_with_type(streets)
  streets.map do |street|
    { name: street.name,
      type: street.type }
  end
end

In the end, formatted_list would be returning what you wanted. (Disclaimer: I have not checked syntax, but the general idea is there. Give it a try, it should work)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM