如何将jooq multiset的结果映射到Hashmap(Java map)?



我有以下类和查询。我想使用multisetimages的结果映射到Map<String, String>(键:OrderNumber/值:FileKey),但我不知道如何做到这一点。你能帮我如何将multiset结果映射到hashmap吗?

data class User(
val id: UUID,
val name: String,
val images: Map<String, String>?
)
@Repository
@Transactional(readOnly = true)
class FetchUserRepository(private val ctx: DSLContext) {
private val user = JUser.USER
private val userImage = JUserImage.USER_IMAGE 
override fun fetch(): List<User> {
return ctx.select(
user.ID,
user.NAME,
multiset(
select(userImage.ORDER_NUMBER.cast(String::class.java), userImage.FILE_KEY)
.from(userImage)
.where(userImage.USER_ID.eq(user.ID))
).convertFrom { r -> r.map(mapping(???)) } // I'm not sure how to map the result to hashmap
)
.from(user)
.fetchInto(User::class.java)
}

jOOQ 3.16 solution

您的multiset()表达式的类型是Result<Record2<String, String>>,因此您可以使用Result.intoMap(Field, Field)方法,甚至可以使用Records.intoMap()收集器使用Result.collect(Collector),这允许避免重复字段名:

{ r -> r.collect(Records.intoMap()) }

我在一篇博客文章中对此作了更详细的解释,在这里。

jOOQ 3.17 solution

实际上,这看起来非常有用和强大,让我们使用一些扩展(位于jOOQ-kotlin扩展模块中)在现有API的基础上添加一些便利:

// New extension functions, e.g.
fun <R : Record, E> Field<Result<R>>.collecting(collector: Collector<R, *, E>)
= convertFrom { it.collect(collector) }
fun <K, V> Field<Result<Record2<K, V>>>.intoMap(): Field<Map<K, V>> 
= collecting(Records.intoMap())
// And then, you can write:
multiset(...).intoMap()

功能请求在这里:https://github.com/jOOQ/jOOQ/issues/13538

除了Lukas的答案,我想提供jsonObject&jsonObjectAgg.

这个查询的结果将以JSON格式返回,并且它可以很容易地通过Jackson或其他方式投射到目标类。(当涉及到目标类中的嵌套集合时,这是一个非常强大的特性)

我相信这是jOOQ作为MULTISET最酷的功能之一:)

data class User(
val id: UUID,
val name: String,
val images: Map<String, String>?
)
@Repository
@Transactional(readOnly = true)
class FetchUserRepository(private val ctx: DSLContext) {
private val user = JUser.USER
private val userImage = JUserImage.USER_IMAGE
override fun fetch(): List<User> {
return ctx.select(
jsonObject(
key("id").value(user.ID),
key("name").value(user.NAME),
key("images").value(
field(
select(
jsonObjectAgg(
userImage.ORDER_NUMBER.cast(String::class.java),
userImage.FILE_KEY
)
)
.from(userImage)
.where(userImage.USER_ID.eq(user.ID))
)
)
)
)
.from(user)
.fetchInto(User::class.java)
}
}

最新更新