java - 使用 JOOQ 的 MockDataProvider,如何设置返回的 lastId()?

标签 java unit-testing mocking jooq

注意:我没有使用Jooq的代码生成器

在 DAO 单元测试中,对 DAO 进行测试以确保在插入对象后,DAO 将 Id 设置为 last_insert_id() 从数据库返回的 Id。由于我使用的是 JOOQ 的 MockConnection 和 MockDataProvider,因此没有联系实际的数据库。

当 DAO 执行以下操作时:

DSLContext ctx = DSL.using(connection, SQLDialect.MYSQL);
//insert
//get id
BigInteger id = ctx.lastId();

JOOQ 执行以下查询:

select last_insert_id() from dual;

在我的 MockDataProvider 中,我检查何时执行此查询并相应地返回结果:

import static org.jooq.impl.DSL.dual;

//other code

@Override
public MockResult[] execute(MockExecuteContext ctx) throws SQLException {
   Field<BigInteger> id = DSL.field("", BigInteger.class);
   Record record = dual().newRecord();
   record.setValue(id, BigInteger.valueOf(1234567));
   return new MockResult[] { new MockResult(record) };             
}

当返回上面的 MockResult 时,我得到以下异常

java.lang.IllegalArgumentException: Field () is not contained in Row ()

为 last_insert_id() 查询填充 MockResult 的正确方法是什么?

最佳答案

这是 DSLContext.lastID()MockDataProvider 的有效实现:

BigInteger expected = BigInteger.valueOf(1234567);
DSLContext ctx = DSL.using(new MockConnection(c -> {
    Field<BigInteger> id = DSL.field("last_insert_id()", BigInteger.class);
    Record record = DSL.using(MYSQL).newRecord(id);
    record.setValue(id, expected);
    return new MockResult[] { new MockResult(record) };
}), SQLDialect.MYSQL);

assertEquals(expected, ctx.lastID());

您的方法基本上有两处错误:

字段名

您选择的字段的字段名称实际上称为 last_insert_id()(至少在 jOOQ 3.5.3 中是这样),因此您还必须这样命名您的模拟字段:

    Field<BigInteger> id = DSL.field("last_insert_id()", BigInteger.class);

记录

您必须创建一个已包含您的字段的记录。 dual() 表包含一个不同的字段。 jOOQ 生成 from dual 查询的事实与您必须生成包含 last_insert_id() 字段的 Record 这一事实无关:

    Record record = DSL.using(MYSQL).newRecord(id);

警告

当然,您对 3.5.3 中的 jOOQ 实现做出了强有力的假设。不能保证 DSLContext.lastID() 生成的确切查询将始终是

select last_insert_id() from dual

关于java - 使用 JOOQ 的 MockDataProvider,如何设置返回的 lastId()?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29081837/

相关文章:

java - 什么时候应该使用 Java 的 StringWriter?

java - 通过知道名称选择 JLabel

java - Mockito 模拟调用点指向 Junit 代码(ParentRunner)

java - 模拟数据库驱动程序

java.lang.UnsupportedOperationException ImmutableList.remove 当我没有使用 ImmutableList 时

Java:反向排序而不保持顺序

ruby-on-rails-3 - 出现错误:Shoulda::Matchers 未定义方法 `greater_than_or_equal_to'

c++ - CppUnitTestFramework 和测试 "vector subscript out of range"

unit-testing - Visual Studio 2015 测试资源管理器在更新后不显示任何测试

c# - 如何模拟新创建的对象?