【问题标题】:ActiveRecord.where(column: array_of_strings) - how to preserve order?ActiveRecord.where(column: array_of_strings) - 如何保持顺序?
【发布时间】:2014-09-13 03:04:09
【问题描述】:

这个问题很像ActiveRecord.find(array_of_ids), preserving order,但是关于使用'where'和一个字符串id数组。

不幸的是,我们的情况有点复杂,我们收到一个 JSON 字符串(ArchiveObject 通过列 media 附加了媒体),例如:

[{"image_id":"ABCD1234", "type":"Image"},
{"image_id":"ABCD2345", "type":"Image"},
{"image_id":"ABCD3456", "type":"Image"}]

这些对象中的每一个都存在于数据库中,但长话短说,我们不能使用它们基于整数的 pk ID,因为我们的数据库会不断地从 XML 数据的导出中刷新和重写。

目前,我们是

  1. 解析 JSON
  2. 映射“image_id”
  3. 执行where 以查找相关对象

代码:

images = JSON.parse(current_archive_object.media)
image_ids = images.map { |image| image['image_id'] }
images = ArchiveObject.where(image_id: @image_ids)

因此我的问题是,有什么方法可以将生成的 activerecord 关系排序到原始数组image_ids?或者,如果我可以遍历image_ids,有没有办法通过其中一个列值有效地访问关系中的特定对象?

补充说明:

我们遇到所有这些映射和where 的麻烦的原因是,每个图像都有一个标题、url 等存储在它自己的行中,而这些在其父对象的media 列中不存在,因此为了防止对每个图像进行数据库查找,我们尝试将其全部编译到一个数据库调用中。

【问题讨论】:

    标签: ruby-on-rails json activerecord sinatra


    【解决方案1】:

    我不确定我的答案是否不是 postgresql 特有的,但在我的项目中我会遇到同样的问题。

    试试下面的解决方案

    images = JSON.parse(current_archive_object.media)
    image_ids = images.map { |image| image['image_id'] }
    order = "position(image_id::text in '#{image_ids.join(',')}')"
    images = ArchiveObject.where(image_id: image_ids).order(order)
    

    希望对你有帮助。

    【讨论】:

    • 感谢您的回复,不幸的是我收到了PG::UndefinedColumn: ERROR: column "ABCD1234" does not exist,控制台中的postgresql语句是(简化的)SELECT "archive_objects".* FROM "archive_objects" WHERE "archive_objects"."image_id" IN ('ABCD1234', 'ABCD3456', 'ABCD4567') ORDER BY image_id=ABCD4567 DESC,image_id=ABCD1234,image_id=ABCD3456
    • 用另一个排序功能更新了我的答案。试试看。
    猜你喜欢
    • 2020-04-17
    • 1970-01-01
    • 2015-05-23
    • 2010-09-16
    • 2021-10-13
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多