объединение гладких запросов в один запрос

Как с помощью Slick 3.1 объединить несколько запросов в один запрос одного типа? Это не объединение или объединение, а объединение "сегментов" запроса для создания единого запроса запроса. Эти «сегменты» могут быть любыми индивидуально допустимыми запросами.

val query = TableQuery[SomeThingValid]

// build up pieces of the query in various parts of the application logic
val q1 = query.filter(_.value > 10)
val q2 = query.filter(_.value < 40)
val q3 = query.sortBy(_.date.desc)
val q4 = query.take(5)

// how to combine these into a single query ?
val finalQ = ??? q1 q2 q3 q4 ???

// in order to run in a single request
val result = DB.connection.run(finalQ.result)

РЕДАКТИРОВАТЬ: ожидаемый sql должен быть примерно таким:

SELECT * FROM "SomeThingValid" WHERE "SomeThingValid"."value" > 10 AND "SomeThingValid"."valid" < 40 ORDER BY "MemberFeedItem"."date" DESC LIMIT 5

person IUnknown    schedule 21.12.2015    source источник
comment
Я не совсем уверен, что вы ожидаете в результате. Думаю, я должен спросить: как бы вы сделали это на простом SQL?   -  person Patryk Ćwiek    schedule 21.12.2015
comment
@PatrykĆwiek обновлен примером ожидаемого sql   -  person IUnknown    schedule 21.12.2015


Ответы (3)


val q1 = query.filter(_.value > 10)
val q2 = q1.filter(_.value < 40)
val q3 = q2.sortBy(_.date.desc)
val q4 = q3.take(5)

Я думаю, вы должны сделать что-то вроде приведенного выше (и передать Querys), но если вы настаиваете на передаче «сегментов» запроса, что-то вроде этого может работать:

type QuerySegment = Query[SomeThingValid, SomeThingValid, Seq] => Query[SomeThingValid, SomeThingValid, Seq]

val q1: QuerySegment = _.filter(_.value > 10)
val q2: QuerySegment = _.filter(_.value < 40)
val q3: QuerySegment = _.sortBy(_.date.desc)
val q4: QuerySegment = _.take(5)

val finalQ = Function.chain(Seq(q1, q2, q3, q4))(query)
person danielnixon    schedule 21.12.2015
comment
да, я могу добавить предложения в запрос, цель состояла в том, чтобы взять различные запросы, которые были созданы, и объединить их для создания sql, как в примере. - person IUnknown; 22.12.2015
comment
хорошо, спасибо - это именно то, что я искал - person IUnknown; 22.12.2015
comment
причина, по которой я не могу обойти Query, заключается в том, что порядок, в котором генерируются QuerySegments, недетерминирован, но порядок, в котором я создаю запрос для фактического выполнения, очень важен. Используя технику, описанную выше, я могу взять набор сгенерированных сегментов и собрать их в правильном порядке, когда они будут готовы к выполнению. - person IUnknown; 22.12.2015

Я использовал этот «шаблон» с slick2.0.

val query = TableQuery[SomeThingValid]

val flag1, flag3 = false
val flag2, flag4 = true

val bottomFilteredQuery = if(flag1) query.filter(_.value > 10) else query
val topFilteredQuery = if(flag2) bottomFilteredQuery.filter(_.value < 40) else bottomFilteredQuery
val sortedQuery = if(flag3) topFilteredQuery.soryBy(_.date.desc) else topFilteredQuery
val finalQ = if(flag4) sortedQuery.take(5) else sortedQuery
person nikiforo    schedule 21.12.2015
comment
в моем случае это не сработает, потому что входящий запрос представляет собой недетерминированный произвольный набор. - person IUnknown; 21.12.2015

Думаю, должно работать. Но я еще не тестировал.

val users = TableQuery[Users]
val filter1: Query[Users, User, Seq] = users.filter(condition1)
val filter2: Query[Users, User, Seq] = users.filter(condition2)
(filter1 ++ filter2).result.headOption
person Lukasz Zuchowski    schedule 21.12.2015