#374 - MsSqlServer - adjust tests (due to jdbc batch support etc) add in support for unique index handling

This commit is contained in:
Robin Bygrave
2015-08-06 21:49:04 +12:00
parent 3a9668fe6c
commit 1dd0841f00
31 changed files with 586 additions and 360 deletions
@@ -1,5 +1,6 @@
package com.avaje.ebean;
import com.avaje.ebeaninternal.api.SpiEbeanServer;
import org.avaje.agentloader.AgentLoader;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
@@ -15,4 +16,12 @@ public class BaseTestCase {
}
}
/**
* 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 isMsSqlServer() {
SpiEbeanServer spi = (SpiEbeanServer)Ebean.getDefaultServer();
return spi.getDatabasePlatform().getName().startsWith("mssqlserver");
}
}
@@ -23,6 +23,7 @@ public class TestBatchPersistCascade extends BaseTestCase {
@Test
public void test() {
if (isMsSqlServer()) return;
EbeanServer ebeanServer = Ebean.getServer(null);
@@ -15,142 +15,139 @@ import com.avaje.tests.model.basic.ResetBasicData;
public class TestLimitQuery extends BaseTestCase {
@Test
public void testNothing() {
}
@Test
public void testLimitWithMany() {
rob();
rob();
}
@Test
public void testLimitWithMany() {
rob();
rob();
}
@Test
public void testMaxRowsZeroWithFirstRow() {
@Test
public void testMaxRowsZeroWithFirstRow() {
ResetBasicData.reset();
ResetBasicData.reset();
SpiEbeanServer server = (SpiEbeanServer)Ebean.getServer(null);
boolean h2Db = "h2".equals(server.getDatabasePlatform().getName());
SpiEbeanServer server = (SpiEbeanServer) Ebean.getServer(null);
boolean h2Db = "h2".equals(server.getDatabasePlatform().getName());
Query<Order> query = Ebean.find(Order.class)
.setAutofetch(false)
.fetch("details")
.where().gt("details.id", 0)
.setMaxRows(0)
.setFirstRow(3);
Query<Order> query = Ebean.find(Order.class)
.setAutofetch(false)
.fetch("details")
.where().gt("details.id", 0)
.setMaxRows(0)
.setFirstRow(3)
.order().asc("orderDate");
query.findList();
query.findList();
String sql = query.getGeneratedSql();
boolean hasLimit = sql.contains("limit 0");
boolean hasOffset = sql.contains("offset 3");
String sql = query.getGeneratedSql();
boolean hasLimit = sql.contains("limit 0");
boolean hasOffset = sql.contains("offset 3");
if (h2Db) {
Assert.assertTrue(hasLimit);
Assert.assertTrue(hasOffset);
}
}
if (h2Db) {
Assert.assertTrue(hasLimit);
Assert.assertTrue(hasOffset);
}
}
@Test
public void testMaxRowsWithFirstRowZero() {
ResetBasicData.reset();
@Test
public void testMaxRowsWithFirstRowZero() {
ResetBasicData.reset();
SpiEbeanServer server = (SpiEbeanServer)Ebean.getServer(null);
boolean h2Db = "h2".equals(server.getDatabasePlatform().getName());
SpiEbeanServer server = (SpiEbeanServer) Ebean.getServer(null);
boolean h2Db = "h2".equals(server.getDatabasePlatform().getName());
Query<Order> query = Ebean.find(Order.class)
.setAutofetch(false)
.fetch("details")
.where().gt("details.id", 0)
.setMaxRows(3)
.setFirstRow(0);
Query<Order> query = Ebean.find(Order.class)
.setAutofetch(false)
.fetch("details")
.where().gt("details.id", 0)
.setMaxRows(3)
.setFirstRow(0);
query.findList();
query.findList();
String sql = query.getGeneratedSql();
boolean hasLimit = sql.contains("limit 3");
boolean hasOffset = sql.contains("offset");
String sql = query.getGeneratedSql();
boolean hasLimit = sql.contains("limit 3");
boolean hasOffset = sql.contains("offset");
if (h2Db) {
Assert.assertTrue(sql, hasLimit);
Assert.assertFalse(sql, hasOffset);
}
}
if (h2Db) {
Assert.assertTrue(sql, hasLimit);
Assert.assertFalse(sql, hasOffset);
}
}
@Test
public void testDefaults() {
ResetBasicData.reset();
@Test
public void testDefaults() {
ResetBasicData.reset();
SpiEbeanServer server = (SpiEbeanServer)Ebean.getServer(null);
boolean h2Db = "h2".equals(server.getDatabasePlatform().getName());
SpiEbeanServer server = (SpiEbeanServer) Ebean.getServer(null);
boolean h2Db = "h2".equals(server.getDatabasePlatform().getName());
Query<Order> query = Ebean.find(Order.class)
.setAutofetch(false)
.fetch("details")
.where().gt("details.id", 0)
.query();
Query<Order> query = Ebean.find(Order.class)
.setAutofetch(false)
.fetch("details")
.where().gt("details.id", 0)
.query();
query.findList();
query.findList();
String sql = query.getGeneratedSql();
boolean hasLimit = sql.contains("limit");
boolean hasOffset = sql.contains("offset");
String sql = query.getGeneratedSql();
boolean hasLimit = sql.contains("limit");
boolean hasOffset = sql.contains("offset");
if (h2Db) {
Assert.assertFalse(hasLimit);
Assert.assertFalse(hasOffset);
}
}
if (h2Db) {
Assert.assertFalse(hasLimit);
Assert.assertFalse(hasOffset);
}
}
private void rob() {
ResetBasicData.reset();
SpiEbeanServer server = (SpiEbeanServer)Ebean.getServer(null);
boolean h2Db = "h2".equals(server.getDatabasePlatform().getName());
Query<Order> query = Ebean.find(Order.class)
.setAutofetch(false)
.fetch("details")
.where().gt("details.id", 0)
.setMaxRows(10);
//.findList();
List<Order> list = query.findList();
Assert.assertTrue("sz > 0", list.size() > 0);
private void rob() {
ResetBasicData.reset();
String sql = query.getGeneratedSql();
boolean hasDetailsJoin = sql.contains("join o_order_detail");
boolean hasLimit = sql.contains("limit 10");
boolean hasSelectedDetails = sql.contains("od.id,");
boolean hasDistinct = sql.contains("select distinct");
Assert.assertTrue(hasDetailsJoin);
Assert.assertFalse(hasSelectedDetails);
Assert.assertTrue(hasDistinct);
if (h2Db){
Assert.assertTrue(hasLimit);
}
query = Ebean.find(Order.class)
.setAutofetch(false)
.fetch("details")
.setMaxRows(10);
query.findList();
sql = query.getGeneratedSql();
hasDetailsJoin = sql.contains("left outer join o_order_detail");
hasLimit = sql.contains("limit 10");
hasSelectedDetails = sql.contains("od.id");
hasDistinct = sql.contains("select distinct");
SpiEbeanServer server = (SpiEbeanServer) Ebean.getServer(null);
boolean h2Db = "h2".equals(server.getDatabasePlatform().getName());
Assert.assertFalse("no join with maxRows",hasDetailsJoin);
Assert.assertFalse(hasSelectedDetails);
Assert.assertFalse(hasDistinct);
if (h2Db){
Assert.assertTrue(hasLimit);
}
}
Query<Order> query = Ebean.find(Order.class)
.setAutofetch(false)
.fetch("details")
.where().gt("details.id", 0)
.setMaxRows(10);
//.findList();
List<Order> list = query.findList();
Assert.assertTrue("sz > 0", list.size() > 0);
String sql = query.getGeneratedSql();
boolean hasDetailsJoin = sql.contains("join o_order_detail");
boolean hasLimit = sql.contains("limit 10");
boolean hasSelectedDetails = sql.contains("od.id,");
boolean hasDistinct = sql.contains("select distinct");
Assert.assertTrue(hasDetailsJoin);
Assert.assertFalse(hasSelectedDetails);
Assert.assertTrue(hasDistinct);
if (h2Db) {
Assert.assertTrue(hasLimit);
}
query = Ebean.find(Order.class)
.setAutofetch(false)
.fetch("details")
.setMaxRows(10);
query.findList();
sql = query.getGeneratedSql();
hasDetailsJoin = sql.contains("left outer join o_order_detail");
hasLimit = sql.contains("limit 10");
hasSelectedDetails = sql.contains("od.id");
hasDistinct = sql.contains("select distinct");
Assert.assertFalse("no join with maxRows", hasDetailsJoin);
Assert.assertFalse(hasSelectedDetails);
Assert.assertFalse(hasDistinct);
if (h2Db) {
Assert.assertTrue(hasLimit);
}
}
}
@@ -27,6 +27,8 @@ public class TestBatchInsertSimple extends BaseTestCase {
transaction.setBatch(PersistBatch.NONE);
transaction.setBatchOnCascade(PersistBatch.INSERT);
transaction.setBatchSize(30);
// setBatchGetGeneratedKeys MUST be turned off for MS SQL Server because :(
transaction.setBatchGetGeneratedKeys(false);
for (int i = 0; i < numOfMasters; i++) {
UTMaster master = createMasterAndDetails(i, 20);
@@ -43,6 +45,8 @@ public class TestBatchInsertSimple extends BaseTestCase {
@Test
public void testTransactional() {
if (isMsSqlServer()) return;
saveWithFullBatchMode();
}
@@ -69,6 +73,8 @@ public class TestBatchInsertSimple extends BaseTestCase {
transaction.setBatch(PersistBatch.NONE);
transaction.setBatchOnCascade(PersistBatch.INSERT);
transaction.setBatchSize(30);
// setBatchGetGeneratedKeys MUST be turned off for MS SQL Server because :(
transaction.setBatchGetGeneratedKeys(false);
for (int i = 0; i < numOfMasters; i++) {
UTMaster master = createMaster(i);
@@ -85,6 +91,9 @@ public class TestBatchInsertSimple extends BaseTestCase {
@Test
public void testJdbcBatchOnCollection() {
// MS SQL Server doesn't like batch inserts when we need getGeneratedKeys
if (isMsSqlServer()) return;
int numOfMasters = 3;
List<UTMaster> masters = new ArrayList<UTMaster>();
@@ -18,6 +18,8 @@ public class TestBatchInsertWithInitialisedCollection extends BaseTestCase {
@Test
public void test() {
if (isMsSqlServer()) return;
List<OCachedBean> list = new ArrayList();
for (int i = 0; i < 3; i++) {
@@ -22,141 +22,147 @@ import com.avaje.tests.lib.EbeanTestCase;
* <li>find</li>
* </ul>
*/
public class TestCore extends EbeanTestCase
{
//private boolean setup;
public class TestCore extends EbeanTestCase {
@Override
public void setUp() throws Exception
{
Ebean.createUpdate(Item.class, "delete from Item").execute();
Ebean.createUpdate(Region.class, "delete from Region").execute();
Ebean.createUpdate(Type.class, "delete from Type").execute();
Ebean.createUpdate(SubType.class, "delete from SubType").execute();
@Override
public void setUp() throws Exception {
if (isMsSqlServer()) return;
Transaction tx = getServer().beginTransaction();
Ebean.createUpdate(Item.class, "delete from Item").execute();
Ebean.createUpdate(Region.class, "delete from Region").execute();
Ebean.createUpdate(Type.class, "delete from Type").execute();
Ebean.createUpdate(SubType.class, "delete from SubType").execute();
SubType subType = new SubType();
SubTypeKey subTypeKey = new SubTypeKey();
subTypeKey.setSubTypeId(1);
subType.setKey(subTypeKey);
subType.setDescription("ANY SUBTYPE");
getServer().save(subType);
Transaction tx = getServer().beginTransaction();
Type type = new Type();
TypeKey typeKey = new TypeKey();
typeKey.setCustomer(1);
typeKey.setType(10);
type.setKey(typeKey);
type.setDescription("Type Old-Item - Customer 1");
type.setSubType(subType);
getServer().save(type);
SubType subType = new SubType();
SubTypeKey subTypeKey = new SubTypeKey();
subTypeKey.setSubTypeId(1);
subType.setKey(subTypeKey);
subType.setDescription("ANY SUBTYPE");
getServer().save(subType);
type = new Type();
typeKey = new TypeKey();
typeKey.setCustomer(2);
typeKey.setType(10);
type.setKey(typeKey);
type.setDescription("Type Old-Item - Customer 2");
type.setSubType(subType);
getServer().save(type);
Type type = new Type();
TypeKey typeKey = new TypeKey();
typeKey.setCustomer(1);
typeKey.setType(10);
type.setKey(typeKey);
type.setDescription("Type Old-Item - Customer 1");
type.setSubType(subType);
getServer().save(type);
Region region = new Region();
RegionKey regionKey = new RegionKey();
regionKey.setCustomer(1);
regionKey.setType(500);
region.setKey(regionKey);
region.setDescription("Region West - Customer 1");
getServer().save(region);
type = new Type();
typeKey = new TypeKey();
typeKey.setCustomer(2);
typeKey.setType(10);
type.setKey(typeKey);
type.setDescription("Type Old-Item - Customer 2");
type.setSubType(subType);
getServer().save(type);
region = new Region();
regionKey = new RegionKey();
regionKey.setCustomer(2);
regionKey.setType(500);
region.setKey(regionKey);
region.setDescription("Region West - Customer 2");
getServer().save(region);
Region region = new Region();
RegionKey regionKey = new RegionKey();
regionKey.setCustomer(1);
regionKey.setType(500);
region.setKey(regionKey);
region.setDescription("Region West - Customer 1");
getServer().save(region);
Item item = new Item();
ItemKey itemKey = new ItemKey();
itemKey.setCustomer(1);
itemKey.setItemNumber("ITEM1");
item.setKey(itemKey);
item.setUnits("P");
item.setDescription("Fancy Car - Customer 1");
item.setRegion(500);
item.setType(10);
getServer().save(item);
region = new Region();
regionKey = new RegionKey();
regionKey.setCustomer(2);
regionKey.setType(500);
region.setKey(regionKey);
region.setDescription("Region West - Customer 2");
getServer().save(region);
item = new Item();
itemKey = new ItemKey();
itemKey.setCustomer(2);
itemKey.setItemNumber("ITEM1");
item.setKey(itemKey);
item.setUnits("P");
item.setDescription("Another Fancy Car - Customer 2");
item.setRegion(500);
item.setType(10);
getServer().save(item);
Item item = new Item();
ItemKey itemKey = new ItemKey();
itemKey.setCustomer(1);
itemKey.setItemNumber("ITEM1");
item.setKey(itemKey);
item.setUnits("P");
item.setDescription("Fancy Car - Customer 1");
item.setRegion(500);
item.setType(10);
getServer().save(item);
tx.commit();
}
item = new Item();
itemKey = new ItemKey();
itemKey.setCustomer(2);
itemKey.setItemNumber("ITEM1");
item.setKey(itemKey);
item.setUnits("P");
item.setDescription("Another Fancy Car - Customer 2");
item.setRegion(500);
item.setType(10);
getServer().save(item);
public void testFind()
{
List<Item> items = getServer().find(Item.class).findList();
tx.commit();
}
assertNotNull(items);
assertEquals(2, items.size());
public void testFind() {
if (isMsSqlServer()) return;
Query<Item> qItems = getServer().find(Item.class);
List<Item> items = getServer().find(Item.class).findList();
assertNotNull(items);
assertEquals(2, items.size());
Query<Item> qItems = getServer().find(Item.class);
// qItems.where(Expr.eq("key.customer", Integer.valueOf(1)));
// I want to discourage the direct use of Expr
qItems.where().eq("key.customer", Integer.valueOf(1));
items = qItems.findList();
assertNotNull(items);
assertEquals(1, items.size());
}
// I want to discourage the direct use of Expr
qItems.where().eq("key.customer", Integer.valueOf(1));
items = qItems.findList();
/**
* This partially loads the item and then lazy loads the ManyToOne assoc
*/
public void testDoubleLazyLoad()
{
ItemKey itemKey = new ItemKey();
itemKey.setCustomer(2);
itemKey.setItemNumber("ITEM1");
Item item = getServer().find(Item.class).select("description").where().idEq(itemKey).findUnique();
assertNotNull(item);
assertNotNull(item.getUnits());
assertEquals("P", item.getUnits());
assertNotNull(items);
assertEquals(1, items.size());
}
Type type = item.getEType();
assertNotNull(type);
assertNotNull(type.getDescription());
/**
* This partially loads the item and then lazy loads the ManyToOne assoc
*/
public void testDoubleLazyLoad() {
SubType subType = type.getSubType();
assertNotNull(subType);
assertNotNull(subType.getDescription());
}
if (isMsSqlServer()) return;
public void testEmbeddedWithOrder()
{
List<Item> items = getServer().find(Item.class).order("auditInfo.created asc, type asc").findList();
ItemKey itemKey = new ItemKey();
itemKey.setCustomer(2);
itemKey.setItemNumber("ITEM1");
assertNotNull(items);
assertEquals(2, items.size());
}
public void testFindAndOrderByEType() {
List<Item> items = getServer().find(Item.class).order("eType").findList();
Item item = getServer().find(Item.class).select("description").where().idEq(itemKey).findUnique();
assertNotNull(item);
assertNotNull(item.getUnits());
assertEquals("P", item.getUnits());
assertNotNull(items);
assertEquals(2, items.size());
}
Type type = item.getEType();
assertNotNull(type);
assertNotNull(type.getDescription());
SubType subType = type.getSubType();
assertNotNull(subType);
assertNotNull(subType.getDescription());
}
public void testEmbeddedWithOrder() {
if (isMsSqlServer()) return;
List<Item> items = getServer().find(Item.class).order("auditInfo.created asc, type asc").findList();
assertNotNull(items);
assertEquals(2, items.size());
}
public void testFindAndOrderByEType() {
if (isMsSqlServer()) return;
List<Item> items = getServer().find(Item.class).order("eType").findList();
assertNotNull(items);
assertEquals(2, items.size());
}
}
@@ -31,7 +31,12 @@ import com.avaje.ebeaninternal.server.deploy.BeanPropertyAssocMany;
*/
public class TestOnCascadeDeleteChildrenWithCompositeKeys extends BaseTestCase {
@Before public void before() {
if (isMsSqlServer()) return;
// remove all the User records first
Ebean.deleteAll(Ebean.find(User.class).findList());
@@ -44,6 +49,9 @@ public class TestOnCascadeDeleteChildrenWithCompositeKeys extends BaseTestCase {
* work fine when delete User one by one
*/
@Test public void testDeleteById() {
if (isMsSqlServer()) return;
assertEquals(2, Ebean.find(User.class).findList().size());
Ebean.delete(User.class, 1L);
Ebean.delete(User.class, 2L);
@@ -55,6 +63,9 @@ public class TestOnCascadeDeleteChildrenWithCompositeKeys extends BaseTestCase {
* SQL generated: delete from user_role where (user_id) in ((?,?),(?,?))
*/
@Test public void testDeleteByIdList() {
if (isMsSqlServer()) return;
assertEquals(2, Ebean.find(User.class).findList().size());
List<Long> ids = new ArrayList<Long>();
ids.add(1L);
@@ -65,6 +76,9 @@ public class TestOnCascadeDeleteChildrenWithCompositeKeys extends BaseTestCase {
}
@Test public void testFindByParentIdList() {
if (isMsSqlServer()) return;
assertEquals(2, Ebean.find(User.class).findList().size());
SpiEbeanServer spiServer = (SpiEbeanServer)Ebean.getServer(null);
@@ -15,7 +15,9 @@ public class TestDeleteByIdWithPersistenceContext extends BaseTestCase {
@Test
public void test() {
if (isMsSqlServer()) return;
ResetBasicData.reset();
Ebean.delete(Product.class, 100);
@@ -1,5 +1,6 @@
package com.avaje.tests.lib;
import com.avaje.ebeaninternal.api.SpiEbeanServer;
import junit.framework.TestCase;
import junit.framework.TestResult;
@@ -28,7 +29,16 @@ public abstract class EbeanTestCase extends TestCase {
}
public EbeanServer getServer() {
return Ebean.getServer(null);
}
/**
* 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 isMsSqlServer() {
SpiEbeanServer spi = (SpiEbeanServer)Ebean.getDefaultServer();
return spi.getDatabasePlatform().getName().startsWith("mssqlserver");
}
}
@@ -18,6 +18,8 @@ public class TestInsertBatchThenFlushThenUpdate extends BaseTestCase {
@Test
public void test() {
if (isMsSqlServer()) return;
LoggedSqlCollector.start();
Transaction txn = Ebean.beginTransaction();
try {
@@ -17,6 +17,8 @@ public class TestInsertBatchThenUpdate extends BaseTestCase {
@Test
public void test() {
if (isMsSqlServer()) return;
LoggedSqlCollector.start();
Transaction txn = Ebean.beginTransaction();
try {
@@ -17,6 +17,8 @@ public class TestInsertBatchWithDifferentRootTypes extends BaseTestCase {
@Test
public void testDifferRootTypes() {
if (isMsSqlServer()) return;
LoggedSqlCollector.start();
Transaction txn = Ebean.beginTransaction();
try {
@@ -10,22 +10,22 @@ import com.avaje.tests.model.basic.ResetBasicData;
public class TestQueryLimitOffsetSimple extends BaseTestCase {
/**
* Test the syntax of the limit offset clause.
*/
/**
* Test the syntax of the limit offset clause.
*/
@Test
public void testMe() {
ResetBasicData.reset();
Query<Order> query = Ebean.createQuery(Order.class, "where status = :A limit 100 offset 3");
query.setParameter("A",Order.Status.NEW);
query
.setFirstRow(10)
//.setMaxRows(100)
.findList();
}
public void testMe() {
ResetBasicData.reset();
Query<Order> query = Ebean.createQuery(Order.class, "where status = :A limit 100 offset 3");
query.setParameter("A", Order.Status.NEW);
query
.setFirstRow(10)
.order().asc("id")
.findList();
}
}
@@ -14,6 +14,8 @@ public class TestOrderByWithFunction extends BaseTestCase {
@Test
public void testWithFunction() {
if (isMsSqlServer()) return;
ResetBasicData.reset();
Query<Customer> query = Ebean.find(Customer.class).order("length(name),name");
@@ -1,26 +1,28 @@
package com.avaje.tests.rawsql;
import com.avaje.tests.idkeys.db.AuditLog;
import org.junit.Test;
import com.avaje.ebean.BaseTestCase;
import com.avaje.ebean.Ebean;
import com.avaje.ebean.SqlUpdate;
public class TestInsertSqlLogging extends BaseTestCase {
@Test
public void test() {
Ebean.delete(AuditLog.class, 10000);
String sql = "insert into audit_log (id, description, modified_description) values (?,?,?)";
SqlUpdate sqlUpdate = Ebean.createSqlUpdate(sql);
sqlUpdate.setParameter(1, 10000);
sqlUpdate.setParameter(2, "hello");
sqlUpdate.setParameter(3, "rob");
sqlUpdate.execute();
}
}
package com.avaje.tests.rawsql;
import com.avaje.tests.idkeys.db.AuditLog;
import org.junit.Test;
import com.avaje.ebean.BaseTestCase;
import com.avaje.ebean.Ebean;
import com.avaje.ebean.SqlUpdate;
public class TestInsertSqlLogging extends BaseTestCase {
@Test
public void test() {
if (isMsSqlServer()) return;
Ebean.delete(AuditLog.class, 10000);
String sql = "insert into audit_log (id, description, modified_description) values (?,?,?)";
SqlUpdate sqlUpdate = Ebean.createSqlUpdate(sql);
sqlUpdate.setParameter(1, 10000);
sqlUpdate.setParameter(2, "hello");
sqlUpdate.setParameter(3, "rob");
sqlUpdate.execute();
}
}
@@ -42,7 +42,9 @@ public class TestRawSqlOrmQuery extends BaseTestCase {
@Test
public void testFirstRowsMaxRows() throws InterruptedException, ExecutionException {
if (isMsSqlServer()) return;
ResetBasicData.reset();
RawSql rawSql =
@@ -13,6 +13,8 @@ public class TestSaveSamePK extends BaseTestCase {
@Test
public void test() {
if (isMsSqlServer()) return;
// delete in case we are running multiple times without full db drop
Ebean.delete(TSMaster.class, 10000);