Slick 3 - 插入多个 tables,交易,基于其他 table

Slick 3 - Insert into multiple tables, transactionally, based on other table

我想做的是插入到 3 个表中,事务性的,但后面的插入是基于第一个。

以下是不同的查询:

val personId = persons returning persons.map(_.id)) += Person(occupation)
translatedProperty += TranslatedProperty(languageId, propertyId, propertyName)
personProperties += PersonProperty(personId, propertyId, propertyValue)

现在我从某处获取 Seq(propertyName, propertyValue) 并对其进行迭代。

如果我像上面那样按顺序插入,一切正常,直到它不起作用,因为说数据库 "crashes"。因此,我想以交易方式进行上述插入。

我试过了:

val dbAction = (for {
  val personId = persons returning persons.map(_.id)) += Person(occupation)
  props <- (properties.values.map {
    x =>
    {
      val name = x.key
      val value = x.value

      translatedProperties += TranslatedProperty(languageId, propertyId, name)
      personProperties += PersonProperty(personId, propertyId, value)
    }
  })
} yield ()).transactionally

db.run(dbAction)

这给了我一个编译错误:

[error] found : Seq[Unit] [error] required: slick.dbio.DBIOAction[?,?,?] [error] props <- (properties.values.map

然后我尝试使用 props = (properties.values.map { ...(而不是 <- 我使用 =)但无济于事。人会被插入,但不会插入属性。

我做错了什么?

我猜是因为 props 会是一个 Seq[FixedSqlAction] 而不是一个?

我应该提一下,我在这里使用的是 h2。

I assume it's because props would be a Seq[FixedSqlAction] instead of just one?

是的,正是这个原因。

您的问题的解决方案是简单地将 properties.values.map... 部分包装到 DBIO.seq 中,如下所示:

val dbAction = (for {
  val personId = persons returning persons.map(_.id)) += Person(occupation)
  props <- DBIO.seq(properties.values.map {
    x =>
    {
      val name = x.key
      val value = x.value

     val insertTranslatedProperties = translatedProperties += TranslatedProperty(languageId, propertyId, name)
     val insertPersonProperties = personProperties += PersonProperty(personId, propertyId, value)

     insertTranslatedProperties andThen insertPersonProperties 
    }
  }: _*)
} yield ()).transactionally

同时将两个内部插入链接 andThen 以将它们合并为一个 DBIOAction