/*
 * 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.ignite.internal.binary;

import org.apache.ignite.binary.BinaryField;
import org.apache.ignite.binary.BinaryObject;
import org.apache.ignite.binary.BinaryTypeConfiguration;
import org.apache.ignite.configuration.BinaryConfiguration;
import org.apache.ignite.configuration.IgniteConfiguration;
import org.apache.ignite.internal.util.IgniteUtils;
import org.apache.ignite.internal.util.typedef.internal.U;
import org.apache.ignite.logger.NullLogger;
import org.apache.ignite.marshaller.MarshallerContextTestImpl;
import org.apache.ignite.testframework.junits.common.GridCommonAbstractTest;

import java.math.BigDecimal;
import java.sql.Timestamp;
import java.util.Arrays;
import java.util.Date;
import java.util.UUID;
import org.junit.Test;

/**
 * Contains tests for binary object fields.
 */
public abstract class BinaryFieldsAbstractSelfTest extends GridCommonAbstractTest {
    /** Marshaller. */
    protected BinaryMarshaller dfltMarsh;

    /**
     * Create marshaller.
     *
     * @return Binary marshaller.
     * @throws Exception If failed.
     */
    protected BinaryMarshaller createMarshaller() throws Exception {
        BinaryContext ctx = new BinaryContext(BinaryCachingMetadataHandler.create(), new IgniteConfiguration(),
            new NullLogger());

        BinaryMarshaller marsh = new BinaryMarshaller();

        BinaryConfiguration bCfg = new BinaryConfiguration();

        bCfg.setCompactFooter(compactFooter());

        bCfg.setTypeConfigurations(Arrays.asList(
            new BinaryTypeConfiguration(TestObject.class.getName()),
            new BinaryTypeConfiguration(TestOuterObject.class.getName()),
            new BinaryTypeConfiguration(TestInnerObject.class.getName())
        ));

        IgniteConfiguration iCfg = new IgniteConfiguration();

        iCfg.setBinaryConfiguration(bCfg);

        marsh.setContext(new MarshallerContextTestImpl(null));

        IgniteUtils.invoke(BinaryMarshaller.class, marsh, "setBinaryContext", ctx, iCfg);

        return marsh;
    }

    /**
     * @return Whether to use compact footer.
     */
    protected boolean compactFooter() {
        return true;
    }

    /**
     * Get binary context for the current marshaller.
     *
     * @param marsh Marshaller.
     * @return Binary context.
     */
    protected static BinaryContext binaryContext(BinaryMarshaller marsh) {
        GridBinaryMarshaller impl = U.field(marsh, "impl");

        return impl.context();
    }

    /** {@inheritDoc} */
    @Override protected void beforeTest() throws Exception {
        super.beforeTest();

        dfltMarsh = createMarshaller();
    }

    /**
     * Test byte field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testByte() throws Exception {
        check("fByte");
    }

    /**
     * Test byte array field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testByteArray() throws Exception {
        check("fByteArr");
    }

    /**
     * Test boolean field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testBoolean() throws Exception {
        check("fBool");
    }

    /**
     * Test boolean array field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testBooleanArray() throws Exception {
        check("fBoolArr");
    }

    /**
     * Test short field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testShort() throws Exception {
        check("fShort");
    }

    /**
     * Test short array field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testShortArray() throws Exception {
        check("fShortArr");
    }

    /**
     * Test char field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testChar() throws Exception {
        check("fChar");
    }

    /**
     * Test char array field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testCharArray() throws Exception {
        check("fCharArr");
    }

    /**
     * Test int field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testInt() throws Exception {
        check("fInt");
    }

    /**
     * Test int array field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testIntArray() throws Exception {
        check("fIntArr");
    }

    /**
     * Test long field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testLong() throws Exception {
        check("fLong");
    }

    /**
     * Test long array field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testLongArray() throws Exception {
        check("fLongArr");
    }

    /**
     * Test float field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testFloat() throws Exception {
        check("fFloat");
    }

    /**
     * Test float array field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testFloatArray() throws Exception {
        check("fFloatArr");
    }

    /**
     * Test double field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testDouble() throws Exception {
        check("fDouble");
    }

    /**
     * Test double array field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testDoubleArray() throws Exception {
        check("fDoubleArr");
    }

    /**
     * Test string field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testString() throws Exception {
        check("fString");
    }

    /**
     * Test string array field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testStringArray() throws Exception {
        check("fStringArr");
    }

    /**
     * Test date field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testDate() throws Exception {
        check("fDate");
    }

    /**
     * Test date array field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testDateArray() throws Exception {
        check("fDateArr");
    }

    /**
     * Test timestamp field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testTimestamp() throws Exception {
        check("fTimestamp");
    }

    /**
     * Test timestamp array field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testTimestampArray() throws Exception {
        check("fTimestampArr");
    }

    /**
     * Test UUID field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testUuid() throws Exception {
        check("fUuid");
    }

    /**
     * Test UUID array field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testUuidArray() throws Exception {
        check("fUuidArr");
    }

    /**
     * Test decimal field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testDecimal() throws Exception {
        check("fDecimal");
    }

    /**
     * Test decimal array field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testDecimalArray() throws Exception {
        check("fDecimalArr");
    }

    /**
     * Test object field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testObject() throws Exception {
        check("fObj");
    }

    /**
     * Test object array field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testObjectArray() throws Exception {
        check("fObjArr");
    }

    /**
     * Test null field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testNull() throws Exception {
        check("fNull");
    }

    /**
     * Test missing field.
     *
     * @throws Exception If failed.
     */
    @Test
    public void testMissing() throws Exception {
        String fieldName = "fMissing";

        checkNormal(dfltMarsh, fieldName, false);
        checkNested(dfltMarsh, fieldName, false);
    }

