Область Rails 3 по умолчанию, область действия с переопределением - PullRequest
7 голосов
/ 03 августа 2011

У меня есть ситуация, когда поведение существующего приложения меняется, и это вызывает у меня сильную головную боль.

В моем приложении есть фотографии.Фотографии имеют статус: "batch", "queue", or "complete".Все существующие фотографии в приложении «завершены».

99% времени мне нужно показывать только полные фотографии, а во всей существующей кодовой базе мне нужно, чтобы каждый вызов фотографий ограничивался только завершениемфотографии.

Однако на экранах, связанных с загрузкой и классификацией фотографий, мне нужно иметь возможность довольно легко переопределить эту область по умолчанию для отображения фотографий в пакетном режиме или в очереди.

Как и многие другие, мне нужночтобы найти способ легко переопределить область по умолчанию в определенных ситуациях.Я посмотрел на эти вопросы ( 1 , 2 ), и они, похоже, не отвечают тому, что я ищу.

Код, который я хотел бы сработать, таков::

class Photo < ActiveRecord::Base
  ...
  default_scope where(:status=>'complete')
  scope :batch, unscoped.where(:status=>'batch')
  scope :queue, unscoped.where(:status=>'queue')
  ...
end

Однако это не работает.Я попытался обернуть методы области видимости в лямбды, но это тоже не сработало.

Я понимаю, что default_scope поставляется с багажом, но если я не могу использовать его с переопределениями, я смотрю на добавление scope :complete ...и необходимость прочесывать каждый вызов к фотографиям в моем существующем приложении и добавлять .complete для фильтрации необработанных фотографий.

Как бы вы решили эту проблему?

Ответы [ 2 ]

6 голосов
/ 03 августа 2011

<code>def self.batch
  Photo.unscoped.where(:status=>"batch")
end
Этот поток является более авторитетным: Переопределение Rails default_scope
3 голосов
/ 20 марта 2013

Я даю ему шанс. Допустим, вы хотите удалить предложение where из области по умолчанию (а не просто переопределить его другим значением) и сохранить ассоциации, которые вы можете попробовать сделать так:

class Photo < ActiveRecord::Base
  default_scope where(:status => 'complete').where(:deleted_at => '').order('id desc')

  def self.without_default_status
    # Get the ActiveRecord::Relation with the default_scope applied.
    photos = scoped.with_default_scope
    # Find the where clause that matches the where clause we want to remove 
    # from the default scope and delete it.
    photos.where_values.delete_if { |query| query.to_sql == "\"photos\".\"status\" = 'complete'" }
    photos
  end

end
...