diff --git a/src/test/java/org/json/junit/EnumTest.java b/src/test/java/org/json/junit/EnumTest.java index 53ac303..cd0d8c0 100644 --- a/src/test/java/org/json/junit/EnumTest.java +++ b/src/test/java/org/json/junit/EnumTest.java @@ -10,6 +10,9 @@ import org.json.JSONArray; import org.json.JSONObject; +import org.json.junit.data.MyEnum; +import org.json.junit.data.MyEnumClass; +import org.json.junit.data.MyEnumField; import org.junit.Test; import com.jayway.jsonpath.Configuration; @@ -195,7 +198,7 @@ public void enumValueToString() { * However, an enum within another class will not be rendered * unless that class overrides default toString() */ - String expectedStr3 = "\"org.json.junit.MyEnumClass@"; + String expectedStr3 = "\"org.json.junit.data.MyEnumClass@"; myEnumClass.setMyEnum(MyEnum.VAL1); myEnumClass.setMyEnumField(MyEnumField.VAL1); String str3 = JSONObject.valueToString(myEnumClass); diff --git a/src/test/java/org/json/junit/JSONObjectLocaleTest.java b/src/test/java/org/json/junit/JSONObjectLocaleTest.java index 9c80ab6..52ef7d5 100755 --- a/src/test/java/org/json/junit/JSONObjectLocaleTest.java +++ b/src/test/java/org/json/junit/JSONObjectLocaleTest.java @@ -5,6 +5,7 @@ import java.util.*; import org.json.*; +import org.json.junit.data.MyLocaleBean; import org.junit.*; /** diff --git a/src/test/java/org/json/junit/JSONObjectTest.java b/src/test/java/org/json/junit/JSONObjectTest.java index 0e6a691..1231ec9 100644 --- a/src/test/java/org/json/junit/JSONObjectTest.java +++ b/src/test/java/org/json/junit/JSONObjectTest.java @@ -3,6 +3,7 @@ import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNotEquals; +import static org.junit.Assert.assertNotNull; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; @@ -30,6 +31,22 @@ import org.json.JSONObject; import org.json.JSONPointerException; import org.json.XML; +import org.json.junit.data.BrokenToString; +import org.json.junit.data.ExceptionalBean; +import org.json.junit.data.Fraction; +import org.json.junit.data.GenericBean; +import org.json.junit.data.GenericBeanInt; +import org.json.junit.data.MyBean; +import org.json.junit.data.MyBigNumberBean; +import org.json.junit.data.MyEnum; +import org.json.junit.data.MyEnumField; +import org.json.junit.data.MyJsonString; +import org.json.junit.data.MyNumber; +import org.json.junit.data.MyNumberContainer; +import org.json.junit.data.MyPublicClass; +import org.json.junit.data.Singleton; +import org.json.junit.data.SingletonEnum; +import org.json.junit.data.WeirdList; import org.junit.Test; import com.jayway.jsonpath.Configuration; @@ -484,7 +501,7 @@ public void jsonObjectByObjectAndNames() { @Test public void jsonObjectByResourceBundle() { JSONObject jsonObject = new - JSONObject("org.json.junit.StringsResourceBundle", + JSONObject("org.json.junit.data.StringsResourceBundle", Locale.getDefault()); // validate JSON @@ -2575,18 +2592,109 @@ public void toMap() { // assert that the new map is mutable assertTrue("Removing a key should succeed", map.remove("key3") != null); assertTrue("Map should have 2 elements", map.size() == 2); + } + + /** + * test that validates a singleton can be serialized as a bean. + */ + @Test + public void testSingletonBean() { + final JSONObject jo = new JSONObject(Singleton.getInstance()); + assertEquals(jo.keySet().toString(), 1, jo.length()); + assertEquals(0, jo.get("someInt")); + assertEquals(null, jo.opt("someString")); + + // Update the singleton values + Singleton.getInstance().setSomeInt(42); + Singleton.getInstance().setSomeString("Something"); + final JSONObject jo2 = new JSONObject(Singleton.getInstance()); + assertEquals(2, jo2.length()); + assertEquals(42, jo2.get("someInt")); + assertEquals("Something", jo2.get("someString")); + // ensure our original jo hasn't changed. + assertEquals(0, jo.get("someInt")); + assertEquals(null, jo.opt("someString")); + } + + /** + * test that validates a singleton can be serialized as a bean. + */ + @Test + public void testSingletonEnumBean() { + final JSONObject jo = new JSONObject(SingletonEnum.getInstance()); + assertEquals(jo.keySet().toString(), 1, jo.length()); + assertEquals(0, jo.get("someInt")); + assertEquals(null, jo.opt("someString")); + + // Update the singleton values + SingletonEnum.getInstance().setSomeInt(42); + SingletonEnum.getInstance().setSomeString("Something"); + final JSONObject jo2 = new JSONObject(SingletonEnum.getInstance()); + assertEquals(2, jo2.length()); + assertEquals(42, jo2.get("someInt")); + assertEquals("Something", jo2.get("someString")); + + // ensure our original jo hasn't changed. + assertEquals(0, jo.get("someInt")); + assertEquals(null, jo.opt("someString")); } /** - * test class for verifying write errors. - * @author John Aylward - * + * Test to validate that a generic class can be serialized as a bean. */ - private static class BrokenToString { - @Override - public String toString() { - throw new IllegalStateException("Something went horribly wrong!"); - } + @Test + public void testGenericBean() { + GenericBean bean = new GenericBean<>(42); + final JSONObject jo = new JSONObject(bean); + assertEquals(jo.keySet().toString(), 8, jo.length()); + assertEquals(42, jo.get("genericValue")); + assertEquals("Expected the getter to only be called once", + 1, bean.genericGetCounter); + assertEquals(0, bean.genericSetCounter); + } + + /** + * Test to validate that a generic class can be serialized as a bean. + */ + @Test + public void testGenericIntBean() { + GenericBeanInt bean = new GenericBeanInt(42); + final JSONObject jo = new JSONObject(bean); + assertEquals(jo.keySet().toString(), 9, jo.length()); + assertEquals(42, jo.get("genericValue")); + assertEquals("Expected the getter to only be called once", + 1, bean.genericGetCounter); + assertEquals(0, bean.genericSetCounter); + } + + /** + * Test to verify key limitations in the JSONObject bean serializer. + */ + @Test + public void testWierdListBean() { + WeirdList bean = new WeirdList(42, 43, 44); + final JSONObject jo = new JSONObject(bean); + // get() should have a key of 0 length + // get(int) should be ignored base on parameter count + // getInt(int) should also be ignored based on parameter count + // add(Integer) should be ignore as it doesn't start with get/is and also has a parameter + // getALL should be mapped + assertEquals("Expected 1 key to be mapped. Instead found: "+jo.keySet().toString(), + 1, jo.length()); + assertNotNull(jo.get("ALL")); + } + + /** + * Tests the exception portions of populateMap. + */ + @Test + public void testExceptionalBean() { + ExceptionalBean bean = new ExceptionalBean(); + final JSONObject jo = new JSONObject(bean); + assertEquals("Expected 1 key to be mapped. Instead found: "+jo.keySet().toString(), + 1, jo.length()); + assertTrue(jo.get("closeable") instanceof JSONObject); + assertTrue(jo.getJSONObject("closeable").has("string")); } } diff --git a/src/test/java/org/json/junit/data/BrokenToString.java b/src/test/java/org/json/junit/data/BrokenToString.java new file mode 100644 index 0000000..585d751 --- /dev/null +++ b/src/test/java/org/json/junit/data/BrokenToString.java @@ -0,0 +1,13 @@ +package org.json.junit.data; + +/** + * test class for verifying write errors. + * @author John Aylward + * + */ +public class BrokenToString { + @Override + public String toString() { + throw new IllegalStateException("Something went horribly wrong!"); + } +} \ No newline at end of file diff --git a/src/test/java/org/json/junit/data/ExceptionalBean.java b/src/test/java/org/json/junit/data/ExceptionalBean.java new file mode 100644 index 0000000..74d78a7 --- /dev/null +++ b/src/test/java/org/json/junit/data/ExceptionalBean.java @@ -0,0 +1,69 @@ +/** + * + */ +package org.json.junit.data; + +import java.io.Closeable; +import java.io.IOException; +import java.lang.reflect.InvocationTargetException; + +import org.json.JSONObject; + +/** + * Object for testing the exception handling in {@link JSONObject#populateMap}. + * + * @author John Aylward + */ +public class ExceptionalBean { + /** + * @return a closeable. + */ + public Closeable getCloseable() { + // anonymous inner class did not work... + return new MyCloseable(); + } + + /** + * @return Nothing really. Just can't be void. + * @throws IllegalAccessException + * always thrown + */ + public int getIllegalAccessException() throws IllegalAccessException { + throw new IllegalAccessException("Yup, it's illegal"); + } + + /** + * @return Nothing really. Just can't be void. + * @throws IllegalArgumentException + * always thrown + */ + public int getIllegalArgumentException() throws IllegalArgumentException { + throw new IllegalArgumentException("Yup, it's illegal"); + } + + /** + * @return Nothing really. Just can't be void. + * @throws InvocationTargetException + * always thrown + */ + public int getInvocationTargetException() throws InvocationTargetException { + throw new InvocationTargetException(new Exception("Yup, it's illegal")); + } + + /** My closeable class. */ + public static final class MyCloseable implements Closeable { + + /** + * @return a string + */ + @SuppressWarnings("unused") + public String getString() { + return "Yup, it's closeable"; + } + + @Override + public void close() throws IOException { + throw new IOException("Closing is too hard!"); + } + } +} diff --git a/src/test/java/org/json/junit/Fraction.java b/src/test/java/org/json/junit/data/Fraction.java similarity index 99% rename from src/test/java/org/json/junit/Fraction.java rename to src/test/java/org/json/junit/data/Fraction.java index d5d9eb6..c418179 100644 --- a/src/test/java/org/json/junit/Fraction.java +++ b/src/test/java/org/json/junit/data/Fraction.java @@ -1,4 +1,4 @@ -package org.json.junit; +package org.json.junit.data; import java.math.BigDecimal; import java.math.BigInteger; diff --git a/src/test/java/org/json/junit/data/GenericBean.java b/src/test/java/org/json/junit/data/GenericBean.java new file mode 100644 index 0000000..4740030 --- /dev/null +++ b/src/test/java/org/json/junit/data/GenericBean.java @@ -0,0 +1,79 @@ +package org.json.junit.data; + +import java.io.StringReader; + +/** + * + * @author John Aylward + * + * @param + * generic number value + */ +public class GenericBean> implements MyBean { + /** + * @param genericValue + * value to initiate with + */ + public GenericBean(T genericValue) { + super(); + this.genericValue = genericValue; + } + + /** */ + private T genericValue; + /** to be used by the calling test to see how often the getter is called */ + public int genericGetCounter; + /** to be used by the calling test to see how often the setter is called */ + public int genericSetCounter; + + /** @return the genericValue */ + public T getGenericValue() { + this.genericGetCounter++; + return this.genericValue; + } + + /** + * @param genericValue + * generic value to set + */ + public void setGenericValue(T genericValue) { + this.genericSetCounter++; + this.genericValue = genericValue; + } + + @Override + public Integer getIntKey() { + return Integer.valueOf(42); + } + + @Override + public Double getDoubleKey() { + return Double.valueOf(4.2); + } + + @Override + public String getStringKey() { + return "MyString Key"; + } + + @Override + public String getEscapeStringKey() { + return "\"My String with \"s"; + } + + @Override + public Boolean isTrueKey() { + return Boolean.TRUE; + } + + @Override + public Boolean isFalseKey() { + return Boolean.FALSE; + } + + @Override + public StringReader getStringReaderKey() { + return new StringReader("Some String Value in a reader"); + } + +} diff --git a/src/test/java/org/json/junit/data/GenericBeanInt.java b/src/test/java/org/json/junit/data/GenericBeanInt.java new file mode 100644 index 0000000..8f0248d --- /dev/null +++ b/src/test/java/org/json/junit/data/GenericBeanInt.java @@ -0,0 +1,42 @@ +/** + * + */ +package org.json.junit.data; + +/** + * @author john + * + */ +public class GenericBeanInt extends GenericBean { + /** */ + final char a = 'A'; + + /** @return the a */ + public char getA() { + return a; + } + + /** + * Should not be beanable + * + * @return false + */ + public boolean getable() { + return false; + } + + /** + * @param genericValue + * the value to initiate with. + */ + public GenericBeanInt(Integer genericValue) { + super(genericValue); + } + + /** override to generate a bridge method */ + @Override + public Integer getGenericValue() { + return super.getGenericValue(); + } + +} diff --git a/src/test/java/org/json/junit/MyBean.java b/src/test/java/org/json/junit/data/MyBean.java similarity index 85% rename from src/test/java/org/json/junit/MyBean.java rename to src/test/java/org/json/junit/data/MyBean.java index 53d150a..3190981 100644 --- a/src/test/java/org/json/junit/MyBean.java +++ b/src/test/java/org/json/junit/data/MyBean.java @@ -1,11 +1,11 @@ -package org.json.junit; +package org.json.junit.data; import java.io.*; /** * Used in testing when Bean behavior is needed */ -interface MyBean { +public interface MyBean { public Integer getIntKey(); public Double getDoubleKey(); public String getStringKey(); diff --git a/src/test/java/org/json/junit/MyBigNumberBean.java b/src/test/java/org/json/junit/data/MyBigNumberBean.java similarity index 72% rename from src/test/java/org/json/junit/MyBigNumberBean.java rename to src/test/java/org/json/junit/data/MyBigNumberBean.java index 0ca1870..934dfee 100644 --- a/src/test/java/org/json/junit/MyBigNumberBean.java +++ b/src/test/java/org/json/junit/data/MyBigNumberBean.java @@ -1,11 +1,11 @@ -package org.json.junit; +package org.json.junit.data; import java.math.*; /** * Used in testing when a Bean containing big numbers is needed */ -interface MyBigNumberBean { +public interface MyBigNumberBean { public BigInteger getBigInteger(); public BigDecimal getBigDecimal(); } \ No newline at end of file diff --git a/src/test/java/org/json/junit/MyEnum.java b/src/test/java/org/json/junit/data/MyEnum.java similarity index 76% rename from src/test/java/org/json/junit/MyEnum.java rename to src/test/java/org/json/junit/data/MyEnum.java index 0952bc2..50d9a4f 100644 --- a/src/test/java/org/json/junit/MyEnum.java +++ b/src/test/java/org/json/junit/data/MyEnum.java @@ -1,4 +1,4 @@ -package org.json.junit; +package org.json.junit.data; /** * An enum with no methods or data diff --git a/src/test/java/org/json/junit/MyEnumClass.java b/src/test/java/org/json/junit/data/MyEnumClass.java similarity index 94% rename from src/test/java/org/json/junit/MyEnumClass.java rename to src/test/java/org/json/junit/data/MyEnumClass.java index 8e71663..4d403c8 100644 --- a/src/test/java/org/json/junit/MyEnumClass.java +++ b/src/test/java/org/json/junit/data/MyEnumClass.java @@ -1,4 +1,4 @@ -package org.json.junit; +package org.json.junit.data; /** * this is simply a class that contains some enum instances diff --git a/src/test/java/org/json/junit/MyEnumField.java b/src/test/java/org/json/junit/data/MyEnumField.java similarity index 95% rename from src/test/java/org/json/junit/MyEnumField.java rename to src/test/java/org/json/junit/data/MyEnumField.java index f0833ef..60e89de 100644 --- a/src/test/java/org/json/junit/MyEnumField.java +++ b/src/test/java/org/json/junit/data/MyEnumField.java @@ -1,4 +1,4 @@ -package org.json.junit; +package org.json.junit.data; /** * An enum that contains getters and some internal fields diff --git a/src/test/java/org/json/junit/MyJsonString.java b/src/test/java/org/json/junit/data/MyJsonString.java similarity index 67% rename from src/test/java/org/json/junit/MyJsonString.java rename to src/test/java/org/json/junit/data/MyJsonString.java index 4e63693..4ddde53 100644 --- a/src/test/java/org/json/junit/MyJsonString.java +++ b/src/test/java/org/json/junit/data/MyJsonString.java @@ -1,11 +1,11 @@ -package org.json.junit; +package org.json.junit.data; import org.json.*; /** * Used in testing when a JSONString is needed */ -class MyJsonString implements JSONString { +public class MyJsonString implements JSONString { @Override public String toJSONString() { diff --git a/src/test/java/org/json/junit/MyLocaleBean.java b/src/test/java/org/json/junit/data/MyLocaleBean.java similarity index 88% rename from src/test/java/org/json/junit/MyLocaleBean.java rename to src/test/java/org/json/junit/data/MyLocaleBean.java index 0d68c39..846e1c5 100755 --- a/src/test/java/org/json/junit/MyLocaleBean.java +++ b/src/test/java/org/json/junit/data/MyLocaleBean.java @@ -1,4 +1,4 @@ -package org.json.junit; +package org.json.junit.data; public class MyLocaleBean { private final String id = "beanId"; diff --git a/src/test/java/org/json/junit/MyNumber.java b/src/test/java/org/json/junit/data/MyNumber.java similarity index 98% rename from src/test/java/org/json/junit/MyNumber.java rename to src/test/java/org/json/junit/data/MyNumber.java index 243a967..4b625af 100644 --- a/src/test/java/org/json/junit/MyNumber.java +++ b/src/test/java/org/json/junit/data/MyNumber.java @@ -1,4 +1,4 @@ -package org.json.junit; +package org.json.junit.data; import java.math.BigDecimal; diff --git a/src/test/java/org/json/junit/MyNumberContainer.java b/src/test/java/org/json/junit/data/MyNumberContainer.java similarity index 90% rename from src/test/java/org/json/junit/MyNumberContainer.java rename to src/test/java/org/json/junit/data/MyNumberContainer.java index 524f318..6527652 100644 --- a/src/test/java/org/json/junit/MyNumberContainer.java +++ b/src/test/java/org/json/junit/data/MyNumberContainer.java @@ -1,4 +1,4 @@ -package org.json.junit; +package org.json.junit.data; /** * Class that holds our MyNumber override as a property. diff --git a/src/test/java/org/json/junit/MyPublicClass.java b/src/test/java/org/json/junit/data/MyPublicClass.java similarity index 87% rename from src/test/java/org/json/junit/MyPublicClass.java rename to src/test/java/org/json/junit/data/MyPublicClass.java index e483d4c..1f30386 100644 --- a/src/test/java/org/json/junit/MyPublicClass.java +++ b/src/test/java/org/json/junit/data/MyPublicClass.java @@ -1,4 +1,4 @@ -package org.json.junit; +package org.json.junit.data; /** * Need a class with some public data members for testing diff --git a/src/test/java/org/json/junit/data/Singleton.java b/src/test/java/org/json/junit/data/Singleton.java new file mode 100644 index 0000000..36a9824 --- /dev/null +++ b/src/test/java/org/json/junit/data/Singleton.java @@ -0,0 +1,91 @@ +package org.json.junit.data; + +/** + * Sample singleton for use with bean testing. + * + * @author John Aylward + * + */ +public final class Singleton { + /** */ + private int someInt; + /** */ + private String someString; + /** single instance. */ + private static final Singleton INSTANCE = new Singleton(); + + /** @return the singleton instance. */ + public static final Singleton getInstance() { + return INSTANCE; + } + + /** */ + private Singleton() { + if (INSTANCE != null) { + throw new IllegalStateException("Already instantiated"); + } + } + + @Override + protected Object clone() throws CloneNotSupportedException { + return INSTANCE; + } + + /** @return someInt */ + public int getSomeInt() { + return someInt; + } + + /** + * sets someInt. + * + * @param someInt + * the someInt to set + */ + public void setSomeInt(int someInt) { + this.someInt = someInt; + } + + /** @return someString */ + public String getSomeString() { + return someString; + } + + /** + * sets someString. + * + * @param someString + * the someString to set + */ + public void setSomeString(String someString) { + this.someString = someString; + } + + @Override + public int hashCode() { + final int prime = 31; + int result = 1; + result = prime * result + someInt; + result = prime * result + ((someString == null) ? 0 : someString.hashCode()); + return result; + } + + @Override + public boolean equals(Object obj) { + if (this == obj) + return true; + if (obj == null) + return false; + if (getClass() != obj.getClass()) + return false; + Singleton other = (Singleton) obj; + if (someInt != other.someInt) + return false; + if (someString == null) { + if (other.someString != null) + return false; + } else if (!someString.equals(other.someString)) + return false; + return true; + } +} diff --git a/src/test/java/org/json/junit/data/SingletonEnum.java b/src/test/java/org/json/junit/data/SingletonEnum.java new file mode 100644 index 0000000..8147cc6 --- /dev/null +++ b/src/test/java/org/json/junit/data/SingletonEnum.java @@ -0,0 +1,62 @@ +package org.json.junit.data; + +/** + * Sample singleton done as an Enum for use with bean testing. + * + * @author John Aylward + * + */ +public enum SingletonEnum { + /** + * the singleton instance. + */ + INSTANCE; + /** */ + private int someInt; + /** */ + private String someString; + + /** single instance. */ + + /** + * @return the singleton instance. I a real application, I'd hope no one did + * this to an enum singleton. + */ + public static final SingletonEnum getInstance() { + return INSTANCE; + } + + /** */ + private SingletonEnum() { + } + + /** @return someInt */ + public int getSomeInt() { + return someInt; + } + + /** + * sets someInt. + * + * @param someInt + * the someInt to set + */ + public void setSomeInt(int someInt) { + this.someInt = someInt; + } + + /** @return someString */ + public String getSomeString() { + return someString; + } + + /** + * sets someString. + * + * @param someString + * the someString to set + */ + public void setSomeString(String someString) { + this.someString = someString; + } +} diff --git a/src/test/java/org/json/junit/StringsResourceBundle.java b/src/test/java/org/json/junit/data/StringsResourceBundle.java similarity index 93% rename from src/test/java/org/json/junit/StringsResourceBundle.java rename to src/test/java/org/json/junit/data/StringsResourceBundle.java index d04aeaf..4479350 100644 --- a/src/test/java/org/json/junit/StringsResourceBundle.java +++ b/src/test/java/org/json/junit/data/StringsResourceBundle.java @@ -1,4 +1,4 @@ -package org.json.junit; +package org.json.junit.data; import java.util.*; diff --git a/src/test/java/org/json/junit/data/WeirdList.java b/src/test/java/org/json/junit/data/WeirdList.java new file mode 100644 index 0000000..77cd17f --- /dev/null +++ b/src/test/java/org/json/junit/data/WeirdList.java @@ -0,0 +1,67 @@ +/** + * + */ +package org.json.junit.data; + +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; + +/** + * @author John Aylward + */ +public class WeirdList { + /** */ + private final List list = new ArrayList<>(); + + /** + * @param vals + */ + public WeirdList(Integer... vals) { + this.list.addAll(Arrays.asList(vals)); + } + + /** + * @return a copy of the list + */ + public List get() { + return new ArrayList<>(this.list); + } + + /** + * @return a copy of the list + */ + public List getALL() { + return new ArrayList<>(this.list); + } + + /** + * get a value at an index. + * + * @param i + * index to get + * @return the value at the index + */ + public Integer get(int i) { + return this.list.get(i); + } + + /** + * get a value at an index. + * + * @param i + * index to get + * @return the value at the index + */ + public int getInt(int i) { + return this.list.get(i); + } + + /** + * @param value + * new value to add to the end of the list + */ + public void add(Integer value) { + this.list.add(value); + } +} \ No newline at end of file