Array aggregate subquery with Slick-pg for postgres

111 Views Asked by At

I am trying to use an aggregate function from slick-pg in a query with subquery but I am getting an Exception slick.SlickException, with message: No type for symbol s5 found for Ref s5..

This is the SQL I want to translate:

select id, customer_id, name, (
    select array_agg(uid) from (
        select uga.user_profile_id as uid 
        from user_group_association uga 
        where uga.group_id = id and uga.customer_id = customer_id) as agg_uid) as members 
from tenant_user_groups;

The result is one row per group, with the "members" column containing an array of user ids: (<uuid>, <uuid>, <string>, <uuid[]>)

My attempt at doing it in Slick:

import com.github.tminglei.slickpg.agg.PgAggFuncSupport.GeneralAggFunctions.arrayAgg

val uidArray = (customerId: Rep[CustomerId], groupId: Rep[GroupId]) =>
    assocTable
      .filter(a => a.groupId === groupId && a.customerId === customerId)
      .subquery
      .map(a => arrayAgg(a.userProfileId.?))
      .shaped.value
     
val q = table.map(t => (t.customerId, t.id, t.name, uidArray(t.customerId, t.id))) 

db.run(q.result).map(_.map(Group.tupled))

I'm using Slick-pg, the extended Postgres Profile with PgArraySupport and ArrayImplicits. The code compiles, but the above exception is thrown at runtime.

The logger "slick.jdbc.JdbcBackend.statement" won't show the statement, bc. it fails before.

I looked at the query compiler output, but it doesn't tell me much:

DEBUG slick.compiler.QueryCompiler - After phase assignUniqueSymbols:
| Bind
|   from s6: TableExpansion
|     table s7: Table tenant_user_groups
|     columns: TypeMapping
|       0: ProductNode
|         1: Path s7.id : MappedJdbcType[customer.server.domain.groups.model.GroupId -> java.util.UUID']
|         2: Path s7.customer_id : MappedJdbcType[customer.model.customer.CustomerId -> java.util.UUID']
|         3: Path s7.name : String'
|   select: Pure t9
|     value: ProductNode
|       1: Path s6.customer_id : MappedJdbcType[customer.model.customer.CustomerId -> java.util.UUID']
|       2: Path s6.id : MappedJdbcType[customer.server.domain.groups.model.GroupId -> java.util.UUID']
|       3: Path s6.name : String'
|       4: AggFuncExpr Function array_agg, ConstArray(OptionApply), ConstArray(), None, false, false
|         0: OptionApply
|           0: Path s5.user_profile_id : MappedJdbcType[customer.model.profile.UserProfileId -> java.util.UUID']

I am using Scala 2.13 on the JVM.

0

There are 0 best solutions below