Ruby on Rails Tips & Tricks

Igor Kasyanchuk
Jan 7, 2023 • 2 minutes read

.to_sql method

If you are not fully comfortable with SQL code, but you know AR - use .to_sql method on AR ::Relation

Read Only Attributes

# models/product.rb
class Product < ApplicationRecord
  attr_readonly :secret_field
end

In Rails Console

product = Product.first
product.secret_field = "changedsku"
product.save # record updates, but secret_field attribute is ignored

Insert All (bulk import)

# Rails Console
products = [
  { name: 'Apple 14" Macbook Pro (2021)', category: "Laptop", sku: "MKGR3LL", in_stock: true },
  { name: 'Apple 16" Macbook Pro (2021)', category: "Laptop", sku: "MK1E3LL", in_stock: true },
  { name: 'Apple Mac Mini (2020)', category: "Desktop", sku: "MGNR3LL", in_stock: true },
  { name: 'Apple Mac Studio (2022)', category: "Desktop", sku: "MJMW3LL", in_stock: true }
]
Product.insert_all(products)
laptops = [
  { name: 'Apple 14" Macbook Pro (2021)', sku: "MKGR3LL", in_stock: true },
  { name: 'Apple 16" Macbook Pro (2021)', sku: "MK1E3LL", in_stock: true }
]
Product.create_with(category: "Laptop").insert_all(laptops)

Upsert records

# Rails Console
desktops = [
  { name: 'Apple Mac Mini (2020)', category: "Desktop", sku: "MGNR3LL", in_stock: false },
  { name: 'Apple Mac Studio (2022)', category: "Desktop", sku: "MJMW3LL", in_stock: true }
]
Product.upsert_all(desktops, update_only: [:in_stock], unique_by: [:sku])

Missing Associations

where.missing a query method missing to search for orphan records within ActiveRecord

[1] pry(main)> JobListing.where.missing(:manager)
JobListing Load (0.1ms)  SELECT "job_listings".* FROM "job_listings" 
LEFT OUTER JOIN "managers" ON "managers"."id" = "job_listings"."manager_id" 
WHERE "managers"."id" IS NULL LIMIT ?  [["LIMIT", 11]]
=> #<ActiveRecord::Relation [#<Manager id: 3, name: "Jane Doe", created_at: "2020-01-20 14:31:16", updated_at: "2020-01-20 14:31:16">]>
[2] pry(main)>

More Info here.

Associated Associations

where.associated checks for the association's presence

[1] pry(main)> JobListing.where.associated(:manager)
JobListing Load (0.1ms)  SELECT "job_listings".* FROM "job_listings"
INNER JOIN "managers" ON "managers"."id" = "job_listings"."manager_id"
WHERE "managers"."id" IS NOT NULL LIMIT ?  [["LIMIT", 11]]
=> #<ActiveRecord::Relation [#<Manager id: 3, name: "Jane Doe", created_at: "2020-01-20 14:31:16", updated_at: "2020-01-20 14:31:16">]>
[2] pry(main)>

More info here.

Generate Rails new app with a specific version

rails _7.0.3_ new appname

Join Path

Rails.root / 'app' / 'models' / 'user.rb'

generate a full path to some file.

button_to + option to use the “form” option

https://apidock.com/rails/ActionView/Helpers/UrlHelper/button_to

• :form - This hash will be form attributes

This one could be useful in many cases.

Other tips on how to improve your skills

  • Subscribe to https://rubyweekly.com/

    To be aligned with the most recent news in the Ruby world

  • run rubocop way faster

    rubocop --start-server

  • rubycop -A if you want to automatically fix issues

Useful gems

See all