Результаты упорядочения по рельсам 3. Работает как магия, но почему? - PullRequest
0 голосов
/ 08 марта 2011
class Course < ActiveRecord::Base
  belongs_to :course_category
  belongs_to :client
  belongs_to :user_created, :foreign_key => :user_created_by, :class_name => "User"
  belongs_to :user_updated, :foreign_key => :user_last_updated_by, :class_name => "User"
  has_many :course_steps, :dependent => :destroy
  has_many :steps, :through => :course_steps
  has_many :course_requests
end

Вот вывод с консоли рельсов ...

>> c=Course.first
=> #<Course id: 1, course_category_id: 1, client_id: 1, user_created_by: 1, user_last_updated_by: 1, title: "Test Course 1", summary: "", hidden: false, auto_register: false, created_at: "2011-03-08 01:03:47", updated_at: "2011-03-08 01:03:47">
>> c.course_steps
=> [#<CourseStep id: 3, step_id: 2, course_id: 1, position: nil, created_at: "2011-03-08 15:03:44", updated_at: "2011-03-08 15:03:44">, #<CourseStep id: 4, step_id: 3, course_id: 1, position: nil, created_at: "2011-03-08 15:03:46", updated_at: "2011-03-08 15:03:46">]
>> c.course_steps.order("id DESC")
=> [#<CourseStep id: 4, step_id: 3, course_id: 1, position: nil, created_at: "2011-03-08 15:03:46", updated_at: "2011-03-08 15:03:46">, #<CourseStep id: 3, step_id: 2, course_id: 1, position: nil, created_at: "2011-03-08 15:03:44", updated_at: "2011-03-08 15:03:44">]
>> c.course_steps.order("id DESC").to_sql
=> "SELECT \"course_steps\".* FROM \"course_steps\" WHERE (\"course_steps\".course_id = 1) ORDER BY id DESC"
>> c.course_steps.order("position DESC").to_sql
=> "SELECT \"course_steps\".* FROM \"course_steps\" WHERE (\"course_steps\".course_id = 1) ORDER BY position DESC"
>> c.steps.order("position DESC").to_sql
=> "SELECT \"steps\".* FROM \"steps\" INNER JOIN \"course_steps\" ON \"steps\".id = \"course_steps\".step_id WHERE ((\"course_steps\".course_id = 1)) ORDER BY position DESC"
>> c.steps.class
    => Array
    >> c.course_steps.class
    => Array
    >> 

Детали, которые меня смущают: (Я рад, что они работают, но мне просто интересно, почему)

  1. Тот факт, что я могу вызвать "order" на course_steps (который является массивом) c.course_steps.order ("id DESC")!?!?

  2. Тот факт, что я могу вызвать c.steps.order ("position DESC"), когда position даже не является частью таблицы шагов.Это как-то делает магическое соединение.

1 Ответ

1 голос
/ 08 марта 2011

То, что я могу назвать "заказ" на course_steps (который является массивом) c.course_steps.order ("id DESC")!?!?

На мой взгляд, rails не сразу запрашивает базу данных после каждого из цепочечных методов. Вместо этого он обрабатывает всю цепочку и создает запрос. Так что order не вызывается в массиве course_steps. Он просто добавляет order часть запроса.

Вот цитата из Начала Rails:

Обратите внимание, что когда вы звоните заказ метод, он возвращает объект массива как Вы, возможно, ожидали. Одна вещь, которая происходит на фоне того, что Active Record позволяет связывать вызовы нескольких методов, прежде чем отправка команды в базу данных; так что вы можете позвонить всем, а затем порядок и некоторые другие методы, которые мы будем поговорим в следующей главе, чтобы создавать более точные запросы к базе данных. Кроме того, Active Record достаточно умен использовать ленивую загрузку, практика, которая только попадает в базу данных, когда необходимо - в этом примере, когда вы вызовите каждый метод.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...