Refactor move into ebean-core directory (#2066)

This commit is contained in:
Rob Bygrave authored and GitHub committed 2020-10-08 21:31:18 +13:00
1 parent 7193b035b2
commit 7c36439daf
3207 files changed
+392 -42499

No files matched your search

@@ -0,0 +1,309 @@
package io.ebean;
import io.ebean.annotation.PersistBatch;
import io.ebean.annotation.Platform;
import io.ebean.cache.ServerCacheStatistics;
import io.ebean.config.dbplatform.IdType;
import io.ebean.meta.MetaTimedMetric;
import io.ebean.meta.ServerMetrics;
import io.ebean.util.StringHelper;
import io.ebeaninternal.api.SpiEbeanServer;
import io.ebeaninternal.api.SpiQuery;
import io.ebeaninternal.api.SpiTransaction;
import io.ebeaninternal.server.core.HelpCreateQueryRequest;
import io.ebeaninternal.server.core.OrmQueryRequest;
import io.ebeaninternal.server.deploy.BeanDescriptor;
import io.ebeaninternal.server.expression.platform.DbExpressionHandler;
import io.ebeaninternal.server.expression.platform.DbExpressionHandlerFactory;
import io.ebeaninternal.server.transaction.TransactionScopeManager;
import org.assertj.core.api.AbstractCharSequenceAssert;
import org.junit.After;
import org.junit.Rule;
import org.junit.rules.TestName;
import org.junit.runner.RunWith;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.tests.model.basic.Country;
import java.sql.Types;
import java.util.List;
import java.util.stream.Collectors;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.fail;
@RunWith(ConditionalTestRunner.class)
public abstract class BaseTestCase {
protected static Logger logger = LoggerFactory.getLogger(BaseTestCase.class);
@Rule public TestName name = new TestName();
@After
public void checkForLeak() {
TransactionScopeManager scope = spiEbeanServer().getTransactionManager().scope();
SpiTransaction trans = scope.getInScope();
if (trans != null) {
String msg = getClass().getSimpleName() + "." + name.getMethodName() + " did not clear threadScope:" + trans;
scope.clearExternal(); // clear for next test
fail(msg);
}
}
/**
* this is the clock delta that may occur between testing machine and db server.
* If the clock delta of DB server is in future, an "asOf" query may not find the
* correct entry.
*
* Note: That some tests may use a Thread.sleep to wait, so that the local system clock
* can catch up. So don't set that to a too high value.
*/
public static final int DB_CLOCK_DELTA;
static {
String s = System.getProperty("dbClockDelta");
if (s != null && !s.isEmpty()) {
DB_CLOCK_DELTA = Integer.parseInt(s);
} else {
DB_CLOCK_DELTA = 100;
}
try {
// First try, if we get the default server. If this fails, all tests will fail.
DB.getDefault();
} catch (Throwable e) {
logger.error("Fatal error while getting ebean-server. Exiting...", e);
System.exit(1);
}
}
protected void clearAllL2Cache() {
server().getServerCacheManager().clearAll();
}
protected void resetAllMetrics() {
server().getMetaInfoManager().resetAllMetrics();
}
protected ServerMetrics collectMetrics() {
return server().getMetaInfoManager().collectMetrics();
}
protected List<MetaTimedMetric> visitTimedMetrics() {
return collectMetrics().getTimedMetrics();
}
protected List<MetaTimedMetric> sqlMetrics() {
List<MetaTimedMetric> timedMetrics = visitTimedMetrics();
return timedMetrics.stream()
.filter((it) -> it.getName().startsWith("sql.") || it.getName().startsWith("orm."))
.collect(Collectors.toList());
}
protected SpiTransaction getInScopeTransaction() {
return spiEbeanServer().getTransactionManager().scope().getInScope();
}
/**
* Return the generated sql trimming column alias if required.
*/
protected String sqlOf(Query<?> query) {
return trimSql(query.getGeneratedSql());
}
/**
* Return the generated sql trimming column alias if required.
*/
protected String sqlOf(Query<?> query, int columns) {
return trimSql(query.getGeneratedSql(), columns);
}
protected void assertSqlBind(String sql) {
assertThat(sql).contains("-- bind");
}
protected void assertSqlBind(List<String> sql, int i) {
assertThat(sql.get(i)).contains("-- bind");
}
protected void assertSqlBind(List<String> sql, int from, int to) {
for (int i = from; i <= to; i++) {
assertThat(sql.get(i)).contains("-- bind");
}
}
protected AbstractCharSequenceAssert<?, String> assertSql(Query<?> query, int count) {
return org.assertj.core.api.Assertions.assertThat(sqlOf(query, count));
}
protected AbstractCharSequenceAssert<?, String> assertSql(Query<?> query) {
return org.assertj.core.api.Assertions.assertThat(sqlOf(query));
}
protected AbstractCharSequenceAssert<?, String> assertSql(String sql) {
return org.assertj.core.api.Assertions.assertThat(trimSql(sql));
}
protected String trimSql(String sql) {
if (sql.contains(" c0,") || sql.contains(" c0 ") || sql.contains(" c1,") || sql.contains(" c1 ")) {
// for oracle we include column alias so lets remove those
return trimSql(sql, 10);
}
return sql;//trimSql(sql, 0);
}
/**
* Trim out column alias if required from the generated sql.
*/
protected String trimSql(String sql, int columns) {
for (int i = 0; i <= columns; i++) {
sql = StringHelper.replace(sql, " c" + i + ",", ",");
}
for (int i = 0; i <= columns; i++) {
sql = StringHelper.replace(sql, " c" + i + " ", " ");
}
return sql;
}
public boolean isPlatformCaseSensitive() {
return spiEbeanServer().getDatabasePlatform().isCaseSensitiveCollation();
}
/**
* MS SQL Server does not allow setting explicit values on identity columns
* so tests that do this need to be skipped for SQL Server.
*/
public boolean isSqlServer() {
return Platform.SQLSERVER == platform();
}
public boolean isH2() {
return Platform.H2 == platform();
}
public boolean isHSqlDb() {
return Platform.HSQLDB == platform();
}
public boolean isOracle() {
return Platform.ORACLE == platform();
}
public boolean isNuoDb() {
return Platform.NUODB == platform();
}
public boolean isDb2() {
return Platform.DB2 == platform();
}
public boolean isPostgres() {
return Platform.POSTGRES == platform().base();
}
public boolean isMySql() {
return Platform.MYSQL == platform();
}
public boolean isMariaDB() {
return Platform.MARIADB == platform();
}
public boolean isHana() {
return Platform.HANA == platform();
}
public boolean isPlatformBooleanNative() {
return Types.BOOLEAN == spiEbeanServer().getDatabasePlatform().getBooleanDbType();
}
public boolean isPlatformOrderNullsSupport() {
return isH2() || isPostgres();
}
public boolean isPlatformSupportsDeleteTableAlias() {
return spiEbeanServer().getDatabasePlatform().isSupportsDeleteTableAlias();
}
public boolean isPersistBatchOnCascade() {
return spiEbeanServer().getDatabasePlatform().getPersistBatchOnCascade() != PersistBatch.NONE;
}
/**
* Wait for the L2 cache to propagate changes post-commit.
*/
protected void awaitL2Cache() {
// do nothing, used to thread sleep
}
protected <T> BeanDescriptor<T> getBeanDescriptor(Class<T> cls) {
return spiEbeanServer().getBeanDescriptor(cls);
}
protected <T> ServerCacheStatistics getBeanCacheStats(Class<T> cls, boolean reset) {
return server().getServerCacheManager().getBeanCache(cls).getStatistics(reset);
}
protected Platform platform() {
return spiEbeanServer().getDatabasePlatform().getPlatform().base();
}
protected IdType idType() {
return spiEbeanServer().getDatabasePlatform().getDbIdentity().getIdType();
}
protected SpiEbeanServer spiEbeanServer() {
return (SpiEbeanServer) DB.getDefault();
}
protected EbeanServer server() {
return Ebean.getDefaultServer();
}
protected void loadCountryCache() {
DB.find(Country.class)
.setBeanCacheMode(CacheMode.PUT)
.findList();
}
/**
* Platform specific IN clause assert.
*/
protected void platformAssertIn(String sql, String containsIn) {
if (isPostgres()) {
assertThat(sql).contains(containsIn+" = any(");
} else {
assertThat(sql).contains(containsIn+" in ");
}
// H2 contains("where t0.name in (select * from table(x varchar = ?)");
}
/**
* Platform specific NOT IN clause assert.
*/
protected void platformAssertNotIn(String sql, String containsIn) {
if (isPostgres()) {
assertThat(sql).contains(containsIn+" != all(");
} else {
assertThat(sql).contains(containsIn+" not in ");
}
}
/**
* Platform specific CONCAT clause.
*/
protected String concat(String property0, String separator, String property1) {
return concat(property0, separator, property1, null);
}
protected String concat(String property0, String separator, String property1, String suffix) {
DbExpressionHandler dbExpressionHandler = DbExpressionHandlerFactory.from(spiEbeanServer().getDatabasePlatform());
return dbExpressionHandler.concat(property0, separator, property1, suffix);
}
protected <T> OrmQueryRequest<T> createQueryRequest(SpiQuery.Type type, Query<T> query, Transaction t) {
return HelpCreateQueryRequest.create(server(), type, query, t);
}
}
@@ -0,0 +1,60 @@
package io.ebean;
import io.ebeaninternal.server.rawsql.SpiRawSql;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class ColumnTest {
SpiRawSql.ColumnMapping.Column col(int indexPos, String dbColumn, String dbAlias) {
return new SpiRawSql.ColumnMapping.Column(indexPos, dbColumn, dbAlias);
}
@Test
public void equals_when_same() {
assertSame(col(1, "name", null), col(1, "name", null));
}
@Test
public void equals_when_same_withAlias() {
assertSame(col(1, "t0.name", "t0"), col(1, "t0.name", "t0"));
}
@Test
public void equals_when_diffIndex() {
assertDifferent(col(1, "name", null), col(2, "name", null));
}
@Test
public void equals_when_diffProperty() {
assertDifferent(col(1, "name", null), col(1, "diffName", null));
}
@Test
public void equals_when_diffAlias() {
assertDifferent(col(1, "t1.name", "t1"), col(1, "t1.name", "t0"));
}
@Test
public void equals_when_diffAliasNullLast() {
assertDifferent(col(1, "t1.name", "t1"), col(1, "t1.name", null));
}
@Test
public void equals_when_diffAliasNullFirst() {
assertDifferent(col(1, "t1.name", null), col(1, "t1.name", "t1"));
}
private void assertSame(Object key, Object key1) {
assertThat(key).isEqualTo(key1);
assertThat(key.hashCode()).isEqualTo(key1.hashCode());
}
private void assertDifferent(Object key, Object key1) {
assertThat(key).isNotEqualTo(key1);
assertThat(key.hashCode()).isNotEqualTo(key1.hashCode());
}
}
@@ -0,0 +1,48 @@
package io.ebean;
import io.ebean.annotation.ForPlatform;
import io.ebean.annotation.IgnorePlatform;
import io.ebean.annotation.Platform;
import org.junit.runner.notification.RunNotifier;
import org.junit.runners.BlockJUnit4ClassRunner;
import org.junit.runners.model.FrameworkMethod;
import org.junit.runners.model.InitializationError;
/**
* This testrunner checks for an {@link IgnorePlatform} annotation and ignores the test.
*
* @author Roland Praml, FOCONIS AG
*/
public class ConditionalTestRunner extends BlockJUnit4ClassRunner {
public ConditionalTestRunner(Class<?> klass) throws InitializationError {
super(klass);
}
@Override
public void runChild(FrameworkMethod method, RunNotifier notifier) {
ForPlatform forPlatform = method.getAnnotation(ForPlatform.class);
if (forPlatform != null) {
if (!platformMath(forPlatform.value())) {
notifier.fireTestIgnored(describeChild(method));
return;
}
}
IgnorePlatform ignore = method.getAnnotation(IgnorePlatform.class);
if (ignore == null || !platformMath(ignore.value())) {
super.runChild(method, notifier);
} else {
notifier.fireTestIgnored(describeChild(method));
}
}
private boolean platformMath(Platform[] platforms) {
Platform basePlatform = DB.getDefault().getPlatform().base();
for (Platform platform : platforms) {
if (platform.equals(basePlatform)) {
return true;
}
}
return false;
}
}
@@ -0,0 +1,38 @@
package io.ebean;
import io.ebean.annotation.ForPlatform;
import io.ebean.annotation.Platform;
import org.junit.Test;
import java.util.Properties;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
public class DbPrimaryTest extends BaseTestCase {
@Test
public void testIsSkipPrimaryServer() {
DbPrimary.setSkip(true);
assertTrue(DbPrimary.isSkip());
DbPrimary.setSkip(false);
assertFalse(DbPrimary.isSkip());
}
@Test
@ForPlatform(Platform.H2)
public void testGetPrimaryServerName() {
String primaryServerName = DbPrimary.getDefaultServerName();
assertEquals("h2", primaryServerName);
}
@Test
public void testLoadProperties() {
Properties properties = DbPrimary.getProperties();
assertTrue(!properties.isEmpty());
}
}
@@ -0,0 +1,452 @@
package io.ebean;
import io.ebean.annotation.ForPlatform;
import io.ebean.annotation.Platform;
import io.ebean.meta.MetaQueryMetric;
import io.ebean.meta.MetaTimedMetric;
import io.ebean.meta.ServerMetrics;
import org.ebeantest.LoggedSqlCollector;
import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.junit.Test;
import org.tests.model.basic.Contact;
import org.tests.model.basic.ResetBasicData;
import java.time.OffsetDateTime;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
public class DtoQueryFromOrmTest extends BaseTestCase {
@BeforeClass
public static void resetStats() {
DB.getDefault().getMetaInfoManager().resetAllMetrics();
}
@AfterClass
public static void reportStats() {
ServerMetrics metrics = DB.getDefault().getMetaInfoManager().collectMetrics();
for (MetaQueryMetric metric : metrics.getQueryMetrics()) {
System.out.println(metric);
}
System.out.println("-- transaction metrics --");
for (MetaTimedMetric metric : metrics.getTimedMetrics()) {
System.out.println(metric);
}
}
private static final ProfileLocation loc0 = ProfileLocation.create();
@ForPlatform(Platform.H2)
@Test
public void testPlanHits() {
ResetBasicData.reset();
resetAllMetrics();
String[] prefix = {"Bl", "B", "Red", "jim"};
for (String val : prefix) {
DB.find(Contact.class)
.setProfileLocation(loc0)
.select("email, " + concat("lastName", ", ", "firstName") + " as fullName").where()
.istartsWith(concat("lastName", ", ", "firstName"), val).order().asc("lastName").setMaxRows(10)
.asDto(ContactDto.class).setLabel("prefixLoop").findList();
}
ServerMetrics metrics = collectMetrics();
List<MetaQueryMetric> stats = metrics.getQueryMetrics();
for (MetaQueryMetric stat : stats) {
long meanMicros = stat.getMean();
assertThat(meanMicros).isLessThan(900_000);
assertThat(stat.getLocation()).isSameAs(loc0.location());
}
assertThat(stats).hasSize(1);
assertThat(stats.get(0).getCount()).isEqualTo(4);
}
@ForPlatform(Platform.H2)
@Test
public void selectFormulaWith_bindPositionedParameters() {
ResetBasicData.reset();
LoggedSqlCollector.start();
List<Contact> list = DB.find(Contact.class)
.select("email, concat(lastName, ISO_WEEK(?)) as lastName")
.setMaxRows(10)
.setParameter(1, OffsetDateTime.now())
.findList();
assertThat(list).isNotEmpty();
List<String> sql = LoggedSqlCollector.stop();
assertThat(sql).hasSize(1);
assertSql(sql.get(0)).contains("select t0.id, t0.email, concat(t0.last_name, ISO_WEEK(?)) lastName from contact");
}
// @ForPlatform(Platform.H2)
// @Test
// public void selectFormulaWith_bindNamedParameters_FAILS_namedParamsNotSupportedInSelectClause() {
//
// ResetBasicData.reset();
//
// LoggedSqlCollector.start();
//
// List<Contact> list = DB.find(Contact.class)
// .select("email, concat(lastName, ISO_WEEK(:date)) as lastName")
// .setMaxRows(10)
// .setParameter("date", OffsetDateTime.now())
// .findList();
//
//
// assertThat(list).isNotEmpty();
//
// List<String> sql = LoggedSqlCollector.stop();
// assertThat(sql).hasSize(2);
// assertSql(sql.get(0)).contains("select t0.id, t0.email, concat(t0.last_name, ISO_WEEK(?)) lastName from contact");
// }
@Test
public void asDto_withExplicitId() {
ResetBasicData.reset();
LoggedSqlCollector.start();
DtoQuery<ContactDto> query = DB.find(Contact.class)
// we must explicitly add the id property for DTO query (if we want it)
.select("id, email, " + concat("lastName", ", ", "firstName") + " as fullName").where().isNotNull("email")
.isNotNull("lastName").order().asc("lastName").asDto(ContactDto.class).setLabel("explicitId")
.setRelaxedMode();
List<ContactDto> dtos = query.findList();
assertThat(dtos).isNotEmpty();
for (ContactDto dto : dtos) {
assertThat(dto.getEmail()).isNotNull();
assertThat(dto.getFullName()).isNotNull();
}
List<String> sql = LoggedSqlCollector.stop();
assertSql(sql.get(0)).contains("select t0.id, t0.email, " + concat("t0.last_name", ", ", "t0.first_name")
+ " fullName from contact t0 where t0.email is not null and t0.last_name is not null order by t0.last_name");
}
@Test
public void asDto_withoutSelectClause() {
ResetBasicData.reset();
LoggedSqlCollector.start();
DtoQuery<ContactDto2> query = DB.find(Contact.class)
.where().isNotNull("email").order().asc("lastName")
.asDto(ContactDto2.class)
.setRelaxedMode();
List<ContactDto2> dtos = query.findList();
assertThat(dtos).isNotEmpty();
for (ContactDto2 dto : dtos) {
assertThat(dto.getEmail()).isNotNull();
assertThat(dto.getFirstName()).isNotNull();
assertThat(dto.getLastName()).isNotNull();
assertThat(dto.getId()).isGreaterThan(0);
}
List<String> sql = LoggedSqlCollector.stop();
assertSql(sql.get(0)).contains("select t0.id, t0.first_name, t0.last_name");
}
@Test
public void asDto_withoutExplicitId() {
ResetBasicData.reset();
LoggedSqlCollector.start();
DtoQuery<ContactDto> query = DB.find(Contact.class)
.select("email, " + concat("lastName", ", ", "firstName") + " as fullName").where().isNotNull("email")
.isNotNull("lastName").order().asc("lastName").asDto(ContactDto.class);
List<ContactDto> dtos = query.findList();
assertThat(dtos).isNotEmpty();
for (ContactDto dto : dtos) {
assertThat(dto.getEmail()).isNotNull();
assertThat(dto.getFullName()).isNotNull();
}
List<String> sql = LoggedSqlCollector.stop();
assertSql(sql.get(0)).contains("select t0.email, " + concat("t0.last_name", ", ", "t0.first_name")
+ " fullName from contact t0 where t0.email is not null and t0.last_name is not null order by t0.last_name");
}
@Test
public void example() {
ResetBasicData.reset();
LoggedSqlCollector.start();
List<ContactDto> contactDtos = DB.find(Contact.class).setLabel("emailFullName")
.select("email, " + concat("lastName", ", ", "firstName") + " as fullName").where().isNotNull("email")
.isNotNull("lastName").order().asc("lastName").setMaxRows(10).asDto(ContactDto.class).findList();
assertThat(contactDtos).isNotEmpty();
for (ContactDto dto : contactDtos) {
assertThat(dto.getEmail()).isNotNull();
assertThat(dto.getFullName()).isNotNull();
}
List<String> sql = LoggedSqlCollector.stop();
if (isSqlServer()) {
assertSql(sql.get(0)).contains("select top 10 t0.email, " + concat("t0.last_name", ", ", "t0.first_name")
+ " fullName from contact t0 where t0.email is not null and t0.last_name is not null order by t0.last_name");
} else {
assertSql(sql.get(0)).contains("select t0.email, " + concat("t0.last_name", ", ", "t0.first_name")
+ " fullName from contact t0 where t0.email is not null and t0.last_name is not null order by t0.last_name");
}
}
@Test
public void example_explicitId() {
ResetBasicData.reset();
LoggedSqlCollector.start();
List<ContactDto> contactDtos = DB.find(Contact.class)
.select("id, email, " + concat("lastName", ", ", "firstName") + " as fullName").where().isNotNull("email")
.isNotNull("lastName").order().asc("lastName").setMaxRows(10).asDto(ContactDto.class).findList();
assertThat(contactDtos).isNotEmpty();
for (ContactDto dto : contactDtos) {
assertThat(dto.getId()).isNotNull();
assertThat(dto.getFullName()).isNotNull();
assertThat(dto.getEmail()).isNotNull();
}
List<String> sql = LoggedSqlCollector.stop();
if (isSqlServer()) {
assertSql(sql.get(0)).contains("select top 10 t0.id, t0.email, "
+ concat("t0.last_name", ", ", "t0.first_name")
+ " fullName from contact t0 where t0.email is not null and t0.last_name is not null order by t0.last_name");
} else {
assertSql(sql.get(0)).contains("select t0.id, t0.email, " + concat("t0.last_name", ", ", "t0.first_name")
+ " fullName from contact t0 where t0.email is not null and t0.last_name is not null order by t0.last_name");
}
}
@Test
public void example_singleProperty() {
ResetBasicData.reset();
LoggedSqlCollector.start();
List<ContactDto> contactDtos = DB.find(Contact.class)
.select(concat("lastName", ", ", "firstName") + " as fullName").where().isNotNull("lastName").order()
.asc("lastName").asDto(ContactDto.class).setFirstRow(2).setMaxRows(5).findList();
assertThat(contactDtos).isNotEmpty();
for (ContactDto dto : contactDtos) {
assertThat(dto.getFullName()).isNotNull();
assertThat(dto.getId()).isNull();
assertThat(dto.getEmail()).isNull();
}
List<String> sql = LoggedSqlCollector.stop();
assertSql(sql.get(0)).contains("select " + concat("t0.last_name", ", ", "t0.first_name") + " fullName from contact t0 where");
}
@Test
public void example_aggregate() {
ResetBasicData.reset();
LoggedSqlCollector.start();
List<ContactTotals> contactDtos = DB.find(Contact.class).select("lastName, count(*) as totalCount").where()
.isNotNull("lastName").having().gt("count(*)", 1).order().desc("count(*)").asDto(ContactTotals.class)
.findList();
assertThat(contactDtos).isNotEmpty();
for (ContactTotals dto : contactDtos) {
assertThat(dto.getLastName()).isNotNull();
assertThat(dto.getTotalCount()).isNotNull();
}
List<String> sql = LoggedSqlCollector.stop();
assertSql(sql.get(0)).contains("select t0.last_name, count(*) totalCount from contact t0 where t0.last_name is not null group by t0.last_name having count(*) > ?");
}
@Test
public void toDto_withIsBooleanProperty() {
ResetBasicData.reset();
DB.sqlUpdate("update contact set is_member=? where last_name like ?")
.setParameters(true, "B%")
.execute();
final List<ContactMemberDto> contacts =
DB.find(Contact.class).select("lastName, isMember")
.where().eq("isMember", true)
.asDto(ContactMemberDto.class)
.findList();
assertThat(contacts).isNotEmpty();
}
@Test
public void toDto_fromExpressionList() {
ResetBasicData.reset();
List<ContactTotals> contactDtos = DB.find(Contact.class).select("lastName, count(*) as totalCount").where()
.isNotNull("lastName").asDto(ContactTotals.class).findList();
assertThat(contactDtos).isNotEmpty();
}
public static class ContactTotals {
String lastName;
Long totalCount;
@Override
public String toString() {
return "lastName:" + lastName + " total:" + totalCount;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public Long getTotalCount() {
return totalCount;
}
public void setTotalCount(Long totalCount) {
this.totalCount = totalCount;
}
}
public static class ContactDto2 {
int id;
String firstName;
String lastName;
String email;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
}
public static class ContactDto {
String email;
String fullName;
Integer id;
@Override
public String toString() {
return "id:" + id + " email:" + email + " fn:" + fullName;
}
public String getEmail() {
return email;
}
public String getFullName() {
return fullName;
}
public void setEmail(String email) {
this.email = email;
}
public void setFullName(String fullName) {
this.fullName = fullName;
}
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
}
public static class ContactMemberDto {
String lastName;
boolean member;
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public boolean isMember() {
return member;
}
public void setMember(boolean member) {
this.member = member;
}
}
}
@@ -0,0 +1,442 @@
package io.ebean;
import io.ebean.annotation.ForPlatform;
import io.ebean.annotation.Platform;
import io.ebean.meta.BasicMetricVisitor;
import io.ebean.meta.MetaQueryMetric;
import io.ebean.meta.ServerMetrics;
import org.ebeantest.LoggedSqlCollector;
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.tests.model.basic.Customer;
import org.tests.model.basic.ResetBasicData;
import java.util.Arrays;
import java.util.List;
import java.util.Optional;
import static org.assertj.core.api.Assertions.assertThat;
public class DtoQueryTest extends BaseTestCase {
private static final Logger log = LoggerFactory.getLogger(DtoQueryTest.class);
@Test
public void dto_findList_constructorMatch() {
ResetBasicData.reset();
resetAllMetrics();
DtoQuery<DCust> dtoQuery = server().findDto(DCust.class, "select id, name from o_customer");
List<DCust> list = dtoQuery.findList();
log.info(list.toString());
assertThat(list).isNotEmpty();
ServerMetrics metrics = collectMetrics();
List<MetaQueryMetric> stats = metrics.getQueryMetrics();
for (MetaQueryMetric stat : stats) {
long meanMicros = stat.getMean();
assertThat(meanMicros).isLessThan(900_000);
}
assertThat(stats).hasSize(1);
assertThat(stats.get(0).getCount()).isEqualTo(1);
}
@Test
public void dto_findEach_constructorMatch() {
ResetBasicData.reset();
LoggedSqlCollector.start();
server().findDto(DCust.class, "select id, name from o_customer where id > :id")
.setParameter("id", 0)
.findEach(it -> log.info("got " + it.getId() + " " + it.getName()));
List<String> sql = LoggedSqlCollector.stop();
assertSql(sql.get(0)).contains("select id, name from o_customer where id > ?");
}
@Test
public void dto_findEachWhile_constructorMatch() {
ResetBasicData.reset();
LoggedSqlCollector.start();
server().findDto(DCust.class, "select id, name from o_customer where id > :id order by id desc")
.setParameter("id", 0)
.findEachWhile(customer -> {
log.info("got " + customer.getId() + " " + customer.getName());
return customer.getId() > 3;
});
List<String> sql = LoggedSqlCollector.stop();
assertSql(sql.get(0)).contains("select id, name from o_customer where id > ?");
}
@Test
public void dto_findOneEmpty() {
ResetBasicData.reset();
Optional<DCust> rob = server().findDto(DCust.class, "select id, name from o_customer where name = :name")
.setParameter("name", "Fiona")
.findOneOrEmpty();
assertThat(rob.isPresent()).isTrue();
Optional<DCust> oneOrEmpty = server().findDto(DCust.class, "select id, name from o_customer where name = :name")
.setParameter("name", "DoesNotExistMyFriend")
.findOneOrEmpty();
assertThat(oneOrEmpty.isPresent()).isFalse();
}
@Test
public void dto_findOne() {
ResetBasicData.reset();
DCust fiona = server().findDto(DCust.class, "select id, name from o_customer where name = :name")
.setParameter("name", "Fiona")
.findOne();
assertThat(fiona.getName()).isEqualTo("Fiona");
DCust empty = server().findDto(DCust.class, "select id, name from o_customer where name = :name")
.setParameter("name", "DoesNotExistMyFriend")
.findOne();
assertThat(empty).isNull();
}
@Test
public void setParameter() {
ResetBasicData.reset();
final List<DCust> list =
server().findDto(DCust.class, "select id, name from o_customer where id > ? and name like ? and status = ?")
.setParameter(0)
.setParameter("Rob%")
.setParameter(Customer.Status.NEW)
.findList();
assertThat(list).isNotEmpty();
}
@Test
public void setParameters() {
ResetBasicData.reset();
final List<DCust> list =
server().findDto(DCust.class, "select id, name from o_customer where id > ? and name like ? and status = ?")
.setParameters(0, "Rob%", Customer.Status.NEW)
.findList();
assertThat(list).isNotEmpty();
}
@ForPlatform(Platform.POSTGRES)
@Test
public void dto_bindList_usingPostrgesAnyWithPositionedParameter() {
ResetBasicData.reset();
List<Integer> ids = Arrays.asList(1, 2);
List<DCust> list = server().findDto(DCust.class, "select id, name from o_customer where id = any(?)")
.setParameter(ids)
.findList();
assertThat(list).isNotEmpty();
list = server().findDto(DCust.class, "select id, name from o_customer where id in (:idList)")
.setParameter("idList", ids)
.findList();
assertThat(list).isNotEmpty();
}
@ForPlatform(Platform.POSTGRES)
@Test
public void sql_bindListParam_usingPostrgesAnyWithPositionedParameter() {
ResetBasicData.reset();
List<Integer> ids = Arrays.asList(1, 2);
List<SqlRow> list = DB.sqlQuery("select id, name from o_customer where id = any(?)")
.setParameter(1, ids)
.findList();
assertThat(list).isNotEmpty();
list = server().sqlQuery("select id, name from o_customer where id in (:idList)")
.setParameter("idList", ids)
.findList();
assertThat(list).isNotEmpty();
}
@ForPlatform(Platform.POSTGRES)
@Test
public void sqlUpdate_bindListParam_usingPostrgesAnyWithPositionedParameter() {
ResetBasicData.reset();
List<Integer> ids = Arrays.asList(999999999, 999999998);
int rows = server().sqlUpdate("update o_customer set name = ? where id = any(?)")
.setParameter(1, "Junk")
.setParameter(2, ids)
.execute();
assertThat(rows).isEqualTo(0);
}
@Test
public void dto_queryPlanHits() {
ResetBasicData.reset();
resetAllMetrics();
String[] names = {"Rob", "Fiona", "Shrek"};
for (String name : names) {
List<DCust> custs = server().findDto(DCust.class, "select c3.id, c3.name from o_customer c3 where c3.name = :name")
.setLabel("basic")
.setParameter("name", name)
.findList();
log.info("Found " + custs);
}
// collect without reset
BasicMetricVisitor basic = new BasicMetricVisitor(false, true, true, true);
server().getMetaInfoManager().visitMetrics(basic);
List<MetaQueryMetric> stats = basic.getQueryMetrics();
assertThat(stats).hasSize(1);
MetaQueryMetric queryMetric = stats.get(0);
assertThat(queryMetric.getLabel()).isEqualTo("basic");
assertThat(queryMetric.getCount()).isEqualTo(3);
assertThat(queryMetric.getName()).isEqualTo("dto.DCust_basic");
server().findDto(DCust.class, "select c4.id, c4.name from o_customer c4 where lower(c4.name) = :name")
.setLabel("basic2")
.setParameter("name", "rob")
.findList();
ServerMetrics metric2 = server().getMetaInfoManager().collectMetrics();
stats = metric2.getQueryMetrics();
assertThat(stats).hasSize(2);
log.info("stats " + stats);
}
@Test
public void dto_findList_relaxedMode() {
ResetBasicData.reset();
List<DCust3> list = server().findDto(DCust3.class, "select id, name, 42 as total, '42' as something_we_cannot_map from o_customer")
.setRelaxedMode()
.findList();
log.info(list.toString());
assertThat(list).isNotEmpty();
}
@Test
public void dto_findList_relaxedMode_defaultConstructor() {
ResetBasicData.reset();
List<DCust2> list = server().findDto(DCust2.class, "select id, '42' as something_we_cannot_map, name from o_customer")
.setRelaxedMode()
.findList();
log.info(list.toString());
assertThat(list).isNotEmpty();
}
@Test
public void dto_findList_constructorPlusMatch() {
ResetBasicData.reset();
String sql = "select c.id, c.name, count(o.id) as totalOrders " +
"from o_customer c " +
"join o_order o on o.kcustomer_id = c.id " +
"where c.name like :name " +
"group by c.id, c.name";
List<DCust> dtos = server().findDto(DCust.class, sql)
.setParameter("name", "Rob")
.findList();
log.info(dtos.toString());
assertThat(dtos).isNotEmpty();
}
@Test
public void dto_findList_setters() {
ResetBasicData.reset();
DtoQuery<DCust2> dtoQuery = server().findDto(DCust2.class, "select id, name from o_customer");
List<DCust2> list = dtoQuery.findList();
assertThat(list).isNotEmpty();
}
@Test
public void dto3_findList_constructorMatch() {
ResetBasicData.reset();
List<DCust3> robs = server().findDto(DCust3.class, "select id, name, 42 as totalOrders from o_customer where name like ?")
.setParameter(1, "Rob")
.setMaxRows(10)
.findList();
log.info(robs.toString());
assertThat(robs).isNotEmpty();
}
@Test
public void dto3_findList_settersMatch() {
ResetBasicData.reset();
List<DCust3> robs = server().findDto(DCust3.class, "select id, name from o_customer where name = :name")
.setParameter("name", "Rob")
.findList();
log.info(robs.toString());
assertThat(robs).isNotEmpty();
}
public static class DCust {
final Integer id;
final String name;
int totalOrders;
public DCust(Integer id, String name) {
this.id = id;
this.name = name;
}
@Override
public String toString() {
return "id:" + id + " name:" + name + " totalOrders:" + totalOrders;
}
public Integer getId() {
return id;
}
public String getName() {
return name;
}
public int getTotalOrders() {
return totalOrders;
}
public void setTotalOrders(int totalOrders) {
this.totalOrders = totalOrders;
}
}
public static class DCust2 {
Integer id;
String name;
@Override
public String toString() {
return "id:" + id + " name:" + name;
}
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
public static class DCust3 {
Integer id;
String name;
int totalOrders;
public DCust3() {
}
public DCust3(Integer id, String name, int totalOrders) {
this.id = id;
this.name = name;
this.totalOrders = totalOrders;
}
@Override
public String toString() {
return "id:" + id + " name:" + name + " totalOrders:" + totalOrders;
}
public Integer getId() {
return id;
}
public String getName() {
return name;
}
public int getTotalOrders() {
return totalOrders;
}
public void setTotalOrders(int totalOrders) {
this.totalOrders = totalOrders;
}
public void setId(Integer id) {
this.id = id;
}
public void setName(String name) {
this.name = name;
}
}
}
@@ -0,0 +1,110 @@
package io.ebean;
import io.ebean.config.CurrentTenantProvider;
import io.ebean.config.ServerConfig;
import io.ebean.config.TenantCatalogProvider;
import io.ebean.config.TenantDataSourceProvider;
import io.ebean.config.TenantMode;
import io.ebean.config.TenantSchemaProvider;
import io.ebean.config.dbplatform.mysql.MySqlPlatform;
import io.ebean.config.dbplatform.postgres.PostgresPlatform;
import org.junit.Test;
import org.mockito.Mockito;
import javax.sql.DataSource;
public class EbeanServerFactory_MultiTenancy_Test extends BaseTestCase {
/**
* Tests using multi tenancy per database
*/
@Test
public void create_new_server_with_multi_tenancy_db() {
String tenant = "customer";
CurrentTenantProvider tenantProvider = Mockito.mock(CurrentTenantProvider.class);
Mockito.doReturn(tenant).when(tenantProvider).currentId();
DataSource mockedDataSource = Mockito.mock(DataSource.class);
TenantDataSourceProvider dataSourceProvider = Mockito.mock(TenantDataSourceProvider.class);
Mockito.doReturn(mockedDataSource).when(dataSourceProvider).dataSource(tenant);
ServerConfig config = new ServerConfig();
config.setName("multiTenantDb");
config.loadFromProperties();
config.setRegister(false);
config.setDefaultServer(false);
config.setTenantMode(TenantMode.DB);
config.setCurrentTenantProvider(tenantProvider);
config.setTenantDataSourceProvider(dataSourceProvider);
// When TenantMode.DB we don't really want to run DDL
// and we want to explicitly specify the Database platform
//config.setDdlGenerate(false);
//config.setDdlRun(false);
config.setDatabasePlatform(new PostgresPlatform());
EbeanServerFactory.create(config);
}
/**
* Tests using multi tenancy per schema
*/
@Test
public void create_new_server_with_multi_tenancy_schema() {
String tenant = "customer";
CurrentTenantProvider tenantProvider = Mockito.mock(CurrentTenantProvider.class);
Mockito.doReturn(tenant).when(tenantProvider).currentId();
TenantSchemaProvider schemaProvider = Mockito.mock(TenantSchemaProvider.class);
Mockito.doReturn("tenant_schema").when(schemaProvider).schema(tenant);
ServerConfig config = new ServerConfig();
config.setName("h2");
config.loadFromProperties();
config.setRegister(false);
config.setDefaultServer(false);
config.setTenantMode(TenantMode.SCHEMA);
config.setCurrentTenantProvider(tenantProvider);
config.setTenantSchemaProvider(schemaProvider);
config.setDdlRun(false);
config.setDatabasePlatform(new MySqlPlatform());
EbeanServerFactory.create(config);
}
/**
* Tests using multi tenancy per schema
*/
@Test
public void create_new_server_with_multi_tenancy_catalog() {
String tenant = "customer";
CurrentTenantProvider tenantProvider = Mockito.mock(CurrentTenantProvider.class);
Mockito.doReturn(tenant).when(tenantProvider).currentId();
TenantCatalogProvider catalogProvider = Mockito.mock(TenantCatalogProvider.class);
Mockito.doReturn("tenant_catalog").when(catalogProvider).catalog(tenant);
ServerConfig config = new ServerConfig();
config.setName("h2");
config.loadFromProperties();
config.setRegister(false);
config.setDefaultServer(false);
config.setTenantMode(TenantMode.CATALOG);
config.setCurrentTenantProvider(tenantProvider);
config.setTenantCatalogProvider(catalogProvider);
config.setDdlRun(false);
config.setDatabasePlatform(new MySqlPlatform());
EbeanServerFactory.create(config);
}
}
@@ -0,0 +1,67 @@
package io.ebean;
import io.ebean.config.DatabaseConfig;
import io.ebean.config.ServerConfig;
import io.ebean.event.ServerConfigStartup;
import org.junit.Test;
import org.tests.model.basic.UTDetail;
import static org.assertj.core.api.Assertions.assertThat;
public class EbeanServerFactory_ServerConfigStart_Test {
@Test
public void test() throws InterruptedException {
ServerConfig config = new ServerConfig();
config.setName("h2");
config.loadFromProperties();
config.setName("h2other");
config.setDdlGenerate(false);
config.setDdlRun(false);
config.setDdlExtra(false);
config.setDefaultServer(false);
config.setRegister(false);
config.addClass(UTDetail.class);
config.addClass(OnStartupViaClass.class);
// act - register an instance
OnStartup onStartup = new OnStartup();
config.addServerConfigStartup(onStartup);
EbeanServer ebeanServer = EbeanServerFactory.create(config);
assertThat(onStartup.calledWithConfig).isSameAs(config);
assertThat(OnStartupViaClass.calledWithConfig).isSameAs(config);
assertThat(ebeanServer).isNotNull();
// test server shutdown and restart using the same ServerConfig
ebeanServer.shutdown(true, false);
EbeanServer restartedServer = EbeanServerFactory.create(config);
restartedServer.shutdown(true, false);
}
public static class OnStartup implements ServerConfigStartup {
DatabaseConfig calledWithConfig;
@Override
public void onStart(DatabaseConfig serverConfig) {
calledWithConfig = serverConfig;
}
}
public static class OnStartupViaClass implements ServerConfigStartup {
static DatabaseConfig calledWithConfig;
@Override
public void onStart(DatabaseConfig serverConfig) {
calledWithConfig = serverConfig;
}
}
}
@@ -0,0 +1,141 @@
package io.ebean;
import org.ebeantest.LoggedSqlCollector;
import org.junit.Test;
import org.tests.model.basic.EBasicVer;
import java.util.ArrayList;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertNotNull;
public class EbeanServer_deleteAllByIdTest extends BaseTestCase {
@Test
public void saveAllByVarArgs() {
final EBasicVer bean0 = bean("foo0");
final EBasicVer bean1 = bean("foo1");
final EBasicVer bean2 = bean("foo2");
LoggedSqlCollector.start();
DB.saveAll(bean0, bean1, bean2);
assertNotNull(bean0.getId());
assertNotNull(bean1.getId());
assertNotNull(bean2.getId());
List<String> loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(4);
assertThat(loggedSql.get(0)).contains("insert into e_basicver");
assertSqlBind(loggedSql, 1, 3);
List<Integer> ids = new ArrayList<>();
ids.add(bean0.getId());
ids.add(bean1.getId());
ids.add(bean2.getId());
DB.deleteAll(EBasicVer.class, ids);
}
@Test
public void deleteAllById() {
List<EBasicVer> someBeans = beans(3);
DB.saveAll(someBeans);
List<Integer> ids = new ArrayList<>();
for (EBasicVer someBean : someBeans) {
ids.add(someBean.getId());
}
// act
LoggedSqlCollector.start();
DB.deleteAll(EBasicVer.class, ids);
List<String> loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(1);
platformAssertIn(loggedSql.get(0), "delete from e_basicver where id ");
}
@Test
public void deleteAllById_withTransaction() {
List<EBasicVer> someBeans = beans(3);
DB.saveAll(someBeans);
List<Integer> ids = new ArrayList<>();
for (EBasicVer someBean : someBeans) {
ids.add(someBean.getId());
}
Database db = DB.getDefault();
// act
LoggedSqlCollector.start();
try (Transaction txn = db.beginTransaction()) {
db.deleteAll(EBasicVer.class, ids, txn);
txn.commit();
}
List<String> loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(1);
platformAssertIn(loggedSql.get(0), "delete from e_basicver where id ");
}
@Test
public void deleteAllPermanentById() {
List<EBasicVer> someBeans = beans(3);
DB.saveAll(someBeans);
List<Integer> ids = new ArrayList<>();
for (EBasicVer someBean : someBeans) {
ids.add(someBean.getId());
}
LoggedSqlCollector.start();
DB.deleteAllPermanent(EBasicVer.class, ids);
List<String> loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(1);
platformAssertIn(loggedSql.get(0), "delete from e_basicver where id ");
}
@Test
public void deleteAllPermanentById_withTransaction() {
List<EBasicVer> someBeans = beans(3);
DB.saveAll(someBeans);
List<Integer> ids = new ArrayList<>();
for (EBasicVer someBean : someBeans) {
ids.add(someBean.getId());
}
Database db = DB.getDefault();
// act
LoggedSqlCollector.start();
try (Transaction txn = db.beginTransaction()) {
db.deleteAllPermanent(EBasicVer.class, ids, txn);
txn.commit();
}
List<String> loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(1);
platformAssertIn(loggedSql.get(0), "delete from e_basicver where id ");
}
private List<EBasicVer> beans(int count) {
List<EBasicVer> beans = new ArrayList<>();
for (int i = 0; i < count; i++) {
beans.add(bean("foo" + i));
}
return beans;
}
private EBasicVer bean(String name) {
return new EBasicVer(name);
}
}
@@ -0,0 +1,90 @@
package io.ebean;
import org.tests.model.basic.EBasicVer;
import org.ebeantest.LoggedSqlCollector;
import org.junit.Test;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
public class EbeanServer_deleteByIdTest extends BaseTestCase {
@Test
public void deleteById() {
EBasicVer someBean = bean("foo1");
Ebean.save(someBean);
// act
LoggedSqlCollector.start();
Ebean.delete(EBasicVer.class, someBean.getId());
List<String> loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(1);
assertThat(loggedSql.get(0)).contains("delete from e_basicver where id = ?");
}
@Test
public void deletePermanentById() {
EBasicVer someBean = bean("foo1");
Ebean.save(someBean);
// act
LoggedSqlCollector.start();
Ebean.deletePermanent(EBasicVer.class, someBean.getId());
List<String> loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(1);
assertThat(loggedSql.get(0)).contains("delete from e_basicver where id = ?");
}
@Test
public void deleteById_withTransaction() {
EBasicVer someBean = bean("foo1");
Ebean.save(someBean);
EbeanServer server = Ebean.getDefaultServer();
// act
LoggedSqlCollector.start();
Transaction txn = server.beginTransaction();
try {
server.delete(EBasicVer.class, someBean.getId(), txn);
txn.commit();
} finally {
txn.end();
}
List<String> loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(1);
assertThat(loggedSql.get(0)).contains("delete from e_basicver where id = ?");
}
@Test
public void deletePermanentById_withTransaction() {
EBasicVer someBean = bean("foo2");
Ebean.save(someBean);
EbeanServer server = Ebean.getDefaultServer();
// act
LoggedSqlCollector.start();
Transaction txn = server.beginTransaction();
try {
server.deletePermanent(EBasicVer.class, someBean.getId(), txn);
txn.commit();
} finally {
txn.end();
}
List<String> loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(1);
assertThat(loggedSql.get(0)).contains("delete from e_basicver where id = ?");
}
private EBasicVer bean(String name) {
return new EBasicVer(name);
}
}
@@ -0,0 +1,53 @@
package io.ebean;
import org.tests.model.basic.EBasicVer;
import org.ebeantest.LoggedSqlCollector;
import org.junit.Test;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
public class EbeanServer_deleteTest extends BaseTestCase {
@Test
public void delete() {
EBasicVer someBean = bean("foo1");
Ebean.save(someBean);
// act
LoggedSqlCollector.start();
Ebean.delete(someBean);
List<String> loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(1);
assertThat(loggedSql.get(0)).contains("delete from e_basicver where id=? and ");
}
@Test
public void delete_withTransaction() {
EBasicVer someBean = bean("foo1");
Ebean.save(someBean);
EbeanServer server = Ebean.getDefaultServer();
// act
LoggedSqlCollector.start();
Transaction txn = server.beginTransaction();
try {
server.delete(someBean, txn);
txn.commit();
} finally {
txn.end();
}
List<String> loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(1);
assertThat(loggedSql.get(0)).contains("delete from e_basicver where id=? and ");
}
private EBasicVer bean(String name) {
return new EBasicVer(name);
}
}
@@ -0,0 +1,265 @@
package io.ebean;
import org.ebeantest.LoggedSqlCollector;
import org.junit.Test;
import org.tests.model.basic.Customer;
import org.tests.model.basic.ResetBasicData;
import javax.persistence.PersistenceException;
import static org.assertj.core.api.Assertions.assertThat;
import java.util.List;
public class EbeanServer_eqlTest extends BaseTestCase {
@Test
public void basic() {
ResetBasicData.reset();
Query<Customer> query = server().createQuery(Customer.class, "order by id limit 10");
query.setMaxRows(100);
query.findList();
if (isSqlServer()) {
assertSql(query).startsWith("select top 100 ");
assertSql(query).endsWith("order by t0.id");
} else if (isOracle()) {
assertSql(query).contains(" fetch next 100 rows only");
} else {
assertSql(query).endsWith("order by t0.id limit 100");
}
}
@Test
public void basic_via_Ebean_defaultServer() {
ResetBasicData.reset();
Query<Customer> query = Ebean.createQuery(Customer.class, "order by id limit 10");
query.findList();
if (isSqlServer()) {
assertSql(query).startsWith("select top 10 ");
assertSql(query).endsWith("order by t0.id");
} else if (isOracle()) {
assertSql(query).contains(" fetch next 10 rows only");
} else {
assertSql(query).endsWith("order by t0.id limit 10");
}
}
@Test
public void basic_limit_offset1() {
ResetBasicData.reset();
Query<Customer> query = Ebean.createQuery(Customer.class, "order by id limit 10 offset 3");
query.findList();
if (isSqlServer()) {
assertSql(query).endsWith("order by t0.id offset 3 rows fetch next 10 rows only");
} else if (isOracle()) {
assertSql(query).contains("offset 3 rows fetch next 10 rows only");
} else {
assertSql(query).endsWith("order by t0.id limit 10 offset 3");
}
}
@Test
public void basic_limit_offset2() {
ResetBasicData.reset();
Query<Customer> query = Ebean.createQuery(Customer.class, "order by name");
query.setMaxRows(10);
query.setFirstRow(3);
query.findList();
if (isSqlServer()) {
assertSql(query).endsWith("order by t0.name offset 3 rows fetch next 10 rows only");
} else if (isOracle()) {
assertSql(query).contains("offset 3 rows fetch next 10 rows only");
} else {
assertSql(query).endsWith("order by t0.name limit 10 offset 3");
}
// check also select count(*)
LoggedSqlCollector.start();
query.findCount();
List<String>sql = LoggedSqlCollector.stop();
assertThat(sql.get(0)).startsWith("select count(*) from o_customer t0;");
}
@Test
public void basic_limit_offset2_with_id() {
ResetBasicData.reset();
Query<Customer> query = Ebean.createQuery(Customer.class, "order by name");
query.setMaxRows(10);
query.setFirstRow(3);
query.orderById(true);
query.findList();
if (isSqlServer()) {
assertSql(query).endsWith("order by t0.name, t0.id offset 3 rows fetch next 10 rows only");
} else if (isOracle()) {
assertSql(query).contains("offset 3 rows fetch next 10 rows only");
} else {
assertSql(query).endsWith("order by t0.name, t0.id limit 10 offset 3");
}
// check also select count(*)
LoggedSqlCollector.start();
query.findCount();
List<String>sql = LoggedSqlCollector.stop();
assertThat(sql.get(0)).startsWith("select count(*) from o_customer t0;");
}
@Test
public void basic_limit_offset3() {
ResetBasicData.reset();
Query<Customer> query = Ebean.createQuery(Customer.class);
query.setMaxRows(10);
query.setFirstRow(3);
if (isSqlServer()) {
query.order("id");
}
query.findList();
if (isSqlServer()) {
assertSql(query).endsWith("from o_customer t0 order by t0.id offset 3 rows fetch next 10 rows only");
} else if (isOracle()) {
assertSql(query).contains("offset 3 rows fetch next 10 rows only");
} else {
assertSql(query).endsWith("from o_customer t0 limit 10 offset 3");
}
}
@Test
public void basic_limit_offset4() {
ResetBasicData.reset();
Query<Customer> query = Ebean.createQuery(Customer.class);
query.setMaxRows(10);
query.findList();
if (isSqlServer()) {
assertSql(query).startsWith("select top 10 ");
} else if (isOracle()) {
assertSql(query).contains("fetch next 10 rows only");
} else {
assertSql(query).endsWith("limit 10");
}
}
@Test
public void orderBy_override() {
ResetBasicData.reset();
Query<Customer> query = server().createQuery(Customer.class, "order by id");
// use clear() and then effectively override the orderBy clause
query.orderBy().clear().asc("name");
query.findList();
assertSql(query).contains("order by t0.name");
}
@Test
public void namedParams() {
ResetBasicData.reset();
Query<Customer> query = server().createQuery(Customer.class, "where name startsWith :name order by name");
query.setParameter("name", "Ro");
query.findList();
assertSql(query).contains("where t0.name like ");
}
@Test(expected = PersistenceException.class)
public void unboundNamedParams_expect_PersistenceException() {
Query<Customer> query = server().createQuery(Customer.class, "where name = :name");
query.findOne();
}
@Test
public void namedQuery() {
ResetBasicData.reset();
Query<Customer> name = server().createNamedQuery(Customer.class, "name");
name.findList();
assertThat(sqlOf(name, 1)).contains("select t0.id, t0.name from o_customer t0 order by t0.name");
}
@Test
public void namedQuery_withStatus() {
ResetBasicData.reset();
Query<Customer> name = server().createNamedQuery(Customer.class, "withStatus");
name.order().clear().asc("status");
name.findList();
assertThat(sqlOf(name, 2)).contains("select t0.id, t0.name, t0.status from o_customer t0 order by t0.status");
}
@Test
public void namedQuery_withContacts() {
ResetBasicData.reset();
Query<Customer> query = server()
.createNamedQuery(Customer.class, "withContacts")
.setParameter("id", 1);
query.setUseCache(false);
query.findOne();
assertSql(query).contains("from o_customer t0 left join contact t1 on t1.customer_id = t0.id ");
}
@Test
public void namedQuery_fromXml() {
ResetBasicData.reset();
Query<Customer> query = server()
.createNamedQuery(Customer.class, "withContactsById")
.setParameter("id", 1);
query.setUseCache(false);
query.findOne();
assertSql(query).contains("from o_customer t0 left join contact t1 on t1.customer_id = t0.id ");
}
@Test
public void namedQuery_fromCustomXmlLocations() {
ResetBasicData.reset();
Query<Customer> query = server()
.createNamedQuery(Customer.class, "withContactsById2")
.setParameter("id", 1);
query.setUseCache(false);
query.findOne();
assertSql(query).contains("from o_customer t0 left join contact t1 on t1.customer_id = t0.id ");
}
}
@@ -0,0 +1,155 @@
package io.ebean;
import org.junit.Test;
import org.tests.model.basic.EBasic;
import org.tests.model.basic.Order;
import org.tests.model.basic.OrderDetail;
import org.tests.model.basic.ResetBasicData;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertEquals;
public class EbeanServer_refresh {
@Test
public void basic() {
Map<String, String> map = new HashMap<>();
map.put("tableName", "e_basic");
EbeanServer server = Ebean.getDefaultServer();
DB.script().run("/scripts/test-script.sql");
DB.script().run("/scripts/test-script-2.sql", map);
server.script().run(this.getClass().getResource("/scripts/test-script.sql"));
server.script().run(this.getClass().getResource("/scripts/test-script-2.sql"), map);
EBasic basic = new EBasic("basic refresh");
basic.setStatus(EBasic.Status.NEW);
server.save(basic);
int rows =
server.update(EBasic.class)
.set("status", EBasic.Status.ACTIVE)
.where().idEq(basic.getId())
.update();
assertEquals(rows, 1);
server.refresh(basic);
assertEquals(basic.getStatus(), EBasic.Status.ACTIVE);
}
@Test
public void refresh_when_oneToManyLoaded() {
ResetBasicData.reset();
Order order = Ebean.find(Order.class, 1);
order.getCustomer().getName();
order.getDetails().size();
Ebean.refresh(order);
}
@Test
public void refresh_when_oneToManyVanilla() {
ResetBasicData.reset();
Order order = Ebean.find(Order.class, 1);
order.getCustomer().getName();
order.setDetails(new ArrayList<>());
Ebean.refresh(order);
}
@Test
public void refresh_when_oneToManyNull() {
ResetBasicData.reset();
Order order = Ebean.find(Order.class, 1);
order.getCustomer().getName();
order.setDetails(null);
Ebean.refresh(order);
}
@Test
public void refresh_on_details_new() {
ResetBasicData.reset();
Order order = Ebean.find(Order.class, 1);
DB.refresh(order); // call refresh BEFORE first access on "getDetail";
assertThat(order.getDetails()).hasSize(3);
OrderDetail detail = new OrderDetail();
detail.setOrder(order);
DB.save(detail);
try {
assertThat(order.getDetails()).hasSize(3);
DB.refresh(order);
assertThat(order.getDetails()).hasSize(4);
} finally {
DB.delete(detail); // restore old state
}
DB.refresh(order);
assertThat(order.getDetails()).hasSize(3);
}
@Test
public void refresh_on_details_changed() {
ResetBasicData.reset();
Order order = Ebean.find(Order.class, 1);
DB.refresh(order); // call refresh BEFORE first access on "getDetail"
// this changes the loader of the details-bean collection from DefaultServer to DLoadManyContext$LoadBuffer
// if this refresh is commented out, the test will pass
assertThat(order.getDetails().get(0).getOrderQty()).isEqualTo(5);
// search the detail in the DB and change qty to 42
OrderDetail detail = DB.find(OrderDetail.class, order.getDetails().get(0).getId());
assertThat(order.getDetails().get(0)).isEqualTo(detail).isNotSameAs(detail);
detail.setOrderQty(42);
DB.save(detail);
try {
assertThat(order.getDetails().get(0).getOrderQty()).isEqualTo(5);
DB.refresh(order);
assertThat(order.getDetails().get(0).getOrderQty()).isEqualTo(42);
} finally {
// restore old value
detail.setOrderQty(5);
DB.save(detail);
}
DB.refresh(order);
assertThat(order.getDetails().get(0).getOrderQty()).isEqualTo(5);
}
}
@@ -0,0 +1,165 @@
package io.ebean;
import org.ebeantest.LoggedSqlCollector;
import org.junit.Test;
import org.tests.model.basic.EBasicVer;
import java.util.ArrayList;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
public class EbeanServer_saveAllTest extends BaseTestCase {
@Test
public void saveAll() {
List<EBasicVer> someBeans = beans(3);
// act
LoggedSqlCollector.start();
Ebean.saveAll(someBeans);
// assert
List<String> loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(4);
assertThat(loggedSql.get(0)).contains("insert into e_basicver (");
assertThat(loggedSql.get(0)).contains("name, description, other, last_update) values (");
for (EBasicVer someBean : someBeans) {
someBean.setName(someBean.getName() + "-mod");
}
// act
LoggedSqlCollector.start();
Ebean.updateAll(someBeans);
loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(3);
assertThat(loggedSql.get(0)).contains("update e_basicver set name=?, last_update=? where id=? ");
// act
LoggedSqlCollector.start();
Ebean.deleteAll(someBeans);
loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(4);
assertThat(loggedSql.get(0)).contains("delete from e_basicver where id=?");
}
@Test
public void saveAll_withExistingBatch_doesNotTriggerFlush() {
EbeanServer server = Ebean.getDefaultServer();
try (Transaction transaction = server.beginTransaction()) {
transaction.setBatchMode(true);
LoggedSqlCollector.start();
for (EBasicVer bean : beans(2)) {
server.save(bean);
}
// jdbc batch, no sql yet
assertThat(LoggedSqlCollector.current()).isEmpty();
server.saveAll(beans(3));
// still batch, no sql yet
assertThat(LoggedSqlCollector.current()).isEmpty();
for (EBasicVer bean : beans(2)) {
server.save(bean);
}
// still batch, no sql yet
assertThat(LoggedSqlCollector.current()).isEmpty();
// flush now
transaction.commit();
// and we have our SQL from jdbc batch flush
assertThat(LoggedSqlCollector.stop()).isNotEmpty();
}
}
@Test
public void deleteAll_withNull() {
Ebean.deleteAll(null);
}
@Test
public void deleteAll_withEmpty() {
Ebean.saveAll(beans(0));
}
@Test
public void saveAll_withNull() {
Ebean.saveAll(null);
}
@Test
public void saveAll_withEmpty() {
Ebean.saveAll(beans(0));
}
@Test
public void saveAll_withTransaction() {
List<EBasicVer> someBeans = beans(3);
EbeanServer server = Ebean.getDefaultServer();
// act
LoggedSqlCollector.start();
try (Transaction txn = server.beginTransaction()) {
server.saveAll(someBeans, txn);
txn.commit();
}
// assert
List<String> loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(4);
assertThat(loggedSql.get(0)).contains("insert into e_basicver (");
assertThat(loggedSql.get(0)).contains("name, description, other, last_update) values (");
for (EBasicVer someBean : someBeans) {
someBean.setName(someBean.getName() + "-mod");
}
// act
LoggedSqlCollector.start();
try (Transaction txn = server.beginTransaction()) {
server.updateAll(someBeans, txn);
txn.commit();
}
loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(3);
assertThat(loggedSql.get(0)).contains("update e_basicver set name=?, last_update=? where id=? ");
// act
LoggedSqlCollector.start();
try (Transaction txn = server.beginTransaction()) {
server.deleteAll(someBeans, txn);
txn.commit();
}
loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(4);
assertThat(loggedSql.get(0)).contains("delete from e_basicver where id=?");
}
private List<EBasicVer> beans(int count) {
List<EBasicVer> beans = new ArrayList<>();
for (int i = 0; i < count; i++) {
beans.add(bean("foo" + i));
}
return beans;
}
private EBasicVer bean(String name) {
return new EBasicVer(name);
}
}
@@ -0,0 +1,95 @@
package io.ebean;
import org.junit.After;
import org.junit.Test;
import org.tests.model.basic.Customer;
import org.tests.model.basic.ResetBasicData;
import java.time.Clock;
import java.time.Instant;
import java.time.temporal.ChronoUnit;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
public class ExtendedServerTest extends BaseTestCase {
@After
public void cleanup() {
Ebean.getDefaultServer()
.extended()
.setClock(Clock.systemUTC());
}
@Test
public void findList() {
ResetBasicData.reset();
EbeanServer server = Ebean.getDefaultServer();
Query<Customer> query = server.find(Customer.class)
.where().startsWith("name", "Rob")
.query();
// rather than use .findList() return the query
// when we use findList() .. it obtains a transaction using
// the normal mechanism
// obtain a transaction somehow ...
// for this test/example we just begin one
try (Transaction transaction = server.beginTransaction()) {
// obtain extended API ... such that we can execute the
// query using an explicit transaction
List<Customer> customers = server.extended().findList(query, transaction);
assertThat(customers).isNotEmpty();
transaction.commit();
}
}
@Test
public void mockClock() {
EbeanServer server = Ebean.getDefaultServer();
final Instant snapshot = Instant.now();
Instant backedSnapshot = snapshot.minus(1, ChronoUnit.DAYS);
Clock snapshotClock = Clock.fixed(backedSnapshot, Clock.systemUTC().getZone());
server.extended().setClock(snapshotClock);
ResetBasicData.reset();
int count = server
.find(Customer.class)
.where()
.gt("cretime", snapshot)
.findCount();
assertThat(count).isEqualTo(0);
int count2 = server
.find(Customer.class)
.where()
.ge("cretime", backedSnapshot)
.findCount();
assertThat(count2).isGreaterThan(0);
int count3 = server
.find(Customer.class)
.where()
.gt("updtime", snapshot)
.findCount();
assertThat(count3).isEqualTo(0);
int count4 = server
.find(Customer.class)
.where()
.ge("updtime", backedSnapshot)
.findCount();
assertThat(count4).isGreaterThan(0);
}
}
@@ -0,0 +1,169 @@
package io.ebean;
import io.ebean.FetchConfig;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class FetchConfigTest {
@Test
public void testLazy() throws Exception {
FetchConfig config = new FetchConfig().lazy();
assertThat(config.getLazyBatchSize()).isEqualTo(0);
assertThat(config.getQueryBatchSize()).isEqualTo(-1);
assertThat(config.isQueryAll()).isEqualTo(false);
}
@Test
public void testLazy_withParameter() throws Exception {
FetchConfig config = new FetchConfig().lazy(50);
assertThat(config.getLazyBatchSize()).isEqualTo(50);
assertThat(config.getQueryBatchSize()).isEqualTo(-1);
assertThat(config.isQueryAll()).isEqualTo(false);
}
@Test
public void testQuery() throws Exception {
FetchConfig config = new FetchConfig().query();
assertThat(config.getLazyBatchSize()).isEqualTo(-1);
assertThat(config.getQueryBatchSize()).isEqualTo(0);
assertThat(config.isQueryAll()).isEqualTo(true);
}
@Test
public void testQuery_withParameter() throws Exception {
FetchConfig config = new FetchConfig().query(50);
assertThat(config.getLazyBatchSize()).isEqualTo(-1);
assertThat(config.getQueryBatchSize()).isEqualTo(50);
assertThat(config.isQueryAll()).isEqualTo(true);
}
@Test
public void testQueryFirst() throws Exception {
FetchConfig config = new FetchConfig().queryFirst(50);
assertThat(config.getLazyBatchSize()).isEqualTo(-1);
assertThat(config.getQueryBatchSize()).isEqualTo(50);
assertThat(config.isQueryAll()).isEqualTo(false);
}
@Test
public void testQueryAndLazy_withParameters() throws Exception {
FetchConfig config = new FetchConfig().query(50).lazy(10);
assertThat(config.getLazyBatchSize()).isEqualTo(10);
assertThat(config.getQueryBatchSize()).isEqualTo(50);
assertThat(config.isQueryAll()).isEqualTo(false);
}
@Test
public void testQueryAndLazy() throws Exception {
FetchConfig config = new FetchConfig().query(50).lazy();
assertThat(config.getLazyBatchSize()).isEqualTo(0);
assertThat(config.getQueryBatchSize()).isEqualTo(50);
assertThat(config.isQueryAll()).isEqualTo(false);
}
@Test
public void testEquals_when_noOptions() throws Exception {
assertSame(new FetchConfig(), new FetchConfig());
}
@Test
public void testEquals_when_query_50_lazy_40() throws Exception {
assertSame(new FetchConfig().query(50).lazy(40), new FetchConfig().query(50).lazy(40));
}
@Test
public void testEquals_when_query_50_lazy() throws Exception {
assertSame(new FetchConfig().query(50).lazy(), new FetchConfig().query(50).lazy());
}
@Test
public void testEquals_when_query_50() throws Exception {
assertSame(new FetchConfig().query(50), new FetchConfig().query(50));
}
@Test
public void testEquals_when_queryFirst_50_lazy_40() throws Exception {
assertSame(new FetchConfig().queryFirst(50).lazy(40), new FetchConfig().queryFirst(50).lazy(40));
}
@Test
public void testEquals_when_queryFirst_50_lazy() throws Exception {
assertSame(new FetchConfig().queryFirst(50).lazy(), new FetchConfig().queryFirst(50).lazy());
}
@Test
public void testEquals_when_queryFirst_50() throws Exception {
assertSame(new FetchConfig().queryFirst(50), new FetchConfig().queryFirst(50));
}
@Test
public void testNotEquals_when_query_50() throws Exception {
assertDifferent(new FetchConfig().query(50), new FetchConfig().query(40));
}
@Test
public void testNotEquals_when_query_50_lazy() throws Exception {
assertDifferent(new FetchConfig().query(50), new FetchConfig().query(50).lazy());
}
@Test
public void testNotEquals_when_query_50_lazy_40() throws Exception {
assertDifferent(new FetchConfig().query(50), new FetchConfig().query(50).lazy(40));
}
@Test
public void testNotEquals_when_queryFirst_50() throws Exception {
assertDifferent(new FetchConfig().queryFirst(50), new FetchConfig().queryFirst(40));
}
@Test
public void testNotEquals_when_queryFirst_50_lazy() throws Exception {
assertDifferent(new FetchConfig().queryFirst(50), new FetchConfig().queryFirst(50).lazy());
}
@Test
public void testNotEquals_when_queryFirst_50_lazy_40() throws Exception {
assertDifferent(new FetchConfig().queryFirst(50), new FetchConfig().queryFirst(50).lazy(40));
}
void assertDifferent(FetchConfig v1, FetchConfig v2) {
assertThat(v1).isNotEqualTo(v2);
assertThat(v1.hashCode()).isNotEqualTo(v2.hashCode());
}
void assertSame(FetchConfig v1, FetchConfig v2) {
assertThat(v1).isEqualTo(v2);
assertThat(v1.hashCode()).isEqualTo(v2.hashCode());
}
}
@@ -0,0 +1,138 @@
package io.ebean;
import io.ebean.service.SpiFetchGroupQuery;
import org.ebeantest.LoggedSqlCollector;
import org.junit.Test;
import org.tests.model.basic.Address;
import org.tests.model.basic.Contact;
import org.tests.model.basic.Customer;
import org.tests.model.basic.ResetBasicData;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
public class FetchGroupTest extends BaseTestCase {
@Test
public void simple() {
FetchGroup<Customer> fetch = FetchGroup.of(Customer.class, "name, status");
Query<Customer> query = Customer.find
.query()
.where()
.ilike("name", "rob")
.select(fetch);
query.findList();
assertThat(sqlOf(query)).contains("select t0.id, t0.name, t0.status from");
}
@Test
public void nestedWithQueryJoin() {
ResetBasicData.reset();
FetchGroup<Customer> fetch = FetchGroup.of(Customer.class)
.select("name, status")
.fetchQuery("contacts", "firstName, lastName, email")
.build();
Query<Customer> query = Customer.find
.query()
.where()
.ilike("name", "rob")
.select(fetch);
LoggedSqlCollector.start();
query.findList();
List<String> sql = LoggedSqlCollector.stop();
assertThat(sql).hasSize(2);
assertSql(sql.get(0)).contains("select t0.id, t0.name, t0.status from o_customer");
assertSql(sql.get(1)).contains("select t0.customer_id, t0.id, t0.first_name, t0.last_name, t0.email from contact");
}
@Test
public void nestedWithQueryJoin_asNestedFetchGroup() {
ResetBasicData.reset();
FetchGroup<Contact> CT_NAME = FetchGroup.of(Contact.class, "firstName, lastName, email");
FetchGroup<Customer> fetch = FetchGroup.of(Customer.class)
.select("name")
.fetchQuery("contacts", CT_NAME)
.build();
Query<Customer> query = Customer.find
.query()
.where()
.ilike("name", "rob")
.select(fetch);
LoggedSqlCollector.start();
query.findList();
List<String> sql = LoggedSqlCollector.stop();
assertThat(sql).hasSize(2);
assertSql(sql.get(0)).contains("select t0.id, t0.name from o_customer");
assertSql(sql.get(1)).contains(" from contact");
}
@Test
public void nested_withNestedFetchGroup() {
ResetBasicData.reset();
FetchGroup<Address> FGAddress = FetchGroup.of(Address.class)
.select("line1, line2, city")
.fetch("country", "name")
.build();
FetchGroup<Customer> FBCustomer = FetchGroup.of(Customer.class)
.select("name, version")
.fetch("billingAddress", FGAddress)
.build();
Query<Customer> query = Customer.find
.query()
.where()
.ilike("name", "rob")
.select(FBCustomer);
LoggedSqlCollector.start();
query.findList();
List<String> sql = LoggedSqlCollector.stop();
assertThat(sql).hasSize(1);
assertSql(sql.get(0)).contains("select t0.id, t0.name, t0.version, t1.id, t1.line_1, t1.line_2, t1.city, t2.code, t2.name from o_customer t0 left join o_address t1 on t1.id = t0.billing_address_id left join o_country t2 on t2.code = t1.country_code ");
}
@Test
public void fetchGroupQuery() {
// in practice this query is used by query beans for type safe FetchGroup construction
final SpiFetchGroupQuery<Customer> query = FetchGroup.queryFor(Customer.class);
query.select("name");
final FetchGroup<Customer> fetchGroup = query.buildFetchGroup();
LoggedSqlCollector.start();
Customer.find
.query()
.where()
.ilike("name", "rob")
.select(fetchGroup)
.findList();
List<String> sql = LoggedSqlCollector.stop();
assertThat(sql).hasSize(1);
assertSql(sql.get(0)).contains("select t0.id, t0.name from o_customer t0 where");
}
}
@@ -0,0 +1,32 @@
package io.ebean;
import io.ebean.config.CurrentUserProvider;
/**
* Returns the current user typically from a Thread local or similar context.
*/
public class MyCurrentUserProvider implements CurrentUserProvider {
public static final String DEFAULT = "42789";
/**
* Do not do this yourself - this is for testing purposes.
*/
private static Object userId = DEFAULT;
@Override
public Object currentUser() {
// just hardcoding here for testing
return userId;
}
public static void setUser(Object value) {
userId = value;
}
public static void resetToDefault() {
userId = DEFAULT;
}
}
@@ -0,0 +1,336 @@
package io.ebean;
import io.ebean.meta.BasicMetricVisitor;
import io.ebean.meta.MetaQueryMetric;
import org.ebeantest.LoggedSqlCollector;
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.tests.model.basic.ResetBasicData;
import java.util.List;
import java.util.Optional;
import static org.assertj.core.api.Assertions.assertThat;
public class NamedDtoQueryTest extends BaseTestCase {
private static final Logger log = LoggerFactory.getLogger(NamedDtoQueryTest.class);
@Test
public void dto_findList_constructorMatch() {
ResetBasicData.reset();
DtoQuery<DCust> dtoQuery = server().createNamedDtoQuery(DCust.class, "findList");
List<DCust> list = dtoQuery.findList();
log.info(list.toString());
assertThat(list).isNotEmpty();
}
@Test
public void dto_findEach_constructorMatch() {
ResetBasicData.reset();
LoggedSqlCollector.start();
server().createNamedDtoQuery(DCust.class, "findGtId")
.setParameter("id", 0)
.findEach(it -> log.info("got " + it.getId() + " " + it.getName()));
List<String> sql = LoggedSqlCollector.stop();
assertSql(sql.get(0)).contains("select id, name from o_customer where id > ?");
}
@Test
public void dto_findEachWhile_constructorMatch() {
ResetBasicData.reset();
LoggedSqlCollector.start();
server().createNamedDtoQuery(DCust.class, "findGtIdDesc")
.setParameter("id", 0)
.findEachWhile(customer -> {
log.info("got " + customer.getId() + " " + customer.getName());
return customer.getId() > 3;
});
List<String> sql = LoggedSqlCollector.stop();
assertSql(sql.get(0)).contains("select id, name from o_customer where id > ?");
}
@Test
public void dto_findOneEmpty() {
ResetBasicData.reset();
Optional<DCust> rob = server().createNamedDtoQuery(DCust.class, "findByName")
.setParameter("name", "Fiona")
.findOneOrEmpty();
assertThat(rob.isPresent()).isTrue();
Optional<DCust> oneOrEmpty = server().createNamedDtoQuery(DCust.class, "findByName")
.setParameter("name", "DoesNotExistMyFriend")
.findOneOrEmpty();
assertThat(oneOrEmpty.isPresent()).isFalse();
}
@Test
public void dto_findOne() {
ResetBasicData.reset();
DCust fiona = server().createNamedDtoQuery(DCust.class, "findByName")
.setParameter("name", "Fiona")
.findOne();
assertThat(fiona.getName()).isEqualTo("Fiona");
DCust empty = server().createNamedDtoQuery(DCust.class, "findByName")
.setParameter("name", "DoesNotExistMyFriend")
.findOne();
assertThat(empty).isNull();
}
@Test
public void dto_queryPlanHits() {
ResetBasicData.reset();
resetAllMetrics();
String[] names = {"Rob", "Fiona", "Shrek"};
for (String name : names) {
List<DCust> custs = server().createNamedDtoQuery(DCust.class, "findByName_c3")
.setLabel("basic")
.setParameter("name", name)
.findList();
log.info("Found " + custs);
}
// collect without reset
BasicMetricVisitor basic = new BasicMetricVisitor(false, true, true, true);
server().getMetaInfoManager().visitMetrics(basic);
List<MetaQueryMetric> stats = basic.getQueryMetrics();
assertThat(stats).hasSize(1);
MetaQueryMetric queryMetric = stats.get(0);
assertThat(queryMetric.getLabel()).isEqualTo("basic");
assertThat(queryMetric.getCount()).isEqualTo(3);
assertThat(queryMetric.getName()).isEqualTo("dto.DCust_basic");
server().createNamedDtoQuery(DCust.class, "findByName_c4")
.setLabel("basic2")
.setParameter("name", "rob")
.findList();
BasicMetricVisitor metric2 = server().getMetaInfoManager().visitBasic();
stats = metric2.getQueryMetrics();
assertThat(stats).hasSize(2);
log.info("stats " + stats);
}
@Test
public void dto_findList_relaxedMode() {
ResetBasicData.reset();
List<DCust3> list = server().createNamedDtoQuery(DCust3.class, "findByName_relaxedMode")
.setRelaxedMode()
.findList();
log.info(list.toString());
assertThat(list).isNotEmpty();
}
@Test
public void dto_findList_relaxedMode_defaultConstructor() {
ResetBasicData.reset();
List<DCust2> list = server().createNamedDtoQuery(DCust2.class, "findByName_relaxedMode")
.setRelaxedMode()
.findList();
log.info(list.toString());
assertThat(list).isNotEmpty();
}
@Test
public void dto_findList_constructorPlusMatch() {
ResetBasicData.reset();
List<DCust> dtos = server().createNamedDtoQuery(DCust.class, "findListByName")
.setParameter("name", "Rob")
.findList();
log.info(dtos.toString());
assertThat(dtos).isNotEmpty();
}
@Test
public void dto_findList_setters() {
ResetBasicData.reset();
DtoQuery<DCust2> dtoQuery = server().createNamedDtoQuery(DCust2.class, "findList");
List<DCust2> list = dtoQuery.findList();
assertThat(list).isNotEmpty();
}
@Test
public void dto3_findList_constructorMatch() {
ResetBasicData.reset();
List<DCust3> robs = server().createNamedDtoQuery(DCust3.class, "findByNameLike")
.setParameter("Rob")
.setMaxRows(10)
.findList();
log.info(robs.toString());
assertThat(robs).isNotEmpty();
}
@Test
public void dto3_findList_settersMatch() {
ResetBasicData.reset();
List<DCust3> robs = server().createNamedDtoQuery(DCust3.class, "findByName")
.setParameter("name", "Rob")
.findList();
log.info(robs.toString());
assertThat(robs).isNotEmpty();
}
public static class DCust {
final Integer id;
final String name;
int totalOrders;
public DCust(Integer id, String name) {
this.id = id;
this.name = name;
}
@Override
public String toString() {
return "id:" + id + " name:" + name + " totalOrders:" + totalOrders;
}
public Integer getId() {
return id;
}
public String getName() {
return name;
}
public int getTotalOrders() {
return totalOrders;
}
public void setTotalOrders(int totalOrders) {
this.totalOrders = totalOrders;
}
}
public static class DCust2 {
Integer id;
String name;
@Override
public String toString() {
return "id:" + id + " name:" + name;
}
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
public static class DCust3 {
Integer id;
String name;
int totalOrders;
public DCust3() {
}
public DCust3(Integer id, String name, int totalOrders) {
this.id = id;
this.name = name;
this.totalOrders = totalOrders;
}
@Override
public String toString() {
return "id:" + id + " name:" + name + " totalOrders:" + totalOrders;
}
public Integer getId() {
return id;
}
public String getName() {
return name;
}
public int getTotalOrders() {
return totalOrders;
}
public void setTotalOrders(int totalOrders) {
this.totalOrders = totalOrders;
}
public void setId(Integer id) {
this.id = id;
}
public void setName(String name) {
this.name = name;
}
}
}
@@ -0,0 +1,45 @@
package io.ebean;
import io.ebean.OrderBy;
import org.junit.Test;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotEquals;
public class PropertyTest {
@Test
public void equals() throws Exception {
assertEquals(prop("foo", true), prop("foo", true));
}
@Test
public void diff_basic() throws Exception {
assertNotEquals(prop("foo", true), prop("bar", true));
assertNotEquals(prop("foo", true), prop("foo", false));
assertNotEquals(prop("foo", false), prop("foo", true));
}
@Test
public void diff_nulls() throws Exception {
assertEquals(prop("foo", true, "nulls", "high"), prop("foo", true, "nulls", "high"));
assertEquals(prop("foo", true, "nulls", "low"), prop("foo", true, "nulls", "low"));
assertNotEquals(prop("foo", true), prop("foo", true, "nulls", "high"));
assertNotEquals(prop("foo", true, "nulls", "high"), prop("foo", true));
assertNotEquals(prop("foo", true, "nulls", "high"), prop("foo", true, "nulls", "low"));
assertNotEquals(prop("foo", true, "nulls", "low"), prop("foo", true, "nulls", "high"));
}
private OrderBy.Property prop(String name, boolean asc) {
return new OrderBy.Property(name, asc, null, null);
}
private OrderBy.Property prop(String name, boolean asc, String nulls, String highLow) {
return new OrderBy.Property(name, asc, nulls, highLow);
}
}
@@ -0,0 +1,28 @@
package io.ebean;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class SqlRowBooleanTest extends BaseTestCase {
@Test
public void getBoolean() {
SqlQuery sqlQuery;
if (isSqlServer()) {
sqlQuery = DB.sqlQuery("SELECT 1 AS ISNT_NULL");
} else if (isOracle() || isNuoDb()) {
sqlQuery = DB.sqlQuery("SELECT 1 AS ISNT_NULL from dual");
} else if (isDb2()) {
sqlQuery = DB.sqlQuery("SELECT 1 AS ISNT_NULL from SYSIBM.SYSDUMMY1");
} else if (isHana()) {
sqlQuery = DB.sqlQuery("SELECT 1 AS ISNT_NULL from sys.dummy");
} else {
sqlQuery = DB.sqlQuery("SELECT 1 IS NOT NULL AS ISNT_NULL");
}
SqlRow row = sqlQuery.findOne();
Boolean value = row.getBoolean("ISNT_NULL");
assertThat(value).isTrue();
}
}
@@ -0,0 +1,109 @@
package io.ebean;
import io.ebean.util.StringHelper;
import org.junit.Test;
import java.util.Map;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertTrue;
public class StringHelperTest {
@Test
public void isNull() {
assertTrue(StringHelper.isNull(null));
assertTrue(StringHelper.isNull(""));
assertTrue(StringHelper.isNull(" "));
assertFalse(StringHelper.isNull("a"));
}
@Test
public void replaceString() {
assertEquals("sJmethJng", StringHelper.replace("somethong", "o","J"));
assertEquals("somethong", StringHelper.replace("somethong", "o", null));
assertNull(StringHelper.replace(null, "o","J"));
}
@Test
public void testSplitNames() {
assertThat(StringHelper.splitNames("")).hasSize(0);
assertThat(StringHelper.splitNames(" , ;")).hasSize(0);
assertThat(StringHelper.splitNames("foo bar")).containsExactly("foo", "bar");
assertThat(StringHelper.splitNames(" foo \n bar ")).containsExactly("foo", "bar");
assertThat(StringHelper.splitNames(" foo , bar ;")).containsExactly("foo", "bar");
assertThat(StringHelper.splitNames("foo, bar")).containsExactly("foo", "bar");
assertThat(StringHelper.splitNames("foo, bar baz")).containsExactly("foo", "bar", "baz");
assertThat(StringHelper.splitNames("foo, bar\nbaz")).containsExactly("foo", "bar", "baz");
}
@Test
public void removeNewLines() {
String content = "This is\na\rmultiline\r\ntext\n\r";
content = StringHelper.removeNewLines(content);
assertThat(content).isEqualTo("This is a multiline text ");
}
@Test
public void testDelimitedToMap() {
String content = "name1=blah; name2 = blubb ;name3\n=foo";
Map<String, String> map = StringHelper.delimitedToMap(content, ";", "=");
assertThat(map)
.containsEntry("name1", "blah")
.containsEntry("name2", " blubb ") // white space is not trimmed
.containsEntry("name3", "foo");
}
@Test
public void testDelimitedToMap_expect_trimLeading() {
String content = ";name1=foo;name2=bar;";
Map<String, String> map = StringHelper.delimitedToMap(content, ";", "=");
assertThat(map).hasSize(2)
.containsEntry("name1", "foo")
.containsEntry("name2", "bar");
}
@Test
public void testDelimitedToMap_when_emptyEntry() {
String content = ";name1=foo;=;name2=bar;";
Map<String, String> map = StringHelper.delimitedToMap(content, ";", "=");
assertThat(map).hasSize(2)
.containsEntry("name1", "foo")
.containsEntry("name2", "bar");
}
@Test
public void testDelimitedToMap_when_missingValue() {
String content = ";name1=foo;nameX;name2=bar;";
Map<String, String> map = StringHelper.delimitedToMap(content, ";", "=");
assertThat(map).hasSize(3)
.containsEntry("nameX", null)
.containsEntry("name1", "foo")
.containsEntry("name2", "bar");
}
@Test
public void testDelimitedToMap_when_missingValueAtEnd() {
String content = ";name1=foo;nameX;name2=bar;nameX2";
Map<String, String> map = StringHelper.delimitedToMap(content, ";", "=");
assertThat(map).hasSize(3)
.containsEntry("nameX", null)
.containsEntry("name1", "foo")
.containsEntry("name2", "bar");
}
@Test
public void testDelimitedToMap_when_null() {
Map<String, String> map = StringHelper.delimitedToMap(null, ";", "=");
assertThat(map).isEmpty();
}
@Test
public void testDelimitedToMap_when_empty() {
Map<String, String> map = StringHelper.delimitedToMap("", ";", "=");
assertThat(map).isEmpty();
}
}
@@ -0,0 +1,135 @@
package io.ebean;
import io.ebean.bean.EntityBean;
import io.ebean.bean.EntityBeanIntercept;
import io.ebeaninternal.server.core.DefaultBeanState;
import org.tests.model.embedded.EMain;
import org.tests.model.embedded.Eembeddable;
import org.junit.Assert;
import org.junit.Test;
import java.util.Map;
import java.util.Set;
public class TestDirtyProperties extends BaseTestCase {
@Test
public void testEmbeddedUpdateEmbeddedProperty() {
EMain emain = new EMain();
EntityBean eb = (EntityBean) emain;
EntityBeanIntercept ebi = eb._ebean_getIntercept();
emain.setId(1);
emain.setName("foo");
Eembeddable embeddable = setEmbeddedBean(emain, "bar");
setEmbeddedLoaded(embeddable);
// sets loaded state so follow setters are deemed as changes to the bean
ebi.setLoaded();
emain.setName("changedFoo");
DefaultBeanState beanState = new DefaultBeanState(eb);
Set<String> changedProps = beanState.getChangedProps();
Assert.assertEquals(1, changedProps.size());
Assert.assertTrue(changedProps.contains("name"));
Map<String, ValuePair> dirtyValues = beanState.getDirtyValues();
Assert.assertEquals(1, dirtyValues.size());
Assert.assertTrue(dirtyValues.keySet().contains("name"));
ValuePair valuePair = dirtyValues.get("name");
Assert.assertNotNull(valuePair);
Assert.assertEquals("changedFoo", valuePair.getNewValue());
Assert.assertEquals("foo", valuePair.getOldValue());
Eembeddable embeddableRead = emain.getEmbeddable();
embeddableRead.setDescription("embChanged");
Set<String> changedProps2 = beanState.getChangedProps();
Assert.assertEquals(2, changedProps2.size());
Assert.assertTrue(changedProps2.contains("name"));
Assert.assertTrue(changedProps2.contains("embeddable.description"));
Map<String, ValuePair> dirtyValues2 = beanState.getDirtyValues();
Assert.assertEquals(2, dirtyValues2.size());
Assert.assertTrue(dirtyValues2.keySet().contains("name"));
Assert.assertTrue(dirtyValues2.keySet().contains("embeddable.description"));
ValuePair valuePair2 = dirtyValues2.get("embeddable.description");
Assert.assertEquals("embChanged", valuePair2.getNewValue());
Assert.assertEquals("bar", valuePair2.getOldValue());
}
@Test
public void testEmbeddedUpdateSetNewBean() {
EMain emain = new EMain();
EntityBean eb = (EntityBean) emain;
EntityBeanIntercept ebi = eb._ebean_getIntercept();
emain.setId(1);
emain.setName("foo");
Eembeddable embeddable = setEmbeddedBean(emain, "bar");
setEmbeddedLoaded(embeddable);
// sets loaded state so follow setters are deemed as changes to the bean
ebi.setLoaded();
emain.setName("changedFoo");
Assert.assertSame(embeddable, emain.getEmbeddable());
Eembeddable embeddable2 = setEmbeddedBean(emain, "changeEmbeddedInstance");
Assert.assertSame(embeddable2, emain.getEmbeddable());
Assert.assertNotSame(embeddable, emain.getEmbeddable());
DefaultBeanState beanState = new DefaultBeanState(eb);
Set<String> changedProps2 = beanState.getChangedProps();
Assert.assertEquals(2, changedProps2.size());
Assert.assertTrue(changedProps2.contains("name"));
Assert.assertTrue("The whole bean instance has changed", changedProps2.contains("embeddable"));
Map<String, ValuePair> dirtyValues2 = beanState.getDirtyValues();
Assert.assertEquals(2, dirtyValues2.size());
Assert.assertTrue(dirtyValues2.keySet().contains("name"));
Assert.assertTrue(dirtyValues2.keySet().contains("embeddable"));
ValuePair valuePair2 = dirtyValues2.get("embeddable");
Assert.assertSame(embeddable2, valuePair2.getNewValue());
Assert.assertSame(embeddable, valuePair2.getOldValue());
}
private void setEmbeddedLoaded(Eembeddable embeddable) {
((EntityBean) embeddable)._ebean_getIntercept().setLoaded();
}
private Eembeddable setEmbeddedBean(EMain emain, String description) {
Eembeddable embeddable = new Eembeddable();
embeddable.setDescription(description);
emain.setEmbeddable(embeddable);
EntityBean owner = (EntityBean) emain;
EntityBeanIntercept ebi = owner._ebean_getIntercept();
// hooks the embeddable bean back to the owner
int embeddablePropertyIndex = ebi.findProperty("embeddable");
Assert.assertTrue(embeddablePropertyIndex > -1);
((EntityBean) embeddable)._ebean_getIntercept().setEmbeddedOwner(owner, embeddablePropertyIndex);
return embeddable;
}
}
@@ -0,0 +1,26 @@
package io.ebean;
import org.tests.model.basic.Order;
import org.tests.model.basic.ResetBasicData;
import org.junit.Assert;
import org.junit.Test;
import java.util.List;
public class TestFilterWithEnum extends BaseTestCase {
@Test
public void test() throws InterruptedException {
ResetBasicData.reset();
List<Order> allOrders = Ebean.find(Order.class).findList();
Filter<Order> filter = Ebean.filter(Order.class);
List<Order> newOrders = filter.eq("status", Order.Status.NEW).filter(allOrders);
Assert.assertNotNull(newOrders);
}
}
@@ -0,0 +1,123 @@
package io.ebean;
import io.ebean.annotation.IgnorePlatform;
import io.ebean.annotation.Platform;
import io.ebean.bean.EntityBean;
import org.ebeantest.LoggedSqlCollector;
import org.junit.Test;
import org.tests.model.converstation.User;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
public class TestUnsetLoadedProperties extends BaseTestCase {
@Test
public void testUnsetPropertyLoadedState() {
// populate db with a user
User seed = new User();
seed.setName("someName");
seed.setEmail("some@junk.com");
seed.save();
// our bean to perform stateless update
User user = new User();
user.setId(seed.getId());
user.setName("name mod");
user.setEmail("change@junk.com");
BeanState beanState = Ebean.getBeanState(user);
assertThat(beanState.getLoadedProps()).containsExactly("id", "name", "email");
user.markPropertyUnset("email");
assertThat(beanState.getLoadedProps()).containsExactly("id", "name");
LoggedSqlCollector.start();
user.update();
List<String> loggedSql = LoggedSqlCollector.stop();
assertThat(loggedSql).hasSize(1);
assertThat(loggedSql.get(0)).doesNotContain("email");
}
@Test
public void testUnloadVia_EntityBeanIntercept_setPropertyLoaded() {
// our bean to perform stateless update
User user = new User();
user.setId(42L);
user.setName("name mod");
user.setEmail("change@junk.com");
BeanState beanState = Ebean.getBeanState(user);
assertThat(beanState.getLoadedProps()).containsExactly("id", "name", "email");
// unset the loaded state for email
((EntityBean) user)._ebean_getIntercept().setPropertyLoaded("email", false);
assertThat(beanState.getLoadedProps()).containsExactly("id", "name");
}
@Test
public void testUnloadVia_Model_markPropertyUnset() {
// our bean to perform stateless update
User user = new User();
user.setId(42L);
user.setName("name mod");
user.setEmail("change@junk.com");
BeanState beanState = Ebean.getBeanState(user);
assertThat(beanState.getLoadedProps()).containsExactly("id", "name", "email");
user.markPropertyUnset("email");
assertThat(beanState.getLoadedProps()).containsExactly("id", "name");
}
@Test
public void testUnloadVia_BeanState_setPropertyLoaded() {
// our bean to perform stateless update
User user = new User();
user.setId(42L);
user.setName("name mod");
user.setEmail("change@junk.com");
BeanState beanState = Ebean.getBeanState(user);
assertThat(beanState.getLoadedProps()).containsExactly("id", "name", "email");
Ebean.getBeanState(user).setPropertyLoaded("email", false);
assertThat(beanState.getLoadedProps()).containsExactly("id", "name");
}
/**
* Strange sql server error that needs to be reviewed.
*/
@IgnorePlatform(Platform.SQLSERVER)
@Test
public void test_markVersionUnset_expect_no_optimistic_locking() {
// our bean to perform stateless update
User newUser = new User();
newUser.setName("some occ");
newUser.setEmail("some@oss.com");
newUser.save();
User updUser = Ebean.find(User.class, newUser.getId());
updUser.setName("mod occ");
updUser.markPropertyUnset("version");
LoggedSqlCollector.start();
updUser.save();
List<String> sql = LoggedSqlCollector.stop();
assertSql(sql.get(0)).contains("where id=?;");
}
}
@@ -0,0 +1,81 @@
package io.ebean;
import io.ebean.Ebean;
import io.ebean.search.Match;
import io.ebean.search.MultiMatch;
import org.tests.model.basic.Order;
import org.junit.Test;
public class TextExpressionListTest {
@Test
public void syntax() {
Ebean.find(Order.class)
.text().match("name", "rob");
Ebean.find(Order.class)
.text().should()
.match("name", "rob")
.match("note", "war and peace");
Ebean.find(Order.class)
.text()
.should()
.match("title", "war and peace")
.match("author", "leo tolstoy")
.should()
.match("translator", "Constance Garnett")
.match("translator", "Louise Maude");
Ebean.find(Order.class)
.text()
.should()
.match("title", "war and peace")
.match("author", "leo tolstoy")
.should()
.match("translator", "Constance Garnett", new Match().opAnd().boost(2).minShouldMatch("75%"))
.match("translator", "Louise Maude")
.where()
.gt("reviewDate", 12345);
Ebean.find(Order.class)
.text()
.must()
.match("title", "quick")
.endJunction()
.should()
.match("title", "brown")
.match("title", "dog")
.endJunction()
.mustNot()
.match("title", "lazy")
.endJunction()
.where()
.gt("reviewDate", 12345);
}
@Test
public void syntax_multiMatch() {
Ebean.find(Order.class)
.text()
.multiMatch("Will Smith", "title", "*name");
MultiMatch match = MultiMatch.fields("title", "*name")
.opAnd()
.type(MultiMatch.Type.PHRASE_PREFIX);
Ebean.find(Order.class)
.text()
.multiMatch("Will Smith", match);
}
}
@@ -0,0 +1,30 @@
package io.ebean;
import org.junit.After;
import org.junit.Before;
import org.tests.model.basic.ResetBasicData;
/**
* Transactional test case. Every test is covered by a transaction, which is roll backed.
* So no changes will persist to database.
*
* Use this test case if you modify data in your test case, so that the test does not interfere
* other tests.
*
* @author Roland Praml, FOCONIS AG
*
*/
public abstract class TransactionalTestCase extends BaseTestCase {
@Before
public void startTransaction() {
ResetBasicData.reset();
Ebean.beginTransaction();
}
@After
public void endTransaction() {
Ebean.rollbackTransaction();
Ebean.endTransaction();
}
}
@@ -0,0 +1,68 @@
package io.ebean;
import io.ebean.annotation.PersistBatch;
import org.junit.Test;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNull;
public class TxScopeTest {
@Test
public void checkBatchMode_when_bothNull() throws Exception {
TxScope scope = new TxScope();
scope.setBatchSize(100);
assertNull(scope.getBatch());
assertNull(scope.getBatchOnCascade());
scope.checkBatchMode();
assertEquals(scope.getBatch(), PersistBatch.ALL);
}
@Test
public void checkBatchMode_when_bothInherit() throws Exception {
TxScope scope = new TxScope();
scope.setBatchSize(100);
scope.setBatch(PersistBatch.INHERIT);
scope.setBatchOnCascade(PersistBatch.INHERIT);
scope.checkBatchMode();
assertEquals(scope.getBatch(), PersistBatch.ALL);
}
@Test
public void checkBatchMode_when_batchSizeZero_and_onCascadeInherit() throws Exception {
TxScope scope = new TxScope();
scope.setBatchOnCascade(PersistBatch.INHERIT);
scope.checkBatchMode();
assertNull(scope.getBatch());
}
@Test
public void checkBatchMode_when_batchSizeZero_and_bothInherit() throws Exception {
TxScope scope = new TxScope();
scope.setBatch(PersistBatch.INHERIT);
scope.setBatchOnCascade(PersistBatch.INHERIT);
scope.checkBatchMode();
assertEquals(scope.getBatch(), PersistBatch.INHERIT);
}
@Test
public void checkBatchMode_when_onCascadeSet() throws Exception {
TxScope scope = new TxScope();
scope.setBatchSize(100);
scope.setBatchOnCascade(PersistBatch.ALL);
scope.checkBatchMode();
assertNull(scope.getBatch());
}
}
@@ -0,0 +1,436 @@
package io.ebean;
import io.ebean.annotation.ForPlatform;
import io.ebean.annotation.IgnorePlatform;
import io.ebean.annotation.Platform;
import io.ebean.meta.MetaQueryMetric;
import io.ebean.meta.ServerMetrics;
import org.ebeantest.LoggedSqlCollector;
import org.junit.Test;
import org.tests.model.basic.Country;
import org.tests.model.basic.Customer;
import org.tests.model.basic.EBasicWithUniqueCon;
import org.tests.model.basic.ResetBasicData;
import java.sql.Timestamp;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
public class UpdateQueryTest extends BaseTestCase {
@Test
public void basic() {
resetAllMetrics();
EbeanServer server = server();
UpdateQuery<Customer> update = server.update(Customer.class);
Query<Customer> query = update
.set("status", Customer.Status.ACTIVE)
.set("updtime", new Timestamp(System.currentTimeMillis()))
.where()
.eq("status", Customer.Status.NEW)
.gt("id", 1000)
.setLabel("updateActive");
query.update();
assertSql(query).contains("update o_customer set status=?, updtime=? where status = ? and id > ?");
ServerMetrics metrics = collectMetrics();
List<MetaQueryMetric> ormQueryMetrics = metrics.getQueryMetrics();
assertThat(ormQueryMetrics).hasSize(1);
assertThat(ormQueryMetrics.get(0).getType()).isEqualTo(Customer.class);
assertThat(ormQueryMetrics.get(0).getLabel()).isEqualTo("updateActive");
}
@Test
public void update() {
ResetBasicData.reset();
resetAllMetrics();
UpdateQuery<Customer> update = server().update(Customer.class);
LoggedSqlCollector.start();
int rows = update
.setRaw("status = status")
.setLabel("updateAll")
.update();
List<String> sql = LoggedSqlCollector.stop();
assertThat(sql).hasSize(1);
assertThat(rows).isGreaterThan(0);
assertSql(sql.get(0)).contains("update o_customer set status = status");
ServerMetrics metrics = collectMetrics();
List<MetaQueryMetric> ormQueryMetrics = metrics.getQueryMetrics();
assertThat(ormQueryMetrics).hasSize(1);
assertThat(ormQueryMetrics.get(0).getType()).isEqualTo(Customer.class);
assertThat(ormQueryMetrics.get(0).getLabel()).isEqualTo("updateAll");
}
@Test
public void query_asUpdate() {
ResetBasicData.reset();
LoggedSqlCollector.start();
int rows = server().find(Customer.class)
.where()
.gt("id", 1000)
.asUpdate()
.setRaw("status = status")
.setLabel("asUpdate")
.update();
List<String> sql = LoggedSqlCollector.stop();
assertThat(sql).hasSize(1);
assertThat(rows).isEqualTo(0);
assertSql(sql.get(0)).contains("update o_customer set status = status where id > ?");
}
@Test
public void query_asUpdate_idIn() {
ResetBasicData.reset();
LoggedSqlCollector.start();
int rows = server().find(Customer.class)
.where()
.idIn(1000, 1001, 1002)
.asUpdate()
.setRaw("status = ?", "A")
.setLabel("asUpdateByIds")
.update();
List<String> sql = LoggedSqlCollector.stop();
assertThat(sql).hasSize(1);
assertThat(rows).isEqualTo(0);
if (isPostgres()) {
assertSql(sql.get(0)).contains("update o_customer set status = ? where id = any(?)");
} else {
assertSql(sql.get(0)).contains("update o_customer set status = ? where id in (?,?,?,?,?)"); // bind padding to 5
}
}
@Test
public void update_withTransactionBatch() {
EbeanServer server = server();
try (Transaction transaction = server.beginTransaction()) {
transaction.setBatchMode(true);
UpdateQuery<Customer> update = server.update(Customer.class);
Query<Customer> query = update
.set("status", Customer.Status.ACTIVE)
.set("updtime", new Timestamp(System.currentTimeMillis()))
.where()
.eq("status", Customer.Status.NEW)
.gt("id", 99999)
.query();
// update executes now regardless of transaction batch mode
int rows = query.update();
assertThat(rows).isEqualTo(0);
transaction.commit();
}
}
@Test
@IgnorePlatform(Platform.SQLSERVER)
public void withTableAlias() {
EbeanServer server = server();
UpdateQuery<Customer> update = server.update(Customer.class);
Query<Customer> query = update
.set("status", Customer.Status.ACTIVE)
.set("updtime", new Timestamp(System.currentTimeMillis()))
.where()
.gt("id", 1000)
.query();
query.alias("cust");
query.update();
assertSql(query).contains("update o_customer cust set status=?, updtime=? where id > ?");
}
@IgnorePlatform({Platform.MYSQL, Platform.MARIADB})
@Test
public void withJoin() {
EbeanServer server = server();
Country nz = server.getReference(Country.class, "NZ");
UpdateQuery<Customer> update = server.update(Customer.class);
Query<Customer> query = update
.set("status", Customer.Status.ACTIVE)
.set("updtime", new Timestamp(System.currentTimeMillis()))
.where()
.eq("status", Customer.Status.NEW)
.eq("billingAddress.country", nz)
//.isEmpty("contacts")
.gt("id", 1000)
.query();
query.update();
assertThat(sqlOf(query)).contains("update o_customer set status=?, updtime=? where id in (select t0.id from o_customer t0 left join o_address t1 on t1.id = t0.billing_address_id where t0.status = ? and t1.country_code = ? and t0.id > ?)");
}
@ForPlatform({Platform.H2, Platform.POSTGRES})
@Test
public void withJoinAndLimit() {
EbeanServer server = server();
Country nz = server.getReference(Country.class, "NZ");
LoggedSqlCollector.start();
server.update(Customer.class)
.set("status", Customer.Status.ACTIVE)
.where()
.eq("billingAddress.country", nz)
.gt("id", 1000)
.setMaxRows(100)
.update();
final List<String> sql = LoggedSqlCollector.stop();
assertSql(sql.get(0)).contains("update o_customer set status=? where id in (select t0.id from o_customer t0 left join o_address t1 on t1.id = t0.billing_address_id where t1.country_code = ? and t0.id > ? limit 100)");
}
@ForPlatform({Platform.H2, Platform.POSTGRES, Platform.MYSQL, Platform.MARIADB})
@Test
public void simpleWithLimit() {
EbeanServer server = server();
LoggedSqlCollector.start();
server.update(Customer.class)
.set("status", Customer.Status.ACTIVE)
.where()
.gt("id", 1000)
.setMaxRows(100)
.update();
final List<String> sql = LoggedSqlCollector.stop();
if (isMySql() || isH2() || isMariaDB()) {
assertSql(sql.get(0)).contains("update o_customer set status=? where id > ? limit 100");
} else {
assertSql(sql.get(0)).contains("update o_customer set status=? where id in (select t0.id from o_customer t0 where t0.id > ? limit 100)");
}
}
@Test
public void whereIsEmpty() {
EbeanServer server = server();
Query<Customer> updateQuery = server
.update(Customer.class)
.set("status", Customer.Status.ACTIVE)
.where()
.isEmpty("contacts")
.gt("id", 1000)
.query();
updateQuery.update();
assertThat(updateQuery.getGeneratedSql()).contains("update o_customer set status=? where not exists (select 1 from contact x where x.customer_id = id) and id > ?");
}
@Test
public void setNull() {
EbeanServer server = server();
Query<Customer> updateQuery = server
.update(Customer.class)
.setNull("status")
.where()
.gt("id", 1000)
.query();
updateQuery.update();
assertThat(updateQuery.getGeneratedSql()).contains("update o_customer set status=null where id > ?");
}
@Test
public void set_whenValueIsNull_expectNull() {
EbeanServer server = server();
Query<Customer> updateQuery = server
.update(Customer.class)
.set("status", null)
.where()
.gt("id", 1000)
.query();
updateQuery.update();
assertThat(updateQuery.getGeneratedSql()).contains("update o_customer set status=null where id > ?");
}
@Test
public void setExpression() {
EbeanServer server = server();
Query<Customer> updateQuery = server
.update(Customer.class)
.setRaw("status = coalesce(status, 'A')")
.where()
.gt("id", 1000)
.query();
updateQuery.update();
assertThat(updateQuery.getGeneratedSql()).contains("update o_customer set status = coalesce(status, 'A') where id > ?");
}
@Test
public void setExpression_withBind() {
EbeanServer server = server();
Query<Customer> updateQuery = server
.update(Customer.class)
.setRaw("status = coalesce(status, ?)", Customer.Status.ACTIVE)
.where()
.gt("id", 1000)
.query();
updateQuery.update();
assertThat(updateQuery.getGeneratedSql()).contains("update o_customer set status = coalesce(status, ?) where id > ?");
}
@Test
public void fluidSyntax() {
EbeanServer server = server();
int rows = server
.update(Customer.class)
.setRaw("status = coalesce(status, ?)", Customer.Status.ACTIVE)
.where()
.gt("id", 10000)
.update();
assertThat(rows).isEqualTo(0);
}
@Test
public void updateQuery_withExplicitTransaction() {
EbeanServer server = server();
int rowsExprList;
int rowsQuery;
try (Transaction transaction = server.beginTransaction()) {
rowsExprList = server
.update(Customer.class)
.setRaw("status = coalesce(status, ?)", Customer.Status.ACTIVE)
.where()
.gt("id", 10000)
.update(transaction);
rowsQuery = server
.update(Customer.class)
.setRaw("status = coalesce(status, ?)", Customer.Status.ACTIVE)
.where()
.gt("id", 10001)
.query().update(transaction);
transaction.commit();
}
assertThat(rowsExprList).isEqualTo(0);
assertThat(rowsQuery).isEqualTo(0);
}
@Test
public void deleteQuery_withExplicitTransaction() {
EbeanServer server = server();
int rowsExprList;
int rowsQuery;
try (Transaction transaction = server.beginTransaction()) {
rowsExprList = server
.update(Customer.class)
.where()
.gt("id", 10000)
.delete(transaction);
rowsQuery = server
.update(Customer.class)
.where()
.gt("id", 10001)
.query().delete(transaction);
transaction.commit();
}
assertThat(rowsExprList).isEqualTo(0);
assertThat(rowsQuery).isEqualTo(0);
}
@Test
public void useViaEbean() {
int rows = Ebean.update(Customer.class)
.setRaw("status = coalesce(status, ?)", Customer.Status.ACTIVE)
.where()
.gt("id", 10000)
.update();
assertThat(rows).isEqualTo(0);
}
@Test(expected = DuplicateKeyException.class)
public void exceptionTranslation() {
newEbasicWithUnique("o1","other1_a");
Integer id = newEbasicWithUnique("o2", "other1_b");
Ebean.update(EBasicWithUniqueCon.class)
.set("other", "other1_a")
.set("otherOne", "other1_a")
.where().idEq(id)
.update();
}
private Integer newEbasicWithUnique(String name, String other) {
EBasicWithUniqueCon b0 = new EBasicWithUniqueCon();
b0.setName(name);
b0.setOther(other);
b0.setOtherOne(other);
Ebean.save(b0);
return b0.getId();
}
}
@@ -0,0 +1,16 @@
package io.ebean.annotation;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
* Annotation to run a test for a certain platform.
* @author Roland Praml, FOCONIS AG
*/
@Target(ElementType.METHOD )
@Retention(RetentionPolicy.RUNTIME)
public @interface ForPlatform {
Platform[] value();
}
@@ -0,0 +1,16 @@
package io.ebean.annotation;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
* Annotation to ignore a test for a certain platform.
* @author Roland Praml, FOCONIS AG
*/
@Target(ElementType.METHOD )
@Retention(RetentionPolicy.RUNTIME)
public @interface IgnorePlatform {
Platform[] value();
}
@@ -0,0 +1,135 @@
package io.ebean.bean;
import io.ebean.BaseTestCase;
import io.ebean.DB;
import org.tests.compositekeys.db.AuditInfo;
import org.tests.model.basic.Customer;
import org.tests.model.basic.EBasic;
import org.tests.model.basic.ResetBasicData;
import org.junit.Test;
import java.sql.Date;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
public class EntityBeanInterceptTest extends BaseTestCase {
@Test
public void testHasDirtyProperty() {
ResetBasicData.reset();
List<Customer> list = DB.find(Customer.class).findList();
Set<String> propertyNames = new HashSet<>();
propertyNames.add("name");
propertyNames.add("status");
Customer customer = list.get(0);
EntityBeanIntercept ebi = ebi(customer);
assertFalse(ebi.hasDirtyProperty(propertyNames));
customer.setAnniversary(new Date(System.currentTimeMillis()));
assertFalse(ebi.hasDirtyProperty(propertyNames));
customer.setStatus(Customer.Status.ACTIVE);
assertTrue(ebi.hasDirtyProperty(propertyNames));
}
@Test
public void isPartial_when_new() {
EBasic basic = new EBasic();
EntityBeanIntercept ebi = ebi(basic);
assertThat(ebi.isPartial()).isTrue();
}
@Test
public void isPartial_when_partial() {
EBasic basic = new EBasic();
basic.setId(42);
basic.setName("some");
EntityBeanIntercept ebi = ebi(basic);
assertThat(ebi.isPartial()).isTrue();
}
@Test
public void isPartial_when_full() {
EBasic basic = new EBasic();
basic.setId(42);
basic.setName("some");
basic.setDescription("asd");
basic.setSomeDate(null);
basic.setStatus(EBasic.Status.ACTIVE);
EntityBeanIntercept ebi = ebi(basic);
assertThat(ebi.isPartial()).isFalse();
}
@Test
public void isEmbeddedNewOrDirty() {
AuditInfo auditInfo = new AuditInfo();
EntityBeanIntercept ebi = ebi(auditInfo);
assertTrue(ebi.isNew());
assertTrue(ebi.isEmbeddedNewOrDirty(auditInfo));
auditInfo.setUpdatedBy("initial");
ebi.setLoaded();
assertTrue(ebi.isLoaded());
assertFalse(ebi.isEmbeddedNewOrDirty(auditInfo));
auditInfo.setUpdatedBy("nowDirty");
assertTrue(ebi.isDirty());
assertTrue(ebi.isEmbeddedNewOrDirty(auditInfo));
assertFalse(ebi.isEmbeddedNewOrDirty(null));
}
@Test
public void setEmbeddedLoaded() {
AuditInfo auditInfo = new AuditInfo();
EntityBeanIntercept ebi = ebi(auditInfo);
assertFalse(ebi.isLoaded());
ebi.setEmbeddedLoaded(auditInfo);
assertTrue(ebi.isLoaded());
}
@Test
public void initialisedMany() {
Customer customer = new Customer();
EntityBeanIntercept ebi = ebi(customer);
final int contactsPos = findProperty("contacts", ebi);
assertFalse(ebi.isLoadedProperty(contactsPos));
ebi.initialisedMany(contactsPos);
assertTrue(ebi.isLoadedProperty(contactsPos));
}
private int findProperty(String name, EntityBeanIntercept eb) {
final String[] names = eb.getOwner()._ebean_getPropertyNames();
for (int i = 0; i < names.length; i++) {
if (names[i].equals(name)) {
return i;
}
}
throw new RuntimeException("property not found");
}
@SuppressWarnings("unchecked")
private EntityBeanIntercept ebi(Object bean) {
return ((EntityBean)bean)._ebean_getIntercept();
}
}
@@ -0,0 +1,72 @@
package io.ebean.cache;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class CacheKeyTest {
@Test
public void equals_when_null_tenantId() {
TenantAwareKey.CacheKey key0 = key("12", null);
TenantAwareKey.CacheKey key1 = key("12", null);
assertMatchEquals(key0, key1);
}
private void assertMatchEquals(TenantAwareKey.CacheKey key0, TenantAwareKey.CacheKey key1) {
assertThat(key0.hashCode()).isEqualTo(key1.hashCode());
assertThat(key0.equals(key1)).isTrue();
assertThat(key0.toString()).isEqualTo(key1.toString());
}
@Test
public void equals_when_same_tenantId() {
TenantAwareKey.CacheKey key0 = key(42L, "1");
TenantAwareKey.CacheKey key1 = key(42L, "1");
assertMatchEquals(key0, key1);
}
@Test
public void not_equal_when_diff_both() {
TenantAwareKey.CacheKey key0 = key(42L, "1");
TenantAwareKey.CacheKey key1 = key(43L, "2");
assertThat(key0.equals(key1)).isFalse();
}
@Test
public void not_equal_when_diff_key() {
TenantAwareKey.CacheKey key0 = key(42L, "1");
TenantAwareKey.CacheKey key1 = key(43L, "1");
assertThat(key0.equals(key1)).isFalse();
}
@Test
public void not_equal_when_diff_key_andNoTenantId() {
TenantAwareKey.CacheKey key0 = key(42L, null);
TenantAwareKey.CacheKey key1 = key(43L, null);
assertThat(key0.equals(key1)).isFalse();
}
@Test
public void not_equal_when_diff_tenantId() {
TenantAwareKey.CacheKey key0 = key(42L, "1");
TenantAwareKey.CacheKey key1 = key(42L, "2");
assertThat(key0.equals(key1)).isFalse();
}
private TenantAwareKey.CacheKey key(Object key, Object tenantId) {
return new TenantAwareKey.CacheKey(key, tenantId);
}
}
@@ -0,0 +1,48 @@
package io.ebean.cache;
import io.ebean.DB;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
public class ServerCacheManagerTest {
@Test
public void test() {
ServerCacheManager cacheManager = DB.getDefault().getServerCacheManager();
for (ServerCacheRegion region : cacheManager.allRegions()) {
assertTrue(region.isEnabled());
}
cacheManager.setEnabledRegions("r0,doesNotExist");
assertThat(cacheManager.getRegion("email").isEnabled()).isFalse();
assertThat(cacheManager.getRegion("r0").isEnabled()).isTrue();
cacheManager.setEnabledRegions("r0");
assertThat(cacheManager.getRegion("email").isEnabled()).isFalse();
assertThat(cacheManager.getRegion("r0").isEnabled()).isTrue();
cacheManager.setEnabledRegions(null);
assertThat(cacheManager.getRegion("email").isEnabled()).isFalse();
assertThat(cacheManager.getRegion("r0").isEnabled()).isTrue();
cacheManager.setEnabledRegions("email");
assertThat(cacheManager.getRegion("email").isEnabled()).isTrue();
assertThat(cacheManager.getRegion("r0").isEnabled()).isFalse();
cacheManager.setAllRegionsEnabled(false);
for (ServerCacheRegion region : cacheManager.allRegions()) {
assertFalse(region.isEnabled());
}
cacheManager.setAllRegionsEnabled(true);
for (ServerCacheRegion region : cacheManager.allRegions()) {
assertTrue(region.isEnabled());
}
}
}
@@ -0,0 +1,30 @@
package io.ebean.cache;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class ServerCacheOptionsTest {
@Test
public void copy_when_off() {
ServerCacheOptions basic = new ServerCacheOptions();
assertThat(basic.isNearCache()).isFalse();
ServerCacheOptions copy = basic.copy(true);
assertThat(copy.isNearCache()).isTrue();
}
@Test
public void copy_when_on() {
ServerCacheOptions basic = new ServerCacheOptions();
basic.setNearCache(true);
assertThat(basic.isNearCache()).isTrue();
ServerCacheOptions copy = basic.copy(false);
assertThat(copy.isNearCache()).isFalse();
}
}
@@ -0,0 +1,345 @@
package io.ebean.common;
import io.ebean.bean.BeanCollection;
import org.junit.Test;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
public class BeanListTest {
private Object object1 = new Object();
private Object object2 = new Object();
private Object object3 = new Object();
private List<Object> all() {
List<Object> all = new ArrayList<>();
all.add(object1);
all.add(object2);
all.add(object3);
return all;
}
private List<Object> some() {
List<Object> some = new ArrayList<>();
some.add(object2);
some.add(object3);
return some;
}
@Test
public void test_setModifyListening_null() throws Exception {
BeanList<Object> list = new BeanList<>();
list.setModifyListening(null);
// act
list.addAll(all());
assertThat(list.getModifyAdditions()).isNull();
}
@Test
public void test_setModifyListening_none() throws Exception {
BeanList<Object> list = new BeanList<>();
list.setModifyListening(BeanCollection.ModifyListenMode.NONE);
// act
list.addAll(all());
assertThat(list.getModifyAdditions()).isNull();
}
@Test
public void testAdd() throws Exception {
BeanList<Object> list = new BeanList<>();
list.setModifyListening(BeanCollection.ModifyListenMode.ALL);
list.add(object1);
assertThat(list.getModifyAdditions()).containsExactly(object1);
assertThat(list.getModifyRemovals()).isEmpty();
list.add(object1);
assertThat(list.getModifyAdditions()).containsExactly(object1);
list.add(object2);
assertThat(list.getModifyAdditions()).containsExactly(object1, object2);
list.remove(object1);
assertThat(list.getModifyAdditions()).containsExactly(object2);
assertThat(list.getModifyRemovals()).isEmpty();
}
@Test
public void testAddAll_given_emptyStart() throws Exception {
BeanList<Object> list = new BeanList<>();
list.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
list.addAll(all());
assertThat(list.getModifyAdditions()).containsExactly(object1, object2, object3);
assertThat(list.getModifyRemovals()).isEmpty();
}
@Test
public void test_removals_DeleteThenAddBack_expect_noChange() throws Exception {
BeanList<Object> list = new BeanList<>(some());
list.setModifyListening(BeanCollection.ModifyListenMode.REMOVALS);
// act
list.remove(object2);
assertThat(list.getModifyRemovals()).isNotEmpty();
list.add(object2);
assertThat(list.getModifyRemovals()).isEmpty();
assertThat(list.getModifyAdditions()).isEmpty();
}
@Test
public void test_sort_whenAll_expect_noChange() throws Exception {
BeanList<Object> list = new BeanList<>(all());
list.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
Collections.sort(list, Comparator.comparingInt(Object::hashCode));
assertThat(list.getModifyRemovals()).isEmpty();
assertThat(list.getModifyAdditions()).isEmpty();
}
@Test
public void test_sort_whenRemovals_expect_noChange() throws Exception {
BeanList<Object> list = new BeanList<>(all());
list.setModifyListening(BeanCollection.ModifyListenMode.REMOVALS);
// act
Collections.sort(list, Comparator.comparingInt(Object::hashCode));
assertThat(list.getModifyRemovals()).isEmpty();
assertThat(list.getModifyAdditions()).isEmpty();
}
@Test
public void testAdd_given_someAlreadyIn() throws Exception {
BeanList<Object> list = new BeanList<>(some());
list.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
assertThat(list.contains(object1)).isFalse();
list.add(object1);
assertThat(list.contains(object2)).isTrue();
list.add(object2); // object2 added as List allows duplicates
assertThat(list.getModifyAdditions()).containsExactly(object1, object2);
assertThat(list.getModifyRemovals()).isEmpty();
}
@Test
public void testAddSome_given_someAlreadyIn() throws Exception {
BeanList<Object> list = new BeanList<>(some());
list.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
list.addAll(all());
assertThat(list.getModifyAdditions()).containsExactly(object1, object2, object3);
assertThat(list.getModifyRemovals()).isEmpty();
}
@Test
public void testRemove_given_beansInAdditions() throws Exception {
BeanList<Object> list = new BeanList<>();
list.setModifyListening(BeanCollection.ModifyListenMode.ALL);
list.addAll(all());
assertThat(list.getModifyAdditions()).containsExactly(object1, object2, object3);
// act
list.remove(object2);
list.remove(object3);
assertThat(list.getModifyAdditions()).containsExactly(object1);
assertThat(list.getModifyRemovals()).isEmpty();
}
@Test
public void testRemoveAll_given_beansInAdditions() throws Exception {
BeanList<Object> list = new BeanList<>();
list.setModifyListening(BeanCollection.ModifyListenMode.ALL);
list.addAll(all());
assertThat(list.getModifyAdditions()).containsExactly(object1, object2, object3);
// act
list.removeAll(some());
assertThat(list.getModifyAdditions()).containsExactly(object1);
assertThat(list.getModifyRemovals()).isEmpty();
}
@Test
public void testRemove_given_beansNotInAdditions() throws Exception {
BeanList<Object> list = new BeanList<>(all());
list.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
list.remove(object2);
list.remove(object3);
// assert
assertThat(list.getModifyAdditions()).isEmpty();
assertThat(list.getModifyRemovals()).containsExactly(object2, object3);
}
@Test
public void testRemoveAll_given_beansNotInAdditions() throws Exception {
BeanList<Object> list = new BeanList<>(all());
list.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
list.removeAll(some());
// assert
assertThat(list.getModifyAdditions()).isEmpty();
assertThat(list.getModifyRemovals()).containsExactly(object2, object3);
}
@Test
public void testClear() throws Exception {
BeanList<Object> list = new BeanList<>(all());
list.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
list.clear();
//assert
assertThat(list.getModifyRemovals()).containsExactly(object1, object2, object3);
assertThat(list.getModifyAdditions()).isEmpty();
}
@Test
public void testClear_given_someBeansInAdditions() throws Exception {
BeanList<Object> list = new BeanList<>();
list.add(object1);
list.setModifyListening(BeanCollection.ModifyListenMode.ALL);
list.add(object2);
list.add(object3);
// act
list.clear();
//assert
assertThat(list.getModifyRemovals()).containsExactly(object1);
assertThat(list.getModifyAdditions()).isEmpty();
}
@Test
public void testRetainAll_given_beansInAdditions() throws Exception {
BeanList<Object> list = new BeanList<>();
list.setModifyListening(BeanCollection.ModifyListenMode.ALL);
list.addAll(all());
assertThat(list.getModifyAdditions()).containsExactly(object1, object2, object3);
// act
list.retainAll(some());
assertThat(list.getModifyAdditions()).containsExactly(object2, object3);
assertThat(list.getModifyRemovals()).isEmpty();
}
@Test
public void testRetainAll_given_someBeansInAdditions() throws Exception {
BeanList<Object> list = new BeanList<>();
list.add(object1);
list.add(object2);
list.setModifyListening(BeanCollection.ModifyListenMode.ALL);
list.add(object3);
// act
list.retainAll(some());
assertThat(list.getModifyAdditions()).containsExactly(object3);
assertThat(list.getModifyRemovals()).containsExactly(object1);
}
@Test
public void testRetainAll_given_noBeansInAdditions() throws Exception {
BeanList<Object> list = new BeanList<>(all());
list.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
list.retainAll(some());
assertThat(list.getModifyRemovals()).containsExactly(object1);
}
@Test
public void internalAddWithCheck_when_interestingEquals_usesInstanceEquality() {
BeanList<Object> list = new BeanList<>();
assertThat(list).hasSize(0);
SomeBean a = new SomeBean("A");
list.internalAddWithCheck(a);
list.internalAddWithCheck(a);
assertThat(list).hasSize(1);
// expect to ignore equals and add as it is a diff instance (aka don't use equals())
list.internalAddWithCheck(new SomeBean("A"));
assertThat(list).hasSize(2);
list.internalAddWithCheck(new SomeBean("B"));
assertThat(list).hasSize(3);
}
/**
* A entity bean with interesting equals implementation.
*/
private static class SomeBean {
final String val;
SomeBean(String val) {
this.val = val;
}
@Override
public int hashCode() {
return 42;
}
@Override
public boolean equals(Object other) {
if (this == other) {
return true;
}
if (other instanceof SomeBean) {
return this.val.equals(((SomeBean) other).val);
} else {
return false;
}
}
}
}
@@ -0,0 +1,191 @@
package io.ebean.common;
import io.ebean.bean.BeanCollection;
import org.junit.Test;
import java.util.LinkedHashMap;
import java.util.Map;
import static org.assertj.core.api.Assertions.assertThat;
public class BeanMapTest {
Object object1 = new Object();
Object object2 = new Object();
Object object3 = new Object();
private Map<String, Object> all() {
Map<String, Object> all = new LinkedHashMap<>();
all.put("1", object1);
all.put("2", object2);
all.put("3", object3);
return all;
}
private Map<String, Object> some() {
Map<String, Object> all = new LinkedHashMap<>();
all.put("2", object2);
all.put("3", object3);
return all;
}
@Test
public void testAdd() throws Exception {
BeanMap<String, Object> map = new BeanMap<>();
map.setModifyListening(BeanCollection.ModifyListenMode.ALL);
map.put("1", object1);
map.put("4", null);
assertThat(map.getModifyAdditions()).containsExactly(object1);
assertThat(map.getModifyRemovals()).isEmpty();
map.put("1", object1);
map.put("4", null);
assertThat(map.getModifyAdditions()).containsExactly(object1);
map.put("2", object2);
assertThat(map.getModifyAdditions()).containsExactly(object1, object2);
map.remove("1");
assertThat(map.getModifyAdditions()).containsExactly(object2);
assertThat(map.getModifyRemovals()).isEmpty();
}
@Test
public void testAddAll_given_emptyStart() throws Exception {
BeanMap<String, Object> set = new BeanMap<>();
set.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
set.putAll(all());
assertThat(set.getModifyAdditions()).containsExactly(object1, object2, object3);
assertThat(set.getModifyRemovals()).isEmpty();
}
@Test
public void testAdd_given_someAlreadyIn() throws Exception {
BeanMap<String, Object> map = new BeanMap<>(some());
map.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
assertThat(map.values().contains(object1)).isFalse();
map.put("1", object1);
assertThat(map.values().contains(object2)).isTrue();
map.put("2", object2);
assertThat(map.getModifyAdditions()).containsExactly(object1);
assertThat(map.getModifyRemovals()).isEmpty();
}
@Test
public void testAddSome_given_someAlreadyIn() throws Exception {
BeanMap<String, Object> map = new BeanMap<>(some());
map.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
map.putAll(all());
assertThat(map.getModifyAdditions()).containsExactly(object1);
assertThat(map.getModifyRemovals()).isEmpty();
}
@Test
public void testRemove_given_beansInAdditions() throws Exception {
BeanMap<String, Object> map = new BeanMap<>();
map.setModifyListening(BeanCollection.ModifyListenMode.ALL);
map.putAll(all());
assertThat(map.getModifyAdditions()).containsExactly(object1, object2, object3);
// act
map.remove("2");
map.remove("3");
assertThat(map.getModifyAdditions()).containsExactly(object1);
assertThat(map.getModifyRemovals()).isEmpty();
}
@Test
public void testRemoveAll_given_beansInAdditions() throws Exception {
BeanMap<String, Object> map = new BeanMap<>();
map.setModifyListening(BeanCollection.ModifyListenMode.ALL);
map.putAll(all());
assertThat(map.getModifyAdditions()).containsExactly(object1, object2, object3);
// act
map.remove("2");
map.remove("3");
assertThat(map.getModifyAdditions()).containsExactly(object1);
assertThat(map.getModifyRemovals()).isEmpty();
}
@Test
public void testRemove_given_beansNotInAdditions() throws Exception {
BeanMap<String, Object> map = new BeanMap<>(all());
map.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
map.remove("2");
map.remove("3");
// assert
assertThat(map.getModifyAdditions()).isEmpty();
assertThat(map.getModifyRemovals()).containsExactly(object2, object3);
}
@Test
public void testRemoveAll_given_beansNotInAdditions() throws Exception {
BeanMap<String, Object> map = new BeanMap<>(all());
map.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
map.remove("2");
map.remove("3");
// assert
assertThat(map.getModifyAdditions()).isEmpty();
assertThat(map.getModifyRemovals()).containsExactly(object2, object3);
}
@Test
public void testClear() throws Exception {
BeanMap<String, Object> map = new BeanMap<>(all());
map.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
map.clear();
//assert
assertThat(map.getModifyRemovals()).containsExactly(object1, object2, object3);
assertThat(map.getModifyAdditions()).isEmpty();
}
@Test
public void testClear_given_someBeansInAdditions() throws Exception {
BeanMap<String, Object> map = new BeanMap<>();
map.put("1", object1);
map.setModifyListening(BeanCollection.ModifyListenMode.ALL);
map.put("2", object2);
map.put("3", object3);
// act
map.clear();
//assert
assertThat(map.getModifyRemovals()).containsExactly(object1);
assertThat(map.getModifyAdditions()).isEmpty();
}
}
@@ -0,0 +1,230 @@
package io.ebean.common;
import io.ebean.bean.BeanCollection;
import org.junit.Test;
import java.util.LinkedHashSet;
import java.util.Set;
import static org.assertj.core.api.Assertions.assertThat;
public class BeanSetTest {
Object object1 = new Object();
Object object2 = new Object();
Object object3 = new Object();
private Set<Object> all() {
Set<Object> all = new LinkedHashSet<>();
all.add(object1);
all.add(object2);
all.add(object3);
return all;
}
private Set<Object> some() {
Set<Object> some = new LinkedHashSet<>();
some.add(object2);
some.add(object3);
return some;
}
@Test
public void testAdd() throws Exception {
BeanSet<Object> set = new BeanSet<>();
set.setModifyListening(BeanCollection.ModifyListenMode.ALL);
set.add(object1);
assertThat(set.getModifyAdditions()).containsExactly(object1);
assertThat(set.getModifyRemovals()).isEmpty();
set.add(object1);
assertThat(set.getModifyAdditions()).containsExactly(object1);
set.add(object2);
assertThat(set.getModifyAdditions()).containsExactly(object1, object2);
set.remove(object1);
assertThat(set.getModifyAdditions()).containsExactly(object2);
assertThat(set.getModifyRemovals()).isEmpty();
}
@Test
public void testAddAll_given_emptyStart() throws Exception {
BeanSet<Object> set = new BeanSet<>();
set.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
set.addAll(all());
assertThat(set.getModifyAdditions()).containsExactly(object1, object2, object3);
assertThat(set.getModifyRemovals()).isEmpty();
}
@Test
public void testAdd_given_someAlreadyIn() throws Exception {
BeanSet<Object> set = new BeanSet<>(some());
set.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
assertThat(set.contains(object1)).isFalse();
set.add(object1);
assertThat(set.contains(object2)).isTrue();
set.add(object2);
assertThat(set.getModifyAdditions()).containsExactly(object1);
assertThat(set.getModifyRemovals()).isEmpty();
}
@Test
public void testAddSome_given_someAlreadyIn() throws Exception {
BeanSet<Object> set = new BeanSet<>(some());
set.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
set.addAll(all());
assertThat(set.getModifyAdditions()).containsExactly(object1);
assertThat(set.getModifyRemovals()).isEmpty();
}
@Test
public void testRemove_given_beansInAdditions() throws Exception {
BeanSet<Object> set = new BeanSet<>();
set.setModifyListening(BeanCollection.ModifyListenMode.ALL);
set.addAll(all());
assertThat(set.getModifyAdditions()).containsExactly(object1, object2, object3);
// act
set.remove(object2);
set.remove(object3);
assertThat(set.getModifyAdditions()).containsExactly(object1);
assertThat(set.getModifyRemovals()).isEmpty();
}
@Test
public void testRemoveAll_given_beansInAdditions() throws Exception {
BeanSet<Object> set = new BeanSet<>();
set.setModifyListening(BeanCollection.ModifyListenMode.ALL);
set.addAll(all());
assertThat(set.getModifyAdditions()).containsExactly(object1, object2, object3);
// act
set.removeAll(some());
assertThat(set.getModifyAdditions()).containsExactly(object1);
assertThat(set.getModifyRemovals()).isEmpty();
}
@Test
public void testRemove_given_beansNotInAdditions() throws Exception {
BeanSet<Object> set = new BeanSet<>(all());
set.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
set.remove(object2);
set.remove(object3);
// assert
assertThat(set.getModifyAdditions()).isEmpty();
assertThat(set.getModifyRemovals()).containsExactly(object2, object3);
}
@Test
public void testRemoveAll_given_beansNotInAdditions() throws Exception {
BeanSet<Object> set = new BeanSet<>(all());
set.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
set.removeAll(some());
// assert
assertThat(set.getModifyAdditions()).isEmpty();
assertThat(set.getModifyRemovals()).containsExactly(object2, object3);
}
@Test
public void testClear() throws Exception {
BeanSet<Object> set = new BeanSet<>(all());
set.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
set.clear();
//assert
assertThat(set.getModifyRemovals()).containsExactly(object1, object2, object3);
assertThat(set.getModifyAdditions()).isEmpty();
}
@Test
public void testClear_given_someBeansInAdditions() throws Exception {
BeanSet<Object> set = new BeanSet<>();
set.add(object1);
set.setModifyListening(BeanCollection.ModifyListenMode.ALL);
set.add(object2);
set.add(object3);
// act
set.clear();
//assert
assertThat(set.getModifyRemovals()).containsExactly(object1);
assertThat(set.getModifyAdditions()).isEmpty();
}
@Test
public void testRetainAll_given_beansInAdditions() throws Exception {
BeanSet<Object> set = new BeanSet<>();
set.setModifyListening(BeanCollection.ModifyListenMode.ALL);
set.addAll(all());
assertThat(set.getModifyAdditions()).containsExactly(object1, object2, object3);
// act
set.retainAll(some());
assertThat(set.getModifyAdditions()).containsExactly(object2, object3);
assertThat(set.getModifyRemovals()).isEmpty();
}
@Test
public void testRetainAll_given_someBeansInAdditions() throws Exception {
BeanSet<Object> set = new BeanSet<>();
set.add(object1);
set.add(object2);
set.setModifyListening(BeanCollection.ModifyListenMode.ALL);
set.add(object3);
// act
set.retainAll(some());
assertThat(set.getModifyAdditions()).containsExactly(object3);
assertThat(set.getModifyRemovals()).containsExactly(object1);
}
@Test
public void testRetainAll_given_noBeansInAdditions() throws Exception {
BeanSet<Object> set = new BeanSet<>(all());
set.setModifyListening(BeanCollection.ModifyListenMode.ALL);
// act
set.retainAll(some());
assertThat(set.getModifyRemovals()).containsExactly(object1);
}
}
@@ -0,0 +1,31 @@
package io.ebean.config;
import org.junit.Test;
import java.util.Properties;
import static org.junit.Assert.assertEquals;
public class ContainerConfigTest {
@Test
public void loadFromProperties() {
Properties p = new Properties();
p.setProperty("ebean.cluster.active", "true");
p.setProperty("ebean.cluster.serviceName", "a");
p.setProperty("ebean.cluster.namespace", "b");
p.setProperty("ebean.cluster.podName", "c");
p.setProperty("ebean.cluster.port", "42");
ContainerConfig containerConfig = new ContainerConfig();
containerConfig.loadFromProperties(p);
assertEquals(true, containerConfig.isActive());
assertEquals("a", containerConfig.getServiceName());
assertEquals("b", containerConfig.getNamespace());
assertEquals("c", containerConfig.getPodName());
assertEquals(42, containerConfig.getPort());
}
}
@@ -0,0 +1,70 @@
package io.ebean.config;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class DbConstraintNamingTest {
DbConstraintNaming naming = new DbConstraintNaming();
@Test
public void testPrimaryKeyName() {
assertThat(naming.primaryKeyName("[cat].[sce].[foo_bar]")).isEqualTo("pk_foo_bar");
}
@Test
public void testUniqueConstraintName() {
assertThat(naming.uniqueConstraintName("[foo_bar]", "[jim]")).isEqualTo("uq_foo_bar_jim");
}
@Test
public void testCheckConstraintName() {
assertThat(naming.checkConstraintName("[foo_bar]", "[jim]")).isEqualTo("ck_foo_bar_jim");
}
@Test
public void testNormalise() {
assertThat(naming.normaliseTable("cat.sch.foo_bar]")).isEqualTo("foo_bar");
assertThat(naming.normaliseTable("sch.foo_bar]")).isEqualTo("foo_bar");
assertThat(naming.normaliseTable("foo_bar]")).isEqualTo("foo_bar");
}
@Test
public void testDefaultToLower() {
assertThat(naming.normaliseTable("SCH.FOO_BAR]")).isEqualTo("foo_bar");
assertThat(naming.lowerTableName("SCH.FOO_BAR]")).isEqualTo("SCH.FOO_BAR]");
assertThat(naming.lowerTableName("SCH.FOO_BAR")).isEqualTo("sch.foo_bar");
assertThat(naming.lowerColumnName("SCH.FOO_BAR]")).isEqualTo("SCH.FOO_BAR]");
assertThat(naming.lowerColumnName("SCH.FOO_BAR")).isEqualTo("sch.foo_bar");
}
@Test
public void testNoLowerCaseTable() {
DbConstraintNaming naming = new DbConstraintNaming(false, true);
assertThat(naming.normaliseTable("SCH.FOO_BAR]")).isEqualTo("FOO_BAR");
assertThat(naming.normaliseColumn("SCH.FOO_BAR]")).isEqualTo("sch.foo_bar");
assertThat(naming.lowerTableName("SCH.FOO_BAR]")).isEqualTo("SCH.FOO_BAR]");
// table name not lowered
assertThat(naming.lowerTableName("SCH.FOO_BAR")).isEqualTo("SCH.FOO_BAR");
assertThat(naming.lowerColumnName("SCH.FOO_BAR]")).isEqualTo("SCH.FOO_BAR]");
assertThat(naming.lowerColumnName("SCH.FOO_BAR")).isEqualTo("sch.foo_bar");
}
@Test
public void testNoLowerCaseColumn() {
DbConstraintNaming naming = new DbConstraintNaming(true, false);
assertThat(naming.normaliseTable("SCH.FOO_BAR]")).isEqualTo("foo_bar");
assertThat(naming.normaliseColumn("SCH.FOO_BAR]")).isEqualTo("SCH.FOO_BAR");
assertThat(naming.lowerTableName("SCH.FOO_BAR]")).isEqualTo("SCH.FOO_BAR]");
assertThat(naming.lowerTableName("SCH.FOO_BAR")).isEqualTo("sch.foo_bar");
assertThat(naming.lowerColumnName("SCH.FOO_BAR]")).isEqualTo("SCH.FOO_BAR]");
// column name not lowered
assertThat(naming.lowerColumnName("SCH.FOO_BAR")).isEqualTo("SCH.FOO_BAR");
}
@Test
public void normaliseColumn_withFormula() {
assertThat(naming.normaliseColumn("lower(name)")).isEqualTo("lowername");
}
}
@@ -0,0 +1,78 @@
package io.ebean.config;
import org.junit.Test;
import java.util.Properties;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertEquals;
public class DbMigrationConfigTest {
@Test
public void testLoad() {
ServerConfig config = new ServerConfig();
config.setName("h2other");
config.loadFromProperties();
config.setDefaultServer(false);
DbMigrationConfig migrationConfig = config.getMigrationConfig();
assertThat(migrationConfig.getMigrationPath()).isEqualTo("dbmigration/myapp");
}
@Test
public void loadProperties_migration() {
Properties properties = new Properties();
properties.setProperty("ebean.migration.dbusername", "banana");
properties.setProperty("ebean.migration.dbpassword", "apple");
properties.setProperty("ebean.migration.patchInsertOn", "1.3,my_views");
properties.setProperty("ebean.migration.patchResetChecksumOn", "foo");
PropertiesWrapper wrapper = new PropertiesWrapper("ebean", "db", properties, null);
DbMigrationConfig migrationConfig = new DbMigrationConfig();
migrationConfig.loadSettings(wrapper, "db");
assertEquals(migrationConfig.getDbUsername(),"banana");
assertEquals(migrationConfig.getDbPassword(),"apple");
assertEquals(migrationConfig.getPatchInsertOn(),"1.3,my_views");
assertEquals(migrationConfig.getPatchResetChecksumOn(),"foo");
}
@Test
public void loadProperties_datasource() {
Properties properties = new Properties();
properties.setProperty("datasource.db.username", "banana");
properties.setProperty("datasource.db.password", "apple");
PropertiesWrapper wrapper = new PropertiesWrapper("ebean", "db", properties, null);
DbMigrationConfig migrationConfig = new DbMigrationConfig();
migrationConfig.loadSettings(wrapper, "db");
// runnerConfig will fall back itsel to the correct password
assertEquals(migrationConfig.getDbUsername(),null);
assertEquals(migrationConfig.getDbPassword(),null);
}
@Test
public void loadProperties_datasource_adminusername() {
Properties properties = new Properties();
properties.setProperty("datasource.db.adminusername", "banana");
properties.setProperty("datasource.db.adminpassword", "apple");
PropertiesWrapper wrapper = new PropertiesWrapper("ebean", "db", properties, null);
DbMigrationConfig migrationConfig = new DbMigrationConfig();
migrationConfig.loadSettings(wrapper, "db");
assertEquals(migrationConfig.getDbUsername(),"banana");
assertEquals(migrationConfig.getDbPassword(),"apple");
}
}
@@ -0,0 +1,76 @@
package io.ebean.config;
import io.ebean.annotation.DocStoreMode;
import org.junit.Test;
import java.util.Properties;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
public class DocStoreConfigTest {
@Test
public void loadSettings() throws Exception {
DocStoreConfig config = new DocStoreConfig();
Properties properties = new Properties();
properties.setProperty("ebean.docstore.active", "true");
properties.setProperty("ebean.docstore.bulkBatchSize", "99");
properties.setProperty("ebean.docstore.url", "http://foo:9800");
properties.setProperty("ebean.docstore.persist", "IGNORE");
properties.setProperty("ebean.docstore.allowAllCertificates", "true");
properties.setProperty("ebean.docstore.username", "fred");
properties.setProperty("ebean.docstore.password", "rock");
PropertiesWrapper wrapper = new PropertiesWrapper("ebean", null, properties, null);
config.loadSettings(wrapper);
assertTrue(config.isActive());
assertTrue(config.isAllowAllCertificates());
assertFalse(config.isGenerateMapping());
assertFalse(config.isDropCreate());
assertEquals("http://foo:9800", config.getUrl());
assertEquals("fred", config.getUsername());
assertEquals("rock", config.getPassword());
assertEquals(DocStoreMode.IGNORE, config.getPersist());
assertEquals(99, config.getBulkBatchSize());
}
@Test
public void loadSettings_generateMapping_dropCreate() throws Exception {
DocStoreConfig config = new DocStoreConfig();
Properties properties = new Properties();
properties.setProperty("ebean.docstore.generateMapping", "true");
properties.setProperty("ebean.docstore.dropCreate", "true");
PropertiesWrapper wrapper = new PropertiesWrapper("ebean", null, properties, null);
config.loadSettings(wrapper);
assertTrue(config.isGenerateMapping());
assertTrue(config.isDropCreate());
assertFalse(config.isCreate());
}
@Test
public void loadSettings_generateMapping_create() throws Exception {
DocStoreConfig config = new DocStoreConfig();
Properties properties = new Properties();
properties.setProperty("ebean.docstore.generateMapping", "true");
properties.setProperty("ebean.docstore.create", "true");
PropertiesWrapper wrapper = new PropertiesWrapper("ebean", null, properties, null);
config.loadSettings(wrapper);
assertTrue(config.isGenerateMapping());
assertTrue(config.isCreate());
assertFalse(config.isDropCreate());
}
}
@@ -0,0 +1,77 @@
package io.ebean.config;
import io.ebean.config.dbplatform.h2.H2Platform;
import io.ebean.config.dbplatform.sqlserver.SqlServer17Platform;
import org.junit.Test;
import org.tests.model.basic.Customer;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNull;
public class MatchingNamingConventionTest {
private MatchingNamingConvention namingConvention;
public MatchingNamingConventionTest() {
this.namingConvention = new MatchingNamingConvention();
this.namingConvention.setDatabasePlatform(new H2Platform());
}
private MatchingNamingConvention createMatchingNamingConventionAllQuoted() {
SqlServer17Platform platform = new SqlServer17Platform();
PlatformConfig config = new PlatformConfig();
config.setAllQuotedIdentifiers(true);
platform.configure(config);
MatchingNamingConvention nc = new MatchingNamingConvention();
nc.setDatabasePlatform(platform);
return nc;
}
@Test
public void getColumnFromProperty_when_allQuoted() {
MatchingNamingConvention nc = createMatchingNamingConventionAllQuoted();
assertThat(nc.getColumnFromProperty(null, "bridgetabUserId")).isEqualTo("[bridgetabUserId]");
assertThat(nc.getColumnFromProperty(null, "order")).isEqualTo("[order]");
}
@Test
public void getTableNameByConvention_when_allQuoted() {
MatchingNamingConvention nc = createMatchingNamingConventionAllQuoted();
final TableName tableName = nc.getTableNameByConvention(Customer.class);
assertEquals("[Customer]", tableName.getName());
assertNull(tableName.getCatalog());
assertNull(tableName.getSchema());
}
@Test
public void getSequenceName() {
MatchingNamingConvention nc = createMatchingNamingConventionAllQuoted();
assertEquals("Customer_seq", nc.getSequenceName("[Customer]", null));
}
@Test
public void getColumnFromProperty() {
String fkCol = "bridgetab_userId";
String col = namingConvention.getColumnFromProperty(null, fkCol);
assertThat(col).isEqualTo(fkCol);
}
@Test
public void getForeignKey() {
String fk = namingConvention.getForeignKey("billingAddress", "id");
assertThat(fk).isEqualTo("billingAddressId");
fk = namingConvention.getForeignKey("billingAddress", "remoteIdProperty");
assertThat(fk).isEqualTo("billingAddressRemoteIdProperty");
}
}
@@ -0,0 +1,121 @@
package io.ebean.config;
import io.ebean.EbeanServer;
import io.ebean.EbeanServerFactory;
import io.ebean.Transaction;
import io.ebean.annotation.Platform;
import io.ebean.config.dbplatform.DbIdentity;
import io.ebean.config.dbplatform.IdType;
import io.ebean.config.dbplatform.h2.H2Platform;
import org.junit.Test;
import org.tests.model.basic.EBasicVer;
import org.tests.model.draftable.BasicDraftableBean;
import static org.assertj.core.api.Assertions.assertThat;
public class PlatformNoGeneratedKeysTest {
static EbeanServer server = testH2Server();
@Test
public void global_serverConfig_setDisableLazyLoading() {
EBasicVer b0 = new EBasicVer("basic");
b0.setDescription("some description");
server.save(b0);
EBasicVer found = server.find(EBasicVer.class)
.select("name")
.setId(b0.getId())
.findOne();
assertThat(found.getName()).isEqualTo("basic");
assertThat(found.getDescription()).isNull();
}
@Test
public void insertBatch_expect_noIdValuesFetched() {
EBasicVer b0 = new EBasicVer("a");
EBasicVer b1 = new EBasicVer("b");
EBasicVer b2 = new EBasicVer("c");
try (Transaction transaction = server.beginTransaction()) {
transaction.setBatchMode(true);
server.save(b0);
server.save(b1);
server.save(b2);
transaction.commit();
}
assertThat(b0.getId()).isNull();
assertThat(b1.getId()).isNull();
assertThat(b2.getId()).isNull();
}
@Test
public void insertNoBatch_expect_selectIdentity() {
EBasicVer b0 = new EBasicVer("one");
server.save(b0);
assertThat(b0.getId()).isNotNull();
BasicDraftableBean d0 = new BasicDraftableBean("done");
server.save(d0);
assertThat(d0.getId()).isNotNull();
server.publish(BasicDraftableBean.class, d0.getId());
BasicDraftableBean one = server.find(BasicDraftableBean.class, d0.getId());
assertThat(one.getName()).isEqualTo("done");
assertThat(one.isDraft()).isFalse();
}
private static EbeanServer testH2Server() {
ServerConfig config = new ServerConfig();
config.setName("h2_noGeneratedKeys");
OtherH2Platform platform = new OtherH2Platform();
DbIdentity dbIdentity = platform.getDbIdentity();
dbIdentity.setIdType(IdType.IDENTITY);
dbIdentity.setSupportsIdentity(true);
dbIdentity.setSupportsGetGeneratedKeys(false);
dbIdentity.setSupportsSequence(false);
dbIdentity.setSelectLastInsertedIdTemplate("select identity() --{table}");
config.setDatabasePlatform(platform);
config.getDataSourceConfig().setUsername("sa");
config.getDataSourceConfig().setPassword("");
config.getDataSourceConfig().setUrl("jdbc:h2:mem:withPCQuery;");
config.getDataSourceConfig().setDriver("org.h2.Driver");
config.setDisableLazyLoading(true);
config.setDisableL2Cache(true);
config.setDefaultServer(false);
config.setRegister(false);
config.setDdlGenerate(true);
config.setDdlRun(true);
config.getClasses().add(EBasicVer.class);
config.getClasses().add(BasicDraftableBean.class);
return EbeanServerFactory.create(config);
}
public static class OtherH2Platform extends H2Platform {
public OtherH2Platform() {
super();
this.platform = Platform.GENERIC;
}
}
}
@@ -0,0 +1,79 @@
package io.ebean.config;
import io.avaje.config.Config;
import io.ebean.annotation.Platform;
import org.junit.Test;
import java.util.Properties;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNull;
public class PropertiesWrapperTest {
@Test
public void testGetServerName() {
PropertiesWrapper pw = new PropertiesWrapper(null, "myserver", new Properties(), null);
assertEquals("myserver", pw.getServerName());
}
@Test
public void testGetEnum() {
Properties properties = new Properties();
properties.put("platform", "postgres");
PropertiesWrapper pw = new PropertiesWrapper("pref", "myserver", properties, null);
assertEquals(Platform.POSTGRES, pw.getEnum(Platform.class, "platform", Platform.H2));
assertEquals(Platform.H2, pw.getEnum(Platform.class, "junk", Platform.H2));
assertNull(pw.getEnum(Platform.class, "junk", null));
}
@Test
public void testTrimPropertyValues() {
Properties properties = new Properties();
properties.put("someBasic", " hello ");
properties.put("someInt", "42");
properties.put("noTrimReqr", "jim");
properties.put("includeSpaces", " jim bob ");
PropertiesWrapper pw = new PropertiesWrapper("pref", "myserver", properties, null);
assertEquals(" hello ", pw.get("someBasic"));
assertEquals(42, pw.getInt("someInt", 1));
assertNull(pw.get("doesNotExist", null));
assertEquals("jim", pw.get("noTrimReqr"));
assertEquals(" jim bob ", pw.get("includeSpaces"));
}
@Test
public void testGetProperties() {
String home = System.getenv("HOME");
String tmpDir = System.getProperty("java.io.tmpdir");
Properties properties = new Properties();
properties.put("someBasic", "hello");
properties.put("someInt", "42");
properties.put("someDouble", "5.5");
properties.put("somePath", "${HOME}/hello");
properties.put("someSystemProp", "/aaa/${java.io.tmpdir}/bbb");
Properties evalCopy = Config.asConfiguration().eval(properties);
PropertiesWrapper pw = new PropertiesWrapper("pref", "myserver", evalCopy, null);
assertEquals(42, pw.getInt("someInt", 99));
assertEquals(Double.valueOf(5.5D), (Double.valueOf(pw.getDouble("someDouble", 99.9D))));
assertEquals(home + "/hello", pw.get("somePath", null));
assertEquals(tmpDir, "/aaa/" + tmpDir + "/bbb", pw.get("someSystemProp"));
pw = new PropertiesWrapper(evalCopy, null);
assertEquals(42, pw.getInt("someInt", 99));
assertEquals(Double.valueOf(5.5D), (Double.valueOf(pw.getDouble("someDouble", 99.9D))));
assertEquals(home + "/hello", pw.get("somePath", null));
assertEquals(tmpDir, "/aaa/" + tmpDir + "/bbb", pw.get("someSystemProp"));
}
}
@@ -0,0 +1,134 @@
package io.ebean.config;
import io.ebean.EbeanServer;
import io.ebean.EbeanServerFactory;
import io.ebean.annotation.ForPlatform;
import io.ebean.annotation.Platform;
import org.junit.Ignore;
import org.junit.Test;
import org.tests.model.basic.EBasicVer;
import javax.persistence.PersistenceException;
import java.util.Properties;
import static org.assertj.core.api.Assertions.assertThat;
public class ServerConfigSqlServerTest {
@Ignore
@ForPlatform({Platform.SQLSERVER})
@Test(expected = PersistenceException.class)
public void need_explicitPlatform() {
Properties props = props("some_sqlserver");
// no explicit databasePlatformName set ..
//props.setProperty("ebean.some_sqlserver.databasePlatformName", "sqlserver17");
ServerConfig config = new ServerConfig();
config.setName("some_sqlserver");
config.loadFromProperties(props);
// not explicitly set ... so we fail to start
// config.setDatabasePlatform(new SqlServer17Platform());
// config.setDatabasePlatformName("sqlserver17");
config.setDefaultServer(false);
config.setRegister(false);
config.getClasses().add(EBasicVer.class);
EbeanServer sqlServer = EbeanServerFactory.create(config);
assertThat(sqlServer).isNotNull();
// javax.persistence.PersistenceException: java.lang.IllegalArgumentException: For SqlServer please choose the more specific sqlserver16 or sqlserver17 platform via ServerConfig.setDatabasePlatformName. Refer to issue #1340 for details
//
// at io.ebeaninternal.server.core.DatabasePlatformFactory.create(DatabasePlatformFactory.java:62)
// at io.ebeaninternal.server.core.DefaultContainer.setDatabasePlatform(DefaultContainer.java:266)
// at io.ebeaninternal.server.core.DefaultContainer.createServer(DefaultContainer.java:126)
// at io.ebeaninternal.server.core.DefaultContainer.createServer(DefaultContainer.java:45)
// at io.ebean.EbeanServerFactory.createInternal(EbeanServerFactory.java:109)
// at io.ebean.EbeanServerFactory.create(EbeanServerFactory.java:70)
// at io.ebean.config.ServerConfigSqlServerTest.need_explicitPlatform(ServerConfigSqlServerTest.java:35)
}
@Ignore
@ForPlatform({Platform.SQLSERVER})
@Test
public void explicit_17() {
String name = "testsqlserver17";
ServerConfig config = new ServerConfig();
config.setName(name);
Properties props = props(name);
// set via properties
//props.setProperty("ebean.testsqlserver17.databasePlatformName", "sqlserver17");
// or set programmatically ...
config.setDatabasePlatformName("sqlserver17");
config.setDefaultServer(false);
config.setRegister(false);
config.setDdlGenerate(true);
config.setDdlRun(true);
config.loadFromProperties(props);
config.getClasses().add(EBasicVer.class);
EbeanServer sqlServer = EbeanServerFactory.create(config);
assertThat(sqlServer).isNotNull();
}
@Ignore
@ForPlatform({Platform.SQLSERVER})
@Test
public void explicit_16() {
String name = "testsqlserver16";
Properties props = props(name);
//props.setProperty("ebean.testsqlserver16.databasePlatformName", "sqlserver16");
ServerConfig config = new ServerConfig();
config.setDefaultServer(false);
config.setRegister(false);
config.setDdlGenerate(true);
config.setDdlRun(true);
config.setName(name); // match dataSource
config.setDatabasePlatformName("sqlserver16");
config.loadFromProperties(props);
config.getClasses().add(EBasicVer.class);
EbeanServer sqlServer = EbeanServerFactory.create(config);
assertThat(sqlServer).isNotNull();
}
private Properties props(String dbName) {
Properties props = new Properties();
// automatically start docker sqlserver 2017 container ...
props.setProperty("ebean.test.platform", "sqlserver");
props.setProperty("ebean.test.dbName", "test_ebean");
props.setProperty("ebean.test.ddlMode", "dropCreate");
//props.setProperty("ebean.test.containerMode","dropCreate");
props.setProperty(key(dbName, "username"), "test_ebean");
props.setProperty(key(dbName, "password"), "SqlS3rv#r");
props.setProperty(key(dbName, "url"), "jdbc:sqlserver://localhost:1433;databaseName=test_ebean");
props.setProperty(key(dbName, "driver"), "com.microsoft.sqlserver.jdbc.SQLServerDriver");
return props;
}
private String key(String dbName, String key) {
return "datasource." + dbName + "." + key;
}
}
@@ -0,0 +1,162 @@
package io.ebean.config;
import com.fasterxml.jackson.databind.ObjectMapper;
import io.ebean.annotation.PersistBatch;
import io.ebean.config.dbplatform.IdType;
import io.ebean.datasource.DataSourceConfig;
import org.junit.Test;
import java.util.Properties;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
public class ServerConfigTest {
@Test
public void testLoadFromEbeanProperties() {
ServerConfig serverConfig = new ServerConfig();
serverConfig.loadFromProperties();
assertEquals(PersistBatch.NONE, serverConfig.getPersistBatch());
assertNotNull(serverConfig.getProperties());
}
@Test
public void evalPropertiesInput() {
String home = System.getenv("HOME");
Properties props = new Properties();
props.setProperty("ddl.initSql", "${HOME}/initSql");
ServerConfig serverConfig = new ServerConfig();
serverConfig.loadFromProperties(props);
String ddlInitSql = serverConfig.getDdlInitSql();
assertThat(ddlInitSql).isEqualTo(home+"/initSql");
}
@Test
public void testLoadWithProperties() {
ServerConfig serverConfig = new ServerConfig();
serverConfig.setPersistBatch(PersistBatch.NONE);
serverConfig.setPersistBatchOnCascade(PersistBatch.NONE);
serverConfig.setAutoReadOnlyDataSource(false);
serverConfig.setReadOnlyDataSource(null);
serverConfig.setReadOnlyDataSourceConfig(new DataSourceConfig());
Properties props = new Properties();
props.setProperty("persistBatch", "ALL");
props.setProperty("persistBatchOnCascade", "ALL");
props.setProperty("dbuuid", "binary");
props.setProperty("jdbcFetchSizeFindEach", "42");
props.setProperty("jdbcFetchSizeFindList", "43");
props.setProperty("backgroundExecutorShutdownSecs", "98");
props.setProperty("backgroundExecutorSchedulePoolSize", "4");
props.setProperty("dbOffline", "true");
props.setProperty("jsonDateTime", "MILLIS");
props.setProperty("jsonDate", "MILLIS");
props.setProperty("autoReadOnlyDataSource", "true");
props.setProperty("disableL2Cache", "true");
props.setProperty("notifyL2CacheInForeground", "true");
props.setProperty("idType", "SEQUENCE");
props.setProperty("mappingLocations", "classpath:/foo;bar");
props.setProperty("namingConvention", "io.ebean.config.MatchingNamingConvention");
props.setProperty("idGeneratorAutomatic", "true");
props.setProperty("enabledL2Regions", "r0,users,orgs");
props.setProperty("caseSensitiveCollation", "false");
props.setProperty("loadModuleInfo", "true");
props.setProperty("collectQueryPlanThresholdMicros", "10000");
serverConfig.loadFromProperties(props);
assertTrue(serverConfig.isDisableL2Cache());
assertTrue(serverConfig.isNotifyL2CacheInForeground());
assertTrue(serverConfig.isDbOffline());
assertTrue(serverConfig.isAutoReadOnlyDataSource());
assertTrue(serverConfig.isAutoLoadModuleInfo());
assertTrue(serverConfig.isIdGeneratorAutomatic());
assertFalse(serverConfig.getPlatformConfig().isCaseSensitiveCollation());
assertThat(serverConfig.getNamingConvention()).isInstanceOf(MatchingNamingConvention.class);
assertEquals(IdType.SEQUENCE, serverConfig.getIdType());
assertEquals(PersistBatch.ALL, serverConfig.getPersistBatch());
assertEquals(PersistBatch.ALL, serverConfig.getPersistBatchOnCascade());
assertEquals(PlatformConfig.DbUuid.BINARY, serverConfig.getPlatformConfig().getDbUuid());
assertEquals(JsonConfig.DateTime.MILLIS, serverConfig.getJsonDateTime());
assertEquals(JsonConfig.Date.MILLIS, serverConfig.getJsonDate());
assertEquals(10000, serverConfig.getCollectQueryPlanThresholdMicros());
assertEquals("r0,users,orgs", serverConfig.getEnabledL2Regions());
assertEquals(42, serverConfig.getJdbcFetchSizeFindEach());
assertEquals(43, serverConfig.getJdbcFetchSizeFindList());
assertEquals(4, serverConfig.getBackgroundExecutorSchedulePoolSize());
assertEquals(98, serverConfig.getBackgroundExecutorShutdownSecs());
assertThat(serverConfig.getMappingLocations()).containsExactly("classpath:/foo","bar");
serverConfig.setPersistBatch(PersistBatch.NONE);
serverConfig.setPersistBatchOnCascade(PersistBatch.NONE);
Properties props1 = new Properties();
props1.setProperty("ebean.persistBatch", "ALL");
props1.setProperty("ebean.persistBatchOnCascade", "ALL");
serverConfig.setNotifyL2CacheInForeground(true);
serverConfig.setDisableL2Cache(true);
props1.setProperty("ebean.disableL2Cache", "false");
props1.setProperty("ebean.notifyL2CacheInForeground", "false");
serverConfig.loadFromProperties(props1);
assertFalse(serverConfig.isDisableL2Cache());
assertFalse(serverConfig.isNotifyL2CacheInForeground());
assertEquals(PersistBatch.ALL, serverConfig.getPersistBatch());
assertEquals(PersistBatch.ALL, serverConfig.getPersistBatchOnCascade());
serverConfig.setEnabledL2Regions("r0,orgs");
assertEquals("r0,orgs", serverConfig.getEnabledL2Regions());
}
@Test
public void test_defaults() {
ServerConfig serverConfig = new ServerConfig();
assertTrue(serverConfig.isIdGeneratorAutomatic());
serverConfig.setIdGeneratorAutomatic(false);
assertFalse(serverConfig.isIdGeneratorAutomatic());
assertEquals(JsonConfig.DateTime.ISO8601, serverConfig.getJsonDateTime());
assertEquals(JsonConfig.Date.ISO8601, serverConfig.getJsonDate());
assertTrue(serverConfig.getPlatformConfig().isCaseSensitiveCollation());
assertTrue(serverConfig.isAutoLoadModuleInfo());
assertEquals(Long.MAX_VALUE, serverConfig.getCollectQueryPlanThresholdMicros());
serverConfig.setLoadModuleInfo(false);
assertFalse(serverConfig.isAutoLoadModuleInfo());
}
@Test
public void test_putServiceObject() {
ObjectMapper objectMapper = new ObjectMapper();
ServerConfig config = new ServerConfig();
config.putServiceObject(objectMapper);
ObjectMapper mapper0 = config.getServiceObject(ObjectMapper.class);
ObjectMapper mapper1 = (ObjectMapper)config.getServiceObject("objectMapper");
assertThat(objectMapper).isSameAs(mapper0);
assertThat(objectMapper).isSameAs(mapper1);
}
}
@@ -0,0 +1,63 @@
package io.ebean.config;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class UnderscoreNamingConventionTest {
private UnderscoreNamingConvention namingConvention = new UnderscoreNamingConvention();
@Test
public void simple() {
String col = namingConvention.getColumnFromProperty(null, "helloThere");
assertThat(col).isEqualTo("hello_there");
assertThat(namingConvention.toCamelFromUnderscore(col)).isEqualTo("helloThere");
}
@Test
public void with_suffix_Id() {
String col = namingConvention.getColumnFromProperty(null, "helloId");
assertThat(col).isEqualTo("hello_id");
assertThat(namingConvention.toCamelFromUnderscore(col)).isEqualTo("helloId");
col = namingConvention.getColumnFromProperty(null, "helloThereId");
assertThat(col).isEqualTo("hello_there_id");
assertThat(namingConvention.toCamelFromUnderscore(col)).isEqualTo("helloThereId");
}
@Test
public void with_suffix_ID() {
String col = namingConvention.getColumnFromProperty(null, "helloID");
assertThat(col).isEqualTo("hello_id");
assertThat(namingConvention.toCamelFromUnderscore(col)).isEqualTo("helloId");
col = namingConvention.getColumnFromProperty(null, "helloThereID");
assertThat(col).isEqualTo("hello_there_id");
assertThat(namingConvention.toCamelFromUnderscore(col)).isEqualTo("helloThereId");
}
@Test
public void getColumnFromProperty() {
String fkCol = "bridgetab_user_id";
String col = namingConvention.getColumnFromProperty(null, fkCol);
assertThat(col).isEqualTo(fkCol);
}
@Test
public void getForeignKey() {
String fk = namingConvention.getForeignKey("billing_address", "id");
assertThat(fk).isEqualTo("billing_address_id");
fk = namingConvention.getForeignKey("billing_address", "remoteIdProperty");
assertThat(fk).isEqualTo("billing_address_remote_id_property");
}
}
@@ -0,0 +1,34 @@
package io.ebean.config.dbplatform;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class BasicSqlLimitOffsetTest {
private BasicSqlLimitOffset limiter = new BasicSqlLimitOffset();
@Test
public void limit_maxRows() throws Exception {
String query = "select * from mytab order by id";
String sql = limiter.limit(query, 0, 10);
assertThat(sql).isEqualTo(query + " limit 10");
}
@Test
public void limit_firstRowMaxRows() throws Exception {
String query = "select * from mytab order by id";
String sql = limiter.limit(query, 5, 10);
assertThat(sql).isEqualTo(query + " limit 10 offset 5");
}
@Test
public void limit_zeros() throws Exception {
String query = "select * from mytab order by id";
String sql = limiter.limit(query, 0, 0);
assertThat(sql).isEqualTo(query);
}
}
@@ -0,0 +1,35 @@
package io.ebean.config.dbplatform;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class BasicSqlStandardLimiterTest {
private BasicSqlAnsiLimiter limiter = new BasicSqlAnsiLimiter();
@Test
public void limit_maxRows() throws Exception {
String query = "select * from mytab order by id";
String sql = limiter.limit(query, 0, 10);
assertThat(sql).isEqualTo(query + " fetch next 10 rows only");
}
@Test
public void limit_firstRowMaxRows() throws Exception {
String query = "select * from mytab order by id";
String sql = limiter.limit(query, 5, 10);
assertThat(sql).isEqualTo(query + " offset 5 rows fetch next 10 rows only");
}
@Test
public void limit_zeros() throws Exception {
String query = "select * from mytab order by id";
String sql = limiter.limit(query, 0, 0);
assertThat(sql).isEqualTo(query);
}
}
@@ -0,0 +1,122 @@
package io.ebean.config.dbplatform;
import io.ebean.BaseTestCase;
import io.ebean.DB;
import io.ebean.annotation.ForPlatform;
import io.ebean.annotation.Platform;
import io.ebean.config.MatchingNamingConvention;
import io.ebean.config.PlatformConfig;
import io.ebean.config.ServerConfig;
import io.ebean.config.dbplatform.h2.H2Platform;
import io.ebean.config.dbplatform.postgres.PostgresPlatform;
import io.ebean.config.dbplatform.sqlserver.SqlServer17Platform;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertEquals;
public class DatabasePlatformTest extends BaseTestCase {
@Test
@ForPlatform(Platform.H2)
public void h2_platform() {
final Platform platform = DB.getDefault().getPlatform();
assertThat(platform).isSameAs(Platform.H2);
}
@Test
@ForPlatform(Platform.POSTGRES)
public void postgres_platform() {
final Platform platform = DB.getDefault().getPlatform().base();
assertThat(platform).isSameAs(Platform.POSTGRES);
}
@Test
@ForPlatform(Platform.MYSQL)
public void mysql_platform() {
final Platform platform = DB.getDefault().getPlatform().base();
assertThat(platform).isSameAs(Platform.MYSQL);
}
@Test
@ForPlatform(Platform.MARIADB)
public void mariadb_platform() {
final Platform platform = DB.getDefault().getPlatform().base();
assertThat(platform).isSameAs(Platform.MARIADB);
}
@Test
@ForPlatform(Platform.SQLSERVER)
public void sqlserver_platform() {
final Platform platform = DB.getDefault().getPlatform().base();
assertThat(platform).isSameAs(Platform.SQLSERVER);
}
@Test
public void convertQuotedIdentifiers_when_allQuotedIdentifier_sqlServer() {
ServerConfig config = new ServerConfig();
config.setAllQuotedIdentifiers(true);
config.setNamingConvention(new MatchingNamingConvention());
DatabasePlatform dbPlatform = new SqlServer17Platform();
dbPlatform.configure(config.getPlatformConfig(), config.isAllQuotedIdentifiers());
assertEquals(dbPlatform.convertQuotedIdentifiers("order"),"[order]");
assertEquals(dbPlatform.convertQuotedIdentifiers("`order`"),"[order]");
assertEquals(dbPlatform.convertQuotedIdentifiers("firstName"),"[firstName]");
}
@Test
public void convertQuotedIdentifiers() {
ServerConfig config = new ServerConfig();
DatabasePlatform dbPlatform = new SqlServer17Platform();
dbPlatform.configure(config.getPlatformConfig(), config.isAllQuotedIdentifiers());
assertEquals(dbPlatform.convertQuotedIdentifiers("order"),"order");
assertEquals(dbPlatform.convertQuotedIdentifiers("`order`"),"[order]");
assertEquals(dbPlatform.convertQuotedIdentifiers("firstName"),"firstName");
assertEquals(dbPlatform.unQuote("order"),"order");
assertEquals(dbPlatform.unQuote("[order]"),"order");
assertEquals(dbPlatform.unQuote("[firstName]"),"firstName");
}
@Test
public void defaultTypesForDecimalAndVarchar() {
DatabasePlatform dbPlatform = new DatabasePlatform();
assertEquals(defaultDecimalDefn(dbPlatform), "decimal(16,3)");
assertEquals(defaultDefn(DbType.VARCHAR, dbPlatform), "varchar(255)");
}
@Test
public void configure_customType() {
PlatformConfig config = new PlatformConfig();
config.addCustomMapping(DbType.VARCHAR, "text", Platform.POSTGRES);
config.addCustomMapping(DbType.DECIMAL, "decimal(24,4)");
// PG renders custom decimal and varchar
PostgresPlatform pgPlatform = new PostgresPlatform();
pgPlatform.configure(config, false);
assertEquals(defaultDecimalDefn(pgPlatform), "decimal(24,4)");
assertEquals(defaultDefn(DbType.VARCHAR, pgPlatform), "text");
// H2 only renders custom decimal
H2Platform h2Platform = new H2Platform();
h2Platform.configure(config, false);
assertEquals(defaultDecimalDefn(h2Platform), "decimal(24,4)");
assertEquals(defaultDefn(DbType.VARCHAR, h2Platform), "varchar(255)");
}
private String defaultDecimalDefn(DatabasePlatform dbPlatform) {
return defaultDefn(DbType.DECIMAL, dbPlatform);
}
private String defaultDefn(DbType type, DatabasePlatform dbPlatform) {
return dbPlatform.getDbTypeMap().get(type).renderType(0, 0);
}
}
@@ -0,0 +1,44 @@
package io.ebean.config.dbplatform;
import org.junit.Test;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNull;
public class DbIdentityTest {
@Test
public void getSelectLastInsertedId() {
DbIdentity identity = new DbIdentity();
identity.setSelectLastInsertedIdTemplate("lastid for {table}");
assertEquals("lastid for customer",identity.getSelectLastInsertedId("customer"));
assertEquals("lastid for contact",identity.getSelectLastInsertedId("contact"));
identity.setSelectLastInsertedIdTemplate("A{table}B{table}C");
assertEquals("AoneBoneC",identity.getSelectLastInsertedId("one"));
identity.setSelectLastInsertedIdTemplate("{table}A{table}");
assertEquals("oneAone",identity.getSelectLastInsertedId("one"));
}
@Test
public void getSelectLastInsertedId_when_null() {
DbIdentity identity = new DbIdentity();
assertNull(identity.getSelectLastInsertedId("customer"));
assertNull(identity.getSelectLastInsertedId("contact"));
}
@Test
public void getSelectLastInsertedId_when_noPlaceHolder() {
DbIdentity identity = new DbIdentity();
identity.setSelectLastInsertedIdTemplate("lastid");
assertEquals("lastid",identity.getSelectLastInsertedId("customer"));
assertEquals("lastid",identity.getSelectLastInsertedId("contact"));
}
}
@@ -0,0 +1,53 @@
package io.ebean.config.dbplatform;
import org.junit.Test;
import java.sql.Types;
import static org.junit.Assert.assertEquals;
public class DbPlatformTypeLookupTest {
DbPlatformTypeLookup lookup = new DbPlatformTypeLookup();
@Test
public void byName() throws Exception {
assertEquals(lookup.byName("DECIMAL"), DbType.DECIMAL);
assertEquals(lookup.byName("Decimal"), DbType.DECIMAL);
assertEquals(lookup.byName("decimal"), DbType.DECIMAL);
assertEquals(lookup.byName("varchar"), DbType.VARCHAR);
assertEquals(lookup.byName("varchar2"), DbType.VARCHAR);
assertEquals(lookup.byName("float"), DbType.REAL);
assertEquals(lookup.byName("real"), DbType.REAL);
assertEquals(lookup.byName("uuid"), DbType.UUID);
assertEquals(lookup.byName("hstore"), DbType.HSTORE);
assertEquals(lookup.byName("json"), DbType.JSON);
assertEquals(lookup.byName("jsonb"), DbType.JSONB);
assertEquals(lookup.byName("jsonclob"), DbType.JSONCLOB);
assertEquals(lookup.byName("jsonblob"), DbType.JSONBLOB);
assertEquals(lookup.byName("jsonVarchar"), DbType.JSONVARCHAR);
}
@Test
public void byId() throws Exception {
assertEquals(lookup.byId(Types.ARRAY), DbType.ARRAY);
assertEquals(lookup.byId(Types.BIGINT), DbType.BIGINT);
assertEquals(lookup.byId(ExtraDbTypes.UUID), DbType.UUID);
assertEquals(lookup.byId(ExtraDbTypes.HSTORE), DbType.HSTORE);
assertEquals(lookup.byId(ExtraDbTypes.JSON), DbType.JSON);
assertEquals(lookup.byId(ExtraDbTypes.JSONB), DbType.JSONB);
assertEquals(lookup.byId(ExtraDbTypes.JSONClob), DbType.JSONCLOB);
assertEquals(lookup.byId(ExtraDbTypes.JSONBlob), DbType.JSONBLOB);
assertEquals(lookup.byId(ExtraDbTypes.JSONVarchar), DbType.JSONVARCHAR);
}
}
@@ -0,0 +1,20 @@
package io.ebean.config.dbplatform;
import org.junit.Test;
import java.sql.Types;
import static org.assertj.core.api.Assertions.assertThat;
public class DbPlatformTypeMappingTest {
@Test
public void logicalBoolean_renderType_expect_noLength() {
DbPlatformTypeMapping logicalMapping = DbPlatformTypeMapping.logicalTypes();
DbPlatformType type = logicalMapping.get(Types.BOOLEAN);
String colDefinition = type.renderType(1, 1, false);
assertThat(colDefinition).isEqualTo("boolean");
}
}
@@ -0,0 +1,67 @@
package io.ebean.config.dbplatform;
import org.junit.Test;
import static org.junit.Assert.assertEquals;
public class DbPlatformTypeParserTest {
@Test
public void parse_text() throws Exception {
DbPlatformType type = DbPlatformTypeParser.parse("text");
assertEquals(type.getName(), "text");
assertEquals(type.getDefaultLength(), 0);
assertEquals(type.getDefaultScale(), 0);
assertEquals(type.renderType(0, 0), "text");
assertEquals(type.renderType(40, 0), "text");
}
@Test
public void parse_varchar20() throws Exception {
DbPlatformType type = DbPlatformTypeParser.parse("varchar(20)");
assertEquals(type.getName(), "varchar");
assertEquals(type.getDefaultLength(), 20);
assertEquals(type.getDefaultScale(), 0);
assertEquals(type.renderType(0, 0), "varchar(20)");
assertEquals(type.renderType(40, 0), "varchar(40)");
}
@Test
public void parse_decimal_18_6() throws Exception {
DbPlatformType type = DbPlatformTypeParser.parse("decimal(18,6)");
assertEquals(type.getName(), "decimal");
assertEquals(type.getDefaultLength(), 18);
assertEquals(type.getDefaultScale(), 6);
assertEquals(type.renderType(0, 0), "decimal(18,6)");
}
@Test
public void parse_something() throws Exception {
DbPlatformType type = DbPlatformTypeParser.parse("something(asd,6)");
assertEquals(type.getName(), "something(asd,6)");
assertEquals(type.getDefaultLength(), 0);
assertEquals(type.getDefaultScale(), 0);
assertEquals(type.renderType(0, 0), "something(asd,6)");
}
@Test
public void parse_invalid() throws Exception {
DbPlatformType type = DbPlatformTypeParser.parse("something(asd");
assertEquals(type.getName(), "something(asd");
assertEquals(type.getDefaultLength(), 0);
assertEquals(type.getDefaultScale(), 0);
assertEquals(type.renderType(0, 0), "something(asd");
}
}
@@ -0,0 +1,39 @@
package io.ebean.config.dbplatform;
import io.ebean.config.dbplatform.postgres.PostgresPlatform;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class DbTypeMapTest {
@Test
public void testLookupRender_given_postgresPlatformType() throws Exception {
PostgresPlatform pg = new PostgresPlatform();
DbPlatformTypeMapping dbTypeMap = pg.getDbTypeMap();
assertThat(dbTypeMap.lookup("clob", false).renderType(0, 0)).isEqualTo("text");
assertThat(dbTypeMap.lookup("CLOB", false).renderType(0, 0)).isEqualTo("text");
assertThat(dbTypeMap.lookup("varchar", true).renderType(20, 0)).isEqualTo("varchar(20)");
assertThat(dbTypeMap.lookup("json", false).renderType(0, 0)).isEqualTo("json");
assertThat(dbTypeMap.lookup("jsonb", false).renderType(0, 0)).isEqualTo("jsonb");
assertThat(dbTypeMap.lookup("jsonclob", false).renderType(0, 0)).isEqualTo("text");
assertThat(dbTypeMap.lookup("jsonblob", false).renderType(0, 0)).isEqualTo("bytea");
assertThat(dbTypeMap.lookup("jsonvarchar", false).renderType(200, 0)).isEqualTo("varchar(200)");
}
@Test
public void testPlatformTypes() {
DbPlatformTypeMapping dbTypeMap = DbPlatformTypeMapping.logicalTypes();
DbPlatformType dbType = dbTypeMap.get(DbPlatformType.JSON);
DbPlatformType json = dbTypeMap.lookup("json", false);
assertThat(dbType).isSameAs(json);
}
}
@@ -0,0 +1,28 @@
package io.ebean.config.dbplatform;
import io.ebean.config.dbplatform.h2.H2Platform;
import io.ebeaninternal.dbmigration.ddlgeneration.platform.PlatformDdl;
import io.ebeaninternal.server.core.PlatformDdlBuilder;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class H2PlatformTest {
@Test
public void testTypeConversion() {
PlatformDdl ddl = PlatformDdlBuilder.create(new H2Platform());
assertThat(ddl.convert("clob")).isEqualTo("clob");
assertThat(ddl.convert("json")).isEqualTo("clob");
assertThat(ddl.convert("jsonb")).isEqualTo("clob");
assertThat(ddl.convert("varchar(20)")).isEqualTo("varchar(20)");
assertThat(ddl.convert("decimal(10)")).isEqualTo("decimal(10)");
assertThat(ddl.convert("decimal(8,4)")).isEqualTo("decimal(8,4)");
assertThat(ddl.convert("decimal")).isEqualTo("decimal(16,3)");
assertThat(ddl.convert("boolean")).isEqualTo("boolean");
assertThat(ddl.convert("bit")).isEqualTo("bit");
}
}
@@ -0,0 +1,47 @@
package io.ebean.config.dbplatform;
import io.ebean.config.dbplatform.hana.HanaHistorySupport;
import org.junit.Test;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNull;
public class HanaHistorySupportTest {
private HanaHistorySupport support = new HanaHistorySupport();
@Test
public void getAsOfPredicate() {
String asOfPredicate = support.getAsOfPredicate("t0", "sys_period");
assertNull(asOfPredicate);
}
@Test
public void getAsOfViewSuffix() {
String asOfViewSuffix = support.getAsOfViewSuffix("_with_history");
assertEquals(asOfViewSuffix, " for system_time as of ?");
}
@Test
public void getVersionsBetweenSuffix() {
String asOfViewSuffix = support.getVersionsBetweenSuffix("_with_history");
assertEquals(asOfViewSuffix, " for system_time between ? and ?");
}
@Test
public void getLower() throws Exception {
String lower = support.getSysPeriodLower("t0", "sys_period");
assertEquals(lower, "t0.sys_period_start");
}
@Test
public void getUpper() throws Exception {
String upper = support.getSysPeriodUpper("t0", "sys_period");
assertEquals(upper, "t0.sys_period_end");
}
}
@@ -0,0 +1,68 @@
package io.ebean.config.dbplatform;
import io.ebean.config.PlatformConfig;
import io.ebean.config.dbplatform.hana.HanaPlatform;
import io.ebeaninternal.dbmigration.ddlgeneration.platform.PlatformDdl;
import io.ebeaninternal.server.core.PlatformDdlBuilder;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class HanaPlatformTest {
HanaPlatform platform = new HanaPlatform();
@Test
public void testTypeConversion() {
PlatformDdl ddl = PlatformDdlBuilder.create(platform);
assertThat(ddl.convert("clob")).isEqualTo("nclob");
assertThat(ddl.convert("blob")).isEqualTo("blob");
assertThat(ddl.convert("json")).isEqualTo("nclob");
assertThat(ddl.convert("jsonb")).isEqualTo("nclob");
assertThat(ddl.convert("jsonvarchar")).isEqualTo("nvarchar(255)");
assertThat(ddl.convert("double")).isEqualTo("double");
assertThat(ddl.convert("varchar(20)")).isEqualTo("nvarchar(20)");
assertThat(ddl.convert("decimal(10)")).isEqualTo("decimal(10)");
assertThat(ddl.convert("decimal(8,4)")).isEqualTo("decimal(8,4)");
assertThat(ddl.convert("decimal")).isEqualTo("decimal(16,3)");
assertThat(ddl.convert("boolean")).isEqualTo("boolean");
assertThat(ddl.convert("bit")).isEqualTo("smallint");
assertThat(ddl.convert("tinyint")).isEqualTo("smallint");
assertThat(ddl.convert("binary")).isEqualTo("varbinary(255)");
assertThat(ddl.convert("binary(16)")).isEqualTo("varbinary(16)");
assertThat(ddl.convert("point")).isEqualTo("st_point");
assertThat(ddl.convert("multilinestring")).isEqualTo("st_geometry");
assertThat(ddl.convert("multipolygon")).isEqualTo("st_geometry");
assertThat(ddl.convert("multipoint")).isEqualTo("st_geometry");
assertThat(ddl.convert("linestring")).isEqualTo("st_geometry");
assertThat(ddl.convert("polygon")).isEqualTo("st_geometry");
}
@Test
public void uuid_default() {
HanaPlatform platform = new HanaPlatform();
platform.configure(new PlatformConfig());
DbPlatformType dbType = platform.getDbTypeMap().get(DbPlatformType.UUID);
assertThat(dbType.renderType(0, 0)).isEqualTo("varchar(40)");
}
@Test
public void uuid_as_binary() {
HanaPlatform platform = new HanaPlatform();
PlatformConfig config = new PlatformConfig();
config.setDbUuid(PlatformConfig.DbUuid.AUTO_BINARY);
platform.configure(config);
DbPlatformType dbType = platform.getDbTypeMap().get(DbPlatformType.UUID);
assertThat(dbType.renderType(0, 0)).isEqualTo("varbinary(16)");
}
}
@@ -0,0 +1,33 @@
package io.ebean.config.dbplatform;
import io.ebean.config.dbplatform.mysql.MySqlHistorySupport;
import org.junit.Test;
import static org.junit.Assert.assertEquals;
public class MySqlHistorySupportTest {
private MySqlHistorySupport support = new MySqlHistorySupport();
@Test
public void getAsOfPredicate() {
String asOfPredicate = support.getAsOfPredicate("t0", "sys_period");
assertEquals(asOfPredicate, "(t0.sys_period_start <= ? and (t0.sys_period_end is null or t0.sys_period_end > ?))");
}
@Test
public void getLower() throws Exception {
String lower = support.getSysPeriodLower("t0", "sys_period");
assertEquals(lower, "t0.sys_period_start");
}
@Test
public void getUpper() throws Exception {
String upper = support.getSysPeriodUpper("t0", "sys_period");
assertEquals(upper, "t0.sys_period_end");
}
}
@@ -0,0 +1,50 @@
package io.ebean.config.dbplatform;
import io.ebean.config.PlatformConfig;
import io.ebean.config.dbplatform.mysql.MySqlPlatform;
import io.ebeaninternal.dbmigration.ddlgeneration.platform.PlatformDdl;
import io.ebeaninternal.server.core.PlatformDdlBuilder;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class MySqlPlatformTest {
MySqlPlatform mySqlPlatform = new MySqlPlatform();
@Test
public void testTypeConversion() {
PlatformDdl ddl = PlatformDdlBuilder.create(mySqlPlatform);
assertThat(ddl.convert("clob")).isEqualTo("longtext");
assertThat(ddl.convert("json")).isEqualTo("json");
assertThat(ddl.convert("jsonb")).isEqualTo("json");
assertThat(ddl.convert("varchar(20)")).isEqualTo("varchar(20)");
assertThat(ddl.convert("boolean")).isEqualTo("tinyint(1)");
assertThat(ddl.convert("bit")).isEqualTo("tinyint(1)");
assertThat(ddl.convert("decimal")).isEqualTo("decimal(16,3)");
}
@Test
public void uuid_default() {
MySqlPlatform platform = new MySqlPlatform();
platform.configure(new PlatformConfig(), false);
DbPlatformType dbType = platform.getDbTypeMap().get(DbPlatformType.UUID);
assertThat(dbType.renderType(0, 0)).isEqualTo("varchar(40)");
}
@Test
public void uuid_as_binary() {
MySqlPlatform platform = new MySqlPlatform();
PlatformConfig config = new PlatformConfig();
config.setDbUuid(PlatformConfig.DbUuid.AUTO_BINARY);
platform.configure(config, false);
DbPlatformType dbType = platform.getDbTypeMap().get(DbPlatformType.UUID);
assertThat(dbType.renderType(0, 0)).isEqualTo("binary(16)");
}
}
@@ -0,0 +1,59 @@
package io.ebean.config.dbplatform;
import io.ebean.config.PlatformConfig;
import io.ebean.config.dbplatform.oracle.OraclePlatform;
import io.ebeaninternal.dbmigration.ddlgeneration.platform.PlatformDdl;
import io.ebeaninternal.server.core.PlatformDdlBuilder;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class OraclePlatformTest {
OraclePlatform platform = new OraclePlatform();
@Test
public void testTypeConversion() {
PlatformDdl ddl = PlatformDdlBuilder.create(platform);
assertThat(ddl.convert("clob")).isEqualTo("clob");
assertThat(ddl.convert("blob")).isEqualTo("blob");
assertThat(ddl.convert("json")).isEqualTo("clob");
assertThat(ddl.convert("jsonb")).isEqualTo("clob");
assertThat(ddl.convert("double")).isEqualTo("number(19,4)");
assertThat(ddl.convert("varchar(20)")).isEqualTo("varchar2(20)");
assertThat(ddl.convert("decimal(10)")).isEqualTo("number(10)");
assertThat(ddl.convert("decimal(8,4)")).isEqualTo("number(8,4)");
assertThat(ddl.convert("decimal")).isEqualTo("number(16,3)");
assertThat(ddl.convert("boolean")).isEqualTo("number(1)");
assertThat(ddl.convert("bit")).isEqualTo("bit");
assertThat(ddl.convert("tinyint")).isEqualTo("number(3)");
assertThat(ddl.convert("binary(16)")).isEqualTo("raw(16)");
}
@Test
public void uuid_default() {
OraclePlatform platform = new OraclePlatform();
platform.configure(new PlatformConfig(), false);
DbPlatformType dbType = platform.getDbTypeMap().get(DbPlatformType.UUID);
assertThat(dbType.renderType(0, 0)).isEqualTo("varchar2(40)");
}
@Test
public void uuid_as_binary() {
OraclePlatform platform = new OraclePlatform();
PlatformConfig config = new PlatformConfig();
config.setDbUuid(PlatformConfig.DbUuid.AUTO_BINARY);
platform.configure(config, false);
DbPlatformType dbType = platform.getDbTypeMap().get(DbPlatformType.UUID);
assertThat(dbType.renderType(0, 0)).isEqualTo("raw(16)");
}
}
@@ -0,0 +1,39 @@
package io.ebean.config.dbplatform;
import io.ebean.config.dbplatform.postgres.PostgresHistorySupport;
import org.junit.Test;
import static org.junit.Assert.assertEquals;
public class PostgresHistorySupportTest {
private PostgresHistorySupport support = new PostgresHistorySupport();
@Test
public void getBindCount() throws Exception {
assertEquals(support.getBindCount(), 1);
}
@Test
public void getAsOfPredicate() throws Exception {
String asOfPredicate = support.getAsOfPredicate("t0", "sys_period");
assertEquals(asOfPredicate, "t0.sys_period @> ?::timestamptz");
}
@Test
public void getSysPeriodLower() throws Exception {
String lower = support.getSysPeriodLower("t0", "sys_period");
assertEquals(lower, "lower(t0.sys_period)");
}
@Test
public void getSysPeriodUpper() throws Exception {
String upper = support.getSysPeriodUpper("t0", "sys_period");
assertEquals(upper, "upper(t0.sys_period)");
}
}
@@ -0,0 +1,48 @@
package io.ebean.config.dbplatform;
import io.ebean.config.PlatformConfig;
import io.ebean.config.dbplatform.postgres.PostgresPlatform;
import io.ebeaninternal.dbmigration.ddlgeneration.platform.PlatformDdl;
import io.ebeaninternal.server.core.PlatformDdlBuilder;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class PostgresPlatformTest {
@Test
public void testTypeConversion() {
PostgresPlatform platform = new PostgresPlatform();
PlatformDdl ddl = PlatformDdlBuilder.create(platform);
assertThat(ddl.convert("clob")).isEqualTo("text");
assertThat(ddl.convert("blob")).isEqualTo("bytea");
assertThat(ddl.convert("json")).isEqualTo("json");
assertThat(ddl.convert("jsonb")).isEqualTo("jsonb");
assertThat(ddl.convert("hstore")).isEqualTo("hstore");
assertThat(ddl.convert("double")).isEqualTo("float");
assertThat(ddl.convert("tinyint")).isEqualTo("smallint");
assertThat(ddl.convert("double")).isEqualTo("float");
assertThat(ddl.convert("varchar(20)")).isEqualTo("varchar(20)");
assertThat(ddl.convert("decimal")).isEqualTo("decimal(16,3)");
assertThat(ddl.convert("decimal(10)")).isEqualTo("decimal(10)");
assertThat(ddl.convert("decimal(8,4)")).isEqualTo("decimal(8,4)");
assertThat(ddl.convert("boolean")).isEqualTo("boolean");
assertThat(ddl.convert("bit")).isEqualTo("bit");
}
@Test
public void testUuidType() {
PostgresPlatform platform = new PostgresPlatform();
platform.configure(new PlatformConfig(), false);
DbPlatformType dbType = platform.getDbTypeMap().get(DbPlatformType.UUID);
String columnDefn = dbType.renderType(0, 0);
assertThat(columnDefn).isEqualTo("uuid");
}
}
@@ -0,0 +1,62 @@
package io.ebean.config.dbplatform;
import org.junit.Test;
import java.sql.ResultSet;
import java.util.List;
import static java.util.Arrays.asList;
import static org.assertj.core.api.Assertions.assertThat;
public class SequenceBatchIdGeneratorTest {
@Test
public void test() {
TD generator = new TD();
// simulate out of order adding of sequence ids
generator.add(asList(1L, 2L));
generator.add(asList(5L, 6L));
generator.add(asList(3L, 4L));
assertThat(generator.nextId(null)).isEqualTo(1L);
assertThat(generator.nextId(null)).isEqualTo(2L);
assertThat(generator.nextId(null)).isEqualTo(3L);
assertThat(generator.nextId(null)).isEqualTo(4L);
assertThat(generator.nextId(null)).isEqualTo(5L);
assertThat(generator.nextId(null)).isEqualTo(6L);
}
private class TD extends SequenceIdGenerator {
protected TD() {
super(null, null, null, 10);
}
void add(List<Long> ids) {
idList.addAll(ids);
}
@Override
public String getSql(int batchSize) {
return "not used";
}
@Override
protected List<Long> readIds(ResultSet resultSet, int loadSize) {
// do nothing
return null;
}
@Override
protected List<Long> getMoreIds(int requestSize) {
return null;
}
@Override
protected void loadInBackground(int requestSize) {
// do nothing
}
}
}
@@ -0,0 +1,69 @@
package io.ebean.config.dbplatform;
import io.ebean.config.PlatformConfig;
import io.ebean.config.dbplatform.sqlserver.SqlServer17Platform;
import io.ebeaninternal.dbmigration.ddlgeneration.platform.PlatformDdl;
import io.ebeaninternal.server.core.PlatformDdlBuilder;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class SqlserverPlatformTest {
SqlServer17Platform platform = new SqlServer17Platform();
@Test
public void testTypeConversion() {
PlatformDdl ddl = PlatformDdlBuilder.create(platform);
assertThat(ddl.convert("clob")).isEqualTo("nvarchar(max)");
assertThat(ddl.convert("blob")).isEqualTo("image");
assertThat(ddl.convert("json")).isEqualTo("nvarchar(max)");
assertThat(ddl.convert("jsonb")).isEqualTo("nvarchar(max)");
assertThat(ddl.convert("double")).isEqualTo("float(32)");
assertThat(ddl.convert("varchar(20)")).isEqualTo("nvarchar(20)");
assertThat(ddl.convert("decimal(10)")).isEqualTo("numeric(10)");
assertThat(ddl.convert("decimal(8,4)")).isEqualTo("numeric(8,4)");
assertThat(ddl.convert("decimal")).isEqualTo("numeric(16,3)");
assertThat(ddl.convert("boolean")).isEqualTo("bit");
assertThat(ddl.convert("bit")).isEqualTo("bit");
assertThat(ddl.convert("tinyint")).isEqualTo("smallint");
assertThat(ddl.convert("binary(16)")).isEqualTo("binary(16)");
}
@Test
public void uuid_default() {
platform.configure(new PlatformConfig());
DbPlatformType dbType = platform.getDbTypeMap().get(DbPlatformType.UUID);
assertThat(dbType.renderType(0, 0)).isEqualTo("uniqueidentifier");
}
@Test
public void uuid_as_binary() {
PlatformConfig config = new PlatformConfig();
config.setDbUuid(PlatformConfig.DbUuid.BINARY);
platform.configure(config);
DbPlatformType dbType = platform.getDbTypeMap().get(DbPlatformType.UUID);
assertThat(dbType.renderType(0, 0)).isEqualTo("binary(16)");
}
@Test
public void uuid_as_varchar() {
PlatformConfig config = new PlatformConfig();
config.setDbUuid(PlatformConfig.DbUuid.VARCHAR);
platform.configure(config);
DbPlatformType dbType = platform.getDbTypeMap().get(DbPlatformType.UUID);
assertThat(dbType.renderType(0, 0)).isEqualTo("nvarchar(40)");
}
}
@@ -0,0 +1,17 @@
package io.ebean.config.dbplatform.sqlserver;
import org.junit.Test;
import static org.junit.Assert.assertTrue;
/**
* @author Vilmos Nagy <vilmos.nagy@outlook.com>
*/
public class SqlServer2016PlatformTest {
@Test
public void testHistorySupport() {
SqlServer17Platform platform = new SqlServer17Platform();
assertTrue(platform.getHistorySupport() instanceof SqlServerHistorySupport);
}
}
@@ -0,0 +1,55 @@
package io.ebean.config.dbplatform.sqlserver;
import io.ebean.BackgroundExecutor;
import io.ebean.BaseTestCase;
import io.ebean.annotation.ForPlatform;
import io.ebean.annotation.Platform;
import org.junit.Ignore;
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import javax.sql.DataSource;
import static org.assertj.core.api.Assertions.assertThat;
public class SqlServerStepSequenceTest extends BaseTestCase {
private static final Logger log = LoggerFactory.getLogger(SqlServerStepSequenceTest.class);
@Ignore
@ForPlatform(Platform.SQLSERVER)
@Test
public void seq() {
server().sqlUpdate("drop sequence if exists sqls_testseq_9876").execute();
server().sqlUpdate("create sequence sqls_testseq_9876 start with 1 increment by 50").execute();
BackgroundExecutor be = server().getBackgroundExecutor();
DataSource ds = server().getPluginApi().getDataSource();
SqlServerStepSequence s = new SqlServerStepSequence(be, ds, "sqls_testseq_9876", 50);
Object id = s.nextId(null);
assertThat(id).isEqualTo(1L);
for (int i = 0; i < 20; i++) {
Object val = s.nextId(null);
log.warn("val: "+val);
}
log.warn("here");
for (int i = 0; i < 20; i++) {
Object val = s.nextId(null);
log.warn("val: "+val);
}
for (int i = 0; i < 100; i++) {
Object val = s.nextId(null);
log.warn("val: "+val);
}
}
}
@@ -0,0 +1,35 @@
package io.ebean.dbmigration;
import io.ebean.annotation.Platform;
import io.ebeaninternal.dbmigration.DbOffline;
import org.junit.Test;
public class DbMigrationSqlServerTest {
@Test(expected = IllegalArgumentException.class)
public void need_explicitPlatform() {
try {
DbMigration dbMigration = DbMigration.create();
dbMigration.setPlatform(Platform.SQLSERVER);
} finally {
DbOffline.reset();
}
}
@Test
public void explicit_16_isGood() {
DbMigration dbMigration = DbMigration.create();
dbMigration.setPlatform(Platform.SQLSERVER16);
DbOffline.reset();
}
@Test
public void explicit_17_isGood() {
DbMigration dbMigration = DbMigration.create();
dbMigration.setPlatform(Platform.SQLSERVER17);
DbOffline.reset();
}
}
@@ -0,0 +1,121 @@
package io.ebean.event;
import io.ebean.BaseTestCase;
import io.ebean.EbeanServer;
import io.ebean.EbeanServerFactory;
import io.ebean.bean.BeanCollection;
import io.ebean.common.BeanList;
import io.ebean.config.ServerConfig;
import org.junit.Test;
import org.tests.example.ModUuidGenerator;
import org.tests.model.basic.EBasic;
import org.tests.model.basic.ECustomId;
import java.util.List;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
public class BeanFindControllerTest extends BaseTestCase {
@Test
public void test() {
ServerConfig config = new ServerConfig();
config.setName("h2otherfind");
config.loadFromProperties();
config.setDdlGenerate(true);
config.setDdlRun(true);
config.setDdlExtra(false);
config.setRegister(false);
config.setDefaultServer(false);
config.add(new ModUuidGenerator());
config.getClasses().add(EBasic.class);
config.getClasses().add(ECustomId.class);
EBasicFindController findController = new EBasicFindController();
config.getFindControllers().add(findController);
EbeanServer ebeanServer = EbeanServerFactory.create(config);
assertFalse(findController.calledInterceptFind);
ebeanServer.find(EBasic.class, 42);
assertTrue(findController.calledInterceptFind);
findController.findIntercept = true;
EBasic eBasic = ebeanServer.find(EBasic.class, 42);
assertEquals(Integer.valueOf(47), eBasic.getId());
assertEquals("47", eBasic.getName());
assertFalse(findController.calledInterceptFindMany);
List<EBasic> list = ebeanServer.find(EBasic.class).where().eq("name", "AnInvalidNameSoEmpty").findList();
assertEquals(0, list.size());
assertTrue(findController.calledInterceptFindMany);
findController.findManyIntercept = true;
list = ebeanServer.find(EBasic.class).where().eq("name", "AnInvalidNameSoEmpty").findList();
assertEquals(1, list.size());
eBasic = list.get(0);
assertEquals(Integer.valueOf(47), eBasic.getId());
assertEquals("47", eBasic.getName());
ECustomId bean = new ECustomId("check");
ebeanServer.save(bean);
assertNotNull(bean.getId());
}
static class EBasicFindController implements BeanFindController {
boolean findIntercept;
boolean findManyIntercept;
boolean calledInterceptFind;
boolean calledInterceptFindMany;
@Override
public boolean isRegisterFor(Class<?> cls) {
return EBasic.class.equals(cls);
}
@Override
public boolean isInterceptFind(BeanQueryRequest<?> request) {
calledInterceptFind = true;
return findIntercept;
}
@SuppressWarnings("unchecked")
@Override
public <T> T find(BeanQueryRequest<T> request) {
return (T) createBean();
}
@Override
public boolean isInterceptFindMany(BeanQueryRequest<?> request) {
calledInterceptFindMany = true;
return findManyIntercept;
}
@SuppressWarnings("unchecked")
@Override
public <T> BeanCollection<T> findMany(BeanQueryRequest<T> request) {
BeanList<T> list = new BeanList<>();
list.add((T) createBean());
return list;
}
}
private static EBasic createBean() {
EBasic b = new EBasic();
b.setId(47);
b.setName("47");
return b;
}
}
@@ -0,0 +1,199 @@
package io.ebean.event;
import io.ebean.EbeanServer;
import io.ebean.EbeanServerFactory;
import io.ebean.Transaction;
import io.ebean.config.ServerConfig;
import org.junit.Test;
import org.tests.model.basic.EBasicVer;
import org.tests.model.basic.UTDetail;
import org.tests.model.basic.UTMaster;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
public class BeanPersistControllerTest {
private PersistAdapter continuePersistingAdapter = new PersistAdapter(true);
private PersistAdapter stopPersistingAdapter = new PersistAdapter(false);
@Test
public void issue_1341() {
EbeanServer ebeanServer = getEbeanServer(continuePersistingAdapter);
UTMaster bean0 = new UTMaster("one0");
UTDetail detail0 = new UTDetail("detail0", 12, 23D);
bean0.getDetails().add(detail0);
ebeanServer.save(bean0);
UTMaster master = ebeanServer.find(UTMaster.class)
.setId(bean0.getId())
.fetch("details", "name, version")
.findOne();
UTDetail utDetail = master.getDetails().get(0);
utDetail.setName("detail0 mod");
Transaction txn = ebeanServer.beginTransaction();
try {
txn.setBatchMode(true);
ebeanServer.save(master);
txn.commit();
} finally {
txn.end();
}
}
@Test
public void testInsertUpdateDelete_given_continuePersistingAdapter() {
EbeanServer ebeanServer = getEbeanServer(continuePersistingAdapter);
EBasicVer bean = new EBasicVer("testController");
ebeanServer.save(bean);
assertThat(continuePersistingAdapter.methodsCalled).hasSize(2);
assertThat(continuePersistingAdapter.methodsCalled).containsExactly("preInsert", "postInsert");
continuePersistingAdapter.methodsCalled.clear();
bean.setName("modified");
ebeanServer.save(bean);
assertThat(continuePersistingAdapter.methodsCalled).hasSize(2);
assertThat(continuePersistingAdapter.methodsCalled).containsExactly("preUpdate", "postUpdate");
continuePersistingAdapter.methodsCalled.clear();
ebeanServer.delete(bean);
assertThat(continuePersistingAdapter.methodsCalled).hasSize(2);
assertThat(continuePersistingAdapter.methodsCalled).containsExactly("preDelete", "postDelete");
}
@Test
public void testInsertUpdateDelete_given_stopPersistingAdapter() {
EbeanServer ebeanServer = getEbeanServer(stopPersistingAdapter);
EBasicVer bean = new EBasicVer("testController");
ebeanServer.save(bean);
assertThat(stopPersistingAdapter.methodsCalled).hasSize(1);
assertThat(stopPersistingAdapter.methodsCalled).containsExactly("preInsert");
stopPersistingAdapter.methodsCalled.clear();
bean.setName("modified");
ebeanServer.update(bean);
assertThat(stopPersistingAdapter.methodsCalled).hasSize(1);
assertThat(stopPersistingAdapter.methodsCalled).containsExactly("preUpdate");
stopPersistingAdapter.methodsCalled.clear();
ebeanServer.delete(bean);
assertThat(stopPersistingAdapter.methodsCalled).hasSize(1);
assertThat(stopPersistingAdapter.methodsCalled).containsExactly("preDelete");
stopPersistingAdapter.methodsCalled.clear();
ebeanServer.delete(EBasicVer.class, 22);
assertThat(stopPersistingAdapter.methodsCalled).hasSize(1);
assertThat(stopPersistingAdapter.methodsCalled).containsExactly("preDeleteById");
stopPersistingAdapter.methodsCalled.clear();
ebeanServer.deleteAll(EBasicVer.class, Arrays.asList(22,23,24));
assertThat(stopPersistingAdapter.methodsCalled).hasSize(3);
assertThat(stopPersistingAdapter.methodsCalled).containsExactly("preDeleteById", "preDeleteById", "preDeleteById");
stopPersistingAdapter.methodsCalled.clear();
}
private EbeanServer getEbeanServer(PersistAdapter persistAdapter) {
ServerConfig config = new ServerConfig();
config.setName("h2ebasicver");
config.loadFromProperties();
config.setDdlGenerate(true);
config.setDdlRun(true);
config.setDdlExtra(false);
config.setRegister(false);
config.setDefaultServer(false);
config.getClasses().add(EBasicVer.class);
config.getClasses().add(UTMaster.class);
config.getClasses().add(UTDetail.class);
config.add(persistAdapter);
return EbeanServerFactory.create(config);
}
static class PersistAdapter extends BeanPersistAdapter {
boolean continueDefaultPersisting;
List<String> methodsCalled = new ArrayList<>();
/**
* No default constructor so only registered manually.
*/
PersistAdapter(boolean continueDefaultPersisting) {
this.continueDefaultPersisting = continueDefaultPersisting;
}
@Override
public boolean isRegisterFor(Class<?> cls) {
return true;
}
@Override
public boolean preDelete(BeanPersistRequest<?> request) {
methodsCalled.add("preDelete");
return continueDefaultPersisting;
}
@Override
public boolean preInsert(BeanPersistRequest<?> request) {
methodsCalled.add("preInsert");
return continueDefaultPersisting;
}
@Override
public boolean preUpdate(BeanPersistRequest<?> request) {
methodsCalled.add("preUpdate");
Object bean = request.getBean();
if (bean instanceof UTDetail) {
UTDetail detail = (UTDetail)bean;
// invoke lazy loading ... which invoke the flush of the jdbc batch
detail.setQty(42);
}
return continueDefaultPersisting;
}
@Override
public void postDelete(BeanPersistRequest<?> request) {
methodsCalled.add("postDelete");
}
@Override
public void postInsert(BeanPersistRequest<?> request) {
methodsCalled.add("postInsert");
}
@Override
public void postUpdate(BeanPersistRequest<?> request) {
methodsCalled.add("postUpdate");
}
@Override
public void preDelete(BeanDeleteIdRequest request) {
methodsCalled.add("preDeleteById");
}
}
}
@@ -0,0 +1,98 @@
package io.ebean.event;
import io.ebean.BaseTestCase;
import io.ebean.BeanState;
import io.ebean.Ebean;
import io.ebean.EbeanServer;
import io.ebean.EbeanServerFactory;
import io.ebean.config.ServerConfig;
import org.tests.model.basic.EBasicVer;
import org.junit.Test;
import java.util.ArrayList;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
public class BeanPostLoadTest extends BaseTestCase {
PostLoad postLoad = new PostLoad(false);
@Test
public void testPostLoad() {
EbeanServer ebeanServer = getEbeanServer();
EBasicVer bean = new EBasicVer("testPostLoad");
bean.setDescription("someDescription");
bean.setOther("other");
ebeanServer.save(bean);
EBasicVer found = ebeanServer.find(EBasicVer.class)
.select("name, other")
.setId(bean.getId())
.findOne();
assertThat(postLoad.methodsCalled).hasSize(1);
assertThat(postLoad.methodsCalled).containsExactly("postLoad");
assertThat(postLoad.beanState.getLoadedProps()).containsExactly("id", "name", "other");
assertThat(postLoad.bean).isSameAs(found);
ebeanServer.delete(bean);
}
private EbeanServer getEbeanServer() {
ServerConfig config = new ServerConfig();
config.setName("h2ebasicver");
config.loadFromProperties();
config.setDdlGenerate(true);
config.setDdlRun(true);
config.setDdlExtra(false);
config.setRegister(false);
config.setDefaultServer(false);
config.getClasses().add(EBasicVer.class);
config.add(postLoad);
return EbeanServerFactory.create(config);
}
static class PostLoad implements BeanPostLoad {
boolean dummy;
List<String> methodsCalled = new ArrayList<>();
Object bean;
BeanState beanState;
/**
* No default constructor so only registered manually.
*/
PostLoad(boolean dummy) {
this.dummy = dummy;
}
@Override
public boolean isRegisterFor(Class<?> cls) {
return true;
}
@Override
public void postLoad(Object bean) {
this.methodsCalled.add("postLoad");
this.bean = bean;
this.beanState = Ebean.getBeanState(bean);
}
}
}
@@ -0,0 +1,21 @@
package io.ebean.event.readaudit;
import org.junit.Test;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotEquals;
public class ReadAuditQueryPlanTest {
@Test
public void testEquals() {
ReadAuditQueryPlan plan1 = new ReadAuditQueryPlan("org.Bean", "queryKey", "select id from foo");
assertEquals(plan1, new ReadAuditQueryPlan("org.Bean", "queryKey", "select id from foo"));
assertNotEquals(plan1, new ReadAuditQueryPlan("org.Bean", "queryKey", "select id from Notfoo"));
assertNotEquals(plan1, new ReadAuditQueryPlan("org.Bean", "notQueryKey", "select id from foo"));
assertNotEquals(plan1, new ReadAuditQueryPlan("org.NotBean", "queryKey", "select id from foo"));
}
}
@@ -0,0 +1,315 @@
package io.ebean.json;
import io.ebean.text.json.EJson;
import io.ebeaninternal.json.ModifyAwareMap;
import io.ebeaninternal.json.ModifyAwareOwner;
import com.fasterxml.jackson.core.JsonFactory;
import com.fasterxml.jackson.core.JsonParser;
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.io.StringReader;
import java.nio.file.Files;
import java.util.Iterator;
import java.util.LinkedHashMap;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import static org.junit.Assert.*;
public class EJsonTests {
private static final Logger log = LoggerFactory.getLogger(EJsonTests.class);
@Test
public void test_map_simple() throws IOException {
JsonFactory factory = new JsonFactory();
String jsonInput = "{\"name\":\"rob\",\"age\":12}";
JsonParser jsonParser = factory.createParser(jsonInput);
Object result = EJson.parse(jsonParser);
assertTrue(result instanceof Map);
Map<?, ?> map = (Map<?, ?>) result;
assertEquals("rob", map.get("name"));
assertEquals(12L, map.get("age"));
String jsonOutput = EJson.write(result);
assertEquals(jsonInput, jsonOutput);
}
@Test
public void write_withWriter_expect_writerNotClosed() throws IOException {
File temp = Files.createTempFile("some", ".json").toFile();
FileWriter writer = new FileWriter(temp);
Map<String,Object> map = new LinkedHashMap<>();
map.put("foo", "bar");
EJson.write(map, writer);
writer.write("The end.");
writer.flush();
writer.close();
log.info("write to file {}", temp.getAbsolutePath());
}
@Test
public void test_parseObject() throws IOException {
JsonFactory factory = new JsonFactory();
String jsonInput = "{\"name\":\"rob\",\"age\":12}";
JsonParser jsonParser = factory.createParser(jsonInput);
Map<String, Object> map = EJson.parseObject(jsonParser);
assertNotNull(map);
assertEquals("rob", map.get("name"));
assertEquals(12L, map.get("age"));
String jsonOutput = EJson.write(map);
assertEquals(jsonInput, jsonOutput);
}
@Test
public void test_parseObject_reader() throws IOException {
String jsonInput = "{\"name\":\"rob\",\"age\":12}";
StringReader reader = new StringReader(jsonInput);
Map<String, Object> map = EJson.parseObject(reader);
assertNotNull(map);
assertEquals("rob", map.get("name"));
assertEquals(12L, map.get("age"));
String jsonOutput = EJson.write(map);
assertEquals(jsonInput, jsonOutput);
}
@Test
public void test_map_nested() throws IOException {
String jsonInput = "{\"name\":\"rob\",\"age\":12,\"org\":{\"name\":\"superorg\",\"rating\":4},\"nums\":[1,2,3]}";
Object result = EJson.parse(jsonInput);
assertTrue(result instanceof Map);
Map<?, ?> map = (Map<?, ?>) result;
assertEquals(4, map.size());
assertEquals("rob", map.get("name"));
assertEquals(12L, map.get("age"));
Map<?, ?> org = (Map<?, ?>) map.get("org");
assertEquals("superorg", org.get("name"));
assertEquals(4L, org.get("rating"));
List<?> nums = (List<?>) map.get("nums");
assertEquals(3, nums.size());
assertEquals(1L, nums.get(0));
assertEquals(2L, nums.get(1));
assertEquals(3L, nums.get(2));
String jsonOutput = EJson.write(result);
assertEquals(jsonInput, jsonOutput);
}
@Test
public void test_map_withNull() throws IOException {
String jsonInput = "{\"name\":\"rob\",\"age\":null}";
Object result = EJson.parse(jsonInput);
assertTrue(result instanceof Map);
Map<?, ?> map = (Map<?, ?>) result;
assertEquals("rob", map.get("name"));
assertNull(map.get("age"));
String jsonOutput = EJson.write(result);
assertEquals(jsonInput, jsonOutput);
}
@Test
public void test_list_simple() throws IOException {
String jsonInput = "[\"name\",\"rob\",12,13]";
List<Object> list = EJson.parseList(jsonInput);
assertEquals(4, list.size());
assertEquals("name", list.get(0));
assertEquals("rob", list.get(1));
assertEquals(12L, list.get(2));
assertEquals(13L, list.get(3));
String jsonOutput = EJson.write(list);
assertEquals(jsonInput, jsonOutput);
}
@Test
public void test_list_reader() throws IOException {
String jsonInput = "[\"name\",\"rob\",12,13]";
StringReader reader = new StringReader(jsonInput);
List<Object> list = EJson.parseList(reader);
assertEquals(4, list.size());
assertEquals("name", list.get(0));
assertEquals("rob", list.get(1));
assertEquals(12L, list.get(2));
assertEquals(13L, list.get(3));
String jsonOutput = EJson.write(list);
assertEquals(jsonInput, jsonOutput);
}
@Test
public void test_list_jsonParser() throws IOException {
String jsonInput = "[\"name\",\"rob\",12,13]";
JsonFactory jsonFactory = new JsonFactory();
JsonParser parser = jsonFactory.createParser(jsonInput);
List<Object> list = EJson.parseList(parser);
assertEquals(4, list.size());
assertEquals("name", list.get(0));
assertEquals("rob", list.get(1));
assertEquals(12L, list.get(2));
assertEquals(13L, list.get(3));
String jsonOutput = EJson.write(list);
assertEquals(jsonInput, jsonOutput);
}
@SuppressWarnings("unchecked")
@Test
public void test_list_ofMaps() throws IOException {
String jsonInput = "[{\"name\":\"rob\",\"age\":12},{\"name\":\"mike\",\"age\":13}]";
Object result = EJson.parse(jsonInput);
assertTrue(result instanceof List);
List<Map<?, ?>> list = (List<Map<?, ?>>) result;
assertEquals(2, list.size());
assertEquals("rob", list.get(0).get("name"));
assertEquals(12L, list.get(0).get("age"));
assertEquals("mike", list.get(1).get("name"));
assertEquals(13L, list.get(1).get("age"));
String jsonOutput = EJson.write(result);
assertEquals(jsonInput, jsonOutput);
}
@Test
public void test_partial_read() throws IOException {
String jsonInput = "{\"name\":\"rob\",\"age\":null,\"friend\":{\"name\":\"mike\",\"age\":13}},some more json would follow...";
StringReader reader = new StringReader(jsonInput);
Object result = EJson.parse(reader);
assertTrue(result instanceof Map);
Map<?, ?> map = (Map<?, ?>) result;
assertEquals("rob", map.get("name"));
assertNull(map.get("age"));
Map<?, ?> friend = (Map<?, ?>) map.get("friend");
assertEquals("mike", friend.get("name"));
assertEquals(13L, friend.get("age"));
}
@Test
public void test_map_nested_modifyAware() throws IOException {
String jsonInput = "{\"name\":\"rob\",\"age\":12,\"org\":{\"name\":\"superorg\",\"rating\":4},\"nums\":[1,2,3]}";
ModifyAwareMap<String, Object> map = (ModifyAwareMap<String, Object>) EJson.parseObject(jsonInput, true);
assertFalse(map.isMarkedDirty());
assertEquals(4, map.size());
map.put("name", "jim");
assertTrue(map.isMarkedDirty());
}
@SuppressWarnings("unchecked")
@Test
public void test_map_nested_modifyAwareNestedList() throws IOException {
String jsonInput = "{\"name\":\"rob\",\"age\":12,\"org\":{\"name\":\"superorg\",\"rating\":4},\"nums\":[1,2,3]}";
ModifyAwareMap<String, Object> map = (ModifyAwareMap<String, Object>) EJson.parseObject(jsonInput, true);
assertFalse(map.isMarkedDirty());
List<Object> nums = (List<Object>) map.get("nums");
nums.add(4);
assertTrue(map.isMarkedDirty());
}
@SuppressWarnings("unchecked")
@Test
public void test_map_nested_modifyAwareNestedObject() throws IOException {
String jsonInput = "{\"name\":\"rob\",\"age\":12,\"org\":{\"name\":\"superorg\",\"rating\":4},\"nums\":[1,2,3]}";
ModifyAwareMap<String, Object> map = (ModifyAwareMap<String, Object>) EJson.parseObject(jsonInput, true);
assertFalse(map.isMarkedDirty());
Map<String, Object> org = (Map<String, Object>) map.get("org");
org.put("extra", "foo");
assertTrue(map.isMarkedDirty());
}
@Test
public void parse_when_null() throws IOException {
Object nothing = EJson.parse((String) null);
assertNull(nothing);
}
@Test
public void parseList_when_null() throws IOException {
Object nothing = EJson.parseList((String) null);
assertNull(nothing);
}
@Test
@SuppressWarnings({ "rawtypes", "unchecked" })
public void parseSet_when_modifyAware() throws IOException {
String jsonInput = "[{\"name\":\"rob\",\"age\":12},{\"name\":\"jim\",\"age\":42}]";
Set set = EJson.parseSet(jsonInput, true);
ModifyAwareOwner modAware = (ModifyAwareOwner) set;
assertFalse(modAware.isMarkedDirty());
Iterator iterator = set.iterator();
if (iterator.hasNext()) {
Map map = (Map) iterator.next();
map.put("name", "stu");
assertTrue(modAware.isMarkedDirty());
}
}
@Test
public void parseSet_when_not_modifyAware() throws IOException {
String jsonInput = "[{\"name\":\"rob\",\"age\":12},{\"name\":\"jim\",\"age\":42}]";
Set<?> set = EJson.parseSet(jsonInput, false);
assertTrue(set instanceof LinkedHashSet);
}
}
@@ -0,0 +1,241 @@
package io.ebean.plugin;
import io.ebean.DB;
import io.ebean.Database;
import io.ebean.FetchPath;
import io.ebean.Query;
import io.ebean.text.PathProperties;
import io.ebeaninternal.api.SpiQuery;
import io.ebeaninternal.server.querydefn.OrmQueryDetail;
import org.junit.Test;
import org.tests.inheritance.Stockforecast;
import org.tests.model.basic.Car;
import org.tests.model.basic.Customer;
import org.tests.model.basic.Order;
import org.tests.model.basic.OrderDetail;
import org.tests.model.basic.Person;
import org.tests.model.basic.Product;
import org.tests.model.basic.Vehicle;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
public class BeanTypeTest {
private static Database db = DB.getDefault();
private <T> BeanType<T> beanType(Class<T> cls) {
return db.getPluginApi().getBeanType(cls);
}
@Test
public void getBeanType() {
assertThat(beanType(Order.class).getBeanType()).isEqualTo(Order.class);
}
@Test
public void getTypeAtPath_when_ManyToOne() {
BeanType<Order> orderType = beanType(Order.class);
BeanType<?> customerType = orderType.getBeanTypeAtPath("customer");
assertThat(customerType.getBeanType()).isEqualTo(Customer.class);
}
@Test
public void getTypeAtPath_when_OneToMany() {
BeanType<Order> orderType = beanType(Order.class);
BeanType<?> detailsType = orderType.getBeanTypeAtPath("details");
assertThat(detailsType.getBeanType()).isEqualTo(OrderDetail.class);
}
@Test
public void getTypeAtPath_when_nested() {
BeanType<Order> orderType = beanType(Order.class);
BeanType<?> productType = orderType.getBeanTypeAtPath("details.product");
assertThat(productType.getBeanType()).isEqualTo(Product.class);
}
@Test(expected = RuntimeException.class)
public void getTypeAtPath_when_simpleType() {
beanType(Order.class).getBeanTypeAtPath("status");
}
@Test
public void createBean() {
assertThat(beanType(Order.class).createBean()).isNotNull();
}
@Test
public void property() {
Order order = new Order();
order.setStatus(Order.Status.APPROVED);
Property statusProperty = beanType(Order.class).getProperty("status");
assertThat(statusProperty.getVal(order)).isEqualTo(order.getStatus());
}
@Test
public void getBaseTable() {
assertThat(beanType(Order.class).getBaseTable()).isEqualTo("o_order");
}
@Test
public void beanId_and_getBeanId() {
Order order = new Order();
order.setId(42);
Object id1 = beanType(Order.class).beanId(order);
Object id2 = beanType(Order.class).getBeanId(order);
assertThat(id1).isEqualTo(order.getId());
assertThat(id2).isEqualTo(order.getId());
}
@Test
public void setBeanId() {
Order order = new Order();
beanType(Order.class).setBeanId(order, 42);
assertThat(42).isEqualTo(order.getId());
}
@Test
public void isDocStoreIndex() {
assertThat(beanType(Order.class).isDocStoreMapped()).isFalse();
assertThat(beanType(Person.class).isDocStoreMapped()).isFalse();
assertThat(beanType(Order.class).getDocMapping()).isNotNull();
assertThat(beanType(Person.class).getDocMapping()).isNull();
}
@Test
public void docStore_getEmbedded() {
BeanDocType<Order> orderDocType = beanType(Order.class).docStore();
FetchPath customer = orderDocType.getEmbedded("customer");
assertThat(customer).isNotNull();
assertThat(customer.getProperties(null)).contains("id", "name");
}
@Test
public void docStore_getEmbeddedManyRoot() {
BeanDocType<Order> orderDocType = beanType(Order.class).docStore();
FetchPath detailsPath = orderDocType.getEmbedded("details");
assertThat(detailsPath).isNotNull();
FetchPath detailsRoot = orderDocType.getEmbeddedManyRoot("details");
assertThat(detailsRoot).isNotNull();
assertThat(detailsRoot.getProperties(null)).containsExactly("id", "details");
assertThat(detailsRoot.hasPath("details")).isTrue();
}
@Test
public void getDocStoreQueueId() {
assertThat(beanType(Order.class).getDocStoreQueueId()).isEqualTo("order");
assertThat(beanType(Customer.class).getDocStoreQueueId()).isEqualTo("customer");
}
@Test
public void getDocStoreIndexType() {
assertThat(beanType(Order.class).docStore().getIndexType()).isEqualTo("order");
assertThat(beanType(Customer.class).docStore().getIndexType()).isEqualTo("customer");
}
@Test
public void getDocStoreIndexName() {
assertThat(beanType(Order.class).docStore().getIndexType()).isEqualTo("order");
assertThat(beanType(Customer.class).docStore().getIndexType()).isEqualTo("customer");
}
@Test
public void docStoreNested() {
FetchPath parse = PathProperties.parse("id,name");
FetchPath nestedCustomer = beanType(Order.class).docStore().getEmbedded("customer");
assertThat(nestedCustomer.toString()).isEqualTo(parse.toString());
}
@Test
public void docStoreApplyPath() {
SpiQuery<Order> orderQuery = (SpiQuery<Order>) db.find(Order.class);
beanType(Order.class).docStore().applyPath(orderQuery);
OrmQueryDetail detail = orderQuery.getDetail();
assertThat(detail.getChunk("customer", false).getSelectInclude()).containsExactly("id", "name");
}
@Test(expected = IllegalStateException.class)
public void docStoreIndex() throws Exception {
beanType(Order.class).docStore().index(1, new Order(), null);
}
@Test(expected = IllegalStateException.class)
public void docStoreDeleteById() throws Exception {
beanType(Order.class).docStore().deleteById(1, null);
}
@Test(expected = IllegalStateException.class)
public void docStoreUpdateEmbedded() throws Exception {
beanType(Order.class).docStore().updateEmbedded(1, "customer", "someJson", null);
}
@Test
public void hasInheritance_when_not() {
assertFalse(beanType(Order.class).hasInheritance());
}
@Test
public void hasInheritance_when_root() {
assertTrue(beanType(Vehicle.class).hasInheritance());
}
@Test
public void hasInheritance_when_leaf() {
assertTrue(beanType(Car.class).hasInheritance());
}
@Test
public void getDiscColumn_when_default() {
assertEquals(beanType(Car.class).getDiscColumn(), "dtype");
}
@Test
public void getDiscColumn_when_set() {
assertEquals(beanType(Stockforecast.class).getDiscColumn(), "type");
}
@Test
public void createBeanUsingDisc_when_set() {
Vehicle vehicle = beanType(Vehicle.class).createBeanUsingDisc("C");
assertTrue(vehicle instanceof Car);
}
@Test
public void addInheritanceWhere_when_leaf() {
Query<Vehicle> query = db.find(Vehicle.class);
beanType(Car.class).addInheritanceWhere(query);
}
@Test
public void addInheritanceWhere_when_root() {
Query<Vehicle> query = db.find(Vehicle.class);
beanType(Vehicle.class).addInheritanceWhere(query);
}
}
@@ -0,0 +1,125 @@
package io.ebean.plugin;
import io.ebean.Ebean;
import io.ebean.EbeanServer;
import org.junit.Test;
import org.tests.model.basic.Customer;
import org.tests.model.basic.Order;
import org.tests.model.basic.ResetBasicData;
import static org.assertj.core.api.Assertions.assertThat;
public class ExpressionPathTest {
static EbeanServer server = Ebean.getDefaultServer();
<T> BeanType<T> beanType(Class<T> cls) {
return server.getPluginApi().getBeanType(cls);
}
@Test
public void containsMany_when_many() throws Exception {
BeanType<Order> beanType = beanType(Order.class);
assertThat(beanType.getExpressionPath("details").containsMany()).isTrue();
}
@Test
public void containsMany_when_manyChild() throws Exception {
BeanType<Order> beanType = beanType(Order.class);
assertThat(beanType.getExpressionPath("details.id").containsMany()).isTrue();
}
@Test
public void containsMany_when_manyGrandChild() throws Exception {
BeanType<Order> beanType = beanType(Order.class);
assertThat(beanType.getExpressionPath("details.product.sku").containsMany()).isTrue();
}
@Test
public void containsMany_when_one() throws Exception {
BeanType<Order> beanType = beanType(Order.class);
assertThat(beanType.getExpressionPath("customer.name").containsMany()).isFalse();
}
@Test
public void containsMany_when_oneWithMany() throws Exception {
BeanType<Order> beanType = beanType(Order.class);
assertThat(beanType.getExpressionPath("customer.contacts").containsMany()).isTrue();
}
@Test
public void containsMany_when_oneWithManyChild() throws Exception {
BeanType<Order> beanType = beanType(Order.class);
assertThat(beanType.getExpressionPath("customer.contacts.firstName").containsMany()).isTrue();
}
@Test
public void set_when_basic() throws Exception {
BeanType<Order> beanType = beanType(Order.class);
Order order = new Order();
beanType.getExpressionPath("id").pathSet(order, 42);
assertThat(order.getId()).isEqualTo(42);
}
@Test
public void set_when_nested() throws Exception {
BeanType<Order> beanType = beanType(Order.class);
Order order = new Order();
beanType.getExpressionPath("customer.name").pathSet(order, "Rob");
assertThat(order.getCustomer().getName()).isEqualTo("Rob");
}
@Test
public void test_dirty() throws Exception {
ResetBasicData.reset();
BeanType<Customer> customerBeanType = beanType(Customer.class);
BeanType<Order> orderBeanType = beanType(Order.class);
Customer customer = new Customer();
customer.setName("foo");
server.save(customer);
customer = server.find(Customer.class, customer.getId());
assertThat(customer.getName()).isEqualTo("foo");
customerBeanType.getExpressionPath("name").pathSet(customer, "bar");
server.save(customer);
customer = server.find(Customer.class, customer.getId());
assertThat(customer.getName()).isEqualTo("bar");
Order order = new Order();
order.setCustomer(customer);
server.save(order);
order = server.find(Order.class, order.getId());
ExpressionPath customerNamePath = orderBeanType.getExpressionPath("customer.name");
assertThat(customerNamePath.pathGet(order)).isEqualTo("bar");
customerNamePath.pathSet(order, "baz");
server.save(order);
order = server.find(Order.class, order.getId());
assertThat(order.getCustomer().getName()).isEqualTo("baz");
// cleanup
server.delete(Order.class, order.getId());
server.delete(Customer.class, customer.getId());
}
}
@@ -0,0 +1,56 @@
package io.ebean.plugin;
import io.ebean.Ebean;
import io.ebean.EbeanServer;
import org.tests.model.basic.Customer;
import org.tests.model.basic.Order;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
/**
*/
public class PropertyTest {
static EbeanServer server = Ebean.getDefaultServer();
<T> BeanType<T> beanType(Class<T> cls) {
return server.getPluginApi().getBeanType(cls);
}
@Test
public void getVal() throws Exception {
Customer customer = new Customer();
Order order = new Order();
order.setCustomer(customer);
order.setStatus(Order.Status.APPROVED);
Property statusProperty = beanType(Order.class).getProperty("status");
assertThat(statusProperty.getVal(order)).isEqualTo(order.getStatus());
Property customerProperty = beanType(Order.class).getProperty("customer");
assertThat(customerProperty.getVal(order)).isEqualTo(customer);
}
@Test
public void isMany_when_not() {
assertThat(beanType(Order.class).getProperty("status").isMany()).isFalse();
assertThat(beanType(Order.class).getProperty("customer").isMany()).isFalse();
}
@Test
public void isMany_when_true() {
assertThat(beanType(Order.class).getProperty("details").isMany()).isTrue();
}
@Test
public void name() {
assertThat(beanType(Order.class).getProperty("status").getName()).isEqualTo("status");
assertThat(beanType(Order.class).getProperty("customer").getName()).isEqualTo("customer");
assertThat(beanType(Order.class).getProperty("details").getName()).isEqualTo("details");
}
}
@@ -0,0 +1,60 @@
package io.ebean.plugin;
import io.ebean.BaseTestCase;
import io.ebean.Ebean;
import io.ebean.EbeanServer;
import org.tests.model.basic.Customer;
import org.junit.Test;
import org.tests.model.basic.VwCustomer;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertTrue;
public class SpiServerTest extends BaseTestCase {
@Test
public void test() {
EbeanServer defaultServer = Ebean.getDefaultServer();
SpiServer pluginApi = defaultServer.getPluginApi();
BeanType<Customer> beanType = pluginApi.getBeanType(Customer.class);
assertEquals("o_customer", beanType.getBaseTable());
assertNotNull(pluginApi.getDatabasePlatform());
assertNull(beanType.getFindController());
assertNotNull(beanType.getPersistController());
assertNull(beanType.getPersistListener());
assertNull(beanType.getQueryAdapter());
assertTrue(beanType.isValidExpression("name"));
assertTrue(beanType.isValidExpression("contacts.firstName"));
assertTrue(beanType.isValidExpression("contacts.group.name"));
assertFalse(beanType.isValidExpression("junk"));
assertFalse(beanType.isValidExpression("Name"));
assertFalse(beanType.isValidExpression("contacts.name"));
Customer customer = new Customer();
customer.setId(42);
assertEquals(42, beanType.getBeanId(customer));
List<? extends BeanType<?>> beanTypes = pluginApi.getBeanTypes("o_customer");
assertEquals(2, beanTypes.size());
BeanType<VwCustomer> vwBeanType = pluginApi.getBeanType(VwCustomer.class);
assertThat(beanTypes.contains(beanType)).isTrue();
assertThat(beanTypes.contains(vwBeanType)).isTrue();
List<? extends BeanType<?>> allTypes = pluginApi.getBeanTypes();
assertFalse(allTypes.isEmpty());
}
}
@@ -0,0 +1,17 @@
package io.ebean.server.type;
import io.ebean.annotation.EnumValue;
/**
* Enum test when DB CHAR column used with spaces.
*/
public enum MyDayOfWeek {
@EnumValue("MONDAY ")MONDAY,
@EnumValue("TUESDAY ")TUESDAY,
@EnumValue("WEDNESDAY")WEDNESDAY,
@EnumValue("THURSDAY ")THURSDAY,
@EnumValue("FRIDAY ")FRIDAY,
@EnumValue("SATURDAY ")SATURDAY,
@EnumValue("SUNDAY ")SUNDAY
}
@@ -0,0 +1,28 @@
package io.ebean.server.type;
import io.ebean.annotation.EnumValue;
/**
* Enum with method overrides (and hence multiple actual classes).
*/
public enum MyEnum {
@EnumValue("A")Aval {
@Override
public String doSomething() {
return "bar";
}
},
@EnumValue("B")Bval,
@EnumValue("C")Cval {
@Override
public String doSomething() {
return "baz";
}
};
public String doSomething() {
return "foo";
}
}
@@ -0,0 +1,5 @@
package io.ebean.server.type;
public enum MySex {
MALE, FEMALE
}
@@ -0,0 +1,154 @@
package io.ebean.server.type;
import io.ebean.BaseTestCase;
import io.ebean.config.ServerConfig;
import io.ebean.config.dbplatform.h2.H2Platform;
import io.ebeaninternal.server.core.bootup.BootupClasses;
import io.ebeaninternal.server.type.DefaultTypeManager;
import io.ebeaninternal.server.type.RsetDataReader;
import io.ebeaninternal.server.type.ScalarType;
import io.ebeaninternal.server.type.ScalarTypeEnumStandard;
import org.junit.Assert;
import org.junit.Test;
import org.tests.model.ivo.Money;
import org.tests.model.ivo.converter.MoneyTypeConverter;
import javax.persistence.EnumType;
import java.sql.SQLException;
import java.sql.Types;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertTrue;
public class TestTypeManager extends BaseTestCase {
@Test
public void testEnumWithSubclasses() throws SQLException {
DefaultTypeManager typeManager = createTypeManager();
ScalarType<?> type = typeManager.createEnumScalarType(MyEnum.class, null);
typeManager.addEnumType(type, MyEnum.class);
Object val = type.read(new DummyDataReader("A"));
assertThat(val).isEqualTo(MyEnum.Aval);
val = type.read(new DummyDataReader("B"));
assertThat(val).isEqualTo(MyEnum.Bval);
val = type.read(new DummyDataReader("C"));
assertThat(val).isEqualTo(MyEnum.Cval);
ScalarType<?> typeGeneral = typeManager.getScalarType(MyEnum.class);
assertThat(typeGeneral).isNotNull();
ScalarType<?> typeB = typeManager.getScalarType(MyEnum.Bval.getClass());
assertThat(typeB).isNotNull();
ScalarType<?> typeA = typeManager.getScalarType(MyEnum.Aval.getClass());
assertThat(typeA).isNotNull();
ScalarType<?> typeC = typeManager.getScalarType(MyEnum.Cval.getClass());
assertThat(typeC).isNotNull();
try {
typeManager.createEnumScalarType(MyEnum.class, EnumType.STRING);
assertTrue("never get here",false);
} catch (IllegalStateException e) {
assertThat(e.getMessage()).contains("It is mapped using 2 different modes when only one is supported");
}
}
@Test
public void testEnumWithChar() throws SQLException {
DefaultTypeManager typeManager = createTypeManager();
ScalarType<?> dayOfWeekType = typeManager.createEnumScalarType(MyDayOfWeek.class, null);
Object val = dayOfWeekType.read(new DummyDataReader("MONDAY "));
assertThat(val).isEqualTo(MyDayOfWeek.MONDAY);
val = dayOfWeekType.read(new DummyDataReader("TUESDAY "));
assertThat(val).isEqualTo(MyDayOfWeek.TUESDAY);
val = dayOfWeekType.read(new DummyDataReader("WEDNESDAY"));
assertThat(val).isEqualTo(MyDayOfWeek.WEDNESDAY);
val = dayOfWeekType.read(new DummyDataReader("THURSDAY "));
assertThat(val).isEqualTo(MyDayOfWeek.THURSDAY);
val = dayOfWeekType.read(new DummyDataReader("FRIDAY "));
assertThat(val).isEqualTo(MyDayOfWeek.FRIDAY);
try {
typeManager.createEnumScalarType(MyDayOfWeek.class, EnumType.ORDINAL);
assertTrue("never get here",false);
} catch (IllegalStateException e) {
assertThat(e.getMessage()).contains("It is mapped using 2 different modes when only one is supported");
}
}
@Test
public void test() {
DefaultTypeManager typeManager = createTypeManager();
ScalarType<?> scalarType = typeManager.getScalarType(Money.class);
assertTrue(scalarType.getJdbcType() == Types.DECIMAL);
assertTrue(!scalarType.isJdbcNative());
Assert.assertEquals(Money.class, scalarType.getType());
}
@Test
public void testWithConfig() {
DefaultTypeManager typeManager1 = createTypeManager();
ScalarType<?> type1 = typeManager1.createEnumScalarType(MySex.class, null);
assertThat(type1 instanceof ScalarTypeEnumStandard.OrdinalEnum);
//
DefaultTypeManager typeManager2 = createTypeManagerDefaultEnumTypeString();
ScalarType<?> type2 = typeManager2.createEnumScalarType(MySex.class, null);
assertThat(type2 instanceof ScalarTypeEnumStandard.StringEnum);
//
DefaultTypeManager typeManager3 = createTypeManagerDefaultEnumTypeString();
ScalarType<?> type3 = typeManager3.createEnumScalarType(MySex.class, EnumType.ORDINAL);
assertThat(type3 instanceof ScalarTypeEnumStandard.OrdinalEnum);
}
private DefaultTypeManager createTypeManager() {
ServerConfig serverConfig = new ServerConfig();
serverConfig.setDatabasePlatform(new H2Platform());
BootupClasses bootupClasses = new BootupClasses();
bootupClasses.getAttributeConverters().add(MoneyTypeConverter.class);
return new DefaultTypeManager(serverConfig, bootupClasses);
}
private DefaultTypeManager createTypeManagerDefaultEnumTypeString() {
ServerConfig serverConfig = new ServerConfig();
serverConfig.setDatabasePlatform(new H2Platform());
serverConfig.setDefaultEnumType(EnumType.STRING);
BootupClasses bootupClasses = new BootupClasses();
bootupClasses.getAttributeConverters().add(MoneyTypeConverter.class);
return new DefaultTypeManager(serverConfig, bootupClasses);
}
/**
* Test double DataReader implementation.
*/
private static class DummyDataReader extends RsetDataReader {
String val;
DummyDataReader(String val) {
super(null, null);
this.val = val;
}
@Override
public String getString() throws SQLException {
return val;
}
}
}
@@ -0,0 +1,217 @@
package io.ebean.text;
import io.ebean.DB;
import io.ebean.FetchPath;
import io.ebean.Query;
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.tests.model.basic.Customer;
import org.tests.model.basic.ResetBasicData;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
public class PathPropertiesTests {
private static final Logger log = LoggerFactory.getLogger(PathPropertiesTests.class);
@Test
public void test_noParentheses() {
PathProperties s0 = PathProperties.parse("id,name");
assertEquals(1, s0.getPathProps().size());
assertTrue(s0.getProperties(null).contains("id"));
assertTrue(s0.getProperties(null).contains("name"));
assertFalse(s0.getProperties(null).contains("status"));
}
@Test
public void test_noParentheses_needTrim() {
PathProperties s0 = PathProperties.parse(" id, name ");
assertEquals(1, s0.getPathProps().size());
assertTrue(s0.getProperties(null).contains("id"));
assertTrue(s0.getProperties(null).contains("name"));
assertFalse(s0.getProperties(null).contains("status"));
}
@Test
public void test_withParentheses() {
PathProperties s0 = PathProperties.parse("(id,name)");
assertEquals(1, s0.getPathProps().size());
assertTrue(s0.getProperties(null).contains("id"));
assertTrue(s0.getProperties(null).contains("name"));
assertFalse(s0.getProperties(null).contains("status"));
}
@Test
public void test_withColon() {
PathProperties s0 = PathProperties.parse(":(id,name)");
assertEquals(1, s0.getPathProps().size());
assertTrue(s0.getProperties(null).contains("id"));
assertTrue(s0.getProperties(null).contains("name"));
assertFalse(s0.getProperties(null).contains("status"));
}
@Test
public void test_nested() {
PathProperties s1 = PathProperties.parse("id,name,shipAddr(*)");
assertEquals(2, s1.getPathProps().size());
assertEquals(3, s1.getProperties(null).size());
assertTrue(s1.getProperties(null).contains("id"));
assertTrue(s1.getProperties(null).contains("name"));
assertTrue(s1.getProperties(null).contains("shipAddr"));
assertTrue(s1.getProperties("shipAddr").contains("*"));
assertEquals(1, s1.getProperties("shipAddr").size());
}
@Test
public void test_withParenthesesColonNested() {
PathProperties s1 = PathProperties.parse(":(id,name,shipAddr(*))");
assertEquals(2, s1.getPathProps().size());
assertEquals(3, s1.getProperties(null).size());
assertTrue(s1.getProperties(null).contains("id"));
assertTrue(s1.getProperties(null).contains("name"));
assertTrue(s1.getProperties(null).contains("shipAddr"));
assertTrue(s1.getProperties("shipAddr").contains("*"));
assertEquals(1, s1.getProperties("shipAddr").size());
}
@Test
public void test_add() {
PathProperties root = PathProperties.parse("status,date");
root.addNested("customer", PathProperties.parse("id,name"));
FetchPath expect = PathProperties.parse("status,date,customer(id,name)");
assertThat(root.toString()).isEqualTo(expect.toString());
}
@Test
public void test_add_nested() {
PathProperties root = PathProperties.parse("status,date");
root.addNested("customer", PathProperties.parse("id,name,address(line1,city)"));
FetchPath expect = PathProperties.parse("status,date,customer(id,name,address(line1,city))");
assertThat(root.toString()).isEqualTo(expect.toString());
}
@Test
public void test_all_properties() {
FetchPath root = PathProperties.parse("*");
assertThat(root.getProperties(null)).containsExactly("*");
}
@Test
public void test_all_properties_multipleLevels() {
PathProperties root = PathProperties.parse("*,customer(*)");
//PathProperties.Props rootProps = root.getProps(null);
PathProperties.Props customerProps = root.getProps("customer");
assertThat(root.getProperties(null)).containsExactly("*", "customer");
assertThat(customerProps.getPropertiesAsString()).isEqualTo("*");
}
@Test
public void test_includesProperty_when_wildcardUsed() {
PathProperties root = PathProperties.parse("*,customer(*)");
assertTrue(root.includesProperty("id"));
assertTrue(root.includesProperty("name"));
assertTrue(root.includesProperty("customer.id"));
assertTrue(root.includesProperty("customer.name"));
assertFalse(root.includesProperty("details.id"));
assertTrue(root.includesProperty("details"));
assertFalse(root.includesPath("details"));
}
@Test
public void test_includesProperty_when_specificPropertiesUsed() {
PathProperties root = PathProperties.parse("id,name,customer(*,billingAddress(city))");
assertTrue(root.includesProperty("id"));
assertTrue(root.includesProperty("name"));
assertFalse(root.includesProperty("status"));
assertTrue(root.includesProperty("customer.id"));
assertTrue(root.includesProperty("customer.foo"));
assertTrue(root.includesProperty("customer.billingAddress"));
assertTrue(root.includesProperty("customer.billingAddress.city"));
assertFalse(root.includesPath("customer.shippingAddress"));
assertFalse(root.includesPath("customer", "shippingAddress"));
assertFalse(root.includesProperty("customer.shippingAddress.city"));
assertTrue(root.includesPath(null));
assertTrue(root.includesPath("customer"));
assertTrue(root.includesPath("customer.billingAddress"));
assertTrue(root.includesPath("customer", "billingAddress"));
assertFalse(root.includesPath("customer.shippingAddress"));
assertFalse(root.includesPath("details"));
}
@Test
public void test_includesPropertyWithPrefix() {
PathProperties root = PathProperties.parse("id,name,customer(*,billingAddress(city))");
assertTrue(root.includesProperty("customer", "id"));
assertTrue(root.includesProperty("customer", "billingAddress"));
assertTrue(root.includesProperty("customer.billingAddress", "city"));
assertFalse(root.includesPath("customer", "shippingAddress"));
assertFalse(root.includesProperty("customer.shippingAddress", "city"));
}
@Test
public void test_includesPathWithPrefix() {
PathProperties root = PathProperties.parse("id,name,customer(*,billingAddress(city))");
assertTrue(root.includesPath(null, "customer"));
assertTrue(root.includesPath("customer", "billingAddress"));
assertFalse(root.includesPath(null, "details"));
assertFalse(root.includesPath("customer", "shippingAddress"));
}
@Test
public void example_withQueryAndJson() {
ResetBasicData.reset();
PathProperties pathProps = PathProperties.parse("id,name,billingAddress(city),shippingAddress(*))");
Query<Customer> query = DB.find(Customer.class)
.where().lt("id", 2)
.query();
pathProps.apply(query);
List<Customer> list = query.findList();
String asJson = DB.json().toJson(list, pathProps);
log.info("Json: {}", asJson);
}
}
@@ -0,0 +1,88 @@
package io.ebean.text.json;
import io.ebean.BaseTestCase;
import io.ebean.Ebean;
import io.ebean.bean.PersistenceContext;
import org.tests.model.basic.Customer;
import com.fasterxml.jackson.core.JsonParser;
import org.junit.Test;
import java.io.StringReader;
import static org.assertj.core.api.Assertions.assertThat;
public class JsonBeanReaderTest extends BaseTestCase {
static JsonContext json = Ebean.json();
@Test
public void read() {
JsonParser parser = getParser();
JsonBeanReader<Customer> beanReader = json.createBeanReader(Customer.class, parser, null);
Customer customer = beanReader.read();
assertThat(customer.getId()).isEqualTo(42);
assertThat(customer.getName()).isEqualTo("dummy");
}
private JsonParser getParser() {
Customer customer = new Customer();
customer.setId(42);
customer.setName("dummy");
String rawJson = json.toJson(customer);
StringReader reader = new StringReader(rawJson);
return json.createParser(reader);
}
@Test
public void forJson() {
JsonParser parser = getParser();
JsonBeanReader<Customer> beanReader = json.createBeanReader(Customer.class, parser, null);
beanReader.read();
JsonParser more = getParser();
JsonBeanReader<Customer> moreReader = beanReader.forJson(more, true);
Customer customer = moreReader.read();
assertThat(customer.getId()).isEqualTo(42);
assertThat(customer.getName()).isEqualTo("dummy");
}
@Test
public void persistenceContextPut_when_noPC() throws Exception {
JsonParser parser = getParser();
JsonBeanReader<Customer> beanReader = json.createBeanReader(Customer.class, parser, null);
beanReader.read();
Customer other = new Customer();
other.setId(54);
beanReader.persistenceContextPut(54, other);
}
@Test
public void persistenceContextPut_when_hasPC() throws Exception {
JsonReadOptions options = new JsonReadOptions().setEnableLazyLoading(true);
JsonParser parser = getParser();
JsonBeanReader<Customer> beanReader = json.createBeanReader(Customer.class, parser, options);
Customer customer = beanReader.read();
Customer other = new Customer();
other.setId(54);
beanReader.persistenceContextPut(54, other);
PersistenceContext pc = beanReader.getPersistenceContext();
assertThat(pc.get(Customer.class, 54)).isSameAs(other);
assertThat(pc.get(Customer.class, 42)).isSameAs(customer);
}
}
@@ -0,0 +1,228 @@
package io.ebean.text.json;
import com.fasterxml.jackson.core.JsonGenerator;
import io.ebean.DB;
import io.ebean.text.PathProperties;
import org.junit.Test;
import org.tests.model.basic.Contact;
import org.tests.model.basic.Customer;
import org.tests.model.basic.Order;
import org.tests.model.basic.ResetBasicData;
import java.io.StringReader;
import java.io.StringWriter;
import java.util.List;
import java.util.Map;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertSame;
import static org.junit.Assert.assertTrue;
public class JsonContextTest {
@Test
public void testIsSupportedType() {
JsonContext json = DB.json();
assertTrue(json.isSupportedType(Customer.class));
assertFalse(json.isSupportedType(System.class));
}
@Test
public void test_jsonWithPersistenceContext() {
ResetBasicData.reset();
List<Order> orders = DB.find(Order.class)
.fetch("customer", "id, name")
.where().eq("customer.id", 1)
.findList();
String json = DB.json().toJson(orders);
List<Order> orders1 = DB.json().toList(Order.class, json);
Customer customer = null;
for (Order order : orders1) {
Customer tempCustomer = order.getCustomer();
if (customer == null) {
customer = tempCustomer;
} else {
assertThat(tempCustomer).isSameAs(customer);
}
}
}
@Test
public void test_json_loadContext() {
ResetBasicData.reset();
List<Order> orders = DB.find(Order.class)
.select("status")
.fetch("customer", "id, name")
.findList();
String json = DB.json().toJson(orders);
JsonReadOptions options = new JsonReadOptions().setEnableLazyLoading(true);
List<Order> orders1 = DB.json().toList(Order.class, json, options);
for (Order order : orders1) {
Customer customer = order.getCustomer();
customer.getName();
customer.getSmallnote();
List<Contact> contacts = customer.getContacts();
contacts.size();
}
}
@Test
public void test_toJsonPretty() {
ResetBasicData.reset();
List<Order> orders = DB.find(Order.class)
.select("status")
.fetch("customer", "id, name")
.findList();
String json = DB.json().toJsonPretty(orders);
assertThat(json).contains("[ {");
assertThat(json).contains("\"customer\": {");
}
@Test
public void test_toObject() {
JsonContext json = DB.getDefault().json();
Customer customer = new Customer();
customer.setId(1);
customer.setName("Jim");
String asJson = json.toJson(customer);
Object bean = json.toObject(Customer.class, asJson);
assertTrue(bean instanceof Customer);
assertEquals(Integer.valueOf(1), ((Customer) bean).getId());
assertEquals("Jim", ((Customer) bean).getName());
StringReader reader = new StringReader(asJson);
bean = json.toObject(Customer.class, reader);
assertTrue(bean instanceof Customer);
assertEquals(Integer.valueOf(1), ((Customer) bean).getId());
assertEquals("Jim", ((Customer) bean).getName());
}
@Test
public void test_unknownProperty() {
String jsonWithUnknown = "{\"id\":42,\"unknownProp\":\"foo\",\"name\":\"rob\",\"version\":1}";
Customer customer = DB.json().toBean(Customer.class, jsonWithUnknown);
assertEquals(Integer.valueOf(42), customer.getId());
assertEquals("rob", customer.getName());
}
class CustReadVisitor implements JsonReadBeanVisitor<Customer> {
Customer bean;
Map<String, Object> unmapped;
@Override
public void visit(Customer bean, Map<String, Object> unmapped) {
this.bean = bean;
this.unmapped = unmapped;
}
}
@SuppressWarnings("unchecked")
@Test
public void test_unknownProperty_withVisitor() {
String jsonWithUnknown = "{\"id\":42,\"unknownProp\":\"foo\",\"name\":\"rob\",\"version\":1,\"extraProp\":{\"name\":\"foobie\",\"sim\":\"bo\"}}";
CustReadVisitor custReadVisitor = new CustReadVisitor();
JsonReadOptions options = new JsonReadOptions();
options.addRootVisitor(custReadVisitor);
Customer customer = DB.json().toBean(Customer.class, jsonWithUnknown, options);
assertEquals(Integer.valueOf(42), customer.getId());
assertEquals("rob", customer.getName());
assertSame(customer, custReadVisitor.bean);
assertEquals("foo", custReadVisitor.unmapped.get("unknownProp"));
assertEquals(2, custReadVisitor.unmapped.size());
assertEquals("foobie", ((Map<String, Object>) custReadVisitor.unmapped.get("extraProp")).get("name"));
assertEquals("bo", ((Map<String, Object>) custReadVisitor.unmapped.get("extraProp")).get("sim"));
}
@Test
public void test_withVisitor_noUnmapped() {
String someJsonAllKnown = "{\"id\":42,\"name\":\"rob\",\"version\":1}";
CustReadVisitor custReadVisitor = new CustReadVisitor();
JsonReadOptions options = new JsonReadOptions();
options.addRootVisitor(custReadVisitor);
Customer customer = DB.json().toBean(Customer.class, someJsonAllKnown, options);
assertEquals(Integer.valueOf(42), customer.getId());
assertEquals("rob", customer.getName());
assertSame(customer, custReadVisitor.bean);
assertNull(custReadVisitor.unmapped);
}
@Test
public void testCreateGenerator() throws Exception {
StringWriter writer = new StringWriter();
JsonContext json = DB.json();
JsonGenerator generator = json.createGenerator(writer);
Customer customer = new Customer();
customer.setId(1);
customer.setName("Jim");
// we can use the generator before and after our json.toJson() call
// ... confirming we are not closing the generator
generator.writeStartArray();
json.toJson(customer, generator, PathProperties.parse("id,name"));
generator.writeEndArray();
generator.close();
String jsonString = writer.toString();
assertTrue(jsonString, jsonString.startsWith("["));
assertTrue(jsonString, jsonString.endsWith("]"));
assertTrue(jsonString, jsonString.contains("{\"id\":1,\"name\":\"Jim\"}"));
}
@Test
public void testCreateGenerator_writeRaw() throws Exception {
StringWriter writer = new StringWriter();
JsonContext json = DB.json();
JsonGenerator generator = json.createGenerator(writer);
// test that we can write anything via writeRaw()
generator.writeRaw("START");
generator.writeStartArray();
generator.writeStartObject();
generator.writeNumberField("count", 12);
generator.writeEndObject();
generator.writeEndArray();
generator.writeRaw("END");
generator.close();
assertEquals("START[{\"count\":12}]END", writer.toString());
}
}
@@ -0,0 +1,60 @@
package io.ebean.text.json;
import io.ebean.FetchPath;
import org.junit.Test;
import java.util.Set;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
public class JsonWriteOptionsTests {
@Test
public void test_parse() {
JsonWriteOptions options = JsonWriteOptions.parsePath("id,status,name");
FetchPath pathProps = options.getPathProperties();
//Assert.assertEquals(1, pathProps.getPaths().size());
assertTrue(pathProps.getProperties(null).contains("id"));
assertTrue(pathProps.getProperties(null).contains("name"));
assertTrue(pathProps.getProperties(null).contains("status"));
assertFalse(pathProps.getProperties(null).contains("foo"));
}
@Test
public void test_with_depth() {
JsonWriteOptions options = JsonWriteOptions.parsePath("id,status,name,customer(id,name,address(street,city)),orders(qty,product(sku,prodName))");
FetchPath pathProps = options.getPathProperties();
//Assert.assertEquals(5, pathProps.getPaths().size());
assertTrue(pathProps.getProperties(null).contains("id"));
assertTrue(pathProps.getProperties(null).contains("name"));
assertTrue(pathProps.getProperties(null).contains("status"));
assertTrue(pathProps.getProperties(null).contains("customer"));
assertTrue(pathProps.getProperties(null).contains("orders"));
assertFalse(pathProps.getProperties(null).contains("foo"));
Set<String> customer = pathProps.getProperties("customer");
assertTrue(customer.contains("id"));
assertTrue(customer.contains("name"));
assertTrue(customer.contains("address"));
Set<String> address = pathProps.getProperties("customer.address");
assertTrue(address.contains("street"));
assertTrue(address.contains("city"));
Set<String> orders = pathProps.getProperties("orders");
assertTrue(orders.contains("qty"));
assertTrue(orders.contains("product"));
Set<String> product = pathProps.getProperties("orders.product");
assertTrue(product.contains("sku"));
assertTrue(product.contains("prodName"));
}
}
@@ -0,0 +1,46 @@
package io.ebean.util;
import org.junit.Test;
import static org.junit.Assert.assertEquals;
public class CamelCaseHelperTest {
@Test
public void when_underscore() {
assertEquals(CamelCaseHelper.toCamelFromUnderscore("hello_there"), "helloThere");
assertEquals(CamelCaseHelper.toCamelFromUnderscore("hello_there_jim"), "helloThereJim");
}
@Test
public void when_trailing_numbers() {
assertEquals(CamelCaseHelper.toCamelFromUnderscore("hello_1"), "hello1");
assertEquals(CamelCaseHelper.toCamelFromUnderscore("hello_there_2"), "helloThere2");
}
@Test
public void when_numbers() {
assertEquals(CamelCaseHelper.toCamelFromUnderscore("hello1_id"), "hello1Id");
assertEquals(CamelCaseHelper.toCamelFromUnderscore("hello_there2_foo"), "helloThere2Foo");
assertEquals(CamelCaseHelper.toCamelFromUnderscore("hello1id"), "hello1id");
assertEquals(CamelCaseHelper.toCamelFromUnderscore("hello_there2foo"), "helloThere2foo");
}
@Test
public void when_numbersProceedUppercase() {
assertEquals(CamelCaseHelper.toCamelFromUnderscore("hello1_id"), "hello1Id");
assertEquals(CamelCaseHelper.toCamelFromUnderscore("hello_there2_foo"), "helloThere2Foo");
assertEquals(CamelCaseHelper.toUnderscoreFromCamel("hello1Id"), "hello1_id");
assertEquals(CamelCaseHelper.toUnderscoreFromCamel("helloThere2Foo"), "hello_there2_foo");
}
@Test
public void when_already_camel() {
assertEquals(CamelCaseHelper.toCamelFromUnderscore("helloThere"), "helloThere");
assertEquals(CamelCaseHelper.toCamelFromUnderscore("helloThereJim"), "helloThereJim");
assertEquals(CamelCaseHelper.toCamelFromUnderscore("hello"), "hello");
assertEquals(CamelCaseHelper.toCamelFromUnderscore("HELLO"), "hello");
}
}
@@ -0,0 +1,40 @@
package io.ebeaninternal.api;
import org.junit.Test;
import java.util.Arrays;
import java.util.List;
import static org.junit.Assert.*;
public class BindParamsTest {
@Test
public void test_hash() {
BindParams bindParams = new BindParams();
List<String> ids = Arrays.asList("1", "2", "3");
bindParams.setParameter("ids", ids);
BindParams.Param param = bindParams.getParameter("ids");
assertEquals(3, param.queryBindCount());
assertFalse(bindParams.isSameBindHash());
List<String> ids2 = Arrays.asList("1", "2", "3", "4");
bindParams.setParameter("ids", ids2);
assertEquals(4, param.queryBindCount());
assertFalse(bindParams.isSameBindHash());
List<String> ids3 = Arrays.asList("2", "99", "44");
bindParams.setParameter("ids", ids3);
assertEquals(3, param.queryBindCount());
assertFalse(bindParams.isSameBindHash());
List<String> ids4 = Arrays.asList("4545", "3499", "3444");
bindParams.setParameter("ids", ids4);
assertEquals(3, param.queryBindCount());
assertTrue(bindParams.isSameBindHash());
}
}
@@ -0,0 +1,50 @@
package io.ebeaninternal.api;
import io.ebean.Ebean;
import io.ebean.TxScope;
import org.junit.Assert;
import org.junit.Test;
import org.tests.model.basic.Contact;
import org.tests.model.basic.Customer;
import org.tests.model.basic.ResetBasicData;
import org.tests.model.basic.UUOne;
public class HelpScopeTransTest {
@Test
public void begin() throws Exception {
ResetBasicData.reset();
HelpScopeTrans.enter(TxScope.required());
HelpScopeTrans.enter(TxScope.required());
Ebean.find(Customer.class).findList();
HelpScopeTrans.enter(TxScope.required());
Ebean.find(Contact.class).findList();
HelpScopeTrans.exit(null, 1);
UUOne one = new UUOne();
one.setName("junk");
Ebean.save(one);
HelpScopeTrans.exit(null, 1);
HelpScopeTrans.exit(null, 1);
}
@Test
public void disableTransaction() {
HelpScopeTrans.setEnabled(false);
try {
HelpScopeTrans.enter(TxScope.required());
Assert.assertNull(Ebean.getDefaultServer().currentTransaction());
HelpScopeTrans.exit(null, 1);
} finally {
HelpScopeTrans.setEnabled(true);
}
}
}
@@ -0,0 +1,48 @@
package io.ebeaninternal.api;
import io.ebean.annotation.Platform;
import org.junit.Test;
import static org.junit.Assert.*;
public class PlatformMatchTest {
@Test
public void match() {
assertTrue(PlatformMatch.matchPlatform(Platform.H2, "h2"));
assertTrue(PlatformMatch.matchPlatform(Platform.H2, "mysql,h2"));
assertTrue(PlatformMatch.matchPlatform(Platform.H2, "mysql,h2,"));
assertTrue(PlatformMatch.matchPlatform(Platform.H2, "mysql , h2 ,"));
assertTrue(PlatformMatch.matchPlatform(Platform.H2, "mysql , h2, oracle"));
assertTrue(PlatformMatch.matchPlatform(Platform.H2, "mysql , h2, oracle"));
assertTrue(PlatformMatch.matchPlatform(Platform.SQLSERVER, "sqlserver"));
assertTrue(PlatformMatch.matchPlatform(Platform.SQLSERVER17, "sqlserver"));
assertTrue(PlatformMatch.matchPlatform(Platform.SQLSERVER16, "sqlserver"));
assertTrue(PlatformMatch.matchPlatform(Platform.POSTGRES, "postgres"));
assertTrue(PlatformMatch.matchPlatform(Platform.POSTGRES9, "postgres"));
}
@Test
public void match_sqlserver17_matchAlsoToGenericName() {
assertTrue(PlatformMatch.matchPlatform(Platform.SQLSERVER17, "sqlserver"));
assertTrue(PlatformMatch.matchPlatform(Platform.SQLSERVER17, "sqlserver17"));
}
@Test
public void matchPlatform_sqlserver16_matchAlsoToGenericName() {
assertTrue(PlatformMatch.matchPlatform(Platform.SQLSERVER16, "sqlserver"));
assertTrue(PlatformMatch.matchPlatform(Platform.SQLSERVER16, "sqlserver16"));
}
@Test
public void matchPlatform_sqlserver_nonMatch() {
assertFalse(PlatformMatch.matchPlatform(Platform.SQLSERVER16, "sqlserver17"));
assertFalse(PlatformMatch.matchPlatform(Platform.SQLSERVER17, "sqlserver16"));
assertFalse(PlatformMatch.matchPlatform(Platform.SQLSERVER, "sqlserver16"));
assertFalse(PlatformMatch.matchPlatform(Platform.SQLSERVER, "sqlserver17"));
}
}
@@ -0,0 +1,993 @@
package io.ebeaninternal.api;
import io.ebean.AutoTune;
import io.ebean.BackgroundExecutor;
import io.ebean.BeanState;
import io.ebean.CallableSql;
import io.ebean.DocumentStore;
import io.ebean.DtoQuery;
import io.ebean.ExpressionFactory;
import io.ebean.ExtendedServer;
import io.ebean.Filter;
import io.ebean.FutureIds;
import io.ebean.FutureList;
import io.ebean.FutureRowCount;
import io.ebean.MergeOptions;
import io.ebean.PagedList;
import io.ebean.PersistenceContextScope;
import io.ebean.Query;
import io.ebean.QueryIterator;
import io.ebean.RowConsumer;
import io.ebean.RowMapper;
import io.ebean.ScriptRunner;
import io.ebean.SqlQuery;
import io.ebean.SqlRow;
import io.ebean.SqlUpdate;
import io.ebean.Transaction;
import io.ebean.TransactionCallback;
import io.ebean.TxScope;
import io.ebean.Update;
import io.ebean.UpdateQuery;
import io.ebean.ValuePair;
import io.ebean.Version;
import io.ebean.annotation.Platform;
import io.ebean.annotation.TxIsolation;
import io.ebean.bean.BeanCollection;
import io.ebean.bean.CallOrigin;
import io.ebean.cache.ServerCacheManager;
import io.ebean.config.ServerConfig;
import io.ebean.config.dbplatform.DatabasePlatform;
import io.ebean.event.readaudit.ReadAuditLogger;
import io.ebean.event.readaudit.ReadAuditPrepare;
import io.ebean.meta.MetaInfoManager;
import io.ebean.meta.MetricVisitor;
import io.ebean.plugin.Property;
import io.ebean.plugin.SpiServer;
import io.ebean.text.csv.CsvReader;
import io.ebean.text.json.JsonContext;
import io.ebeaninternal.dbmigration.ddlgeneration.DdlHandler;
import io.ebeaninternal.server.core.SpiResultSet;
import io.ebeaninternal.server.core.timezone.DataTimeZone;
import io.ebeaninternal.server.deploy.BeanDescriptor;
import io.ebeaninternal.server.query.CQuery;
import io.ebeaninternal.server.transaction.RemoteTransactionEvent;
import javax.persistence.OptimisticLockException;
import javax.persistence.PersistenceException;
import java.lang.reflect.Type;
import java.time.Clock;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.Set;
import java.util.concurrent.Callable;
import java.util.function.Consumer;
import java.util.function.Predicate;
import java.util.stream.Stream;
/**
* Test double for SpiEbeanServer.
*/
public class TDSpiEbeanServer implements SpiEbeanServer {
String name;
public TDSpiEbeanServer() {
}
public TDSpiEbeanServer(String name) {
this.name = name;
}
@Override
public ExtendedServer extended() {
return this;
}
@Override
public long clockNow() {
return System.currentTimeMillis();
}
@Override
public void setClock(Clock clock) {
}
@Override
public boolean isDisableL2Cache() {
return false;
}
@Override
public SpiLogManager log() {
return null;
}
@Override
public void shutdownManaged() {
}
@Override
public ScriptRunner script() {
return null;
}
@Override
public void truncate(String... tables) {
}
@Override
public void truncate(Class<?>... tables) {
}
@Override
public void scopedTransactionEnter(TxScope txScope) {
}
@Override
public void scopedTransactionExit(Object returnOrThrowable, int opCode) {
}
@Override
public Object currentTenantId() {
return null;
}
@Override
public DataTimeZone getDataTimeZone() {
return null;
}
@Override
public Platform getPlatform() {
return Platform.GENERIC;
}
@Override
public SpiServer getPluginApi() {
return null;
}
@Override
public boolean isUpdateAllPropertiesInBatch() {
return false;
}
@Override
public ServerConfig getServerConfig() {
return null;
}
@Override
public DatabasePlatform getDatabasePlatform() {
return null;
}
@Override
public DdlHandler createDdlHandler() {
return null;
}
@Override
public CallOrigin createCallOrigin() {
return null;
}
@Override
public PersistenceContextScope getPersistenceContextScope(SpiQuery<?> query) {
return null;
}
@Override
public DocumentStore docStore() {
return null;
}
@Override
public ReadAuditLogger getReadAuditLogger() {
return null;
}
@Override
public ReadAuditPrepare getReadAuditPrepare() {
return null;
}
@Override
public void clearQueryStatistics() {
}
@Override
public BeanDescriptor<?> getBeanDescriptorByQueueId(String queueId) {
return null;
}
@Override
public SpiTransactionManager getTransactionManager() {
return null;
}
@Override
public List<BeanDescriptor<?>> getBeanDescriptors() {
return null;
}
@Override
public <T> BeanDescriptor<T> getBeanDescriptor(Class<T> type) {
return null;
}
@Override
public BeanDescriptor<?> getBeanDescriptorById(String descriptorId) {
return null;
}
@Override
public List<BeanDescriptor<?>> getBeanDescriptors(String tableName) {
return null;
}
@Override
public void externalModification(TransactionEventTable event) {
}
@Override
public void clearServerTransaction() {
}
@Override
public SpiTransaction beginServerTransaction() {
return null;
}
@Override
public SpiTransaction currentServerTransaction() {
return null;
}
@Override
public SpiTransaction createReadOnlyTransaction(Object tenantId) {
return null;
}
@Override
public void remoteTransactionEvent(RemoteTransactionEvent event) {
}
@Override
public <T> CQuery<T> compileQuery(Query<T> query, Transaction t) {
return null;
}
@Override
public <T> int delete(Query<T> query, Transaction t) {
return 0;
}
@Override
public <T> UpdateQuery<T> update(Class<T> beanType) {
return null;
}
@Override
public <T> int update(Query<T> query, Transaction transaction) {
return 0;
}
@Override
public void merge(Object bean) {
}
@Override
public void merge(Object bean, MergeOptions options) {
}
@Override
public void merge(Object bean, MergeOptions options, Transaction transaction) {
}
@Override
public <T> List<Version<T>> findVersions(Query<T> query, Transaction transaction) {
return null;
}
@Override
public <A, T> List<A> findIdsWithCopy(Query<T> query, Transaction t) {
return null;
}
@Override
public <T> int findCountWithCopy(Query<T> query, Transaction t) {
return 0;
}
@Override
public void loadBean(LoadBeanRequest loadRequest) {
}
@Override
public void loadMany(LoadManyRequest loadRequest) {
}
@Override
public int getLazyLoadBatchSize() {
return 0;
}
@Override
public boolean isSupportedType(Type genericType) {
return false;
}
@Override
public void visitMetrics(MetricVisitor visitor) {
}
@Override
public void loadMany(BeanCollection<?> collection, boolean onlyIds) {
}
@Override
public void shutdown(boolean shutdownDataSource, boolean deregisterDriver) {
}
@Override
public AutoTune getAutoTune() {
return null;
}
@Override
public String getName() {
return name;
}
@Override
public ExpressionFactory getExpressionFactory() {
return null;
}
@Override
public MetaInfoManager getMetaInfoManager() {
return null;
}
@Override
public BeanState getBeanState(Object bean) {
return null;
}
@Override
public Object setBeanId(Object bean, Object id) {
return id;
}
@Override
public Object getBeanId(Object bean) {
return null;
}
@Override
public Map<String, ValuePair> diff(Object a, Object b) {
return null;
}
@Override
public <T> T createEntityBean(Class<T> type) {
return null;
}
@Override
public <T> CsvReader<T> createCsvReader(Class<T> beanType) {
return null;
}
@Override
public <T> Query<T> createNamedQuery(Class<T> beanType, String namedQuery) {
return null;
}
@Override
public <T> Query<T> createQuery(Class<T> beanType, String eql) {
return null;
}
@Override
public <T> Query<T> createQuery(Class<T> beanType) {
return null;
}
@Override
public <T> Query<T> find(Class<T> beanType) {
return null;
}
@Override
public <T> Query<T> findNative(Class<T> beanType, String nativeSql) {
return null;
}
@Override
public <T> Set<String> validateQuery(Query<T> query) {
return null;
}
@Override
public Object nextId(Class<?> beanType) {
return null;
}
@Override
public <T> Filter<T> filter(Class<T> beanType) {
return null;
}
@Override
public <T> void sort(List<T> list, String sortByClause) {
}
@Override
public <T> Update<T> createUpdate(Class<T> beanType, String ormUpdate) {
return null;
}
@Override
public <T> void findDtoEach(SpiDtoQuery<T> query, Consumer<T> consumer) {
}
@Override
public <T> void findDtoEachWhile(SpiDtoQuery<T> query, Predicate<T> consumer) {
}
@Override
public <T> List<T> findDtoList(SpiDtoQuery<T> query) {
return null;
}
@Override
public <T> T findDtoOne(SpiDtoQuery<T> query) {
return null;
}
@Override
public <D> DtoQuery<D> findDto(Class<D> dtoType, String sql) {
return null;
}
@Override
public <T> DtoQuery<T> createNamedDtoQuery(Class<T> dtoType, String namedQuery) {
return null;
}
@Override
public <D> DtoQuery<D> findDto(Class<D> dtoType, SpiQuery<?> ormQuery) {
return null;
}
@Override
public SpiResultSet findResultSet(SpiQuery<?> ormQuery, SpiTransaction transaction) {
return null;
}
@Override
public <T> T findSingleAttribute(SpiSqlQuery query, Class<T> cls) {
return null;
}
@Override
public <T> List<T> findSingleAttributeList(SpiSqlQuery query, Class<T> cls) {
return null;
}
@Override
public <T> T findOneMapper(SpiSqlQuery query, RowMapper<T> mapper) {
return null;
}
@Override
public <T> List<T> findListMapper(SpiSqlQuery query, RowMapper<T> mapper) {
return null;
}
@Override
public void findEachRow(SpiSqlQuery query, RowConsumer consumer) {
}
@Override
public SqlQuery sqlQuery(String sql) {
return null;
}
@Override
public SqlQuery createSqlQuery(String sql) {
return sqlQuery(sql);
}
@Override
public SqlUpdate sqlUpdate(String sql) {
return null;
}
@Override
public SqlUpdate createSqlUpdate(String sql) {
return sqlUpdate(sql);
}
@Override
public CallableSql createCallableSql(String callableSql) {
return null;
}
@Override
public void register(TransactionCallback transactionCallback) throws PersistenceException {
}
@Override
public <T> T publish(Class<T> beanType, Object id) {
return null;
}
@Override
public <T> List<T> publish(Query<T> query) {
return null;
}
@Override
public <T> T publish(Class<T> beanType, Object id, Transaction transaction) {
return null;
}
@Override
public <T> List<T> publish(Query<T> query, Transaction transaction) {
return null;
}
@Override
public <T> T draftRestore(Class<T> beanType, Object id, Transaction transaction) {
return null;
}
@Override
public <T> List<T> draftRestore(Query<T> query, Transaction transaction) {
return null;
}
@Override
public <T> T draftRestore(Class<T> beanType, Object id) {
return null;
}
@Override
public <T> List<T> draftRestore(Query<T> query) {
return null;
}
@Override
public Transaction createTransaction() {
return null;
}
@Override
public Transaction createTransaction(TxIsolation isolation) {
return null;
}
@Override
public Transaction beginTransaction() {
return null;
}
@Override
public Transaction beginTransaction(TxScope scope) {
return null;
}
@Override
public Transaction beginTransaction(TxIsolation isolation) {
return null;
}
@Override
public Transaction currentTransaction() {
return null;
}
@Override
public void flush() {
}
@Override
public void commitTransaction() {
}
@Override
public void rollbackTransaction() {
}
@Override
public void endTransaction() {
}
@Override
public void refresh(Object bean) {
}
@Override
public void refreshMany(Object bean, String propertyName) {
}
@Override
public boolean exists(Class<?> beanType, Object beanId, Transaction transaction) {
return false;
}
@Override
public <T> boolean exists(Query<?> ormQuery, Transaction transaction) {
return false;
}
@Override
public <T> T find(Class<T> beanType, Object uid) {
return null;
}
@Override
public <T> T getReference(Class<T> beanType, Object id) {
return null;
}
@Override
public <T> int findCount(Query<T> query, Transaction transaction) {
return 0;
}
@Override
public <A, T> List<A> findIds(Query<T> query, Transaction transaction) {
return null;
}
@Override
public <T> QueryIterator<T> findIterate(Query<T> query, Transaction transaction) {
return null;
}
@Override
public <T> Stream<T> findStream(Query<T> query, Transaction transaction) {
return null;
}
@Override
public <T> Stream<T> findLargeStream(Query<T> query, Transaction transaction) {
return null;
}
@Override
public <T> void findEach(Query<T> query, Consumer<T> consumer, Transaction transaction) {
}
@Override
public <T> void findEachWhile(Query<T> query, Predicate<T> consumer, Transaction transaction) {
}
@Override
public <T> List<T> findList(Query<T> query, Transaction transaction) {
return null;
}
@Override
public <T> FutureRowCount<T> findFutureCount(Query<T> query, Transaction transaction) {
return null;
}
@Override
public <T> FutureIds<T> findFutureIds(Query<T> query, Transaction transaction) {
return null;
}
@Override
public <T> FutureList<T> findFutureList(Query<T> query, Transaction transaction) {
return null;
}
@Override
public <T> PagedList<T> findPagedList(Query<T> query, Transaction transaction) {
return null;
}
@Override
public <T> Set<T> findSet(Query<T> query, Transaction transaction) {
return null;
}
@Override
public <K, T> Map<K, T> findMap(Query<T> query, Transaction transaction) {
return null;
}
@Override
public <A, T> List<A> findSingleAttributeList(Query<T> query, Transaction transaction) {
return null;
}
@Override
public <T> T findOne(Query<T> query, Transaction transaction) {
return null;
}
@Override
public <T> Optional<T> findOneOrEmpty(Query<T> query, Transaction transaction) {
return null;
}
@Override
public List<SqlRow> findList(SqlQuery query, Transaction transaction) {
return null;
}
@Override
public void findEach(SqlQuery query, Consumer<SqlRow> consumer, Transaction transaction) {
}
@Override
public void findEachWhile(SqlQuery query, Predicate<SqlRow> consumer, Transaction transaction) {
}
@Override
public SqlRow findOne(SqlQuery query, Transaction transaction) {
return null;
}
@Override
public void save(Object bean) throws OptimisticLockException {
}
@Override
public boolean delete(Object bean) throws OptimisticLockException {
return false;
}
@Override
public int delete(Class<?> beanType, Object id) {
return 0;
}
@Override
public int delete(Class<?> beanType, Object id, Transaction transaction) {
return 0;
}
@Override
public int deletePermanent(Class<?> beanType, Object id) {
return 0;
}
@Override
public int deletePermanent(Class<?> beanType, Object id, Transaction transaction) {
return 0;
}
@Override
public int execute(SqlUpdate updSql) {
return 0;
}
@Override
public int execute(Update<?> update) {
return 0;
}
@Override
public int execute(Update<?> update, Transaction t) {
return 0;
}
@Override
public int execute(CallableSql callableSql) {
return 0;
}
@Override
public void externalModification(String tableName, boolean inserted, boolean updated, boolean deleted) {
}
@Override
public <T> T find(Class<T> beanType, Object uid, Transaction transaction) {
return null;
}
@Override
public void save(Object bean, Transaction transaction) throws OptimisticLockException {
}
@Override
public void markAsDirty(Object bean) {
}
@Override
public void update(Object bean) throws OptimisticLockException {
}
@Override
public void update(Object bean, Transaction t) throws OptimisticLockException {
}
@Override
public void insert(Object bean) {
}
@Override
public void insert(Object bean, Transaction t) {
}
@Override
public boolean delete(Object bean, Transaction t) throws OptimisticLockException {
return false;
}
@Override
public boolean deletePermanent(Object bean) throws OptimisticLockException {
return false;
}
@Override
public boolean deletePermanent(Object bean, Transaction transaction) throws OptimisticLockException {
return false;
}
@Override
public int deleteAllPermanent(Collection<?> beans) throws OptimisticLockException {
return 0;
}
@Override
public int deleteAllPermanent(Collection<?> beans, Transaction transaction) throws OptimisticLockException {
return 0;
}
@Override
public int execute(SqlUpdate updSql, Transaction t) {
return 0;
}
@Override
public int executeNow(SpiSqlUpdate sqlUpdate) {
return 0;
}
@Override
public void addBatch(SpiSqlUpdate sqlUpdate, SpiTransaction transaction) {
}
@Override
public int[] executeBatch(SpiSqlUpdate defaultSqlUpdate, SpiTransaction transaction) {
return new int[0];
}
@Override
public int execute(CallableSql callableSql, Transaction t) {
return 0;
}
@Override
public void execute(TxScope scope, Runnable r) {
}
@Override
public void execute(Runnable r) {
}
@Override
public <T> T executeCall(TxScope scope, Callable<T> callable) {
return null;
}
@Override
public <T> T executeCall(Callable<T> callable) {
return null;
}
@Override
public ServerCacheManager getServerCacheManager() {
return null;
}
@Override
public BackgroundExecutor getBackgroundExecutor() {
return null;
}
@Override
public JsonContext json() {
return null;
}
@Override
public SpiJsonContext jsonExtended() {
return null;
}
@Override
public int saveAll(Object... beans) throws OptimisticLockException {
return 0;
}
@Override
public int saveAll(Collection<?> beans) throws OptimisticLockException {
return 0;
}
@Override
public int deleteAll(Collection<?> beans) throws OptimisticLockException {
return 0;
}
@Override
public int deleteAll(Collection<?> beans, Transaction transaction) throws OptimisticLockException {
return 0;
}
@Override
public int deleteAll(Class<?> beanType, Collection<?> ids) {
return 0;
}
@Override
public int deleteAll(Class<?> beanType, Collection<?> ids, Transaction transaction) {
return 0;
}
@Override
public int deleteAllPermanent(Class<?> beanType, Collection<?> ids) {
return 0;
}
@Override
public int deleteAllPermanent(Class<?> beanType, Collection<?> ids, Transaction transaction) {
return 0;
}
@Override
public int saveAll(Collection<?> beans, Transaction transaction) throws OptimisticLockException {
return 0;
}
@Override
public void updateAll(Collection<?> beans) throws OptimisticLockException {
}
@Override
public void updateAll(Collection<?> beans, Transaction transaction) throws OptimisticLockException {
}
@Override
public void insertAll(Collection<?> beans) {
}
@Override
public void insertAll(Collection<?> beans, Transaction transaction) {
}
@Override
public void slowQueryCheck(long executionTimeMicros, int rowCount, SpiQuery<?> query) {
}
@Override
public Set<Property> checkUniqueness(Object bean) {
return Collections.emptySet();
}
@Override
public Set<Property> checkUniqueness(Object bean, Transaction transaction) {
return Collections.emptySet();
}
@Override
public SpiQueryBindCapture createQueryBindCapture(SpiQueryPlan queryPlan) {
return null;
}
}
@@ -0,0 +1,88 @@
package io.ebeaninternal.dbmigration;
import io.ebean.EbeanServer;
import io.ebean.EbeanServerFactory;
import io.ebean.config.ServerConfig;
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.Arrays;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.assertThatThrownBy;
/**
* This is the Migrationscript generator. It generates 3 migrationscript for the models
* @author Roland Praml, FOCONIS AG
*
*/
public class DbMigrationDropHistoryTest {
private static final Logger logger = LoggerFactory.getLogger(DbMigrationDropHistoryTest.class);
@Test
public void invokeTest() throws IOException {
main(null);
}
public static void main(String[] args) throws IOException {
logger.info("start");
DefaultDbMigration migration = new DefaultDbMigration();
// We use src/test/resources as output directory (so we see in GIT if files will change)
migration.setPathToResources("src/test/resources");
ServerConfig config = new ServerConfig();
config.setName("migrationtest-history");
config.loadFromProperties();
config.setRegister(false);
config.setDefaultServer(false);
config.setPackages(Arrays.asList("misc.migration.history.v1_0"));
EbeanServer server = EbeanServerFactory.create(config);
migration.setServer(server);
// First, we clean up the output-directory
assertThat(migration.getMigrationDirectory().getAbsolutePath()).contains("migrationtest-history");
Files.walk(migration.getMigrationDirectory().toPath())
.filter(Files::isRegularFile).map(Path::toFile).forEach(File::delete);
// then we generate migration scripts for v1_0
assertThat(migration.generateMigration()).isEqualTo("1.0__initial");
// and we check repeatative calls
assertThat(migration.generateMigration()).isNull();
// and now for v1_1
config.setPackages(Arrays.asList("misc.migration.history.v1_1"));
server = EbeanServerFactory.create(config);
migration.setServer(server);
assertThat(migration.generateMigration()).isEqualTo("1.1");
assertThat(migration.generateMigration()).isNull(); // subsequent call
List<String> pendingDrops = migration.getPendingDrops();
assertThat(pendingDrops).contains("1.1");
//System.setProperty("ddl.migration.pendingDropsFor", "1.1");
migration.setGeneratePendingDrop("1.1");
assertThat(migration.generateMigration()).isEqualTo("1.2__dropsFor_1.1");
assertThatThrownBy(()->migration.generateMigration())
.isInstanceOf(IllegalArgumentException.class)
.hasMessageContaining("No 'pendingDrops'"); // subsequent call
System.clearProperty("ddl.migration.pendingDropsFor");
logger.info("end");
}
}
@@ -0,0 +1,121 @@
package io.ebeaninternal.dbmigration;
import io.ebean.EbeanServer;
import io.ebean.EbeanServerFactory;
import io.ebean.annotation.Platform;
import io.ebean.config.ServerConfig;
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.Arrays;
import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.assertThatThrownBy;
/**
* This is the Migrationscript generator. It generates 3 migrationscript for the models
* @author Roland Praml, FOCONIS AG
*
*/
public class DbMigrationGenerateTest {
private static final Logger logger = LoggerFactory.getLogger(DbMigrationGenerateTest.class);
@Test
public void invokeTest() throws IOException {
main(null);
}
public static void main(String[] args) throws IOException {
logger.info("start");
DefaultDbMigration migration = new DefaultDbMigration();
// We use src/test/resources as output directory (so we see in GIT if files will change)
migration.setPathToResources("src/test/resources");
migration.setMigrationPath("db/migration");
migration.setMigrationPath(null); // use the default for this test
// migration.addPlatform(Platform.GENERIC, "generic"); there is no ddl handler for generic
// migration.addPlatform(Platform.SQLANYWHERE, "sqlanywhere"); and sqlanywhere
migration.addPlatform(Platform.DB2, "db2");
migration.addPlatform(Platform.H2, "h2");
migration.addPlatform(Platform.HSQLDB, "hsqldb");
migration.addPlatform(Platform.MYSQL, "mysql");
migration.addPlatform(Platform.MYSQL55, "mysql55");
migration.addPlatform(Platform.POSTGRES, "postgres");
migration.addPlatform(Platform.ORACLE, "oracle");
migration.addPlatform(Platform.SQLITE, "sqlite");
migration.addPlatform(Platform.SQLSERVER17, "sqlserver17");
migration.addPlatform(Platform.HANA, "hana");
ServerConfig config = new ServerConfig();
config.setName("migrationtest");
config.loadFromProperties();
config.setRegister(false);
config.setDefaultServer(false);
config.getProperties().put("ebean.hana.generateUniqueDdl", "true"); // need to generate unique statements to prevent them from being filtered out as duplicates by the DdlRunner
config.setPackages(Arrays.asList("misc.migration.v1_0"));
EbeanServer server = EbeanServerFactory.create(config);
migration.setServer(server);
// First, we clean up the output-directory
assertThat(migration.getMigrationDirectory().getAbsolutePath()).contains("migrationtest");
Files.walk(migration.getMigrationDirectory().toPath())
.filter(Files::isRegularFile).map(Path::toFile).forEach(File::delete);
// then we generate migration scripts for v1_0
assertThat(migration.generateMigration()).isEqualTo("1.0__initial");
// and we check repeatative calls
assertThat(migration.generateMigration()).isNull();
// and now for v1_1
config.setPackages(Arrays.asList("misc.migration.v1_1"));
server = EbeanServerFactory.create(config);
migration.setServer(server);
assertThat(migration.generateMigration()).isEqualTo("1.1");
assertThat(migration.generateMigration()).isNull(); // subsequent call
System.setProperty("ddl.migration.pendingDropsFor", "1.1");
assertThat(migration.generateMigration()).isEqualTo("1.2__dropsFor_1.1");
assertThatThrownBy(()->migration.generateMigration())
.isInstanceOf(IllegalArgumentException.class)
.hasMessageContaining("No 'pendingDrops'"); // subsequent call
System.clearProperty("ddl.migration.pendingDropsFor");
assertThat(migration.generateMigration()).isNull(); // subsequent call
// and now for v1_2 with
config.setPackages(Arrays.asList("misc.migration.v1_2"));
server = EbeanServerFactory.create(config);
migration.setServer(server);
assertThat(migration.generateMigration()).isEqualTo("1.3");
assertThat(migration.generateMigration()).isNull(); // subsequent call
System.setProperty("ddl.migration.pendingDropsFor", "1.3");
assertThat(migration.generateMigration()).isEqualTo("1.4__dropsFor_1.3");
assertThatThrownBy(()->migration.generateMigration())
.isInstanceOf(IllegalArgumentException.class)
.hasMessageContaining("No 'pendingDrops'"); // subsequent call
System.clearProperty("ddl.migration.pendingDropsFor");
assertThat(migration.generateMigration()).isNull(); // subsequent call
logger.info("end");
}
}
@@ -0,0 +1,191 @@
package io.ebeaninternal.dbmigration;
import io.ebean.BaseTestCase;
import io.ebean.SqlRow;
import io.ebean.SqlUpdate;
import io.ebean.annotation.IgnorePlatform;
import io.ebean.annotation.Platform;
import io.ebeaninternal.dbmigration.ddlgeneration.Helper;
import org.junit.Test;
import java.io.IOException;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
public class DbMigrationTest extends BaseTestCase {
private void runScript(boolean expectErrors, String scriptName) throws IOException {
String ddl = Helper.asText(this, "/dbmigration/migrationtest/" + server().getPluginApi().getDatabasePlatform().getName()+"/" + scriptName);
runScript(expectErrors, ddl, scriptName);
}
private void runScript(boolean useAutoCommit, String content, String scriptName) {
server().script().runScript(scriptName, content, useAutoCommit);
}
@IgnorePlatform({Platform.ORACLE, Platform.NUODB, Platform.MARIADB})
@Test
public void testRunMigration() throws IOException {
// first clean up previously created objects
cleanup("migtest_ckey_assoc",
"migtest_ckey_detail",
"migtest_ckey_parent",
"migtest_e_basic",
"migtest_e_enum",
"migtest_e_history",
"migtest_e_history2",
"migtest_e_history3",
"migtest_e_history4",
"migtest_e_history5",
"migtest_e_history6",
"migtest_e_ref",
"migtest_e_softdelete",
"migtest_e_user",
"migtest_fk_cascade",
"migtest_fk_cascade_one",
"migtest_fk_none",
"migtest_fk_none_via_join",
"migtest_fk_one",
"migtest_fk_set_null",
"migtest_mtm_c",
"migtest_mtm_m",
"migtest_mtm_c_migtest_mtm_m",
"migtest_mtm_m_migtest_mtm_c",
"migtest_oto_child",
"migtest_oto_master");
if (isSqlServer()) { // || isMySql()
runScript(false, "I__create_procs.sql");
}
runScript(false, "1.0__initial.sql");
if (isOracle() || isHana()) {
SqlUpdate update = server().sqlUpdate("insert into migtest_e_basic (id, old_boolean, user_id) values (1, :false, 1)");
update.setParameter("false", false);
assertThat(server().execute(update)).isEqualTo(1);
update = server().sqlUpdate("insert into migtest_e_basic (id, old_boolean, user_id) values (2, :true, 1)");
update.setParameter("true", true);
assertThat(server().execute(update)).isEqualTo(1);
} else {
SqlUpdate update = server().sqlUpdate("insert into migtest_e_basic (id, old_boolean, user_id) values (1, :false, 1), (2, :true, 1)");
update.setParameter("false", false);
update.setParameter("true", true);
assertThat(server().execute(update)).isEqualTo(2);
}
createHistoryEntities();
// Run migration
runScript(false, "1.1.sql");
List<SqlRow> result = server().sqlQuery("select * from migtest_e_basic order by id").findList();
assertThat(result).hasSize(2);
SqlRow row = result.get(0);
assertThat(row.keySet()).contains("old_boolean", "old_boolean2");
assertThat(row.getInteger("id")).isEqualTo(1);
assertThat(row.getBoolean("old_boolean")).isFalse();
assertThat(row.getBoolean("new_boolean_field")).isFalse(); // test if update old_boolean -> new_boolean_field works well
assertThat(row.getString("new_string_field")).isEqualTo("foo'bar");
assertThat(row.getBoolean("new_boolean_field2")).isTrue();
//assertThat(row.getTimestamp("some_date")).isCloseTo(new Date(), 86_000); // allow 1 minute delta
row = result.get(1);
assertThat(row.getInteger("id")).isEqualTo(2);
assertThat(row.getBoolean("old_boolean")).isTrue();
assertThat(row.getBoolean("new_boolean_field")).isTrue(); // test if update old_boolean -> new_boolean_field works well
assertThat(row.getString("new_string_field")).isEqualTo("foo'bar");
assertThat(row.getBoolean("new_boolean_field2")).isTrue();
//assertThat(row.getTimestamp("some_date")).isCloseTo(new Date(), 60_000); // allow 1 minute delta
runScript(false, "1.2__dropsFor_1.1.sql");
// Oracle caches the statement and does not detect schema change. It fails with
// an ORA-01007
if (isOracle()) {
result = server().sqlQuery("select * from migtest_e_basic order by id,id").findList();
} else {
result = server().sqlQuery("select * from migtest_e_basic order by id").findList();
}
assertThat(result).hasSize(2);
row = result.get(0);
assertThat(row.keySet()).doesNotContain("old_boolean", "old_boolean2");
runScript(false, "1.3.sql");
runScript(false, "1.4__dropsFor_1.3.sql");
// now DB structure shoud be the same as v1_0
result = server().sqlQuery("select * from migtest_e_basic order by id").findList();
assertThat(result).hasSize(2);
row = result.get(0);
assertThat(row.keySet()).contains("old_boolean", "old_boolean2");
}
/**
*
*/
private void createHistoryEntities() {
SqlUpdate update = server().sqlUpdate("insert into migtest_e_history (id, test_string) values (1, '42')");
assertThat(server().execute(update)).isEqualTo(1);
update = server().sqlUpdate("update migtest_e_history set test_string = '45' where id = 1");
assertThat(server().execute(update)).isEqualTo(1);
update = server().sqlUpdate("insert into migtest_e_history2 (id, test_string, obsolete_string1, obsolete_string2) values (1, 'foo', 'bar', null)");
assertThat(server().execute(update)).isEqualTo(1);
update = server().sqlUpdate("update migtest_e_history2 set test_string = 'baz' where id = 1");
assertThat(server().execute(update)).isEqualTo(1);
update = server().sqlUpdate("insert into migtest_e_history3 (id, test_string) values (1, '42')");
assertThat(server().execute(update)).isEqualTo(1);
update = server().sqlUpdate("update migtest_e_history3 set test_string = '45' where id = 1");
assertThat(server().execute(update)).isEqualTo(1);
update = server().sqlUpdate("insert into migtest_e_history4 (id, test_number) values (1, 42)");
assertThat(server().execute(update)).isEqualTo(1);
update = server().sqlUpdate("update migtest_e_history4 set test_number = 45 where id = 1");
assertThat(server().execute(update)).isEqualTo(1);
update = server().sqlUpdate("insert into migtest_e_history5 (id, test_number) values (1, 42)");
assertThat(server().execute(update)).isEqualTo(1);
update = server().sqlUpdate("update migtest_e_history5 set test_number = 45 where id = 1");
assertThat(server().execute(update)).isEqualTo(1);
update = server().sqlUpdate("insert into migtest_e_history6 (id, test_number1, test_number2) values (1, 2, 7)");
assertThat(server().execute(update)).isEqualTo(1);
update = server().sqlUpdate("update migtest_e_history6 set test_number2 = 45 where id = 1");
assertThat(server().execute(update)).isEqualTo(1);
}
private void cleanup(String ... tables) {
final boolean sqlServer = isSqlServer();
final boolean postgres = isPostgres();
StringBuilder sb = new StringBuilder();
for (String table : tables) {
// simple and stupid try to execute all commands on all dialects.
if (sqlServer) {
sb.append("alter table ").append(table).append(" set ( system_versioning = OFF );\n");
sb.append("alter table ").append(table).append(" drop system versioning;\n");
}
if (postgres) {
sb.append("drop table ").append(table).append(" cascade;\n");
sb.append("drop table ").append(table).append("_history cascade;\n");
} else {
sb.append("drop table ").append(table).append(";\n");
sb.append("drop table ").append(table).append("_history;\n");
}
sb.append("drop view ").append(table).append("_with_history;\n");
sb.append("drop sequence ").append(table).append("_seq;\n");
}
runScript(true, sb.toString(), "cleanup");
runScript(true, sb.toString(), "cleanup");
}
}
@@ -0,0 +1,66 @@
package io.ebeaninternal.dbmigration;
import org.junit.Test;
import java.io.File;
import static org.assertj.core.api.Assertions.assertThat;
public class LastMigrationTest {
@Test
public void lastVersion() {
File d = new File("src/test/resources/dbmigration/migrationtest/h2");
assertThat(LastMigration.lastVersion(d, null)).isEqualTo("1.4");
assertThat(LastMigration.nextVersion(d, null, false)).isEqualTo("1.5");
assertThat(LastMigration.nextVersion(d, null, true)).isEqualTo("1.4");
}
@Test
public void lastVersion_no_v_Prefix() {
File d = new File("src/test/resources/dbmigration/migrationtest-history");
assertThat(LastMigration.lastVersion(d, null)).isEqualTo("1.2");
}
@Test
public void lastVersion_test() {
File d = new File("src/test/resources/test-dbmigration");
assertThat(LastMigration.lastVersion(d, null)).isEqualTo("2.1");
assertThat(LastMigration.nextVersion(d, null, false)).isEqualTo("2.2");
}
@Test
public void lastVersion_app2() {
File d = new File("src/test/resources/dbmigration/app2");
assertThat(LastMigration.lastVersion(d, null)).isEqualTo("3.1");
assertThat(LastMigration.nextVersion(d, null, false)).isEqualTo("3.2");
}
@Test
public void lastVersion_app3() {
File d = new File("src/test/resources/dbmigration/app3");
assertThat(LastMigration.lastVersion(d, null)).isEqualTo("3.1.2");
assertThat(LastMigration.nextVersion(d, null, false)).isEqualTo("3.1.3");
assertThat(LastMigration.nextVersion(d, null, true)).isEqualTo("3.1.2");
}
@Test
public void lastVersion_app3_with_model_larger() {
File d = new File("src/test/resources/dbmigration/app3");
File m = new File("src/test/resources/dbmigration/app3/model_larger");
assertThat(LastMigration.lastVersion(d, m)).isEqualTo("4.1");
assertThat(LastMigration.nextVersion(d, m, false)).isEqualTo("4.2");
assertThat(LastMigration.nextVersion(d, m, true)).isEqualTo("4.1");
}
@Test
public void lastVersion_app3_with_model_smaller() {
File d = new File("src/test/resources/dbmigration/app3");
File m = new File("src/test/resources/dbmigration/app3/model_smaller");
assertThat(LastMigration.lastVersion(d, m)).isEqualTo("3.1.2");
assertThat(LastMigration.nextVersion(d, m, false)).isEqualTo("3.1.3");
assertThat(LastMigration.nextVersion(d, m, true)).isEqualTo("3.1.2");
}
}
@@ -0,0 +1,271 @@
package io.ebeaninternal.dbmigration.ddlgeneration;
import io.ebean.BaseTestCase;
import io.ebean.Ebean;
import io.ebean.config.ServerConfig;
import io.ebean.config.dbplatform.DatabasePlatform;
import io.ebean.config.dbplatform.h2.H2Platform;
import io.ebean.config.dbplatform.hana.HanaPlatform;
import io.ebean.config.dbplatform.postgres.PostgresPlatform;
import io.ebean.config.dbplatform.sqlserver.SqlServer17Platform;
import io.ebeaninternal.api.SpiEbeanServer;
import io.ebeaninternal.dbmigration.migration.ChangeSet;
import io.ebeaninternal.dbmigration.model.CurrentModel;
import io.ebeaninternal.server.core.PlatformDdlBuilder;
import org.junit.Ignore;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class BaseDdlHandlerTest extends BaseTestCase {
private ServerConfig serverConfig = new ServerConfig();
private DdlHandler handler(DatabasePlatform platform) {
return PlatformDdlBuilder.create(platform).createDdlHandler(serverConfig);
}
private DdlHandler h2Handler() {
return handler(new H2Platform());
}
private DdlHandler postgresHandler() {
return handler(new PostgresPlatform());
}
private DdlHandler sqlserverHandler() {
return handler(new SqlServer17Platform());
}
private DdlHandler hanaHandler() {
return handler(new HanaPlatform());
}
@Test
public void addColumn_nullable_noConstraint() throws Exception {
DdlWrite write = new DdlWrite();
h2Handler().generate(write, Helper.getAddColumn());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add column added_to_foo varchar(20);\n\n");
write = new DdlWrite();
sqlserverHandler().generate(write, Helper.getAddColumn());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add added_to_foo nvarchar(20);\n\n");
write = new DdlWrite();
hanaHandler().generate(write, Helper.getAddColumn());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add ( added_to_foo nvarchar(20));\n\n");
}
@Test
public void addColumn_withCheckConstraint() throws Exception {
DdlWrite write = new DdlWrite();
h2Handler().generate(write, Helper.getAlterTableAddColumnWithCheckConstraint());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add column status integer;\n"
+ "alter table foo add constraint ck_ordering_status check ( status in (0,1));\n\n");
write = new DdlWrite();
hanaHandler().generate(write, Helper.getAlterTableAddColumnWithCheckConstraint());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add ( status integer);\n"
+ "alter table foo add constraint ck_ordering_status check ( status in (0,1));\n\n");
}
/**
* Test the functionality of the Ebean {@literal @}DbArray extension during DDL
* generation.
*/
@Test
public void addColumn_dbarray() throws Exception {
DdlWrite write = new DdlWrite();
DdlHandler postgresHandler = postgresHandler();
postgresHandler.generate(write, Helper.getAlterTableAddDbArrayColumn());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add column dbarray_added_to_foo varchar[];\n\n");
write = new DdlWrite();
DdlHandler sqlserverHandler = sqlserverHandler();
sqlserverHandler.generate(write, Helper.getAlterTableAddDbArrayColumn());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add dbarray_added_to_foo varchar(1000);\n\n");
write = new DdlWrite();
DdlHandler hanaHandler = hanaHandler();
hanaHandler.generate(write, Helper.getAlterTableAddDbArrayColumn());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add ( dbarray_added_to_foo nvarchar(255) array);\n\n");
}
@Test
public void addColumn_dbarray_withLength() throws Exception {
DdlWrite write = new DdlWrite();
postgresHandler().generate(write, Helper.getAlterTableAddDbArrayColumnWithLength());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add column dbarray_ninety varchar[];\n\n");
write = new DdlWrite();
h2Handler().generate(write, Helper.getAlterTableAddDbArrayColumnWithLength());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add column dbarray_ninety array;\n\n");
write = new DdlWrite();
sqlserverHandler().generate(write, Helper.getAlterTableAddDbArrayColumnWithLength());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add dbarray_ninety varchar(90);\n\n");
write = new DdlWrite();
hanaHandler().generate(write, Helper.getAlterTableAddDbArrayColumnWithLength());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add ( dbarray_ninety nvarchar(255) array(90));\n\n");
}
@Test
public void addColumn_dbarray_integer_withLength() throws Exception {
DdlWrite write = new DdlWrite();
postgresHandler().generate(write, Helper.getAlterTableAddDbArrayColumnIntegerWithLength());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add column dbarray_integer integer[];\n\n");
write = new DdlWrite();
h2Handler().generate(write, Helper.getAlterTableAddDbArrayColumnIntegerWithLength());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add column dbarray_integer array;\n\n");
write = new DdlWrite();
sqlserverHandler().generate(write, Helper.getAlterTableAddDbArrayColumnIntegerWithLength());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add dbarray_integer varchar(90);\n\n");
write = new DdlWrite();
sqlserverHandler().generate(write, Helper.getAlterTableAddDbArrayColumnInteger());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add dbarray_integer varchar(1000);\n\n");
write = new DdlWrite();
hanaHandler().generate(write, Helper.getAlterTableAddDbArrayColumnIntegerWithLength());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add ( dbarray_integer integer array(90));\n\n");
write = new DdlWrite();
hanaHandler().generate(write, Helper.getAlterTableAddDbArrayColumnInteger());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo add ( dbarray_integer integer array);\n\n");
}
@Test
public void addColumn_withForeignKey() throws Exception {
DdlWrite write = new DdlWrite();
DdlHandler handler = h2Handler();
handler.generate(write, Helper.getAlterTableAddColumn());
String buffer = write.apply().getBuffer();
assertThat(buffer).contains("alter table foo add column some_id integer;");
String fkBuffer = write.applyForeignKeys().getBuffer();
assertThat(fkBuffer).contains(
"alter table foo add constraint fk_foo_some_id foreign key (some_id) references bar (id) on delete restrict on update restrict;");
assertThat(fkBuffer).contains("create index idx_foo_some_id on foo (some_id);");
assertThat(write.dropAll().getBuffer()).isEqualTo("");
}
@Test
public void dropColumn() throws Exception {
DdlWrite write = new DdlWrite();
DdlHandler handler = h2Handler();
handler.generate(write, Helper.getDropColumn());
assertThat(write.apply().getBuffer()).isEqualTo("alter table foo drop column col2;\n\n");
assertThat(write.dropAll().getBuffer()).isEqualTo("");
write = new DdlWrite();
DdlHandler hanaHandler = hanaHandler();
hanaHandler.generate(write, Helper.getDropColumn());
assertThat(write.apply().getBuffer()).isEqualTo("CALL usp_ebean_drop_column('foo', 'col2');\n\n");
assertThat(write.dropAll().getBuffer()).isEqualTo("");
}
@Test
public void createTable() throws Exception {
DdlWrite write = new DdlWrite();
DdlHandler handler = h2Handler();
handler.generate(write, Helper.getCreateTable());
String createTableDDL = Helper.asText(this, "/assert/create-table.txt");
assertThat(write.apply().getBuffer()).isEqualTo(createTableDDL);
assertThat(write.dropAll().getBuffer().trim()).isEqualTo("drop table if exists foo;");
write = new DdlWrite();
DdlHandler hanaHandler = hanaHandler();
hanaHandler.generate(write, Helper.getCreateTable());
String createColumnTableDDL = Helper.asText(this, "/assert/create-column-table.txt");
assertThat(write.apply().getBuffer()).isEqualTo(createColumnTableDDL);
assertThat(write.dropAll().getBuffer().trim()).isEqualTo("drop table foo cascade;");
}
@Test
public void generateChangeSet() throws Exception {
DdlWrite write = new DdlWrite();
DdlHandler handler = h2Handler();
handler.generate(write, Helper.getChangeSet());
String apply = Helper.asText(this, "/assert/BaseDdlHandlerTest/baseApply.sql");
String rollbackLast = Helper.asText(this, "/assert/BaseDdlHandlerTest/baseDropAll.sql");
assertThat(write.apply().getBuffer()).isEqualTo(apply);
assertThat(write.dropAll().getBuffer()).isEqualTo(rollbackLast);
}
@Ignore
@Test
public void generateChangeSetFromModel() throws Exception {
SpiEbeanServer defaultServer = (SpiEbeanServer) Ebean.getDefaultServer();
ChangeSet createChangeSet = new CurrentModel(defaultServer).getChangeSet();
DdlWrite write = new DdlWrite();
DdlHandler handler = h2Handler();
handler.generate(write, createChangeSet);
String apply = Helper.asText(this, "/assert/changeset-apply.txt");
String rollbackLast = Helper.asText(this, "/assert/changeset-dropAll.txt");
assertThat(write.apply().getBuffer()).isEqualTo(apply);
assertThat(write.dropAll().getBuffer()).isEqualTo(rollbackLast);
}
@Ignore
@Test
public void generateChangeSetFromModel_given_postgresTypes() throws Exception {
SpiEbeanServer defaultServer = (SpiEbeanServer) Ebean.getDefaultServer();
ChangeSet createChangeSet = new CurrentModel(defaultServer).getChangeSet();
DdlWrite write = new DdlWrite();
DdlHandler handler = postgresHandler();
handler.generate(write, createChangeSet);
String apply = Helper.asText(this, "/assert/changeset-pg-apply.sql");
String applyLast = Helper.asText(this, "/assert/changeset-pg-applyLast.sql");
String rollbackFirst = Helper.asText(this, "/assert/changeset-pg-rollbackFirst.sql");
String rollbackLast = Helper.asText(this, "/assert/changeset-pg-rollbackLast.sql");
assertThat(write.apply().getBuffer()).isEqualTo(apply);
assertThat(write.applyForeignKeys().getBuffer()).isEqualTo(applyLast);
assertThat(write.dropAllForeignKeys().getBuffer()).isEqualTo(rollbackFirst);
assertThat(write.dropAll().getBuffer()).isEqualTo(rollbackLast);
}
}
@@ -0,0 +1,109 @@
package io.ebeaninternal.dbmigration.ddlgeneration;
import io.ebeaninternal.dbmigration.migration.AddColumn;
import io.ebeaninternal.dbmigration.migration.ChangeSet;
import io.ebeaninternal.dbmigration.migration.CreateTable;
import io.ebeaninternal.dbmigration.migration.DropColumn;
import io.ebeaninternal.dbmigration.migration.Migration;
import io.ebeaninternal.dbmigration.migrationreader.MigrationXmlReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.LineNumberReader;
import java.util.List;
/**
* Helper for testing to return some basic migration objects.
*/
public class Helper {
static Migration migration = MigrationXmlReader.read("/container/test-create-table.xml");
static Migration alterTableMigration = MigrationXmlReader.read("/container/test-alter-table.xml");
static ChangeSet changeSet;
static List<Object> changeSetChildren;
static ChangeSet alterTableChangeSet;
static List<Object> alterTableChangeSetChildren;
static {
List<ChangeSet> changeSets = migration.getChangeSet();
changeSet = changeSets.get(0);
changeSetChildren = changeSet.getChangeSetChildren();
alterTableChangeSet = alterTableMigration.getChangeSet().get(0);
alterTableChangeSetChildren = alterTableChangeSet.getChangeSetChildren();
}
public static ChangeSet getChangeSet() {
return changeSet;
}
public static CreateTable getCreateTable() {
return (CreateTable) changeSetChildren.get(0);
}
public static AddColumn getAddColumn() {
return (AddColumn) changeSetChildren.get(1);
}
public static AddColumn getAlterTableAddColumn() {
return (AddColumn) alterTableChangeSetChildren.get(0);
}
public static AddColumn getAlterTableAddDbArrayColumn() {
return (AddColumn) alterTableChangeSetChildren.get(1);
}
public static AddColumn getAlterTableAddDbArrayColumnWithLength() {
return (AddColumn) alterTableChangeSetChildren.get(2);
}
public static AddColumn getAlterTableAddDbArrayColumnIntegerWithLength() {
return (AddColumn) alterTableChangeSetChildren.get(3);
}
public static AddColumn getAlterTableAddDbArrayColumnInteger() {
return (AddColumn) alterTableChangeSetChildren.get(4);
}
public static AddColumn getAlterTableAddColumnWithCheckConstraint() {
return (AddColumn) alterTableChangeSetChildren.get(5);
}
public static DropColumn getDropColumn() {
return (DropColumn) changeSetChildren.get(2);
}
public static String asText(Object instance, String relativePath) throws IOException {
InputStream is = instance.getClass().getResourceAsStream(relativePath);
if (is == null) {
throw new IllegalArgumentException("resource " + relativePath + " not found");
}
return asText(is);
}
public static String asText(InputStream in) throws IOException {
try {
InputStreamReader reader = new InputStreamReader(in);
LineNumberReader lineNumberReader = new LineNumberReader(reader);
StringBuilder builder = new StringBuilder(400);
String line;
while ((line = lineNumberReader.readLine()) != null) {
builder.append(line).append("\n");
}
return builder.toString();
} finally {
in.close();
}
}
}
@@ -0,0 +1,204 @@
package io.ebeaninternal.dbmigration.ddlgeneration.platform;
import io.ebean.config.ServerConfig;
import io.ebean.config.dbplatform.clickhouse.ClickHousePlatform;
import io.ebean.config.dbplatform.h2.H2Platform;
import io.ebean.config.dbplatform.mysql.MySqlPlatform;
import io.ebean.config.dbplatform.oracle.OraclePlatform;
import io.ebeaninternal.dbmigration.ddlgeneration.DdlWrite;
import io.ebeaninternal.dbmigration.ddlgeneration.Helper;
import io.ebeaninternal.dbmigration.migration.AddTableComment;
import io.ebeaninternal.dbmigration.migration.AlterColumn;
import io.ebeaninternal.dbmigration.migration.Column;
import io.ebeaninternal.dbmigration.migration.CreateTable;
import io.ebeaninternal.server.core.PlatformDdlBuilder;
import org.junit.Test;
import java.io.IOException;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertEquals;
public class BaseTableDdlTest {
private ServerConfig serverConfig = new ServerConfig();
private PlatformDdl h2ddl = PlatformDdlBuilder.create(new H2Platform());
@Test
public void testAlterColumn() throws IOException {
BaseTableDdl ddlGen = new BaseTableDdl(serverConfig, h2ddl);
DdlWrite write = new DdlWrite();
AlterColumn alterColumn = new AlterColumn();
alterColumn.setTableName("mytab");
alterColumn.setCheckConstraint("check (acol in ('A','B'))");
alterColumn.setCheckConstraintName("ck_mytab_acol");
ddlGen.generate(write, alterColumn);
String ddl = write.apply().getBuffer();
assertThat(ddl).contains("alter table mytab drop constraint if exists ck_mytab_acol");
assertThat(ddl).contains("alter table mytab add constraint ck_mytab_acol check (acol in ('A','B'))");
}
@Test
public void testAddColumn_withTypeConversion() throws IOException {
BaseTableDdl ddlGen = new BaseTableDdl(serverConfig, PlatformDdlBuilder.create(new OraclePlatform()));
DdlWrite write = new DdlWrite();
Column column = new Column();
column.setName("col_name");
column.setType("varchar(20)");
ddlGen.alterTableAddColumn(write.apply(), "mytable", column, false, false);
String ddl = write.apply().getBuffer();
assertThat(ddl).contains("alter table mytable add column col_name varchar2(20)");
}
@Test
public void testAddColumn_withTypeConversion_clickHouseVarchar() throws IOException {
ClickHouseTableDdl ddlGen = new ClickHouseTableDdl(serverConfig, PlatformDdlBuilder.create(new ClickHousePlatform()));
DdlWrite write = new DdlWrite();
Column column = new Column();
column.setName("col_name");
column.setType("varchar(20)");
ddlGen.alterTableAddColumn(write.apply(), "mytable", column, false, false);
String ddl = write.apply().getBuffer();
assertThat(ddl).contains("alter table mytable add column col_name String");
}
@Test
public void testAlterColumnComment() throws IOException {
BaseTableDdl ddlGen = new BaseTableDdl(serverConfig, h2ddl);
DdlWrite write = new DdlWrite();
AlterColumn alterColumn = new AlterColumn();
alterColumn.setTableName("mytab");
alterColumn.setColumnName("acol");
alterColumn.setComment("my comment");
ddlGen.generate(write, alterColumn);
String ddl = write.apply().getBuffer();
assertThat(ddl).contains("comment on column mytab.acol is 'my comment'");
}
@Test
public void alterTableAddColumnWithComment() throws IOException {
BaseTableDdl ddl = new BaseTableDdl(serverConfig, h2ddl);
DdlWrite write = new DdlWrite();
Column column = new Column();
column.setName("my_column");
column.setComment("some comment");
column.setType("int");
ddl.alterTableAddColumn(write.apply(), "my_table", column, false, false);
assertEquals(
"alter table my_table add column my_column int;\n" +
"comment on column my_table.my_column is 'some comment';\n", write.apply().getBuffer());
}
@Test
public void testAddTableComment() throws IOException {
BaseTableDdl ddlGen = new BaseTableDdl(serverConfig, h2ddl);
DdlWrite write = new DdlWrite();
AddTableComment addTableComment = new AddTableComment();
addTableComment.setName("mytab");
addTableComment.setComment("my comment");
ddlGen.generate(write, addTableComment);
String ddl = write.apply().getBuffer();
assertThat(ddl).contains("comment on table mytab is 'my comment'");
}
@Test
public void testAddTableComment_mysql() throws IOException {
BaseTableDdl ddlGen = new BaseTableDdl(serverConfig, PlatformDdlBuilder.create(new MySqlPlatform()));
DdlWrite write = new DdlWrite();
AddTableComment addTableComment = new AddTableComment();
addTableComment.setName("mytab");
addTableComment.setComment("my comment");
ddlGen.generate(write, addTableComment);
String ddl = write.apply().getBuffer();
assertThat(ddl).contains("alter table mytab comment = 'my comment'");
}
@Test
public void testGenerate() throws Exception {
BaseTableDdl ddlGen = new BaseTableDdl(serverConfig, h2ddl);
DdlWrite write = new DdlWrite();
ddlGen.generate(write, createTable());
String apply = write.apply().getBuffer();
String applyLast = write.applyForeignKeys().getBuffer();
String rollbackFirst = write.dropAllForeignKeys().getBuffer();
String rollbackLast = write.dropAll().getBuffer();
assertThat(apply).isEqualTo(Helper.asText(this, "/assert/BaseTableDdlTest/createTable-apply.txt"));
assertThat(applyLast).isEqualTo(Helper.asText(this, "/assert/BaseTableDdlTest/createTable-applyLast.txt"));
assertThat(rollbackFirst).isEqualTo(Helper.asText(this, "/assert/BaseTableDdlTest/createTable-rollbackFirst.txt"));
assertThat(rollbackLast).isEqualTo(Helper.asText(this, "/assert/BaseTableDdlTest/createTable-rollback.txt"));
}
private CreateTable createTable() {
CreateTable createTable = new CreateTable();
createTable.setName("mytable");
createTable.setPkName("pk_mytable");
List<Column> columns = createTable.getColumn();
Column col = new Column();
col.setName("id");
col.setType("integer");
col.setPrimaryKey(true);
columns.add(col);
Column col2 = new Column();
col2.setName("status");
col2.setType("varchar(1)");
col2.setNotnull(true);
col2.setCheckConstraint("check (status in ('A','B'))");
col2.setCheckConstraintName("ck_mytable_status");
columns.add(col2);
Column col3 = new Column();
col3.setName("order_id");
col3.setType("integer");
col3.setNotnull(true);
col3.setReferences("orders.id");
col3.setForeignKeyName("fk_mytable_order_id");
col3.setForeignKeyIndex("ix_mytable_order_id");
columns.add(col3);
return createTable;
}
}
@@ -0,0 +1,24 @@
package io.ebeaninternal.dbmigration.ddlgeneration.platform;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class ClickHouseDbArrayTest {
@Test
public void logicalToNative() {
assertThat(ClickHouseDbArray.logicalToNative("uuid[]")).isEqualTo("Array(UUID)");
assertThat(ClickHouseDbArray.logicalToNative("varchar[]")).isEqualTo("Array(String)");
assertThat(ClickHouseDbArray.logicalToNative("integer[]")).isEqualTo("Array(UInt32)");
assertThat(ClickHouseDbArray.logicalToNative("bigint[]")).isEqualTo("Array(UInt64)");
}
@Test
public void logicalToNative_withFallbackDefined() {
assertThat(ClickHouseDbArray.logicalToNative("uuid[]:(1000)")).isEqualTo("Array(UUID)");
}
}
@@ -0,0 +1,30 @@
package io.ebeaninternal.dbmigration.ddlgeneration.platform;
import io.ebean.config.DbConstraintNormalise;
import org.junit.Test;
import static org.assertj.core.api.Assertions.assertThat;
public class DbNameNormaliseTest {
DbConstraintNormalise normalise = new DbConstraintNormalise();
@Test
public void testNormalise() throws Exception {
assertThat(normalise.normaliseTable("cat.sch.foo_bar]")).isEqualTo("foo_bar");
assertThat(normalise.normaliseTable("sch.foo_bar]")).isEqualTo("foo_bar");
assertThat(normalise.normaliseTable("foo_bar]")).isEqualTo("foo_bar");
}
@Test
public void testTrimQuotes() throws Exception {
assertThat(normalise.trimQuotes("[foo]")).isEqualTo("foo");
assertThat(normalise.trimQuotes("'foo'")).isEqualTo("foo");
assertThat(normalise.trimQuotes("\"foo\"")).isEqualTo("foo");
assertThat(normalise.trimQuotes("`foo`")).isEqualTo("foo");
assertThat(normalise.trimQuotes("`fo_o`")).isEqualTo("fo_o");
}
}
Loaded 100 of 3207 files, more files were not shown because too many files have changed in this diff. Show more