Slick 3在Scala中使用逻辑进行交易

opu*_*111 8 scala transactions slick typesafe

我有关于Slick 3和Transactions的问题

我已阅读文档

http://slick.typesafe.com/doc/3.1.0/dbio.html

和其他Slick 3交易问题

Slick 3 Transactions

在Slick 3中的事务中执行非数据库操作

但他们没有帮助我

我需要从数据库中读取一些值,在Scala中运行一些逻辑,然后根据结果修改数据库.我希望整个操作都是原子的.

我的代码看起来像这样:

database.run(TableQuery[X].filter(blah).result).map { x =>
  database.run { 
    if( someLogicNotInSQL(x) ) 
      TableQuery[Y].insert(someFoo) 
    else 
      TableQuery[Y].insert(someBah)
  } 
}
Run Code Online (Sandbox Code Playgroud)

如何获取查询的值,在Scala中运行一些逻辑,然后将另一个操作(例如insert)全部作为一个原子事务运行.

谢谢彼得

Ric*_*way 6

要在事务中运行此操作,您需要构建包含查询和逻辑的单个操作.然后使用事务运行该操作.

修改你的例子:

import scala.concurrent.ExecutionContext.Implicits.global 

val action = 
  tableQuery.filter(blah).result.flatMap { x =>
     if (someLogicNotInSql(x)) 
        tableQuery.insert(someFoo)
     else 
        tableQuery.insert(someBah)
  }
Run Code Online (Sandbox Code Playgroud)

flatMap需要作为参数从xa到a 的函数DBIO[T].它将两个动作排在一起,允许第二个动作使用第一个动作的结果.

要运行此组合操作,您需要执行上下文.(因为你的计算,if (someLogicNotInSql ...必须在某个地方的某个线程上运行,而不是Slick的内部执行上下文).

您可以将此组合操作包装在事务中,只需调用run一次:

 val future = database.run(action.transactionally)
Run Code Online (Sandbox Code Playgroud)