1

トランザクションクエリブロックのデバッグ中に、このヘッドスクラッチャーに遭遇しました。

何らかの理由で、左折/失敗操作で接続のロールバックが発生したにもかかわらず、成功/右の結果もロールバックされていました。

例:

// returns Either[String, Int]
db.handle withSession { implicit ss: Session=>
  ss.withTransaction {
    val result = for {
      u  <- either(User.insert(User(model)), ss)
      ur <- either(UserRole.insert( UserRole(u) ), ss)
      m  <- either(Membership.insert(Membership(u)), ss)
    } yield u

// bad: rollback occurs regardless of left/right outcome
result fold( {ss.rollback; Left(_)}, Right(_) )

// good: rollback occurs as expected on left outcome only
result fold( e=>{ss.rollback; Left(e)}, Right(_) )
4

1 に答える 1

4

次の少し単純な例を考えてみましょう。

def foo[A, B](e: Either[A, B]) = e.fold(
  { println("Launch the missiles!"); Left(_) },
  Right(_)
)

ミサイルは、呼び出すたびに起動されますfoo。これは、渡す最初の引数が正確に関数ではないためです。これは、関数に評価されるブロックであり、そのブロックは、関数が使用されているかどうかに関係なく評価されます。

この動作の詳細については、JesseEicharによるこのブログ投稿を参照してください。

于 2012-07-06T01:04:32.070 に答える