首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >rails中的复杂postgres查询

rails中的复杂postgres查询
EN

Stack Overflow用户
提问于 2016-03-11 07:36:05
回答 2查看 163关注 0票数 2

当前具有参数premium_amount_lower_range, premium_amount_upper_range, application_date_lower_range, application_date_upper_range, insurance_type_id的筛选器的查询

代码语言:javascript
复制
@filtered_quotes = current_user.insurance_subscribers.includes(:insurance_types).includes(:insurance_subscribers_types, :insurance_subscribers_types_carriers).
                   premium_amount(params[:dashboard][:premium_amount_lower_range], params[:dashboard][:premium_amount_upper_range]).
                   duration(params[:dashboard][:application_date_lower_range], params[:dashboard][:application_date_upper_range]).
                   insurance_type(params[:dashboard][:insurance_type_id])

但现在也需要根据自己的状态进行过滤。有问题。在insurance_subscribersinsurance_subscribers_types_carriers表中有status列,这两个列都是enum。

我试着添加where子句

代码语言:javascript
复制
@filtered_quotes = current_user.insurance_subscribers.includes(:insurance_types).includes(:insurance_subscribers_types, :insurance_subscribers_types_carriers).
               where("insurance_subscribers_types_carriers.status = 1")
#              ...

这给了我错误的PG::UndefinedTable: ERROR: missing FROM-clause entry for table "insurance_subscribers_types_carriers"

但当我试着做的时候

代码语言:javascript
复制
@filtered_quotes = current_user.insurance_subscribers.includes(:insurance_types).includes(:insurance_subscribers_types, :insurance_subscribers_types_carriers).
           where(status: 1)
#          .... 

这将把where子句放在insurance_subscribers上。

试图在上面的查询中添加一个简单的where子句WHERE insurance_subscribers_types_carriers.status = 1,但是这个查询有很多问题。

联想

insurance_subscriber.rb

代码语言:javascript
复制
has_many :insurance_subscribers_types, dependent: :destroy
has_many :insurance_types, through: :insurance_subscribers_types
has_many :insurance_subscribers_types_carriers, through: :insurance_subscribers_types

insurance_types.rb

代码语言:javascript
复制
has_many :insurance_subscribers, through: :insurance_subscribers_types
has_many :insurance_subscribers_types
has_many :insurance_subscribers_types_carriers

insurance_subscriber_type.rb

代码语言:javascript
复制
belongs_to :insurance_subscriber
belongs_to :insurance_type
has_many :carriers, through: :insurance_subscribers_types_carriers
has_many :insurance_subscribers_types_carriers, dependent: :destroy

insurance_subscribers_types_carrier.rb

代码语言:javascript
复制
belongs_to :carrier
belongs_to :insurance_subscribers_type
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2016-03-20 17:17:08

如果要跨关联模型添加queries,首先需要加入它们。由于您有has_may :through关联,所以您可以按以下方式实现您的需要:

代码语言:javascript
复制
InsuranceSubscriber.joins(insurance_subscriber_types: :insurance_subscribers_types_carriers)
.includes(:insurance_types, :insurance_subscribers_types, :insurance_subscribers_types_carriers)
.where("insurance_subscribers_types_carriers.status = ?", 1)

正如您所看到的,您可以加入和引用您的关联,即使您有has_many :through关联,如下所示joins(.joins(insurance_subscriber_types: :insurance_subscribers_types_carriers)

您将得到如下的sql输出:

代码语言:javascript
复制
InsuranceSubscriber Load (3.3ms)  SELECT "insurance_subscribers".* FROM 
"insurance_subscribers" INNER JOIN "insurance_subscriber_types" ON 
"insurance_subscriber_types"."insurance_subscriber_id" = 
"insurance_subscribers"."id" INNER JOIN "insurance_subscribers_types_carriers" ON 
"insurance_subscribers_types_carriers"."insurance_subscriber_type_id" = 
"insurance_subscriber_types"."id" WHERE (insurance_subscribers_types_carriers.status = 1)

我用模型结构复制并测试了您的问题,如下所示:

PS:我对您的模型名做了一些小改动,所以要小心。它们令人困惑,试图简化它们。

insurance_subscriber.rb

代码语言:javascript
复制
# == Schema Information
#
# Table name: insurance_subscribers
#
#  id         :integer          not null, primary key
#  name       :string
#  status     :integer          default("0")
#  created_at :datetime         not null
#  updated_at :datetime         not null
#

class InsuranceSubscriber < ActiveRecord::Base
  has_many :insurance_subscriber_types, dependent: :destroy
  has_many :insurance_types, through: :insurance_subscriber_types
  has_many :insurance_subscribers_types_carriers, through:     :insurance_subscriber_types

  enum status: {active: 0, passive: 1}
end

insurance_subscriber_types.rb

代码语言:javascript
复制
# == Schema Information
#
# Table name: insurance_subscriber_types
#
#  id                      :integer          not null, primary key
#  name                    :string
#  insurance_subscriber_id :integer
#  insurance_type_id       :integer
#  created_at              :datetime         not null
#  updated_at              :datetime         not null
#

class InsuranceSubscriberType < ActiveRecord::Base
  belongs_to :insurance_subscriber
  belongs_to :insurance_type

  has_many :insurance_subscribers_types_carriers, dependent: :destroy
  has_many :carriers, through: :insurance_subscribers_types_carriers
end

insurance_subscribers_types_carriers.rb

代码语言:javascript
复制
# == Schema Information
#
# Table name: insurance_subscribers_types_carriers
#
#  id                           :integer          not null, primary key
#  carrier_id                   :integer
#  insurance_subscriber_type_id :integer
#  status                       :integer          default("0")
#  created_at                   :datetime         not null
#  updated_at                   :datetime         not null
#

class InsuranceSubscribersTypesCarrier < ActiveRecord::Base
  belongs_to :carrier
  belongs_to :insurance_subscriber_type

  enum status: {active: 0, passive: 1}
end

insurance_types.rb

代码语言:javascript
复制
# == Schema Information
#
# Table name: insurance_types
#
#  id         :integer          not null, primary key
#  name       :string
#  created_at :datetime         not null
#  updated_at :datetime         not null
#

class InsuranceType < ActiveRecord::Base
  has_many :insurance_subscribers_types_carriers
  has_many :insurance_subscribers_types_carriers
  has_many :insurance_subscribers, through: :insurance_subscribers_types
end
票数 3
EN

Stack Overflow用户

发布于 2016-03-14 09:09:13

如果要在查询中使用包含的关联( insurance_subscribers_types_carriers ),则必须添加“引用”,否则insurance_subscribers_types_carriers将与主查询分开加载:

代码语言:javascript
复制
InsuranceSubscriber.includes(:insurance_subscribers_types_carriers)
               .where("insurance_subscribers_types_carriers.status = ?", 1)
               .references(:insurance_subscribers_types_carriers)
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/35934667

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档