Reputation: 14404
I'm trying to define a Type on the query side to map my join so that I can avoid returning a tuple of values that I have to manually apply to my projection case class post query.
Given a relationship like:
case class Parent(id: Int, name: String, extra: String)
class ParentTable(tag: Tag) extends Table[Parent](tag, "parent") {
def id = column[Int]("id", O.PrimaryKey, O.AutoInc)
def name = column[String]("name")
def extra = column[String]("extra")
def * = (id, name, extra) <> (Parent.tupled, Parent.unapply)
}
val parents = TableQuery[ParentTable]
case class Child(id: Int, parentId: Int, name: String, extra: String)
class ChildTable(tag: Tag) extends Table[Child](tag, "child") {
def id = column[Int]("id", O.PrimaryKey, O.AutoInc)
def parentId = column[Int]("parent_id")
def parent = foreignKey("parent_fk", parentId, parents)(_.id)
def name = column[String]("name")
def extra = column[String]("extra")
def * = (id, parentId, name, extra) <> (Child.tupled, Child.unapply)
}
val children = TableQuery[ChildTable]
I want to project into a case class like:
case class ChildWithParentName(id: Int, name: String, parentName: String)
The join and projection looks like:
val q = for {
c <- children
p <- parents if c.parentId === p.id
} yield (c.id,c.name,p.name)
I put this in a function and allow children
and parents
to be parameterized. The function doesn't run the query, because sometimes I want .result
and sometimes I want .result.headOption
, so my function signature is:
Query[(Rep[Int], Rep[String], Rep[String]), (Int, String, String), Seq]
I would like to create a Type on the Query side with a shape something like:
class ChildParentProjection(val id: Rep[Int],
val name: Rep[String],
val parentName[String])
so that I could get a function signature like:
Query[ChildParentProjection, ChildWithParentName, Seq]
Is that possible in slick?
Upvotes: 1
Views: 279
Reputation: 60
I don't really understand why you would like to use the class ChildParentProjection
.
if you want to return a Seq[ChildWithParentName]
when executing result
on the query, you'll have to map the tuple resulting from your monadic join to the ChildWithParentName
class like this :
val q = for {
c <- children
p <- parents if c.parentId === p.id
} yield (c.id,c.name,p.name) <> (ChildWithParentName.tupled,ChildWithParentName.unapply)
I wish I have understood your question
Upvotes: 1