首页 > 解决方案 > 允许 Simpleflatmapper 忽略构造函数并仅使用 setter

问题描述

以下映射器配置工作正常(MyPojo 没有其他构造函数)

class MyPojo {
    private Long id;
    private String name;

    // No constructor
}
DynamicJdbcMapper<MyPojo> mapper = JdbcMapperFactory.newInstance().addKeys("id").newMapper(MyPojo.class);
ResultQuery<?> query = dsl
        .select(
                MY_TABLE.ID.as("id"),
                MY_TABLE.NAME.as("name"))
        .from(MY_TABLE).where(MY_TABLE.ID.eq(1));

MyPojo pojo = mapper.stream(query.fetchResultSet()).findFirst().orElse(null);

但就我而言,MyPojo 是一个遗留类,并带有一大堆构造函数:

class MyPojo {
    private Long id;
    private String name;

    public MyPojo(Long id) {
        this.id = id;
    }
}

这会导致映射器无法工作。我收到以下错误:

Could not find eligible property for 'name' on  class com.bla.bla.MyPojo

很明显,映射器正试图寻找一个参数与 SELECT 子句中的每个列匹配的构造函数。我不想添加重载的构造函数(SELECT 列列表很大)。

如何设置映射器来调用设置器而不是构造器?

标签: javasqljooqsetter-injectionsimpleflatmapper

解决方案


SimpleFlatMapper 解决方案

这个答案并不能帮助您使用 SimpleFlatMapper 实现这一点(我不太了解),但是由于这个问题的未来访问者可能对开箱即用的 jOOQ 解决方案感兴趣,所以无论如何我都会回答。

开箱即用的 jOOQ 解决方案

从 jOOQ 3.14 开始,没有一种简单的方法可以防止 jOOQDefaultRecordMapper使用调用其中一个构造函数,而不是直接为属性赋值。从未来的 jOOQ 版本开始,这将成为可能:https ://github.com/jOOQ/jOOQ/issues/10349

由于您已经为查询的所有列设置了别名,因此您可以添加一个带有注释的构造函数@ConstructorProperties以及查询中的确切名称集:

class MyPojo {
    private Long id;
    private String name;

    public MyPojo(Long id) {
        this.id = id;
    }

    @ConstructorProperties({ "id", "name" })
    public MyPojo(Long id, String name) {
        this.id = id;
        this.name = name;
    }
}

我知道你说过你不想添加更多的构造函数,但也许你可以用你的 IDE 生成这个?


推荐阅读