[解決済み】Rails: railsのモデルのデフォルトのソート順?
質問
モデルでデフォルトのソート順を指定したい。
を実行したときに
.where()
を指定せずに
.order()
では、デフォルトのソートが使用されます。しかし、もし私が
.order()
を指定すると、デフォルトを上書きしてしまいます。
解決方法は?
default_scope
Rails 4+で動作します。
class Book < ActiveRecord::Base
default_scope { order(created_at: :desc) }
end
Rails 2.3, 3 の場合、代わりにこれが必要です。
default_scope order('created_at DESC')
Rails 2.x用。
default_scope :order => 'created_at DESC'
ここで
created_at
は、デフォルトで並べ替えを行いたいフィールドです。
注
ASC
は、昇順に使用するコードであり
<サブ
DESC
は降順の場合 (
desc
,
NOT
dsc
!).
scope
これに慣れたら、さらに
scope
:
class Book < ActiveRecord::Base
scope :confirmed, :conditions => { :confirmed => true }
scope :published, :conditions => { :published => true }
end
Rails 2 では、以下のものが必要です。
named_scope
.
:published
スコープを使用すると
Book.published
の代わりに
Book.find(:published => true)
.
Rails 3以降では、これらのメソッドをピリオドでつなげて「連結」することができるようになりました。
Book.published.confirmed
.
この方法では、実際に結果が必要になるまでクエリは実行されません(遅延評価)。したがって、7つのスコープを連結しても、実際のデータベースクエリは1つだけとなり、7つの別々のクエリを実行することによるパフォーマンスの問題を回避することができます。
日付やuser_idのようなパラメータ(実行時に変更されるため、「遅延評価」が必要となるもの)を、このようにラムダで使用することができます。
scope :recent_books, lambda
{ |since_when| where("created_at >= ?", since_when) }
# Note the `where` is making use of AREL syntax added in Rails 3.
最後に、デフォルトのスコープを無効化します。
Book.with_exclusive_scope { find(:all) }
あるいはもっといい。
Book.unscoped.all
で、フィルタ(条件)やソート(並び順)が無効になります。
最初のバージョンはRails2+で動作しますが、2番目のバージョン(unscoped)はRails3+のみであることに注意してください。
だから
もしあなたが、ふーん、じゃあこれはメソッドのようなものなんだ、と思っているなら、そうです、まさにこれがスコープなのです!
これらは
def self.method_name ...code... end
しかし、ruby の場合と同様に、これらはちょっとした構文上のショートカット (または「シュガー」) で、物事を簡単にすることができます!
実際には、これらは「すべての」レコードの1つのセットに対して操作するので、クラスレベルのメソッドです。
しかし、その形式は変化しています。
rails 4では、呼び出し可能なオブジェクトを渡さずに#scopeを使用すると、非推奨の警告が表示されます。
例えば、scope :red, where(color: 'red')は次のように変更する必要があります。
scope :red, -> { where(color: 'red') }
.
余談ですが、間違った使い方をすると
デフォルト
_scopeは誤用/悪用される可能性があります。
これは主に、以下のような動作に使用される場合についてです。
where
を制限(フィルタリング)しています。
デフォルト
を選択します。
<強い
悪知恵
は、単に結果の順序付けのために使われるのではなく、デフォルトのために使用されます。
については
where
を選択する場合は、通常の名前付きスコープを使用し、クエリでそのスコープを追加します。
Book.all.published
ここで
published
は名前付きスコープです。
結論として、スコープは本当に素晴らしいもので、「太いモデル、細いコントローラ」というDRYerなアプローチのために、物事をモデルに押し上げるのに役立つのです。
関連
-
[解決済み] Herokuの問題 : あなたが探しているページは存在しません。
-
[解決済み] Ruby: public static メソッドを作るには?
-
[解決済み] Ruby on Railsのマイグレーションでデータベースのカラムの名前を変更するにはどうすればよいですか?
-
[解決済み] Ruby on Railsで現在の絶対URLを取得するにはどうすればよいですか?
-
[解決済み] エラーが発生しました。pgsqlをrailsで動作させようとすると、Peer authentication failed for user "postgres" と表示されます。
-
[解決済み] Rails 4で懸念事項を使用する方法
-
[解決済み] Ruby/RailsでHashからキーを削除して残りのHashを取得する方法は?
-
[解決済み] Railsです。ActiveRecordでデフォルト値を設定するにはどうすればよいですか?
-
[解決済み】Railsの認証トークンを理解する
-
[解決済み】Rails: モデルがすでに存在するときに`rails generate scaffold`を実行するにはどうすればよいですか?
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
[解決済み] サーバーに接続できませんでした。そのようなファイルまたはディレクトリがありません (PG::ConnectionBad)
-
[解決済み】ActionController::InvalidAuthenticityTokenについて
-
[解決済み] gemのインストールができない - gemネイティブ拡張の構築に失敗 - そのようなファイルをロードできない -- mkmf (LoadError)
-
[解決済み] どのようにrailsでラジオボタンを正しく使用するには?
-
[解決済み] AWS S3です。アクセスしようとしているバケットは、指定されたエンドポイントを使用してアドレスされている必要があります。
-
[解決済み] Paramが無いか、値が空である。ParameterMissing in ResultsController#update
-
[解決済み] RoRにおけるSpringサーバーの機能とは?
-
[解決済み] rails/rubyでgroup_byを使用する。
-
[解決済み] Rails 4で、以前のバージョンのRailsでattr_accessibleを使用していた状況に遭遇した場合、Forbidden Attributes Errorが発生する。
-
[解決済み] 未初期化の定数 "コントローラ名"