在数据库中刷新对象之前,将返回光滑的更新操作

问题描述 投票:0回答:1

我遇到的情况是,当我在更新后立即获取对象时,有时我从数据库获得的结果不包含最新的更改。

这使我认为更新线程在对象实际在DB中提交之前返回。这是预期的行为吗?

我认为更新方法只会在更改成功刷新到数据库后返回,但看起来这样做无法保证。

下面是伪代码,展示了我在说什么。

def processObject = {
  for {
    objectId: Option[Long] <- saveObjectInDb

    _ <- {
     //perform other synchronous business logic and then update created object details
      dao.findById(objectId.get).map { objectOption: Option[MyObject] =>
        dao.update(objectOption.get.copy(processingStep = "third-step"))
      }
    }

    mostRecentMyObject <- dao.findById(objectId.get)
  } yield mostRecentMyObject
}

下面是我的update逻辑的样子

def update(myObject: MyObject): Future[Int] = {
  db.run(table.filter(_.id === myObject.id).update(myObject))
}
scala asynchronous playframework slick
1个回答
2
投票

问题是你没有考虑Future方法返回的内部update

鉴于findById的签名:

def findById(id: Long): Future[Option[MyObject]]

片段:

dao.findById(objectId.get).map { objectOption: Option[MyObject] =>
  dao.update(objectOption.get.copy(processingStep = "third-step"))
}

将给出Future[Future[Int]]类型的对象。

你应该在flatMap未来而不是map而不是findById,如下:

dao.findById(objectId.get).flatMap { objectOption: Option[MyObject] =>
  dao.update(objectOption.get.copy(processingStep = "third-step"))
}

这将简化为单个未来(Future[Int]),因此您可以确保只在插入后检索对象。

此外,您可以将其重写为:

def processObject = {
  for {
    objectId: Option[Long] <- saveObjectInDb

    objectOption <- dao.findById(objectId.get)

    _ <- dao.update(objectOption.get.copy(processingStep = "third-step"))

    mostRecentMyObject <- dao.findById(objectId.get)
  } yield mostRecentMyObject
}

因为,为了理解,<-flatMap的语法糖

最新问题
© www.soinside.com 2019 - 2024. All rights reserved.