    /**
     * Check field resolution in both normal and nested modes.
     *
     * @param fieldName Field name.
     * @throws Exception If failed.
     */
    public void check(String fieldName) throws Exception {
        checkNormal(dfltMarsh, fieldName, true);
        checkNested(dfltMarsh, fieldName, true);
    }

    /**
     * Check field.
     *
     * @param marsh Marshaller.
     * @param fieldName Field name.
     * @param exists Whether field should exist.
     * @throws Exception If failed.
     */
    private void checkNormal(BinaryMarshaller marsh, String fieldName, boolean exists) throws Exception {
        TestContext testCtx = context(marsh, fieldName);

        check0(fieldName, testCtx, exists);
    }

    /**
     * Check nested field.
     *
     * @param marsh Marshaller.
     * @param fieldName Field name.
     * @param exists Whether field should exist.
     * @throws Exception If failed.
     */
    private void checkNested(BinaryMarshaller marsh, String fieldName, boolean exists) throws Exception {
        TestContext testCtx = nestedContext(marsh, fieldName);

        check0(fieldName, testCtx, exists);
    }

    /**
     * Internal check routine.
     *
     * @param fieldName Field name.
     * @param ctx Context.
     * @param exists Whether field should exist.
     * @throws Exception If failed.
     */
    private void check0(String fieldName, TestContext ctx, boolean exists) throws Exception {
        Object val = ctx.field.value(ctx.portObj);

        if (exists) {
            assertTrue(ctx.field.exists(ctx.portObj));

            Object expVal = U.field(ctx.obj, fieldName);

            if (val instanceof BinaryObject)
                val = ((BinaryObject) val).deserialize();

            if (val != null && val.getClass().isArray()) {
                assertNotNull(expVal);

                if (val instanceof byte[])
                    assertTrue(Arrays.equals((byte[]) expVal, (byte[]) val));
                else if (val instanceof boolean[])
                    assertTrue(Arrays.equals((boolean[]) expVal, (boolean[]) val));
                else if (val instanceof short[])
                    assertTrue(Arrays.equals((short[]) expVal, (short[]) val));
                else if (val instanceof char[])
                    assertTrue(Arrays.equals((char[]) expVal, (char[]) val));
                else if (val instanceof int[])
                    assertTrue(Arrays.equals((int[]) expVal, (int[]) val));
                else if (val instanceof long[])
                    assertTrue(Arrays.equals((long[]) expVal, (long[]) val));
                else if (val instanceof float[])
                    assertTrue(Arrays.equals((float[]) expVal, (float[]) val));
                else if (val instanceof double[])
                    assertTrue(Arrays.equals((double[]) expVal, (double[]) val));
                else {
                    Object[] expVal0 = (Object[])expVal;
                    Object[] val0 = (Object[])val;

                    assertEquals(expVal0.length, val0.length);

                    for (int i = 0; i < expVal0.length; i++) {
                        Object expItem = expVal0[i];
                        Object item = val0[i];

                        if (item instanceof BinaryObject)
                            item = ((BinaryObject)item).deserialize();

                        assertEquals(expItem, item);
                    }
                }
            }
            else
                assertEquals(expVal, val);
        }
        else {
            assertFalse(ctx.field.exists(ctx.portObj));

            assert val == null;
        }
    }

    /**
     * Get test context.
     *
     * @param marsh Binary marshaller.
     * @param fieldName Field name.
     * @return Test context.
     * @throws Exception If failed.
     */
    private TestContext context(BinaryMarshaller marsh, String fieldName) throws Exception {
        TestObject obj = createObject();

        BinaryObjectExImpl portObj = toBinary(marsh, obj);

        BinaryField field = portObj.type().field(fieldName);

        return new TestContext(obj, portObj, field);
    }

    /**
     * Get test context with nested test object.
     *
     * @param marsh Binary marshaller.
     * @param fieldName Field name.
     * @return Test context.
     * @throws Exception If failed.
     */
    private TestContext nestedContext(BinaryMarshaller marsh, String fieldName)
        throws Exception {
        TestObject obj = createObject();
        TestOuterObject outObj = new TestOuterObject(obj);

        BinaryObjectExImpl portOutObj = toBinary(marsh, outObj);
        BinaryObjectExImpl portObj = portOutObj.field("fInner");

        assert portObj != null;

        BinaryField field = portObj.type().field(fieldName);

        return new TestContext(obj, portObj, field);
    }

