SLICK:使用联合和参数列表的简单查询

SLICK: A simple query using union and parameter lists

我是 SLICK (2.1) 的新手,在使用 union 创建我的第一个查询时迷失了方向。因为参数最终是从外部(通过 Web 界面)提供的,所以我将它们设置为可选。请参阅下面代码中的注释。如何创建合适的查询?

我的实际 class 更复杂,为了这个问题我简化了。

case class MyStuff(id: Int, value: Int, text: String)

class MyTable (tag: Tag) extends Table[MyStuff](tag, "MYSTUFF"){

  def id = column[Int]("ID", O NotNull)
  def value = column[Int]("VALUE", O NotNull)
  def text = column[String]("TEXT", O NotNull)

  def * = 
  (id, 
  value, 
  text).shaped <> ((MyStuff.apply _).tupled, MyStuff.unapply)
}

object myTable extends TableQuery(new MyTable(_)){
  def getStuff(ids: Option[List[Int]], values: Option[List[Int]])(implicit session: Session): Option[List[MyStuff]] = {
    /*
    1) If 'ids' are given, retrieve all matching entries, if any.
    2) If 'values' are given, retrieve all matching entries (if any), union with the results of the previous step, and remove duplicate entries.
    4) If neither 'ids' nor 'values' are given, retrieve all entries.
    */
  }
}

getStuff 是这样调用的:

db: Database withSession { implicit session => val myStuff = myTable.getStuff(...) }

如果我对你的理解是正确的,你想在运行时根据给定的输入构建一个过滤器。您可以在 "building criteria using a " 动态过滤器“例如来自网络表单”处查看 3.0 (http://slick.typesafe.com/doc/3.0.0-RC1/queries.html#sorting-and-filtering) 的扩展文档。这部分文档也适用于 2.1 版本。

如果值为 Some,则可以使用 inset,否则为 false,仅在不是 None.

时进行过滤
  if(ids.isDefined || values.isDefined)
    myTable.filter(row =>
      ids.map(row.id inSet _).getOrElse(slick.lifted.LiteralColumn(false))
    ) union myTable.filter(row =>
      values.map(row.value inSet _).getOrElse(slick.lifted.LiteralColumn(false))
    )
  else myTable