davegurnell
davegurnell

Reputation: 231

Transforming/repacking the results of a Slick query

I have what I hope is a simple question about Slick. Apologies if this is well documented - I may have overlooked something in my searching.

I have an aggregate query built as follows:

def doQuery(/* ... */) = for {
  a <- Query(TableA)
  b <- a.relationship.where // ...
  c <- b.relationship.where // ...
} yield (a, b, c)

This returns me a Query[(A, B, C)].

I also have a case class:

case class Aggregate(a: A, b: B, c: C)

I'd like to transform my query to a Query[Aggregate] so my fellow developers can call .list() or .firstOption() and get a List or Option as appropriate.

I naturally went for the .map() method on Query, but it has an implicit Shape argument that I'm not sure how to handle.

Is this straightforward in Slick? We're using v1.0.1 at the moment but upgrading to 2.0 is also a possibility.

Best regards,

Dave

Upvotes: 1

Views: 218

Answers (2)

davegurnell
davegurnell

Reputation: 231

After a lot of playing around, I have concluded that this is not possible in Slick 1.

In Slick 2 you can use the <> operator to transform a projection assembled in the yield portion of the for comprehension:

def doQuery(/* ... */) = for {
  a <- Query(TableA)
  b <- a.relationship.where // ...
  c <- b.relationship.where // ...
} yield (a, b, c) <> (Aggregate.tupled, Aggregate.unapply)

This works as expected in conjunction with .list and .firstOption. I'm unsure what the consequences are of trying to use .insert, .update and .delete.

Upvotes: 3

pheaver
pheaver

Reputation: 1843

If you can modify doQuery, then you just want to do yield Aggregate(a, b, c) instead of yield (a, b, c).

Or, if you want to transform the result without modifying doQuery, then you can call .map { case (a, b, c) => Aggregate(a, b, c) } on the result of doQuery.

Upvotes: 0

Related Questions