Files
matrix/cygnus-onprem-db/src/test/java/com/cygnus/db/JdbcCygnusDbExecutorTest.java

87 lines
3.7 KiB
Java

package com.cygnus.db;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertThrows;
import static org.junit.jupiter.api.Assertions.assertTrue;
import java.sql.Connection;
import java.sql.Statement;
import java.util.Map;
import java.util.concurrent.atomic.AtomicInteger;
import org.h2.jdbcx.JdbcDataSource;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
class JdbcCygnusDbExecutorTest {
private JdbcCygnusDbExecutor executor;
@BeforeEach
void setUp() throws Exception {
JdbcDataSource dataSource = new JdbcDataSource();
dataSource.setURL("jdbc:h2:mem:cygnus;DB_CLOSE_DELAY=-1");
try (Connection connection = dataSource.getConnection(); Statement statement = connection.createStatement()) {
statement.execute("DROP TABLE IF EXISTS person");
statement.execute("CREATE TABLE person (id bigint generated by default as identity primary key, name varchar(100), active boolean)");
statement.execute("INSERT INTO person(name, active) VALUES ('Asha', true), ('Ravi', false)");
}
Map<Integer, QueryDefinition> queries = Map.of(
1, new QueryDefinition(1, QueryType.SELECT,
"select id, name from person where active = ? order by id"),
2, new QueryDefinition(2, QueryType.INSERT,
"insert into person(name, active) values (?, ?)"),
3, new QueryDefinition(3, QueryType.UPDATE,
"update person set active = ? where name = ?"),
4, new QueryDefinition(4, QueryType.DELETE,
"delete from person where name = ?"),
5, new QueryDefinition(5, QueryType.PROCEDURE, "call abs(?)"));
executor = new JdbcCygnusDbExecutor(dataSource, queries::get, new ExecutorOptions(10, 5));
}
@Test
void mapsSelectDirectlyToRecordsAndDynamicRows() {
var people = executor.query(1, new Object[]{true}, Person.class);
assertEquals(java.util.List.of(new Person(1L, "Asha")), people);
RowView row = executor.query(1, new Object[]{true}).getFirst();
assertEquals("Asha", row.get("NAME", String.class));
assertEquals(1L, row.get("id", Long.class));
}
@Test
void executesInsertUpdateDeleteAndGeneratedKeys() {
Long id = executor.insert(2, new Object[]{"Mira", true}, Long.class);
assertTrue(id > 0);
assertEquals(1, executor.update(3, new Object[]{false, "Mira"}));
assertEquals(1, executor.delete(4, new Object[]{"Mira"}));
}
@Test
void executesProcedureAndStreamsWithoutMaterializingRows() {
assertEquals(7, executor.procedure(5, new Object[]{-7}, Integer.class));
AtomicInteger count = new AtomicInteger();
executor.stream(1, new Object[]{true},
result -> new Person(result.getLong("id"), result.getString("name")),
row -> count.incrementAndGet());
assertEquals(1, count.get());
}
@Test
void rollsBackFailedTransactions() {
assertThrows(IllegalStateException.class, () -> executor.transaction(tx -> {
tx.insert(2, new Object[]{"Rollback", true});
throw new IllegalStateException("stop");
}));
assertFalse(executor.query(1, new Object[]{true}, Person.class).stream()
.anyMatch(person -> person.name().equals("Rollback")));
}
@Test
void rejectsLegacyStringReplacementQueries() {
assertThrows(QueryDefinitionException.class, () ->
QueryDefinition.parse(513, "select!C0L!select * from person where id=val0"));
}
record Person(long id, String name) {}
}