1
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

【Rails】レコードの中から、ある項目ごとの最新データを取得する方法

Last updated at Posted at 2024-04-12

株式会社学びと成長しくみデザイン研究所の藤澤です。

前提

データベースに蓄積されたログから、特定の項目ごとの最新のデータを取得したいことがあるかと思います。

例えば、各タスクの実行状況を記録する TaskLog テーブルがあるとします。このテーブルには、タスクの識別コード(タスクコード)、ステータス、作成日時、更新日時が記録されています。

TaskLog(id, task_code, status, created_at, updated_at)

そして、テーブルには以下のようなデータが存在するとします。

id | task_code | status |     created_at      |     updated_at      |
 1 |  "taskA"  |  "ok"  | 2022/04/01 12:30:00 | 2022/04/01 12:30:00 |
 2 |  "taskB"  |  "ok"  | 2022/04/02 12:30:00 | 2022/04/02 12:30:00 |
 3 |  "taskA"  |  "ng"  | 2022/04/03 12:30:00 | 2022/04/03 12:30:00 |
 4 |  "taskC"  |  "ng"  | 2022/04/04 12:30:00 | 2022/04/04 12:30:00 |
 5 |  "taskC"  |  "ok"  | 2022/04/05 12:30:00 | 2022/04/05 12:30:00 |

課題と解決法

このデータの中から、タスクコードごとに最新のステータスを取得したいケースを考えます。

その場合、以下のようなコードで取得することが可能です。

TaskLog.order(:created_at).index_by(&:task_code).transform_values(&:status)
#=> {"taskA"=>"ng", "taskB"=>"ok", "taskC"=>"ok"}

このコードでは、

  1. .order(:created_at) で、作成日時順にソート
  2. .index_by(&:task_code) で、タスクコードごとにハッシュを作成

という手順を踏んでいます。

index_by の仕様により、同じキーに紐づく値はあとから取得したもので上書きされます。そして、事前にレコードの作成日時順でソートしていることで、最終的に最新のものがハッシュの値として適用されます。
つまりここでは、各タスクコードごとに作成日時が最新のレコードを取得するということを行っています。

最後に、.transform_values(&:status) によって必要な値だけ抽出して完了です。

1
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?