From 828f231adfe9cad8ff5a7da058489c9c096657d7 Mon Sep 17 00:00:00 2001 From: highsource Date: Wed, 16 Dec 2015 19:49:08 +0100 Subject: [PATCH] Issue #42. --- .../plugin/util/StrategyClassUtils.java | 17 +++++- tests/superclass/.gitignore | 2 + tests/superclass/a/.gitignore | 4 ++ tests/superclass/a/pom.xml | 38 ++++++++++++ tests/superclass/a/src/main/resources/a.xsd | 11 ++++ .../a/src/main/resources/binding.xjb | 15 +++++ tests/superclass/b/.gitignore | 4 ++ tests/superclass/b/pom.xml | 61 +++++++++++++++++++ .../b/src/main/resources/binding.xjb | 32 ++++++++++ .../b/src/main/resources/schema.xsd | 15 +++++ .../test/superclass/b/tests/CopyToTest.java | 20 ++++++ .../test/superclass/b/tests/RunPlugins.java | 42 +++++++++++++ tests/superclass/b/src/test/samples/1.xml | 8 +++ tests/superclass/pom.xml | 20 ++++++ .../jvnet/jaxb2_commons/util/JClassUtils.java | 45 ++++++++++++++ .../util/tests/JClassUtilsTest.java | 48 +++++++++++++++ 16 files changed, 379 insertions(+), 3 deletions(-) create mode 100644 tests/superclass/.gitignore create mode 100644 tests/superclass/a/.gitignore create mode 100644 tests/superclass/a/pom.xml create mode 100644 tests/superclass/a/src/main/resources/a.xsd create mode 100644 tests/superclass/a/src/main/resources/binding.xjb create mode 100644 tests/superclass/b/.gitignore create mode 100644 tests/superclass/b/pom.xml create mode 100644 tests/superclass/b/src/main/resources/binding.xjb create mode 100644 tests/superclass/b/src/main/resources/schema.xsd create mode 100644 tests/superclass/b/src/test/java/org/jvnet/jaxb2_commons/test/superclass/b/tests/CopyToTest.java create mode 100644 tests/superclass/b/src/test/java/org/jvnet/jaxb2_commons/test/superclass/b/tests/RunPlugins.java create mode 100644 tests/superclass/b/src/test/samples/1.xml create mode 100644 tests/superclass/pom.xml create mode 100644 tools/src/main/java/org/jvnet/jaxb2_commons/util/JClassUtils.java create mode 100644 tools/src/test/java/org/jvnet/jaxb2_commons/util/tests/JClassUtilsTest.java diff --git a/basic/src/main/java/org/jvnet/jaxb2_commons/plugin/util/StrategyClassUtils.java b/basic/src/main/java/org/jvnet/jaxb2_commons/plugin/util/StrategyClassUtils.java index 0900fca2..7896decd 100644 --- a/basic/src/main/java/org/jvnet/jaxb2_commons/plugin/util/StrategyClassUtils.java +++ b/basic/src/main/java/org/jvnet/jaxb2_commons/plugin/util/StrategyClassUtils.java @@ -5,6 +5,7 @@ import java.lang.reflect.Modifier; import org.jvnet.jaxb2_commons.plugin.Ignoring; +import org.jvnet.jaxb2_commons.util.JClassUtils; import com.sun.codemodel.JClass; import com.sun.codemodel.JCodeModel; @@ -55,6 +56,14 @@ public static JExpression createStrategyInstanceExpression( public static Boolean superClassImplements(ClassOutline classOutline, Ignoring ignoring, Class theInterface) { + if (classOutline.implClass != null + && classOutline.implClass._extends() != null) { + if (JClassUtils.isInstanceOf(classOutline.implClass._extends(), + theInterface)) { + return Boolean.TRUE; + } + } + if (classOutline.target.getBaseClass() != null) { if (!ignoring.isIgnored(classOutline.parent().getClazz( classOutline.target.getBaseClass()))) { @@ -62,7 +71,9 @@ public static Boolean superClassImplements(ClassOutline classOutline, } else { return Boolean.FALSE; } - } else if (classOutline.target.getRefBaseClass() != null) { + } + + if (classOutline.target.getRefBaseClass() != null) { try { if (theInterface.isAssignableFrom(Class .forName(classOutline.target.getRefBaseClass() @@ -75,9 +86,9 @@ public static Boolean superClassImplements(ClassOutline classOutline, // We'll assume it does implement return Boolean.TRUE; } - } else { - return null; } + // Unknown + return null; } public static Boolean superClassNotIgnored(ClassOutline classOutline, diff --git a/tests/superclass/.gitignore b/tests/superclass/.gitignore new file mode 100644 index 00000000..a5a68e4f --- /dev/null +++ b/tests/superclass/.gitignore @@ -0,0 +1,2 @@ +.settings +.project \ No newline at end of file diff --git a/tests/superclass/a/.gitignore b/tests/superclass/a/.gitignore new file mode 100644 index 00000000..6ebe318f --- /dev/null +++ b/tests/superclass/a/.gitignore @@ -0,0 +1,4 @@ +.settings +.project +.classpath +target diff --git a/tests/superclass/a/pom.xml b/tests/superclass/a/pom.xml new file mode 100644 index 00000000..baac488c --- /dev/null +++ b/tests/superclass/a/pom.xml @@ -0,0 +1,38 @@ + + 4.0.0 + + org.jvnet.jaxb2_commons + jaxb2-basics-test-superclass + 0.10.1-SNAPSHOT + + jaxb2-basics-test-superclass-a + jar + JAXB2 Basics - Test [superclass-a] + + test + + + org.jvnet.jaxb2.maven2 + maven-jaxb2-plugin + + true + + -XtoString + -Xequals + -XhashCode + -Xcopyable + -Xmergeable + + + + org.jvnet.jaxb2_commons + jaxb2-basics + + + + + + + \ No newline at end of file diff --git a/tests/superclass/a/src/main/resources/a.xsd b/tests/superclass/a/src/main/resources/a.xsd new file mode 100644 index 00000000..777ff079 --- /dev/null +++ b/tests/superclass/a/src/main/resources/a.xsd @@ -0,0 +1,11 @@ + + + + + + + \ No newline at end of file diff --git a/tests/superclass/a/src/main/resources/binding.xjb b/tests/superclass/a/src/main/resources/binding.xjb new file mode 100644 index 00000000..e6250e90 --- /dev/null +++ b/tests/superclass/a/src/main/resources/binding.xjb @@ -0,0 +1,15 @@ + + + + + + + + diff --git a/tests/superclass/b/.gitignore b/tests/superclass/b/.gitignore new file mode 100644 index 00000000..6ebe318f --- /dev/null +++ b/tests/superclass/b/.gitignore @@ -0,0 +1,4 @@ +.settings +.project +.classpath +target diff --git a/tests/superclass/b/pom.xml b/tests/superclass/b/pom.xml new file mode 100644 index 00000000..8196811e --- /dev/null +++ b/tests/superclass/b/pom.xml @@ -0,0 +1,61 @@ + + 4.0.0 + + org.jvnet.jaxb2_commons + jaxb2-basics-test-superclass + 0.10.1-SNAPSHOT + + jaxb2-basics-test-superclass-b + jar + JAXB2 Basics - Test [superclass-b] + + + org.jvnet.jaxb2_commons + jaxb2-basics-test-superclass-a + ${project.version} + + + org.jvnet.jaxb2_commons + jaxb2-basics + test + + + org.jvnet.jaxb2.maven2 + maven-jaxb2-plugin-testing + test + + + + test + + + org.jvnet.jaxb2.maven2 + maven-jaxb2-plugin + + true + + -XtoString + -Xequals + -XhashCode + -Xcopyable + -Xmergeable + + + + org.jvnet.jaxb2_commons + jaxb2-basics + + + + + org.jvnet.jaxb2_commons + jaxb2-basics-test-superclass-a + + + + + + + \ No newline at end of file diff --git a/tests/superclass/b/src/main/resources/binding.xjb b/tests/superclass/b/src/main/resources/binding.xjb new file mode 100644 index 00000000..d5b2a7a1 --- /dev/null +++ b/tests/superclass/b/src/main/resources/binding.xjb @@ -0,0 +1,32 @@ + + + + + + + + + + + + + + + diff --git a/tests/superclass/b/src/main/resources/schema.xsd b/tests/superclass/b/src/main/resources/schema.xsd new file mode 100644 index 00000000..a498dad4 --- /dev/null +++ b/tests/superclass/b/src/main/resources/schema.xsd @@ -0,0 +1,15 @@ + + + + + + + + + + + \ No newline at end of file diff --git a/tests/superclass/b/src/test/java/org/jvnet/jaxb2_commons/test/superclass/b/tests/CopyToTest.java b/tests/superclass/b/src/test/java/org/jvnet/jaxb2_commons/test/superclass/b/tests/CopyToTest.java new file mode 100644 index 00000000..13c11485 --- /dev/null +++ b/tests/superclass/b/src/test/java/org/jvnet/jaxb2_commons/test/superclass/b/tests/CopyToTest.java @@ -0,0 +1,20 @@ +package org.jvnet.jaxb2_commons.test.superclass.b.tests; + +import org.junit.Assert; +import org.junit.Test; +import org.jvnet.jaxb2_commons.test.superclass.b.AnotherObjectType; + +public class CopyToTest { + + @Test + public void correctlyCopies() { + final AnotherObjectType source = new AnotherObjectType(); + source.setId("Id"); + source.setData("Data"); + final AnotherObjectType target = (AnotherObjectType) source.clone(); + Assert.assertEquals("Id", target.getId()); + Assert.assertEquals("Data", target.getData()); + Assert.assertEquals(source, target); + Assert.assertEquals(source.hashCode(), target.hashCode()); + } +} diff --git a/tests/superclass/b/src/test/java/org/jvnet/jaxb2_commons/test/superclass/b/tests/RunPlugins.java b/tests/superclass/b/src/test/java/org/jvnet/jaxb2_commons/test/superclass/b/tests/RunPlugins.java new file mode 100644 index 00000000..5411e7f0 --- /dev/null +++ b/tests/superclass/b/src/test/java/org/jvnet/jaxb2_commons/test/superclass/b/tests/RunPlugins.java @@ -0,0 +1,42 @@ +package org.jvnet.jaxb2_commons.test.superclass.b.tests; + +import java.io.File; +import java.net.URL; + +import org.junit.Before; +import org.junit.Test; + +import com.sun.codemodel.JCodeModel; +import com.sun.tools.xjc.ConsoleErrorReporter; +import com.sun.tools.xjc.ModelLoader; +import com.sun.tools.xjc.Options; +import com.sun.tools.xjc.model.Model; + +public class RunPlugins { + + @Before + public void setUp() { + System.setProperty("javax.xml.accessExternalSchema", "all"); + } + + @Test + public void compilesSchema() throws Exception { + + new File("target/generated-sources/xjc").mkdirs(); + + URL schema = getClass().getResource("/schema.xsd"); + URL binding = getClass().getResource("/binding.xjb"); + final String[] arguments = new String[] { "-xmlschema", + schema.toExternalForm(), "-b", binding.toExternalForm(), "-d", + "target/generated-sources/xjc", "-extension", "-XtoString", + "-Xequals", "-XhashCode", "-Xcopyable", "-Xmergeable" }; + + Options options = new Options(); + options.parseArguments(arguments); + ConsoleErrorReporter receiver = new ConsoleErrorReporter(); + Model model = ModelLoader.load(options, new JCodeModel(), receiver); + model.generateCode(options, receiver); + com.sun.codemodel.CodeWriter cw = options.createCodeWriter(); + model.codeModel.build(cw); + } +} diff --git a/tests/superclass/b/src/test/samples/1.xml b/tests/superclass/b/src/test/samples/1.xml new file mode 100644 index 00000000..3922598a --- /dev/null +++ b/tests/superclass/b/src/test/samples/1.xml @@ -0,0 +1,8 @@ + + + test + + + test + + \ No newline at end of file diff --git a/tests/superclass/pom.xml b/tests/superclass/pom.xml new file mode 100644 index 00000000..3fdcd0da --- /dev/null +++ b/tests/superclass/pom.xml @@ -0,0 +1,20 @@ + + 4.0.0 + + org.jvnet.jaxb2_commons + jaxb2-basics-tests + 0.10.1-SNAPSHOT + + jaxb2-basics-test-superclass + pom + JAXB2 Basics - Test [superclass] + + a + b + + + test + + \ No newline at end of file diff --git a/tools/src/main/java/org/jvnet/jaxb2_commons/util/JClassUtils.java b/tools/src/main/java/org/jvnet/jaxb2_commons/util/JClassUtils.java new file mode 100644 index 00000000..3aa723e6 --- /dev/null +++ b/tools/src/main/java/org/jvnet/jaxb2_commons/util/JClassUtils.java @@ -0,0 +1,45 @@ +package org.jvnet.jaxb2_commons.util; + +import java.util.Iterator; + +import org.apache.commons.lang3.Validate; + +import com.sun.codemodel.JClass; + +public class JClassUtils { + + public static boolean isInstanceOf(JClass _class, + Class _interface) { + Validate.notNull(_class); + Validate.notNull(_interface); + + final String className = _class.fullName(); + + try { + if (_interface.isAssignableFrom(Class.forName(className))) { + return true; + } + } catch (ClassNotFoundException cnfex) { + // Unknown + } + + final JClass superClass = _class._extends(); + if (superClass != null) { + if (isInstanceOf(superClass, _interface)) { + return true; + } + } + + for (final Iterator implementsIterator = _class + ._implements(); implementsIterator.hasNext();) { + final JClass superInterface = implementsIterator.next(); + + if (isInstanceOf(superInterface, _interface)) { + return true; + } + } + + return false; + } + +} diff --git a/tools/src/test/java/org/jvnet/jaxb2_commons/util/tests/JClassUtilsTest.java b/tools/src/test/java/org/jvnet/jaxb2_commons/util/tests/JClassUtilsTest.java new file mode 100644 index 00000000..c7120bc5 --- /dev/null +++ b/tools/src/test/java/org/jvnet/jaxb2_commons/util/tests/JClassUtilsTest.java @@ -0,0 +1,48 @@ +package org.jvnet.jaxb2_commons.util.tests; + +import java.io.Externalizable; +import java.util.Collection; + +import org.junit.Assert; +import org.junit.Test; +import org.jvnet.jaxb2_commons.util.JClassUtils; + +import com.sun.codemodel.JClass; +import com.sun.codemodel.JClassAlreadyExistsException; +import com.sun.codemodel.JCodeModel; +import com.sun.codemodel.JDefinedClass; + +public class JClassUtilsTest { + + private JCodeModel codeModel = new JCodeModel(); + + @Test + public void correctlyChecksIsInstanceOf() + throws JClassAlreadyExistsException { + + final JClass arrayList = codeModel.ref("java.util.ArrayList"); + Assert.assertTrue(JClassUtils.isInstanceOf(arrayList, Collection.class)); + final JDefinedClass subArrayList = codeModel._class("SubArrayList"); + subArrayList._extends(arrayList); + Assert.assertTrue(JClassUtils.isInstanceOf(subArrayList, + Collection.class)); + + final JClass subArrayListOfObjects = subArrayList.narrow(Object.class); + Assert.assertTrue(JClassUtils.isInstanceOf(subArrayListOfObjects, + Collection.class)); + + final JDefinedClass subExternalizable = codeModel + ._class("SubExternalizable"); + subExternalizable._implements(Externalizable.class); + Assert.assertTrue(JClassUtils.isInstanceOf(subExternalizable, + Externalizable.class)); + + subArrayList._implements(subExternalizable); + Assert.assertTrue(JClassUtils.isInstanceOf(subArrayList, + Externalizable.class)); + + Assert.assertFalse(JClassUtils.isInstanceOf(codeModel.NULL, + Collection.class)); + + } +}