Repository: ignite
Updated Branches:
  refs/heads/ignite-1.5 c12d17e2a -> d2008c53d


IGNITE-2098 - Added test for java Proxy - Fixes #301.

Signed-off-by: Alexey Goncharuk <[email protected]>


Project: http://git-wip-us.apache.org/repos/asf/ignite/repo
Commit: http://git-wip-us.apache.org/repos/asf/ignite/commit/d2008c53
Tree: http://git-wip-us.apache.org/repos/asf/ignite/tree/d2008c53
Diff: http://git-wip-us.apache.org/repos/asf/ignite/diff/d2008c53

Branch: refs/heads/ignite-1.5
Commit: d2008c53d2d3ab25ba19b018081f88798140a274
Parents: c12d17e
Author: Alexey Goncharuk <[email protected]>
Authored: Thu Dec 10 12:51:16 2015 +0300
Committer: Alexey Goncharuk <[email protected]>
Committed: Thu Dec 10 12:51:16 2015 +0300

----------------------------------------------------------------------
 .../portable/PortableClassDescriptor.java       |  14 +-
 .../portable/BinaryMarshallerSelfTest.java      | 198 +++++++++++++++++++
 2 files changed, 207 insertions(+), 5 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/ignite/blob/d2008c53/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableClassDescriptor.java
----------------------------------------------------------------------
diff --git 
a/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableClassDescriptor.java
 
b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableClassDescriptor.java
index 2dda9eb..9a65da1 100644
--- 
a/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableClassDescriptor.java
+++ 
b/modules/core/src/main/java/org/apache/ignite/internal/portable/PortableClassDescriptor.java
@@ -42,10 +42,12 @@ import org.apache.ignite.binary.BinaryObjectException;
 import org.apache.ignite.binary.BinarySerializer;
 import org.apache.ignite.binary.Binarylizable;
 import org.apache.ignite.internal.processors.cache.CacheObjectImpl;
+import org.apache.ignite.internal.util.GridUnsafe;
 import org.apache.ignite.internal.util.typedef.internal.U;
 import org.apache.ignite.marshaller.MarshallerExclusions;
 import org.apache.ignite.marshaller.optimized.OptimizedMarshaller;
 import org.jetbrains.annotations.Nullable;
+import sun.misc.Unsafe;
 
 import static java.lang.reflect.Modifier.isStatic;
 import static java.lang.reflect.Modifier.isTransient;
