Home > Mobile >  Mapping large array of objects with the spread operator
Mapping large array of objects with the spread operator

Time:07-05

I've got a API-only Rails 7 app with Ruby 3.1.2. I'm using the jb gem for serialization of data.

In the app, I have a Part table, which belongs_to a Company. I want to deliver the name of the company the part belongs to in order to avoid having to call a 2nd query just for the company names later down the line.

The actual index action is pretty simple (it's actually paginated with the Pagy gem, but that has no tangible effect here)

@parts = Part.includes(:company)

Problem is, my Parts model is massive, and has around 35 fields that my users need to see. As such, writing out any kind of query, or create, or anything like that is a massive pain and takes up a humongous amount of screen real estate, not to mention being incredibly tedious and error prone to write down.

For example, my jb file for the Parts index page looks something like this

@parts.map do |part|
  {
    id: part.id,
    part_number: part.part_number,
    available: part.available,
    #... And so on for another 30 lines
    company_name: part.company.name,
    company_id: part.company.id
  }
end

You can probably spot the problem. The only things I'm even adding to this are the company_name and ID, yet I still need to write down all 30-odd lines for the other attributes as well.

Is there a way for me to avoid this? I tried using the spread operator, but it errors out on me with

ActionView::Template::Error: no implicit conversion of Part into Hash
@parts.map do |part|
  **part,
  company_name: part.company.name,
  company_id: part.company.id
end

CodePudding user response:

You can use attributes instead of splat operator.

@parts.map do |part|
  part.attributes.merge(company_name: part.company.name, company_id: part.company.id)
end

But instead of doing this, you can use includes to fetch company and can avoid n 1 query

  • Related