简体   繁体   English

如何基于Rails中的外键列选择唯一记录?

[英]How to select unique records based on foreign key column in Rails?

I have the following model structure in my Rails 4.1 application: 我的Rails 4.1应用程序中具有以下模型结构:

delivery_service.rb delivery_service.rb

class DeliveryService < ActiveRecord::Base
    attr_accessible :name, :description, :courier_name, :active, :country_ids

    has_many :prices, class_name: 'DeliveryServicePrice', dependent: :delete_all
end

delivery_service_price.rb delivery_service_price.rb

class DeliveryServicePrice < ActiveRecord::Base

  attr_accessible :code, :price, :description, :min_weight, :max_weight, :min_length, :max_length, 
  :min_thickness, :max_thickness, :active, :delivery_service_id

  belongs_to :delivery_service
end

As you can see, a delivery service has many delivery service prices. 如您所见,送货服务有很多送货价格。 I'm trying to retrieve records from the delivery service price table; 我正在尝试从送货服务价格表中检索记录; selecting the record with the lowest price attribute within the unique scope of the foreign key , delivery_service_id (so essentially the cheapest delivery service price per delivery service). 在外键的唯一范围 (delivery_service_id)中选择具有最低价格属性的记录 (因此实质上是每个交付服务的最便宜交付服务价格)。

How can I select unique records from a table, with the foreign key attribute as the scope? 如何使用外键属性作为范围从表中选择唯一记录?

I hope I've explained this enough, let me know if you need anymore information. 希望我已经对此进行了足够的解释,如果您需要更多信息,请告诉我。

Thanks 谢谢

UPDATE #1: 更新#1:

Example of what I'm trying to achieve: 我要实现的示例:

delivery_service_prices table: delivery_service_prices表:

id: 1, price: 2.20, delivery_service_id: 1 id:1,价格:2.20,delivery_service_id:1

id: 2, price: 10.58, delivery_service_id: 1 id:2,价格:10.58,delivery_service_id:1

id: 3, price: 4.88, delivery_service_id: 2 id:3,价格:4.88,delivery_service_id:2

id: 4, price: 1.20, delivery_service_id: 2 id:4,价格:1.20,delivery_service_id:2

id: 5, price: 14.99, delivery_service_id: 3 id:5,价格:14.99,delivery_service_id:3

expected results: 预期成绩:

id: 1, price: 2.20, delivery_service_id: 1 id:1,价格:2.20,delivery_service_id:1

id: 4, price: 1.20, delivery_service_id: 2 id:4,价格:1.20,delivery_service_id:2

id: 5, price: 14.99, delivery_service_id: 3 id:5,价格:14.99,delivery_service_id:3

Due to PostgreSQL being more strict with abiding the SQL standard (rightly so), it requires a bit of tweaking to get the correct results. 由于PostgreSQL严格遵守SQL标准(正确的做法),因此需要一些调整才能获得正确的结果。

The following query returns the correct results for the lowest delivery service price, per delivery service: 以下查询为每个交付服务以最低的交付服务价格返回正确的结果:

DeliveryServicePrice.select('DISTINCT ON (delivery_service_id) *').order('delivery_service_id, price ASC')

I need to add the delivery_service_id attribute to the order condition, or PostgreSQL throws the following column error: 我需要将delivery_service_id属性添加到订单条件中,否则PostgreSQL会引发以下列错误:

PG::InvalidColumnReference: ERROR:  SELECT DISTINCT ON expressions must match initial ORDER BY expressions

Hope this helps anyone who stumbles upon it! 希望这对偶然发现它的人有所帮助!

To get the minimum for a single record you can use 要获得单个记录的最小值,您可以使用

DeliveryServicePrice.where(delivery_service_id: x).order(:price).limit(1).first

or if you have a delivery_service object available 或者如果您有delivery_service对象可用

delivery_service.prices.order(:price).limit(1).first

UPDATE 更新

If you want all minimums for all service_delivery_id s you can use a group query 如果您想要所有service_delivery_id的所有最小值,则可以使用group查询

DeliveryServicePrice.group(:delivery_service_id).minimum(:price)

which will get you almost where you want to go 这将使您几乎想要去的地方

{
  1: 2.20,
  2: 1.20,
  3: 14.99
}

with a hash containing the delivery_service_id and the price. 包含包含delivery_service_id和价格的哈希。 (you can't see the price_id ) (您看不到price_id)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM