jooq动态with子句

xggvc2p6  于 2021-07-26  发布在  Java
关注(0)|答案(1)|浏览(529)

我在jooq中找不到关于如何用子句(即公共表表达式/cte)动态构造的文档。我的用例是:
我需要嵌套动态创建的列,以便从这些动态创建的列生成新数据
例如,我正在创建一个新字段,它是完全外部联接的非空结果。此字段仅在执行查询时可用,因此我需要将其存储在with子句中,以便在其他查询中引用它以进行其他计算。
理想情况下,我可以动态地请求with子句类型的查询,并且可以通过将这个连接的数据集放在它自己的cte中以在下游引用中使用来整理这个依赖关系。
我尝试使用以下方法,但运气不佳:

SelectQuery<Record> query =
        getQuery(
            dslContext,
            selectFields,
            fromClause,
            groupFields,
            conditionClause,
            orderFields,
            query.getOffset(),
            query.getLimit());

    // WORKS JUST FINE
    Supplier<Stream<Map<String, Object>>> results = () ->
        query
            .fetchStream()
            .map(Record::intoMap);

    // make a nested query here. static for now.
    // DOES NOT WORK
    Supplier<Stream<Map<String, Object>>> resultsWith =
        () ->
            DSL.with("s1")
                .as(query) // Shouldn't I be able to reference a SelectQuery here?
                .select()
                .from(table(name("s1")))
                .fetchStream()
                .map(Record::intoMap);

query.tostring()如下所示:

select 
  table1.field1,
  coalesce( 
    table1.id, 
    table2.id) as table1.id_table2.id, 
  count(*) as table2.field1.count, 
  sum(table2.field2) as table2.field2.sum
  from table1.table1 as table1
  full outer join table2.table2 as table2
  on table1.id = table2.id
  where table1.field2 < 3000.0
  group by 
  table1.id_table2.id,
  table1.field1
  order by table1.field1 asc
  limit 100

我想做的至少是参考 coalesced 在其他下游查询中的上述字段。理想情况下,在jooq中构造with子句时,我完全不会受到动态引用的方式或数量的限制。最后,我希望能够动态创建这样的查询,这些查询显示引用CTE的CTE:

-- WITH Clause usage is preferrable
with
  myFirstSelection as (
    select
      (id + 100) as newfield
    from table1.table1 n
  ),
  mySecondSelection as (
    select
      (newField + 200) as newerField
    from myFirstSelection
  )
select

* 

from mySecondSelection
;

-- Inline queries, while not ideal, would be permissible
select 

* 

from (
  select
  (newField + 200) as newerField
  from (
    select
      (id + 100) as newField
    from table1.table1 n
  ) as myFirstSelection
) as mySecondSelection
;

那有可能吗?还是只限于静态表和静态选择?

链接

堆栈溢出

不支持“with”子句
在约克参加cte
另一个cte中的参考cte#1
另一个cte中的参考cte#2

jooq网站

生成sql:with子句
v3.13手册:带条款
使用Step javadocs

github公司

已删除的旧ctetests存储库
问题454:添加cte支持
问题3174:添加带dml的cte支持
问题3175:嵌套cte
问题4474:来自普通sql的表单cte

谷歌集团

如何处理常用表表达式的名称等?
结合dsl使用任意sql字符串作为cte
在postgres中使用递归cte
ctes、递归ctes和jooq
递归cte
递归cte

t9aqgxwy

t9aqgxwy1#

这个问题是jackson在json负载中的一个属性反序列化的问题,这个属性被转换为我的查询。我得到了一个 NullPointerException 当其中一个属性转换为查询类的一部分时。关于 jOOQ ,此示例运行良好。此外,这是一个测试查询,通过引用结果集中的相对位置对第一个字段求和:

/* Output looks like this : 
    +-----------------+
    |sum_of_everything|
    +-----------------+
    |              100|
    +-----------------+
     */

    Supplier<Stream<Map<String, Object>>> resultsWith =
        () ->
            dslContext
                .with("s1")
                .as(query)
                .select(sum(field("1", Integer.class)).as("sum_of_everything"))
                .from(table(name("s1")))
                .fetchStream()
                .map(Record::intoMap);

这个提供者可以作为restful框架中的响应返回,以将结果流式返回给请求者。

相关问题