Slick.io - 处理连接表
Slick.io - Handling Joined Tables
我在 Slick (2.1) 中有一个简单的查询,它以一对多的关系连接两个表。大致定义如下...
class Users( tag: Tag ) extends Table[ User ]( tag, "users" )
// each field here...
def * = ( id, name ).shaped <> ( User.tupled, User.unapply)
class Items( tag: Tag ) extends Table[ Item ]( tag, "items" )
// each field here...
// foreign key to Users table
def userId = column[ Int ]( "user_id")
def user_fk = foreignKey( "users_fk", userId, Users )( _.id )
def * = ( id, userId.?, description ).shaped <> ( Item.tupled, Item.unapply)
一个用户可以有多个项目。我想要编组的用户案例 class 看起来像...
case class User(id: Option[Int] = None, name:String, items:Option[List[Item]] = None)
然后我用这样的隐式连接查询数据库...
for{
u <- Users
i <- Items
if i.userId === u.id
} yield(u, i)
这个"runs"很好。但是,查询显然会为属于用户的每个 "Item" 复制 "Users" 记录...
List(
(User(Some(1),"User1Name"),Item(Some(1),Some(1),"Item Description 1")),
(User(Some(1),"User1Name"),Item(Some(2),Some(1),"Item Description 2")))
是否有一种优雅的方式将 "many" 部分拉入用户案例 class?无论是 Slick 还是 Scala。我最理想的结局是...
User(Some(1),"User1Name",
List(Item(Some(1),Some(1),"Item Description 1"),
Item(Some(2),Some(1),"Item Description 2")))
谢谢!
一种在 Scala 中实现的方法:
val results = List((User(Some(1), "User1Name"), Item(Some(1), Some(1), "Item Description 1")),
(User(Some(1), "User1Name"), Item(Some(2), Some(1), "Item Description 2")))
val grouped = results.groupBy(_._1)
.map { case (user, item: List[(User, Item)]) =>
user.copy(items = Option(item.map(_._2))) }
这处理多个不同的 User
s(grouped
是一个 Iterable[User]
)。
我在 Slick (2.1) 中有一个简单的查询,它以一对多的关系连接两个表。大致定义如下...
class Users( tag: Tag ) extends Table[ User ]( tag, "users" )
// each field here...
def * = ( id, name ).shaped <> ( User.tupled, User.unapply)
class Items( tag: Tag ) extends Table[ Item ]( tag, "items" )
// each field here...
// foreign key to Users table
def userId = column[ Int ]( "user_id")
def user_fk = foreignKey( "users_fk", userId, Users )( _.id )
def * = ( id, userId.?, description ).shaped <> ( Item.tupled, Item.unapply)
一个用户可以有多个项目。我想要编组的用户案例 class 看起来像...
case class User(id: Option[Int] = None, name:String, items:Option[List[Item]] = None)
然后我用这样的隐式连接查询数据库...
for{
u <- Users
i <- Items
if i.userId === u.id
} yield(u, i)
这个"runs"很好。但是,查询显然会为属于用户的每个 "Item" 复制 "Users" 记录...
List(
(User(Some(1),"User1Name"),Item(Some(1),Some(1),"Item Description 1")),
(User(Some(1),"User1Name"),Item(Some(2),Some(1),"Item Description 2")))
是否有一种优雅的方式将 "many" 部分拉入用户案例 class?无论是 Slick 还是 Scala。我最理想的结局是...
User(Some(1),"User1Name",
List(Item(Some(1),Some(1),"Item Description 1"),
Item(Some(2),Some(1),"Item Description 2")))
谢谢!
一种在 Scala 中实现的方法:
val results = List((User(Some(1), "User1Name"), Item(Some(1), Some(1), "Item Description 1")),
(User(Some(1), "User1Name"), Item(Some(2), Some(1), "Item Description 2")))
val grouped = results.groupBy(_._1)
.map { case (user, item: List[(User, Item)]) =>
user.copy(items = Option(item.map(_._2))) }
这处理多个不同的 User
s(grouped
是一个 Iterable[User]
)。