使用 elastic4s 动态构建弹性请求
Build dynamically an elastic request with elastic4s
我想用 elastic4s 构建一个动态查询。
我有一个名为 myRequest 的请求对象,其中包含两个字段(fieldA 和 fieldB)
实际上我是这样构建查询的:
val req =
search in indexName -> indexType query {
bool {
should(
matchQuery("fieldA", myRequest.fieldA.getOrElse("")),
matchQuery("fieldB", myRequest.fieldA.getOrElse("")),
)
}
}
但我想要的是:当 fieldA 为空时,不会将 matchQuery 添加到我的查询中
感谢您的帮助
hbellahc。
您可以使用展平构建包含所有子查询的列表。这是一个超级冗长的代码来说明:
val fieldA: Option[String] = ...
val fieldB: Option[String] = ...
val shouldA: Option[QueryDefinition] = fieldA.map(a => matchQuery("fieldA", a))
val shouldB: Option[QueryDefinition] = fieldB.map(b => matchQuery("fieldB", b))
val req =
search in indexName -> indexType query {
bool {
should(Seq(shouldA, shouldB).flatten: _*)
}
}
请注意 _*
类型注释:需要解压参数列表。一般来说,无论何时调用具有可变长度参数列表的方法,每个参数都是 T 类型,您可以使用 Seq[T]
并使用 : T*
解压缩它。为方便起见,您可以改写 _*
,编译器将为您推断类型。
所以,简洁的方式:
def search(maybeA: Option[String], maybeB: Option[String]) =
search in indexName -> indexType query {
bool {
should(
Seq(
maybeA.map(a => matchQuery("fieldA", a),
maybeB.map(b => matchQuery("fieldB", b)
).flatten: _*
)
}
}
我想用 elastic4s 构建一个动态查询。
我有一个名为 myRequest 的请求对象,其中包含两个字段(fieldA 和 fieldB)
实际上我是这样构建查询的:
val req =
search in indexName -> indexType query {
bool {
should(
matchQuery("fieldA", myRequest.fieldA.getOrElse("")),
matchQuery("fieldB", myRequest.fieldA.getOrElse("")),
)
}
}
但我想要的是:当 fieldA 为空时,不会将 matchQuery 添加到我的查询中
感谢您的帮助
hbellahc。
您可以使用展平构建包含所有子查询的列表。这是一个超级冗长的代码来说明:
val fieldA: Option[String] = ...
val fieldB: Option[String] = ...
val shouldA: Option[QueryDefinition] = fieldA.map(a => matchQuery("fieldA", a))
val shouldB: Option[QueryDefinition] = fieldB.map(b => matchQuery("fieldB", b))
val req =
search in indexName -> indexType query {
bool {
should(Seq(shouldA, shouldB).flatten: _*)
}
}
请注意 _*
类型注释:需要解压参数列表。一般来说,无论何时调用具有可变长度参数列表的方法,每个参数都是 T 类型,您可以使用 Seq[T]
并使用 : T*
解压缩它。为方便起见,您可以改写 _*
,编译器将为您推断类型。
所以,简洁的方式:
def search(maybeA: Option[String], maybeB: Option[String]) =
search in indexName -> indexType query {
bool {
should(
Seq(
maybeA.map(a => matchQuery("fieldA", a),
maybeB.map(b => matchQuery("fieldB", b)
).flatten: _*
)
}
}