Bird
Raised Fist0
Ruby on Railsframework~3 mins

Why Scopes for reusable queries in Ruby on Rails? - Purpose & Use Cases

Choose your learning style10 modes available
The Big Idea

Discover how a tiny change can save you hours of repetitive work and bugs!

The Scenario

Imagine you have a website with thousands of users, and you want to find all active users or users created in the last week. You write the same complex database query again and again in different parts of your code.

The Problem

Manually repeating queries is tiring and risky. If you make a mistake or want to change the query, you must update every place it appears. This leads to bugs and wasted time.

The Solution

Scopes let you define a query once inside your model. Then you can reuse it everywhere by calling a simple method. This keeps your code clean, consistent, and easy to update.

Before vs After
✗ Before
User.where(active: true).order(created_at: :desc)
User.where(active: true).order(created_at: :desc).limit(10)
✓ After
class User < ApplicationRecord
  scope :active, -> { where(active: true).order(created_at: :desc) }
end

User.active
User.active.limit(10)
What It Enables

Scopes make your queries reusable and your code easier to read and maintain.

Real Life Example

In a blog app, you can create a scope to get all published posts. Then anywhere you need published posts, just call Post.published instead of rewriting the query.

Key Takeaways

Manually repeating queries causes errors and extra work.

Scopes let you write queries once and reuse them easily.

This improves code clarity, consistency, and maintenance.

Practice

(1/5)
1. What is the main purpose of using scopes in a Rails model?
easy
A. To define database table columns
B. To write controller actions
C. To create new database tables
D. To reuse common database queries easily

Solution

  1. Step 1: Understand what scopes do

    Scopes are defined in models to encapsulate common queries for reuse.
  2. Step 2: Identify the correct purpose

    They help avoid repeating query code by providing reusable query methods.
  3. Final Answer:

    To reuse common database queries easily -> Option D
  4. Quick Check:

    Scopes = reusable queries [OK]
Hint: Scopes are for reusable queries inside models [OK]
Common Mistakes:
  • Confusing scopes with database schema definitions
  • Thinking scopes create tables or columns
  • Mixing scopes with controller logic
2. Which of the following is the correct syntax to define a scope named active that selects records with status: 'active'?
easy
A. scope :active, -> { where(status: 'active') }
B. scope active: where(status: 'active')
C. def scope :active; where(status: 'active'); end
D. scope :active { where(status: 'active') }

Solution

  1. Step 1: Recall scope syntax

    Scopes use the syntax: scope :name, -> { query }.
  2. Step 2: Match the correct option

    scope :active, -> { where(status: 'active') } matches this syntax exactly with a lambda returning the query.
  3. Final Answer:

    scope :active, -> { where(status: 'active') } -> Option A
  4. Quick Check:

    Scope syntax = scope :name, -> { ... } [OK]
Hint: Use lambda with -> { ... } for scope queries [OK]
Common Mistakes:
  • Omitting the lambda syntax -> { ... }
  • Using incorrect method definitions for scopes
  • Missing colon before scope name
3. Given the following scopes in a Rails model:
scope :published, -> { where(published: true) }
scope :recent, -> { order(created_at: :desc) }

What will Article.published.recent.to_sql return?
medium
A. SELECT * FROM "articles" WHERE "articles"."published" = FALSE ORDER BY "articles"."created_at" ASC
B. SELECT * FROM "articles" ORDER BY "articles"."created_at" DESC WHERE "articles"."published" = TRUE
C. SELECT * FROM "articles" WHERE "articles"."published" = TRUE ORDER BY "articles"."created_at" DESC
D. SELECT * FROM "articles" WHERE "articles"."published" = TRUE

Solution

  1. Step 1: Understand scope chaining

    Chaining scopes combines their queries in order: published adds a WHERE clause, recent adds ORDER BY.
  2. Step 2: Analyze the SQL generated

    The SQL will filter published = true and order by created_at descending.
  3. Final Answer:

    SELECT * FROM "articles" WHERE "articles"."published" = TRUE ORDER BY "articles"."created_at" DESC -> Option C
  4. Quick Check:

    Chained scopes combine WHERE and ORDER BY [OK]
Hint: Chained scopes combine queries in order [OK]
Common Mistakes:
  • Placing ORDER BY before WHERE in SQL
  • Confusing true/false values in conditions
  • Ignoring scope chaining order
4. Identify the error in this scope definition:
scope :recent, { order(created_at: :desc) }
medium
A. Missing lambda syntax -> { ... } around the query
B. Incorrect scope name format
C. Using order instead of where
D. Scope must be defined in controller, not model

Solution

  1. Step 1: Check scope syntax requirements

    Scopes require a lambda (-> { ... }) to wrap the query for lazy evaluation.
  2. Step 2: Identify missing lambda

    The given scope uses curly braces without the lambda arrow, causing a syntax error.
  3. Final Answer:

    Missing lambda syntax -> { ... } around the query -> Option A
  4. Quick Check:

    Scopes need -> { ... } [OK]
Hint: Always wrap scope queries in -> { ... } [OK]
Common Mistakes:
  • Omitting the lambda arrow ->
  • Defining scopes outside models
  • Confusing order and where methods
5. You want to create a scope recent_active that returns records which are both active: true and created in the last 7 days. Which is the correct way to define this scope?
hard
A. scope :recent_active, -> { where(active: true).order('created_at >= 7.days.ago') }
B. scope :recent_active, -> { where(active: true).where('created_at >= ?', 7.days.ago) }
C. scope :recent_active, -> { where(active: true && created_at >= 7.days.ago) }
D. scope :recent_active, -> { where(active: true).where(created_at: 7.days.ago) }

Solution

  1. Step 1: Combine conditions with where

    Use chained where calls to combine multiple conditions logically ANDed.
  2. Step 2: Use correct date comparison syntax

    Use a SQL fragment with placeholder and 7.days.ago to compare dates properly.
  3. Final Answer:

    scope :recent_active, -> { where(active: true).where('created_at >= ?', 7.days.ago) } -> Option B
  4. Quick Check:

    Chain where with SQL and placeholders [OK]
Hint: Chain where with SQL and placeholders for complex conditions [OK]
Common Mistakes:
  • Using && inside where hash instead of chaining
  • Using order for filtering conditions
  • Comparing created_at with exact date instead of range
Recommended

Ready to prove it?

Pass the test and this pattern moves unknown strong while earning +1 Grip toward your certificate.

10 questions~5 mineasy hard