/* | |
* Licensed to the Apache Software Foundation (ASF) under one | |
* or more contributor license agreements. See the NOTICE file | |
* distributed with this work for additional information | |
* regarding copyright ownership. The ASF licenses this file | |
* to you under the Apache License, Version 2.0 (the | |
* "License"); you may not use this file except in compliance | |
* with the License. You may obtain a copy of the License at | |
* | |
* http://www.apache.org/licenses/LICENSE-2.0 | |
* | |
* Unless required by applicable law or agreed to in writing, | |
* software distributed under the License is distributed on an | |
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY | |
* KIND, either express or implied. See the License for the | |
* specific language governing permissions and limitations | |
* under the License. | |
*/ | |
package org.apache.openjpa.persistence.kernel; | |
import java.lang.reflect.Array; | |
import java.text.Collator; | |
import java.util.Arrays; | |
import java.util.Comparator; | |
import java.util.Date; | |
import org.apache.openjpa.persistence.kernel.common.apps.ArraysTest; | |
import org.apache.openjpa.persistence.common.utils.AbstractTestCase; | |
import junit.framework.AssertionFailedError; | |
import org.apache.openjpa.persistence.OpenJPAEntityManager; | |
/** | |
* Test varying kinds of array values. | |
* | |
* @author Marc Prud'hommeaux | |
* @author Abe White | |
*/ | |
public class TestArrayValues2 extends BaseKernelTest { | |
private static double DOUBLE_PRECISION = 0.01D; | |
public static float FLOAT_PRECISION = 0.01F; | |
public void testStringArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
String[] array = new String[max]; | |
for (int i = 0; i < max; i++) | |
array[i] = randomString(); | |
saveArray(array, false, false); | |
} | |
public void testLongArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
Long[] array = new Long[max]; | |
for (int i = 0; i < max; i++) | |
array[i] = randomLong(); | |
try { | |
saveArray(array, false, false); | |
} catch (AssertionFailedError afe) { | |
} | |
} | |
public void testLongPrimitiveArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
long[] array = new long[max]; | |
for (int i = 0; i < max; i++) | |
array[i] = randomLong().longValue(); | |
try { | |
saveArray(array, true, false); | |
} catch (AssertionFailedError afe) { | |
} | |
} | |
public void testShortArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
Short[] array = new Short[max]; | |
for (int i = 0; i < max; i++) | |
array[i] = randomShort(); | |
saveArray(array, false, false); | |
} | |
public void testShortPrimitiveArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
short[] array = new short[max]; | |
for (int i = 0; i < max; i++) | |
array[i] = randomShort().shortValue(); | |
saveArray(array, true, false); | |
} | |
public void testIntArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
Integer[] array = new Integer[max]; | |
for (int i = 0; i < max; i++) | |
array[i] = randomInt(); | |
saveArray(array, false, false); | |
} | |
public void testIntPrimitiveArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
int[] array = new int[max]; | |
for (int i = 0; i < max; i++) | |
array[i] = randomInt().intValue(); | |
saveArray(array, true, false); | |
} | |
// FixMe: Both tests hangs on Mysql | |
/*public void testByteArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
Byte[] array = new Byte[max]; | |
for (int i = 0; i < max; i++) | |
array[i] = randomByte(); | |
saveArray(array, false, false); | |
} | |
public void testBytePrimitiveArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
byte[] array = new byte[max]; | |
for (int i = 0; i < max; i++) | |
array[i] = randomByte().byteValue(); | |
saveArray(array, true, false); | |
}*/ | |
public void testBooleanArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
Boolean[] array = new Boolean[max]; | |
for (int i = 0; i < max; i++) | |
array[i] = randomBoolean(); | |
saveArray(array, false, false); | |
} | |
public void testCharacterArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
Character[] array = new Character[max]; | |
array[0] = new Character((char) 1); | |
for (int i = 1; i < max; i++) | |
array[i] = randomChar(); | |
saveArray(array, false, false); | |
} | |
public void testCharacterPrimitiveArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
char[] array = new char[max]; | |
array[0] = 1; | |
for (int i = 1; i < max; i++) | |
array[i] = randomChar().charValue(); | |
saveArray(array, true, false); | |
} | |
public void testCharacterPrimitiveClobArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
char[] array = new char[max]; | |
array[0] = 1; | |
for (int i = 1; i < max; i++) | |
array[i] = randomChar().charValue(); | |
saveArray(array, true, true); | |
} | |
public void testBooleanPrimitiveArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
boolean[] array = new boolean[max]; | |
for (int i = 0; i < max; i++) | |
array[i] = randomBoolean().booleanValue(); | |
saveArray(array, true, false); | |
} | |
public void testFloatArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
Float[] array = new Float[max]; | |
for (int i = 0; i < max; i++) | |
array[i] = randomFloat(); | |
saveArray(array, false, false); | |
} | |
public void testFloatPrimitiveArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
float[] array = new float[max]; | |
for (int i = 0; i < max; i++) | |
array[i] = randomFloat().floatValue(); | |
saveArray(array, true, false); | |
} | |
public void testDoubleArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
Double[] array = new Double[max]; | |
for (int i = 0; i < max; i++) | |
array[i] = randomDouble(); | |
saveArray(array, false, false); | |
} | |
public void testDoublePrimitiveArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
double[] array = new double[max]; | |
for (int i = 0; i < max; i++) | |
array[i] = randomDouble().doubleValue(); | |
saveArray(array, true, false); | |
} | |
public void testDateArray() | |
throws Exception { | |
int max = ((int) (Math.random() * 20)) + 5; | |
Date[] array = new Date[max]; | |
for (int i = 0; i < max; i++) | |
array[i] = randomDate(); | |
saveArray(array, false, false); | |
} | |
/*Fix Me aokeke - Takes a lot of time to run */ | |
// public void testFirstClassObjectArray()throws Exception | |
// { | |
// int max = ((int) (Math.random() * 20)) + 5; | |
// ArraysTest[] array = new ArraysTest[max]; | |
// for (int i = 0; i < max; i++) | |
// array[i] = new ArraysTest(); | |
// saveArray(array, false, false); | |
// } | |
private void saveArray(Object array, boolean primitive, boolean lob) | |
throws Exception { | |
try { | |
saveArrayInternal(array, primitive, lob); | |
} catch (Exception e) { | |
throw e; | |
} catch (Error error) { | |
throw error; | |
} finally { | |
// | |
} | |
} | |
private void saveArrayInternal(Object vals, boolean primitive, boolean lob) | |
throws Exception { | |
Object[] array; | |
if (primitive) | |
array = convertPrimitiveArray(vals); | |
else | |
array = (Object[]) vals; | |
Arrays.sort(array, new TestArraySorter()); | |
OpenJPAEntityManager pm = | |
(OpenJPAEntityManager) currentEntityManager(); | |
startTx(pm); | |
ArraysTest test = new ArraysTest(); | |
pm.persist(test); | |
int testID = test.getId(); | |
setGetTestArray(test, vals, primitive, lob, true); | |
endTx(pm); | |
pm = (OpenJPAEntityManager) currentEntityManager(); | |
startTx(pm); | |
ArraysTest retrievedObject = pm.find(ArraysTest.class, testID); | |
Object retrievedVals = setGetTestArray(retrievedObject, vals, | |
primitive, lob, false); | |
Object[] retrievedArray; | |
if (primitive) | |
retrievedArray = convertPrimitiveArray(retrievedVals); | |
else | |
retrievedArray = (Object[]) retrievedVals; | |
assertNotNull(retrievedArray); | |
assertTrue(array.length != 0); | |
assertEquals(array.length, retrievedArray.length); | |
assertNotNull(array[0]); | |
assertNotNull(retrievedArray[0]); | |
// make sure the classes of the keys are the same. | |
assertEquals(array[0].getClass(), retrievedArray[0].getClass()); | |
Arrays.sort(retrievedArray, new TestArraySorter()); | |
for (int i = 0; i < array.length; i++) | |
assertClassAndValueEquals(array[i], retrievedArray[i]); | |
pm.remove(retrievedObject); | |
endTx(pm); | |
} | |
private Object[] convertPrimitiveArray(Object array) throws Exception { | |
int length = Array.getLength(array); | |
Class type = Array.get(array, 0).getClass(); | |
Object[] copy = (Object[]) Array.newInstance(type, length); | |
for (int i = 0; i < length; i++) | |
copy[i] = Array.get(array, i); | |
return copy; | |
} | |
private void assertClassAndValueEquals(Object o1, Object o2) { | |
assertTrue("First object was null", o1 != null); | |
assertTrue("Second object was null", o2 != null); | |
assertTrue("Types did not match (class1=" | |
+ o1.getClass().getName() + ", class2=" | |
+ o2.getClass().getName() + ")", | |
o1.getClass().isAssignableFrom(o2.getClass())); | |
// floats and doubles are a little special: we only | |
// compare them to a certain precision, after which | |
// we give up. | |
if (o1 instanceof Double) | |
assertEquals(((Double) o1).doubleValue(), | |
((Double) o2).doubleValue(), | |
DOUBLE_PRECISION); | |
else if (o1 instanceof Float) | |
assertEquals(((Float) o1).floatValue(), | |
((Float) o2).floatValue(), | |
FLOAT_PRECISION); | |
else | |
assertEquals("Object did not match (class1=" | |
+ o1.getClass().getName() + ", class2=" | |
+ o2.getClass().getName() + ")", | |
o1, o2); | |
} | |
/** | |
* Generic setter/getter for setting the array. | |
*/ | |
private Object setGetTestArray(ArraysTest test, Object array, | |
boolean primitive, boolean lob, boolean doSet) | |
throws Exception { | |
if (array == null) | |
return null; | |
Object first = Array.get(array, 0); | |
if (first instanceof Date) { | |
if (doSet) | |
test.setDate((Date[]) array); | |
return test.getDate(); | |
} else if (first instanceof String) { | |
if (doSet) | |
test.setString((String[]) array); | |
return test.getString(); | |
} else if (first instanceof Character) { | |
if (doSet && !primitive) | |
test.setCharacter((Character[]) array); | |
else if (doSet && !lob) | |
test.setCharacterP((char[]) array); | |
else if (doSet) | |
test.setCharacterPClob((char[]) array); | |
else if (!primitive) | |
return test.getCharacter(); | |
else if (!lob) | |
return test.getCharacterP(); | |
else | |
return test.getCharacterPClob(); | |
return null; | |
} else if (first instanceof Double) { | |
if (doSet && !primitive) | |
test.setDouble((Double[]) array); | |
else if (doSet) | |
test.setDoubleP((double[]) array); | |
else if (!primitive) | |
return test.getDouble(); | |
else | |
return test.getDoubleP(); | |
return null; | |
} else if (first instanceof Byte) { | |
if (doSet && !primitive) | |
test.setByte((Byte[]) array); | |
else if (doSet) | |
test.setByteP((byte[]) array); | |
else if (!primitive) | |
return test.getByte(); | |
else | |
return test.getByteP(); | |
return null; | |
} else if (first instanceof Float) { | |
if (doSet && !primitive) | |
test.setFloat((Float[]) array); | |
else if (doSet) | |
test.setFloatP((float[]) array); | |
else if (!primitive) | |
return test.getFloat(); | |
else | |
return test.getFloatP(); | |
return null; | |
} else if (first instanceof Long) { | |
if (doSet && !primitive) | |
test.setLong((Long[]) array); | |
else if (doSet) | |
test.setLongP((long[]) array); | |
else if (!primitive) | |
return test.getLong(); | |
else | |
return test.getLongP(); | |
return null; | |
} else if (first instanceof Integer) { | |
if (doSet && !primitive) | |
test.setInt((Integer[]) array); | |
else if (doSet) | |
test.setIntP((int[]) array); | |
else if (!primitive) | |
return test.getInt(); | |
else | |
return test.getIntP(); | |
return null; | |
} else if (first instanceof Short) { | |
if (doSet && !primitive) | |
test.setShort((Short[]) array); | |
else if (doSet) | |
test.setShortP((short[]) array); | |
else if (!primitive) | |
return test.getShort(); | |
else | |
return test.getShortP(); | |
return null; | |
} else if (first instanceof Boolean) { | |
if (doSet && !primitive) | |
test.setBoolean((Boolean[]) array); | |
else if (doSet) | |
test.setBooleanP((boolean[]) array); | |
else if (!primitive) | |
return test.getBoolean(); | |
else | |
return test.getBooleanP(); | |
return null; | |
} else if (first instanceof ArraysTest) { | |
if (doSet) | |
test.setArraysTest((ArraysTest[]) array); | |
return test.getArraysTest(); | |
} | |
fail("Unknown array type"); | |
return null; | |
} | |
private static class TestArraySorter | |
implements Comparator { | |
private Collator collator = Collator.getInstance(); | |
public int compare(Object o1, Object o2) { | |
if (o1.equals(o2)) | |
return 0; | |
if (o1 instanceof Number) { | |
return ((Number) o1).doubleValue() > | |
((Number) o2).doubleValue() ? 1 : -1; | |
} else if (o1 instanceof Date) { | |
return ((Date) o1).before((Date) o2) ? 1 : -1; | |
} else if (o1 instanceof ArraysTest) { | |
return ((ArraysTest) o1).compareTo(o2); | |
} | |
return collator.compare(o1.toString(), o2.toString()); | |
} | |
} | |
} | |