@@ -55,6 +57,9 @@ import static java.lang.reflect.Modifier.isTransient;
  */
 public class PortableClassDescriptor {
     /** */
+    public static final Unsafe UNSAFE = GridUnsafe.unsafe();
+
+    /** */
     private final PortableContext ctx;
 
     /** */
@@ -228,7 +233,8 @@ public class PortableClassDescriptor {
                 break;
 
             case OBJECT:
-                ctor = constructor(cls);
+                // Must not use constructor to honor transient fields 
semantics.
+                ctor = null;
                 ArrayList<BinaryFieldAccessor> fields0 = new ArrayList<>();
                 stableFieldsMeta = metaDataEnabled ? new HashMap<String, 
Integer>() : null;
 
@@ -748,10 +754,8 @@ public class PortableClassDescriptor {
      * @throws BinaryObjectException In case of error.
      */
     private Object newInstance() throws BinaryObjectException {
-        assert ctor != null;
-
         try {
-            return ctor.newInstance();
+            return ctor != null ? ctor.newInstance() : 
UNSAFE.allocateInstance(cls);
         }
         catch (InstantiationException | InvocationTargetException | 
IllegalAccessException e) {
             throw new BinaryObjectException("Failed to instantiate instance: " 
+ cls, e);
@@ -799,7 +803,7 @@ public class PortableClassDescriptor {
                     writeObj.getReturnType() == void.class && 
readObj.getReturnType() == void.class)
                     return true;
             }
-            catch (NoSuchMethodException e) {
+            catch (NoSuchMethodException ignored) {
                 // No-op.
             }
         }

http://git-wip-us.apache.org/repos/asf/ignite/blob/d2008c53/modules/core/src/test/java/org/apache/ignite/internal/portable/BinaryMarshallerSelfTest.java
----------------------------------------------------------------------
diff --git 
a/modules/core/src/test/java/org/apache/ignite/internal/portable/BinaryMarshallerSelfTest.java
 
b/modules/core/src/test/java/org/apache/ignite/internal/portable/BinaryMarshallerSelfTest.java
index 037adf9..9277a77 100644
--- 
a/modules/core/src/test/java/org/apache/ignite/internal/portable/BinaryMarshallerSelfTest.java
+++ 
b/modules/core/src/test/java/org/apache/ignite/internal/portable/BinaryMarshallerSelfTest.java
@@ -23,8 +23,10 @@ import java.io.ObjectInput;
 import java.io.ObjectOutput;
 import java.io.Serializable;
 import java.lang.reflect.Field;
+import java.lang.reflect.InvocationHandler;
 import java.lang.reflect.InvocationTargetException;
 import java.lang.reflect.Method;
+import java.lang.reflect.Proxy;
 import java.math.BigDecimal;
 import java.math.BigInteger;
 import java.net.InetSocketAddress;
@@ -75,9 +77,11 @@ import org.apache.ignite.internal.util.typedef.F;
 import org.apache.ignite.internal.util.typedef.internal.S;
 import org.apache.ignite.internal.util.typedef.internal.U;
 import org.apache.ignite.marshaller.MarshallerContextTestImpl;
+import org.apache.ignite.marshaller.optimized.OptimizedMarshaller;
 import org.apache.ignite.testframework.GridTestUtils;
 import org.apache.ignite.testframework.junits.common.GridCommonAbstractTest;
 import org.jetbrains.annotations.NotNull;
+import org.jetbrains.annotations.Nullable;
 import org.jsr166.ConcurrentHashMap8;
 import sun.misc.Unsafe;
 
@@ -2329,6 +2333,200 @@ public class BinaryMarshallerSelfTest extends 
GridCommonAbstractTest {
     }
 
     /**
+     * @throws Exception If failed.
+     */
+    public void testProxy() throws Exception {
+        BinaryMarshaller marsh = binaryMarshaller();
+
+        SomeItf inItf = (SomeItf)Proxy.newProxyInstance(
+            BinaryMarshallerSelfTest.class.getClassLoader(), new Class[] 
{SomeItf.class},
+            new InvocationHandler() {
+                private NonSerializable obj = new NonSerializable(null);
+
+                @Override public Object invoke(Object proxy, Method mtd, 
Object[] args) throws Throwable {
+                    if ("hashCode".equals(mtd.getName()))
+                        return obj.hashCode();
+
+                    obj.checkAfterUnmarshalled();
+
+                    return 17;
+                }
+            }
+        );
+
+        SomeItf outItf = marsh.unmarshal(marsh.marshal(inItf), null);
+
+        assertEquals(outItf.checkAfterUnmarshalled(), 17);
+    }
+
+    /**
+     *
+     */
+    private static interface SomeItf {
+        /**
+         * @return Check result.
+         */
+        int checkAfterUnmarshalled();
+    }
+
+    /**
+     * Some non-serializable class.
+     */
+    @SuppressWarnings( 
{"PublicField","TransientFieldInNonSerializableClass","FieldMayBeStatic"})
+    private static class NonSerializableA {
+        /** */
+        private final long longVal = 0x33445566778899AAL;
+
+        /** */
+        protected Short shortVal = (short)0xAABB;
+
+        /** */
+        public String[] strArr = {"AA","BB"};
+
+        /** */
+        public boolean flag1 = true;
+
+        /** */
+        public boolean flag2;
+
+        /** */
+        public Boolean flag3;
+
+        /** */
+        public Boolean flag4 = true;
+
+        /** */
+        public Boolean flag5 = false;
+
+        /** */
+        private transient int intVal = 0xAABBCCDD;
+
+        /**
+         * @param strArr Array.
+         * @param shortVal Short value.
+         */
+        @SuppressWarnings( {"UnusedDeclaration"})
+        private NonSerializableA(@Nullable String[] strArr, @Nullable Short 
shortVal) {
+            // No-op.
+        }
+
+        /**
+         * Checks correctness of the state after unmarshalling.
+         */
+        void checkAfterUnmarshalled() {
+            assertEquals(longVal, 0x33445566778899AAL);
+
+            assertEquals(shortVal.shortValue(), (short)0xAABB);
+
+            assertTrue(Arrays.equals(strArr, new String[] {"AA","BB"}));
+
+            assertEquals(0, intVal);
+
+            assertTrue(flag1);
+            assertFalse(flag2);
+            assertNull(flag3);
+            assertTrue(flag4);
+            assertFalse(flag5);
+        }
+    }
+
+    /**
+     * Some non-serializable class.
+     */
+    @SuppressWarnings( 
{"PublicField","TransientFieldInNonSerializableClass","PackageVisibleInnerClass"})
+    static class NonSerializableB extends NonSerializableA {
+        /** */
+        public Short shortValue = 0x1122;
+
+        /** */
+        public long longValue = 0x8877665544332211L;
+
+        /** */
+        private transient NonSerializableA[] aArr = {
+            new NonSerializableA(null, null),
+            new NonSerializableA(null, null),
+            new NonSerializableA(null, null)
+        };
+
+        /** */
+        protected Double doubleVal = 123.456;
+
+        /**
+         * Just to eliminate the default constructor.
+         */
+        private NonSerializableB() {
+            super(null, null);
+        }
+
+        /**
+         * Checks correctness of the state after unmarshalling.
+         */
+        @Override void checkAfterUnmarshalled() {
+            super.checkAfterUnmarshalled();
+
+            assertEquals(shortValue.shortValue(), 0x1122);
+
+            assertEquals(longValue, 0x8877665544332211L);
+
+            assertNull(aArr);
+
+            assertEquals(doubleVal, 123.456);
+        }
+    }
+
+    /**
+     * Some non-serializable class.
+     */
+    @SuppressWarnings( {"TransientFieldInNonSerializableClass","PublicField"})
+    private static class NonSerializable extends NonSerializableB {
+        /** */
+        private int idVal = -17;
+
+        /** */
+        private final NonSerializableA aVal = new NonSerializableB();
+
+        /** */
+        private transient NonSerializableB bVal = new NonSerializableB();
+
+        /** */
+        private NonSerializableA[] bArr = new NonSerializableA[] {
+            new NonSerializableB(),
+            new NonSerializableA(null, null)
+        };
+
+        /** */
+        public float floatVal = 567.89F;
+
+        /**
+         * Just to eliminate the default constructor.
+         *
+         * @param aVal Unused.
+         */
+        @SuppressWarnings( {"UnusedDeclaration"})
+        private NonSerializable(NonSerializableA aVal) {
+        }
+
+        /**
+         * Checks correctness of the state after unmarshalling.
+         */
+        @Override void checkAfterUnmarshalled() {
+            super.checkAfterUnmarshalled();
+
+            assertEquals(idVal, -17);
+
+            aVal.checkAfterUnmarshalled();
+
+            assertNull(bVal);
+
+            for (NonSerializableA a : bArr) {
+                a.checkAfterUnmarshalled();
+            }
+
+            assertEquals(floatVal, 567.89F);
+        }
+    }
+
+    /**
      * Object with class fields.
      */
     private static class ObjectWithClassFields {

Reply via email to