Merge pull request #1697 from ebean-orm/feature/1695-binary

#1695 - For MySql like remove the binary keyword + Add caseSensitiveCollation configuration option
This commit is contained in:
Rob Bygrave
2019-05-16 19:46:38 +12:00
committed by GitHub
27 changed files with 243 additions and 91 deletions
+4 -4
View File
@@ -227,9 +227,9 @@
<!--</dependency>-->
<dependency>
<groupId>io.ebean</groupId>
<artifactId>ebean-docker-run</artifactId>
<version>1.5.1</version>
<groupId>io.ebean.test</groupId>
<artifactId>ebean-test-docker</artifactId>
<version>2.5.1</version>
<scope>test</scope>
</dependency>
@@ -280,7 +280,7 @@
<dependency>
<groupId>com.microsoft.sqlserver</groupId>
<artifactId>mssql-jdbc</artifactId>
<version>7.2.0.jre8</version>
<version>7.2.2.jre8</version>
<scope>test</scope>
</dependency>
@@ -52,6 +52,8 @@ public class PlatformConfig {
*/
private boolean databaseInetAddressVarchar;
private boolean caseSensitiveCollation = true;
/**
* Modify the default mapping of standard types such as default precision for DECIMAL etc.
*/
@@ -74,6 +76,7 @@ public class PlatformConfig {
this.idType = platformConfig.idType;
this.geometrySRID = platformConfig.geometrySRID;
this.dbUuid = platformConfig.dbUuid;
this.caseSensitiveCollation = platformConfig.caseSensitiveCollation;
}
/**
@@ -90,6 +93,20 @@ public class PlatformConfig {
this.allQuotedIdentifiers = allQuotedIdentifiers;
}
/**
* Return true if the collation is case sensitive.
*/
public boolean isCaseSensitiveCollation() {
return caseSensitiveCollation;
}
/**
* Set to false to indicate that the collation is case insensitive.
*/
public void setCaseSensitiveCollation(boolean caseSensitiveCollation) {
this.caseSensitiveCollation = caseSensitiveCollation;
}
/**
* Return a value used to represent TRUE in the database.
* <p>
@@ -255,6 +272,7 @@ public class PlatformConfig {
databaseBooleanTrue = p.get("databaseBooleanTrue", databaseBooleanTrue);
databaseBooleanFalse = p.get("databaseBooleanFalse", databaseBooleanFalse);
databaseInetAddressVarchar = p.getBoolean("databaseInetAddressVarchar", databaseInetAddressVarchar);
caseSensitiveCollation = p.getBoolean("caseSensitiveCollation", caseSensitiveCollation);
DbUuid dbUuid = p.getEnum(DbUuid.class, "dbuuid", null);
if (dbUuid != null) {
@@ -71,6 +71,8 @@ public class DatabasePlatform {
*/
protected boolean allQuotedIdentifiers;
protected boolean caseSensitiveCollation = true;
/**
* For limit/offset, row_number etc limiting of SQL queries.
*/
@@ -226,6 +228,7 @@ public class DatabasePlatform {
*/
public void configure(PlatformConfig config) {
this.sequenceBatchSize = config.getDatabaseSequenceBatchSize();
this.caseSensitiveCollation = config.isCaseSensitiveCollation();
configureIdType(config.getIdType());
configure(config, config.isAllQuotedIdentifiers());
}
@@ -315,6 +318,16 @@ public class DatabasePlatform {
return supportsDeleteTableAlias;
}
/**
* Return true if the collation is case sensitive.
* <p>
* This is expected to be used for testing only.
* </p>
*/
public boolean isCaseSensitiveCollation() {
return caseSensitiveCollation;
}
/**
* Return the maximum table name length.
* <p>
@@ -35,7 +35,7 @@ public class MySqlPlatform extends DatabasePlatform {
this.dbIdentity.setSupportsGetGeneratedKeys(true);
this.dbIdentity.setSupportsIdentity(true);
this.dbIdentity.setSupportsSequence(false);
this.dbDefaultValue.setNow("now(6)"); // must have same precision as TIMESTAMP
this.dbDefaultValue.setFalse("0");
this.dbDefaultValue.setTrue("1");
@@ -51,8 +51,8 @@ public class MySqlPlatform extends DatabasePlatform {
this.openQuote = "`";
this.closeQuote = "`";
// use pipe for escaping as it depends if mysql runs in no_backslash_escapes or not.
this.likeClauseRaw = "like binary ? escape ''";
this.likeClauseEscaped = "like binary ? escape '|'";
this.likeClauseRaw = "like ? escape ''";
this.likeClauseEscaped = "like ? escape '|'";
this.forwardOnlyHintOnFindIterate = true;
this.booleanDbType = Types.BIT;
@@ -47,8 +47,8 @@ abstract class SqlServerBasePlatform extends DatabasePlatform {
this.openQuote = "[";
this.closeQuote = "]";
this.likeSpecialCharacters = new char[]{'%', '_', '['};
this.likeClauseRaw = "like ? collate Latin1_General_BIN";
this.likeClauseEscaped = "like ? collate Latin1_General_BIN";
this.likeClauseRaw = "like ?";
this.likeClauseEscaped = "like ?";
booleanDbType = Types.INTEGER;
this.dbDefaultValue.setFalse("0");
@@ -49,11 +49,11 @@ CREATE OR ALTER PROCEDURE usp_ebean_drop_default_constraint @tableName nvarchar(
AS SET NOCOUNT ON
declare @tmp nvarchar(1000)
BEGIN
select @Tmp = t1.name from sys.default_constraints t1
select @tmp = t1.name from sys.default_constraints t1
join sys.columns t2 on t1.object_id = t2.default_object_id
where t1.parent_object_id = OBJECT_ID(@tableName) and t2.name = @columnName;
if @Tmp is not null EXEC('alter table ' + @tableName +' drop constraint ' + @tmp);
if @tmp is not null EXEC('alter table ' + @tableName +' drop constraint ' + @tmp);
END
$$
@@ -171,13 +171,13 @@ AS
BEGIN
DECLARE foreign_key_names TABLE(CONSTRAINT_NAME NVARCHAR(256), TABLE_NAME NVARCHAR(256));
DECLARE i INT;
foreign_key_names = SELECT CONSTRAINT_NAME, TABLE_NAME FROM SYS.REFERENTIAL_CONSTRAINTS WHERE SCHEMA_NAME=CURRENT_SCHEMA AND TABLE_NAME=UPPER(:table_name) AND COLUMN_NAME=UPPER(:column_name);
FOR I IN 1 .. RECORD_COUNT(:foreign_key_names) DO
EXEC 'ALTER TABLE "' || ESCAPE_DOUBLE_QUOTES(:foreign_key_names.TABLE_NAME[i]) || '" DROP CONSTRAINT "' || ESCAPE_DOUBLE_QUOTES(:foreign_key_names.CONSTRAINT_NAME[i]) || '"';
END FOR;
END;
$$
+4
View File
@@ -126,6 +126,10 @@ public abstract class BaseTestCase {
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.
@@ -132,10 +132,13 @@ public class EbeanServer_eqlTest extends BaseTestCase {
Query<Customer> query = Ebean.createQuery(Customer.class);
query.setMaxRows(10);
query.setFirstRow(3);
if (isSqlServer()) {
query.orderBy("id");
}
query.findList();
if (isSqlServer()) {
assertThat(query.getGeneratedSql()).endsWith("from o_customer t0 offset 3 rows fetch next 10 rows only");
assertThat(query.getGeneratedSql()).endsWith("from o_customer t0 order by t0.id offset 3 rows fetch next 10 rows only");
} else if (isOracle()) {
assertThat(query.getGeneratedSql()).contains("where rownum <= 13");
assertThat(query.getGeneratedSql()).contains("where rn_ > 3");
@@ -70,6 +70,7 @@ public class ServerConfigTest {
props.setProperty("namingConvention", "io.ebean.config.MatchingNamingConvention");
props.setProperty("idGeneratorAutomatic", "true");
props.setProperty("enabledL2Regions", "r0,users,orgs");
props.setProperty("caseSensitiveCollation", "false");
serverConfig.loadFromProperties(props);
@@ -79,6 +80,7 @@ public class ServerConfigTest {
assertTrue(serverConfig.isDbOffline());
assertTrue(serverConfig.isAutoReadOnlyDataSource());
assertTrue(serverConfig.isIdGeneratorAutomatic());
assertFalse(serverConfig.getPlatformConfig().isCaseSensitiveCollation());
assertThat(serverConfig.getNamingConvention()).isInstanceOf(MatchingNamingConvention.class);
@@ -131,6 +133,7 @@ public class ServerConfigTest {
assertFalse(serverConfig.isIdGeneratorAutomatic());
assertEquals(JsonConfig.DateTime.ISO8601, serverConfig.getJsonDateTime());
assertEquals(JsonConfig.Date.ISO8601, serverConfig.getJsonDate());
assertTrue(serverConfig.getPlatformConfig().isCaseSensitiveCollation());
}
@Test
@@ -596,7 +596,7 @@ public class EqlParserTest extends BaseTestCase {
ResetBasicData.reset();
Query<Customer> query = parse("limit 10 offset 5");
Query<Customer> query = parse("order by name limit 10 offset 5");
query.findList();
if (isH2()) {
assertThat(query.getGeneratedSql()).contains(" limit 10 offset 5");
+28
View File
@@ -0,0 +1,28 @@
package main;
import io.ebean.docker.commands.MySqlConfig;
import io.ebean.docker.commands.MySqlContainer;
public class StartMyServer {
public static void main(String[] args) {
MySqlConfig config = new MySqlConfig("5.7");
config.setDbName("unit");
config.setUser("unit");
config.setPassword("unit");
// by default this mysql docker collation is case sensitive
// using utf8mb4_bin
//
// when changing to a CI collation (e.g. utf8mb4_unicode_ci) we also set
// ebean.<db>.caseSensitiveCollation=false
// ... such that tests now take that into account
// config.setCollation("default");
// config.setCollation("utf8mb4_unicode_ci");
// config.setCharacterSet("utf8mb4");
MySqlContainer container = new MySqlContainer(config);
container.start();
}
}
+27
View File
@@ -0,0 +1,27 @@
package main;
import io.ebean.docker.commands.SqlServerConfig;
import io.ebean.docker.commands.SqlServerContainer;
public class StartSqlServer {
public static void main(String[] args) {
SqlServerConfig config = new SqlServerConfig("2017-CU4");
config.setDbName("test_ebean");
config.setUser("test_ebean");
// by default this sqlserver docker collation is case sensitive
// using MSSQL_COLLATION=Latin1_General_100_BIN2
//
// when changing to a CI collation also use
// ebean.sqlserver.caseSensitiveCollation=false
// ... such that tests now take that into account
//config.setCollation("default");
//config.setCollation("Latin1_General_100_CI");
SqlServerContainer container = new SqlServerContainer(config);
container.start();
}
}
@@ -3,6 +3,8 @@ package org.tests.basic;
import io.ebean.BaseTestCase;
import io.ebean.DB;
import io.ebean.Transaction;
import io.ebean.annotation.IgnorePlatform;
import io.ebean.annotation.Platform;
import org.junit.Test;
import org.tests.model.basic.Country;
import org.tests.model.basic.ResetBasicData;
@@ -32,6 +34,7 @@ public class TestQueryUsingConnection extends BaseTestCase {
}
}
@IgnorePlatform(Platform.SQLSERVER)
@Test
public void usingTransaction() {
@@ -54,7 +54,7 @@ public class TestSecondaryQueries extends TransactionalTestCase {
assertThat(sql).hasSize(1);
if (isSqlServer()) {
assertThat(trimSql(sql.get(0), 2)).contains("select top 10 t0.id, t0.status, t0.kcustomer_id from o_order t0 order by t0.id");
assertThat(trimSql(sql.get(0), 2)).contains("select top 10 t0.id, t0.status, t0.kcustomer_id from o_order t0");
} else {
assertThat(trimSql(sql.get(0), 2)).contains("select t0.id, t0.status, t0.kcustomer_id from o_order t0");
}
@@ -91,7 +91,7 @@ public class TestSecondaryQueries extends TransactionalTestCase {
assertThat(sql).hasSize(1);
if (isSqlServer()) {
assertThat(trimSql(sql.get(0), 2)).contains("select top 10 t0.id, t0.status from o_order t0 order by t0.id");
assertThat(trimSql(sql.get(0), 2)).contains("select top 10 t0.id, t0.status from o_order t0");
} else {
assertThat(trimSql(sql.get(0), 2)).contains("select t0.id, t0.status from o_order t0");
}
@@ -34,15 +34,20 @@ public class TestOneToManyJoinTableInheritance extends BaseTestCase {
List<String> sql = LoggedSqlCollector.current();
boolean hasSequence = isSqlServer(); // uses sequence
assertThat(sql).hasSize(11);
assertThat(sql.get(0)).contains("insert into class_super ");
assertThat(sql.get(1)).contains("-- bind(ClassA)");
assertThat(sql.get(2)).contains("-- bind(ClassB)");
if (!hasSequence) {
assertThat(sql.get(1)).contains("-- bind(ClassA)");
assertThat(sql.get(2)).contains("-- bind(ClassB)");
}
assertThat(sql.get(3)).contains("insert into monkey ");
assertThat(sql.get(4)).contains("-- bind(Sim");
assertThat(sql.get(5)).contains("-- bind(Tim");
assertThat(sql.get(6)).contains("-- bind(Uim");
assertThat(sql.get(7)).contains("insert into class_super_monkey (class_super_sid, monkey_mid) values (?, ?)");
if (!hasSequence) {
assertThat(sql.get(4)).contains("-- bind(Sim");
assertThat(sql.get(5)).contains("-- bind(Tim");
assertThat(sql.get(6)).contains("-- bind(Uim");
assertThat(sql.get(7)).contains("insert into class_super_monkey (class_super_sid, monkey_mid) values (?, ?)");
}
assertSqlBind(sql, 8, 10);
ClassA dbA = Ebean.find(ClassA.class, 1);
@@ -126,6 +126,7 @@ public class TestAddOrderByWithFirstRowsMaxRows extends BaseTestCase {
Ebean.find(Order.class)
.setFirstRow(10)
.setMaxRows(10)
.orderBy("id")
.findPagedList()
.getList();
@@ -1,7 +1,7 @@
package org.tests.query;
import io.ebean.BaseTestCase;
import io.ebean.Ebean;
import io.ebean.DB;
import org.junit.BeforeClass;
import org.junit.Test;
import org.tests.model.basic.Customer;
@@ -23,13 +23,17 @@ public class TestQueryFilterCaseInsensitive extends BaseTestCase {
// Note: this test uses only customer#1..#4
List<Customer> customers = Ebean.find(Customer.class).where()
List<Customer> customers = DB.find(Customer.class).where()
.eq("name", "ROB") // case match
.le("id", 4).findList();
assertThat(customers).isEmpty();
if (isPlatformCaseSensitive()) {
assertThat(customers).isEmpty();
} else {
assertThat(customers).isNotEmpty();
}
customers = Ebean.find(Customer.class).where()
customers = DB.find(Customer.class).where()
.ieq("name", "ROB") // case insensitive match
.le("id", 4).findList();
@@ -38,13 +42,17 @@ public class TestQueryFilterCaseInsensitive extends BaseTestCase {
@Test
public void testNe() {
List<Customer> customers = Ebean.find(Customer.class).where()
List<Customer> customers = DB.find(Customer.class).where()
.ne("name", "ROB") // case match
.le("id", 4).findList();
assertThat(customers).hasSize(4);
if (isPlatformCaseSensitive()) {
assertThat(customers).hasSize(4);
} else {
assertThat(customers).isNotEmpty();
}
customers = Ebean.find(Customer.class).where()
customers = DB.find(Customer.class).where()
.ine("name", "ROB") // case insensitive match
.le("id", 4).findList();
@@ -54,13 +62,17 @@ public class TestQueryFilterCaseInsensitive extends BaseTestCase {
@Test
public void testLike() {
List<Customer> customers = Ebean.find(Customer.class).where()
List<Customer> customers = DB.find(Customer.class).where()
.like("name", "%O%") // case match
.le("id", 4).findList();
assertThat(customers).isEmpty();
if (isPlatformCaseSensitive()) {
assertThat(customers).isEmpty();
} else {
assertThat(customers).isNotEmpty();
}
customers = Ebean.find(Customer.class).where()
customers = DB.find(Customer.class).where()
.ilike("name", "%O%") // case insensitive match
.le("id", 4).findList();
@@ -69,29 +81,36 @@ public class TestQueryFilterCaseInsensitive extends BaseTestCase {
@Test
public void testContains() {
List<Customer> customers = Ebean.find(Customer.class).where()
List<Customer> customers = DB.find(Customer.class).where()
.contains("name", "O") // case match
.le("id", 4).findList();
assertThat(customers).isEmpty();
if (isPlatformCaseSensitive()) {
assertThat(customers).isEmpty();
} else {
assertThat(customers).isNotEmpty();
}
customers = Ebean.find(Customer.class).where()
customers = DB.find(Customer.class).where()
.icontains("name", "O") // case insensitive match
.le("id", 4).findList();
assertThat(customers).hasSize(4); // Rob / Fiona / Cust No address / NocCust
}
@Test
public void testStartsWith() {
List<Customer> customers = Ebean.find(Customer.class).where()
List<Customer> customers = DB.find(Customer.class).where()
.startsWith("name", "RO") // case match
.le("id", 4).findList();
assertThat(customers).isEmpty();
if (isPlatformCaseSensitive()) {
assertThat(customers).isEmpty();
} else {
assertThat(customers).isNotEmpty();
}
customers = Ebean.find(Customer.class).where()
customers = DB.find(Customer.class).where()
.istartsWith("name", "RO") // case insensitive match
.le("id", 4).findList();
@@ -100,13 +119,17 @@ public class TestQueryFilterCaseInsensitive extends BaseTestCase {
@Test
public void testEndsWith() {
List<Customer> customers = Ebean.find(Customer.class).where()
List<Customer> customers = DB.find(Customer.class).where()
.endsWith("name", "OB") // case match
.le("id", 4).findList();
assertThat(customers).isEmpty();
if (isPlatformCaseSensitive()) {
assertThat(customers).isEmpty();
} else {
assertThat(customers).isNotEmpty();
}
customers = Ebean.find(Customer.class).where()
customers = DB.find(Customer.class).where()
.iendsWith("name", "OB") // case insensitive match
.le("id", 4).findList();
@@ -94,6 +94,7 @@ public class TestQueryFindPagedList extends BaseTestCase {
PagedList<Order> pagedList2 = Ebean.find(Order.class)
.setFirstRow(1)
.setMaxRows(3)
.orderBy("id")
.findPagedList();
pagedList2.loadCount();
@@ -109,6 +110,7 @@ public class TestQueryFindPagedList extends BaseTestCase {
PagedList<Order> pagedList3 = Ebean.find(Order.class)
.setFirstRow(2)
.setMaxRows(150)
.orderBy("id")
.findPagedList();
assertFalse(pagedList3.hasNext());
@@ -15,11 +15,16 @@ public class TestQueryOrderById extends BaseTestCase {
Query<Customer> query = DB.find(Customer.class)
.select("id,name")
.orderBy("id")
.setFirstRow(1)
.setMaxRows(5);
query.findList();
assertThat(sqlOf(query)).isEqualTo("select t0.id, t0.name from o_customer t0 limit 5 offset 1");
if (isSqlServer()) {
assertThat(sqlOf(query)).isEqualTo("select t0.id, t0.name from o_customer t0 order by t0.id offset 1 rows fetch next 5 rows only");
} else {
assertThat(sqlOf(query)).isEqualTo("select t0.id, t0.name from o_customer t0 order by t0.id limit 5 offset 1");
}
}
@Test
@@ -32,6 +37,10 @@ public class TestQueryOrderById extends BaseTestCase {
.orderById(true);
query.findList();
assertThat(sqlOf(query)).isEqualTo("select t0.id, t0.name from o_customer t0 order by t0.id limit 5 offset 1");
if (isSqlServer()) {
assertThat(sqlOf(query)).isEqualTo("select t0.id, t0.name from o_customer t0 order by t0.id offset 1 rows fetch next 5 rows only");
} else {
assertThat(sqlOf(query)).isEqualTo("select t0.id, t0.name from o_customer t0 order by t0.id limit 5 offset 1");
}
}
}
@@ -1,6 +1,6 @@
package org.tests.query.other;
import io.ebean.Ebean;
import io.ebean.DB;
import io.ebean.TransactionalTestCase;
import org.tests.model.basic.Customer;
@@ -16,76 +16,80 @@ public class TestLikeEscaping extends TransactionalTestCase {
public void testLikeEscaping() {
// Mysql, PgSql, H2 special chars: "_" "%"
// MsSql special chars: "_" "%" "[" AND different Quoting!
Ebean.save(ResetBasicData.createCustomer("Paul % Percentage", "*Star", "[none]", 0, null));
Ebean.save(ResetBasicData.createCustomer("(none)", "More * Star", "[none]", 0, null));
DB.save(ResetBasicData.createCustomer("Paul % Percentage", "*Star", "[none]", 0, null));
DB.save(ResetBasicData.createCustomer("(none)", "More * Star", "[none]", 0, null));
Ebean.save(ResetBasicData.createCustomer("Paul %% Doublepercentage", "|Pipeway", "[other]", 1, null));
Ebean.save(ResetBasicData.createCustomer("_Udo Underscore", "|Pipeway", "[other]", 1, null));
DB.save(ResetBasicData.createCustomer("Paul %% Doublepercentage", "|Pipeway", "[other]", 1, null));
DB.save(ResetBasicData.createCustomer("_Udo Underscore", "|Pipeway", "[other]", 1, null));
Ebean.save(ResetBasicData.createCustomer("Bodo \\ backslash", "\\BS", "[other]", 1, null));
DB.save(ResetBasicData.createCustomer("Bodo \\ backslash", "\\BS", "[other]", 1, null));
assertThat(Ebean.find(Customer.class)
assertThat(DB.find(Customer.class)
.where().contains("name", "Paul %%").findCount()
).isEqualTo(1);
assertThat(Ebean.find(Customer.class)
assertThat(DB.find(Customer.class)
.where().contains("name", "o \\ b").findCount()
).isEqualTo(1);
assertThat(Ebean.find(Customer.class)
assertThat(DB.find(Customer.class)
.where().contains("name", "o \\\\ b").findCount()
).isEqualTo(0);
assertThat(Ebean.find(Customer.class)
assertThat(DB.find(Customer.class)
.where().startsWith("name", "_").findCount()
).isEqualTo(1);
assertThat(Ebean.find(Customer.class)
if (isPlatformCaseSensitive()) {
assertThat(DB.find(Customer.class)
.where().startsWith("name", "_u").findCount()
).isEqualTo(0);
).isEqualTo(0);
}
assertThat(Ebean.find(Customer.class)
assertThat(DB.find(Customer.class)
.where().istartsWith("name", "_U").findCount()
).isEqualTo(1);
assertThat(Ebean.find(Customer.class)
if (isPlatformCaseSensitive()) {
assertThat(DB.find(Customer.class)
.where().startsWith("shippingAddress.line1", "|p").findCount()
).isEqualTo(0);
).isEqualTo(0);
}
assertThat(Ebean.find(Customer.class)
assertThat(DB.find(Customer.class)
.where().startsWith("shippingAddress.line1", "|P").findCount()
).isEqualTo(2);
assertThat(Ebean.find(Customer.class)
assertThat(DB.find(Customer.class)
.where().startsWith("shippingAddress.line1", "\\B").findCount()
).isEqualTo(1);
assertThat(Ebean.find(Customer.class)
assertThat(DB.find(Customer.class)
.where().endsWith("billingAddress.line1", "]").findCount()
).isEqualTo(5);
assertThat(Ebean.find(Customer.class)
assertThat(DB.find(Customer.class)
.where().endsWith("billingAddress.line1", "[none]").findCount()
).isEqualTo(2);
assertThat(Ebean.find(Customer.class)
assertThat(DB.find(Customer.class)
.where().startsWith("billingAddress.line1", "[none]").findCount()
).isEqualTo(2);
assertThat(Ebean.find(Customer.class)
assertThat(DB.find(Customer.class)
.where().contains("billingAddress.line1", "[none]").findCount()
).isEqualTo(2);
assertThat(Ebean.find(Customer.class)
assertThat(DB.find(Customer.class)
.where().contains("shippingAddress.line1", "*").findCount()
).isEqualTo(2);
assertThat(Ebean.find(Customer.class)
assertThat(DB.find(Customer.class)
.where().startsWith("shippingAddress.line1", "*").findCount()
).isEqualTo(1);
assertThat(Ebean.find(Customer.class)
assertThat(DB.find(Customer.class)
.where().endsWith("shippingAddress.line1", "*").findCount()
).isEqualTo(0);
}
@@ -26,10 +26,11 @@ public class TestWhereLikeWithSlash extends BaseTestCase {
Query<EBasic> query1 = Ebean.find(EBasic.class).where().like("name", "slash\\mon%").query();
List<EBasic> list1 = query1.findList();
// This doesn't work in the latest version of H2 so disable for now.
// Still good on Postgres which was the original issue
assertEquals(1, list1.size());
if (!isMySql()) {
// For mysql this assert depends on no_backslash_escapes setting so we won't assert here
// Still good on Postgres which was the original issue
assertEquals(1, list1.size());
}
}
@Test
@@ -151,6 +151,7 @@ public class TestRawSqlOrmQuery extends BaseTestCase {
query.setFirstRow(1);
query.setMaxRows(2);
query.orderBy("id");
List<Customer> list = query.findList();
@@ -75,17 +75,22 @@ public class TestBatchModelFlush extends BaseTestCase {
assertThat(sql).hasSize(9);
// first saved to batch - (depth 100)
boolean hasSequence = isSqlServer();
assertThat(sql.get(0)).contains("insert into mny_b");
assertThat(sql.get(1)).contains(" -- bind(BatchMultipleTop_0");
assertThat(sql.get(2)).contains(" -- bind(BatchMultipleTop_1");
if (!hasSequence) {
assertThat(sql.get(1)).contains(" -- bind(BatchMultipleTop_0");
assertThat(sql.get(2)).contains(" -- bind(BatchMultipleTop_1");
}
// second saved to batch - (depth 101)
assertThat(sql.get(3)).contains("insert into mt_role");
assertThat(sql.get(4)).contains(" -- bind(");
assertThat(sql.get(5)).contains(" -- bind(");
// third saved to batch - (depth 102)
assertThat(sql.get(6)).contains("insert into mny_topic");
assertThat(sql.get(7)).contains(" -- bind(MnyTopic_0");
assertThat(sql.get(8)).contains(" -- bind(MnyTopic_1");
if (!hasSequence) {
assertThat(sql.get(7)).contains(" -- bind(MnyTopic_0");
assertThat(sql.get(8)).contains(" -- bind(MnyTopic_1");
}
DB.delete(t0);
DB.delete(t1);
@@ -9,13 +9,13 @@ AS
BEGIN
DECLARE foreign_key_names TABLE(CONSTRAINT_NAME NVARCHAR(256), TABLE_NAME NVARCHAR(256));
DECLARE i INT;
foreign_key_names = SELECT CONSTRAINT_NAME, TABLE_NAME FROM SYS.REFERENTIAL_CONSTRAINTS WHERE SCHEMA_NAME=CURRENT_SCHEMA AND TABLE_NAME=UPPER(:table_name) AND COLUMN_NAME=UPPER(:column_name);
FOR I IN 1 .. RECORD_COUNT(:foreign_key_names) DO
EXEC 'ALTER TABLE "' || ESCAPE_DOUBLE_QUOTES(:foreign_key_names.TABLE_NAME[i]) || '" DROP CONSTRAINT "' || ESCAPE_DOUBLE_QUOTES(:foreign_key_names.CONSTRAINT_NAME[i]) || '"';
END FOR;
END;
$$
@@ -46,11 +46,11 @@ CREATE OR ALTER PROCEDURE usp_ebean_drop_default_constraint @tableName nvarchar(
AS SET NOCOUNT ON
declare @tmp nvarchar(1000)
BEGIN
select @Tmp = t1.name from sys.default_constraints t1
select @tmp = t1.name from sys.default_constraints t1
join sys.columns t2 on t1.object_id = t2.default_object_id
where t1.parent_object_id = OBJECT_ID(@tableName) and t2.name = @columnName;
if @Tmp is not null EXEC('alter table ' + @tableName +' drop constraint ' + @tmp);
if @tmp is not null EXEC('alter table ' + @tableName +' drop constraint ' + @tmp);
END
$$
+9 -4
View File
@@ -129,10 +129,12 @@ datasource.hsqldb.password=
datasource.hsqldb.databaseUrl=jdbc:hsqldb:mem:tests
datasource.hsqldb.databaseDriver=org.hsqldb.jdbcDriver
# Set caseSensitiveCollation to false when using
# MySql with case insenstive collation
#ebean.mysql.caseSensitiveCollation=false
datasource.mysql.username=unit
datasource.mysql.password=unit
datasource.mysql.databaseUrl=jdbc:mysql://127.0.0.1:3306/unit
datasource.mysql.databaseUrl=jdbc:mysql://127.0.0.1:4306/unit
#datasource.mysql.username=test_ebean
#datasource.mysql.password=test
#datasource.mysql.databaseUrl=jdbc:mysql://127.0.0.1:4306/test_ebean
@@ -158,10 +160,13 @@ datasource.pg.maxStackTraceSize=50
# Our main testing target for SqlServer is sqlserver17
ebean.sqlserver.databasePlatformName=sqlserver17
# set caseSensitiveCollation=false when using a
# case insenstive collation with sql server - See main.StartSqlServer
#ebean.sqlserver.caseSensitiveCollation=false
datasource.sqlserver.username=test_ebean
datasource.sqlserver.password=SqlS3rv#r
datasource.sqlserver.databaseUrl=jdbc:sqlserver://localhost:1433;databaseName=test_ebean
datasource.sqlserver.databaseDriver=com.microsoft.sqlserver.jdbc.SQLServerDriver
datasource.sqlserver.url=jdbc:sqlserver://localhost:1433;databaseName=test_ebean;sendTimeAsDateTime=false
datasource.sqlserver.driver=com.microsoft.sqlserver.jdbc.SQLServerDriver
datasource.db2.username=db2admin
datasource.db2.password=veryverysecret#1234
+1 -4
View File
@@ -73,13 +73,10 @@
</root>
<logger name="io.ebeaninternal.dbmigration.DdlGenerator" level="TRACE"/>
<logger name="org.avaje.dbmigration.ddl" level="TRACE"/>
<logger name="org.tests" level="INFO"/>
<logger name="io.ebean" level="INFO"/>
<!--<logger name="org.avaje.docker" level="TRACE"/>-->
<logger name="io.ebean.docker" level="TRACE"/>
<!--<logger name="io.ebean.DDL" level="DEBUG"/>-->
<!-- <logger name="io.ebean.SQL" level="TRACE"/>-->