    /**
     * Create test object.
     *
     * @return Test object.
     */
    private TestObject createObject() {
        return new TestObject(0);
    }

    /**
     * Convert object to binary object.
     *
     * @param marsh Marshaller.
     * @param obj Object.
     * @return Binary object.
     * @throws Exception If failed.
     */
    protected abstract BinaryObjectExImpl toBinary(BinaryMarshaller marsh, Object obj) throws Exception;

    /**
     * Outer test object.
     */
    public static class TestOuterObject {
        /** Inner object. */
        public TestObject fInner;

        /**
         * Default constructor.
         */
        public TestOuterObject() {
            // No-op.
        }

        /**
         * Constructor.
         *
         * @param fInner Inner object.
         */
        public TestOuterObject(TestObject fInner) {
            this.fInner = fInner;
        }
    }

    /**
     * Test object class, c
     */
    public static class TestObject {
        /** Primitive fields. */
        public byte fByte;

        public boolean fBool;

        public short fShort;

        public char fChar;

        public int fInt;

        public long fLong;

        public float fFloat;

        public double fDouble;

        public byte[] fByteArr;

        public boolean[] fBoolArr;

        public short[] fShortArr;

        public char[] fCharArr;

        public int[] fIntArr;

        public long[] fLongArr;

        public float[] fFloatArr;

        public double[] fDoubleArr;

        /** Special fields. */
        public String fString;

        public Date fDate;

        public Timestamp fTimestamp;

        public UUID fUuid;

        public BigDecimal fDecimal;

        public String[] fStringArr;

        public Date[] fDateArr;

        public Timestamp[] fTimestampArr;

        public UUID[] fUuidArr;

        public BigDecimal[] fDecimalArr;

        /** Nested object. */
        public TestInnerObject fObj;

        public TestInnerObject[] fObjArr;

        /** Field which is always set to null. */
        public Object fNull;

        /**
         * Default constructor.
         */
        public TestObject() {
            // No-op.
        }

        /**
         * Non-default constructor.
         *
         * @param ignore Ignored.
         */
        public TestObject(int ignore) {
            fByte = 1;
            fBool = true;
            fShort = 2;
            fChar = 3;
            fInt = 4;
            fLong = 5;
            fFloat = 6.6f;
            fDouble = 7.7;

            fByteArr = new byte[] { 1, 2 };
            fBoolArr = new boolean[] { true, false };
            fShortArr = new short[] { 2, 3 };
            fCharArr = new char[] { 3, 4 };
            fIntArr = new int[] { 4, 5 };
            fLongArr = new long[] { 5, 6 };
            fFloatArr = new float[] { 6.6f, 7.7f };
            fDoubleArr = new double[] { 7.7, 8.8 };

            fString = "8";
            fDate = new Date();
            fTimestamp = new Timestamp(new Date().getTime() + 1);
            fUuid = UUID.randomUUID();
            fDecimal = new BigDecimal(9);

            fStringArr = new String[] { "8", "9" };
            fDateArr = new Date[] { new Date(), new Date(new Date().getTime() + 1) };
            fTimestampArr =
                new Timestamp[] { new Timestamp(new Date().getTime() + 1), new Timestamp(new Date().getTime() + 2) };
            fUuidArr = new UUID[] { UUID.randomUUID(), UUID.randomUUID() };
            fDecimalArr = new BigDecimal[] { new BigDecimal(9), new BigDecimal(10) };

            fObj = new TestInnerObject(10);
            fObjArr = new TestInnerObject[] { new TestInnerObject(10), new TestInnerObject(11) };
        }
    }

    /**
     * Inner test object.
     */
    public static class TestInnerObject {
        /** Value. */
        private int val;

        /**
         * Default constructor.
         */
        public TestInnerObject() {
            // No-op.
        }

        /**
         * Constructor.
         *
         * @param val Value.
         */
        public TestInnerObject(int val) {
            this.val = val;
        }

        /** {@inheritDoc} */
        @Override public int hashCode() {
            return val;
        }

        /** {@inheritDoc} */
        @Override public boolean equals(Object other) {
            return other != null && other instanceof TestInnerObject && val == ((TestInnerObject)(other)).val;
        }
    }

    /**
     * Test context.
     */
    public static class TestContext {
        /** Object. */
        public final TestObject obj;

        /** Binary object. */
        public final BinaryObjectExImpl portObj;

        /** Field. */
        public final BinaryField field;

        /**
         * Constructor.
         *
         * @param obj Object.
         * @param portObj Binary object.
         * @param field Field.
         */
        public TestContext(TestObject obj, BinaryObjectExImpl portObj, BinaryField field) {
            this.obj = obj;
            this.portObj = portObj;
            this.field = field;
        }
    }
}
