将一个 DBIO 的结果传递给另一个

Passing result of one DBIO into another

我是 Slick 的新手,我正在尝试重写以下两个查询以在一个事务中工作。我的目标是 1.检查元素是否存在 2. return 现有元素或创建它处理来自 MySQL

的自动增量

这两个函数是:

  def createEmail(email: String): DBIO[Email]  = {
    // We create a projection of just the email column, since we're not inserting a value for the id column
    (emails.map(p => p.email)
      returning emails.map(_.id)
      into ((email, id) => Email(id, email))
      ) += email
  }

  def findEmail(email: String): DBIO[Option[Email]] =
    emails.filter(_.email === email).result.headOption

我怎样才能安全地链接它们,即。 运行 首先检查是否存在,return 如果对象已经存在,如果不存在则创建它,并且 return 在一个事务中创建新元素?

你可以使用 a 来理解:

def findOrCreate(email: String) = {
  (for {
    found <- findEmail(email)
    em <- found match {
      case Some(e) => DBIO.successful(e)
      case None => createEmail(email)
    }
  } yield em).transactionally
}

val result = db.run(findOrCreate("batman@gotham.gov"))
// Future[Email]

在 cats 库的帮助下:

def findOrCreate(email: String): DBIO[Email] = {
    OptionT(findEmail(email)).getOrElseF(createEmail(email)).transactionally
}