【问题标题】:Filtering on multiple associations and optional where clauses过滤多个关联和可选的 where 子句
【发布时间】:2012-03-23 11:49:31
【问题描述】:

我有几个领域类,它们之间有一些简单的关联,如下所示:

class Business {
  String name
  City city
  Industry industry
}

class City {
  String name
}

class Industry {
  String name
}

在我的应用程序中,我想要一个“过滤器”,可以根据城市和行业过滤所有企业的列表。我可以将过滤器中的城市和行业 ID 返回到业务控制器,但是,当我到达控制器进行过滤时,我有以下代码:

...
def industry = Industry.get(params.int('industryid'))
def city = City.get(params.int('cityid'))

def businessList = Business.findAllByIndustryAndCity(industry, city)
...

当 City 和 Industry 字段都有值时,此代码有效。但是,有时用户可能只想按城市或行业进行过滤,而不是两者。在这种情况下,过滤器会失败,因为当任何一个值为 null 时,都不会返回任何结果。我怎么能指定如果任何一个关联值为“null”,那么“find”查询应该完全删除这个约束?即匹配该字段的“全部”

请注意,我意识到很容易放置一个 if 语句来检查值是否为空,然后基于此执行不同的“查找”语句。然而,虽然这适用于两个值,但我认为随着更多可过滤值的添加,它不会很好地扩展。

【问题讨论】:

    标签: grails grails-orm


    【解决方案1】:

    您可以建立标准。

    def c = Business.createCriteria()
    def results = c.list{
        and {
            if (industry) {
                eq("industry", industry)
            }
            if (city) {
                eq("city", city)
            }
        }
    }
    

    检查 grails 文档中的参考 here

    但是,您的代码需要对 N 个参数进行 N+1 次查询。也许您可以使用标准的想法将其减少为一个查询?如果您的Business 实体同时拥有IndustryCity 的外键,那么这个应该可以工作:

    def c = Business.createCriteria()
    def results = c.list{
        and {
            if (params.industryid) {
                eq("industry_id", params.industryId as Long)
            }
            if (params.cityid) {
                eq("city_id", params.cityid as Long)
            }
        }
    }
    

    这两个例子都未经测试,但你应该明白了。

    【讨论】:

      猜你喜欢
      • 2014-05-10
      • 2016-10-06
      • 2020-03-21
      • 2016-02-18
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多