// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc.  All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
//     * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//     * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//     * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

package com.google.protobuf.util;

import protobuf_unittest.UnittestProto.NestedTestAllTypes;
import protobuf_unittest.UnittestProto.TestAllTypes;
import protobuf_unittest.UnittestProto.TestAllTypes.NestedMessage;
import junit.framework.TestCase;

public class FieldMaskTreeTest extends TestCase {
  public void testAddFieldPath() throws Exception {
    FieldMaskTree tree = new FieldMaskTree();
    assertEquals("", tree.toString());
    tree.addFieldPath("");
    assertEquals("", tree.toString());
    // New branch.
    tree.addFieldPath("foo");
    assertEquals("foo", tree.toString());
    // Redundant path.
    tree.addFieldPath("foo");
    assertEquals("foo", tree.toString());
    // New branch.
    tree.addFieldPath("bar.baz");
    assertEquals("bar.baz,foo", tree.toString());
    // Redundant sub-path.
    tree.addFieldPath("foo.bar");
    assertEquals("bar.baz,foo", tree.toString());
    // New branch from a non-root node.
    tree.addFieldPath("bar.quz");
    assertEquals("bar.baz,bar.quz,foo", tree.toString());
    // A path that matches several existing sub-paths.
    tree.addFieldPath("bar");
    assertEquals("bar,foo", tree.toString());
  }

  public void testMergeFromFieldMask() throws Exception {
    FieldMaskTree tree = new FieldMaskTree(FieldMaskUtil.fromString("foo,bar.baz,bar.quz"));
    assertEquals("bar.baz,bar.quz,foo", tree.toString());
    tree.mergeFromFieldMask(FieldMaskUtil.fromString("foo.bar,bar"));
    assertEquals("bar,foo", tree.toString());
  }

  public void testIntersectFieldPath() throws Exception {
    FieldMaskTree tree = new FieldMaskTree(FieldMaskUtil.fromString("foo,bar.baz,bar.quz"));
    FieldMaskTree result = new FieldMaskTree();
    // Empty path.
    tree.intersectFieldPath("", result);
    assertEquals("", result.toString());
    // Non-exist path.
    tree.intersectFieldPath("quz", result);
    assertEquals("", result.toString());
    // Sub-path of an existing leaf.
    tree.intersectFieldPath("foo.bar", result);
    assertEquals("foo.bar", result.toString());
    // Match an existing leaf node.
    tree.intersectFieldPath("foo", result);
    assertEquals("foo", result.toString());
    // Non-exist path.
    tree.intersectFieldPath("bar.foo", result);
    assertEquals("foo", result.toString());
    // Match a non-leaf node.
    tree.intersectFieldPath("bar", result);
    assertEquals("bar.baz,bar.quz,foo", result.toString());
  }

  public void testMerge() throws Exception {
    TestAllTypes value =
        TestAllTypes.newBuilder()
            .setOptionalInt32(1234)
            .setOptionalNestedMessage(NestedMessage.newBuilder().setBb(5678))
            .addRepeatedInt32(4321)
            .addRepeatedNestedMessage(NestedMessage.newBuilder().setBb(8765))
            .build();
    NestedTestAllTypes source =
        NestedTestAllTypes.newBuilder()
            .setPayload(value)
            .setChild(NestedTestAllTypes.newBuilder().setPayload(value))
            .build();
    // Now we have a message source with the following structure:
    //   [root] -+- payload -+- optional_int32
    //           |           +- optional_nested_message
    //           |           +- repeated_int32
    //           |           +- repeated_nested_message
    //           |
    //           +- child --- payload -+- optional_int32
    //                                 +- optional_nested_message
    //                                 +- repeated_int32
    //                                 +- repeated_nested_message

    FieldMaskUtil.MergeOptions options = new FieldMaskUtil.MergeOptions();

    // Test merging each individual field.
    NestedTestAllTypes.Builder builder = NestedTestAllTypes.newBuilder();
    new FieldMaskTree().addFieldPath("payload.optional_int32").merge(source, builder, options);
    NestedTestAllTypes.Builder expected = NestedTestAllTypes.newBuilder();
    expected.getPayloadBuilder().setOptionalInt32(1234);
    assertEquals(expected.build(), builder.build());

    builder = NestedTestAllTypes.newBuilder();
    new FieldMaskTree()
        .addFieldPath("payload.optional_nested_message")
        .merge(source, builder, options);
    expected = NestedTestAllTypes.newBuilder();
    expected.getPayloadBuilder().setOptionalNestedMessage(NestedMessage.newBuilder().setBb(5678));
    assertEquals(expected.build(), builder.build());

    builder = NestedTestAllTypes.newBuilder();
    new FieldMaskTree().addFieldPath("payload.repeated_int32").merge(source, builder, options);
    expected = NestedTestAllTypes.newBuilder();
    expected.getPayloadBuilder().addRepeatedInt32(4321);
    assertEquals(expected.build(), builder.build());

    builder = NestedTestAllTypes.newBuilder();
    new FieldMaskTree()
        .addFieldPath("payload.repeated_nested_message")
        .merge(source, builder, options);
    expected = NestedTestAllTypes.newBuilder();
    expected.getPayloadBuilder().addRepeatedNestedMessage(NestedMessage.newBuilder().setBb(8765));
    assertEquals(expected.build(), builder.build());

    builder = NestedTestAllTypes.newBuilder();
    new FieldMaskTree()
        .addFieldPath("child.payload.optional_int32")
        .merge(source, builder, options);
    expected = NestedTestAllTypes.newBuilder();
    expected.getChildBuilder().getPayloadBuilder().setOptionalInt32(1234);
    assertEquals(expected.build(), builder.build());

    builder = NestedTestAllTypes.newBuilder();
    new FieldMaskTree()
        .addFieldPath("child.payload.optional_nested_message")
        .merge(source, builder, options);
    expected = NestedTestAllTypes.newBuilder();
    expected
        .getChildBuilder()
        .getPayloadBuilder()
        .setOptionalNestedMessage(NestedMessage.newBuilder().setBb(5678));
    assertEquals(expected.build(), builder.build());

    builder = NestedTestAllTypes.newBuilder();
    new FieldMaskTree()
        .addFieldPath("child.payload.repeated_int32")
        .merge(source, builder, options);
    expected = NestedTestAllTypes.newBuilder();
    expected.getChildBuilder().getPayloadBuilder().addRepeatedInt32(4321);
    assertEquals(expected.build(), builder.build());

    builder = NestedTestAllTypes.newBuilder();
    new FieldMaskTree()
        .addFieldPath("child.payload.repeated_nested_message")
        .merge(source, builder, options);
    expected = NestedTestAllTypes.newBuilder();
    expected
        .getChildBuilder()
        .getPayloadBuilder()
        .addRepeatedNestedMessage(NestedMessage.newBuilder().setBb(8765));
    assertEquals(expected.build(), builder.build());

    // Test merging all fields.
    builder = NestedTestAllTypes.newBuilder();
    new FieldMaskTree()
        .addFieldPath("child")
        .addFieldPath("payload")
        .merge(source, builder, options);
    assertEquals(source, builder.build());

    // Test repeated options.
    builder = NestedTestAllTypes.newBuilder();
    builder.getPayloadBuilder().addRepeatedInt32(1000);
    new FieldMaskTree().addFieldPath("payload.repeated_int32").merge(source, builder, options);
    // Default behavior is to append repeated fields.
    assertEquals(2, builder.getPayload().getRepeatedInt32Count());
    assertEquals(1000, builder.getPayload().getRepeatedInt32(0));
    assertEquals(4321, builder.getPayload().getRepeatedInt32(1));
    // Change to replace repeated fields.
    options.setReplaceRepeatedFields(true);
    new FieldMaskTree().addFieldPath("payload.repeated_int32").merge(source, builder, options);
    assertEquals(1, builder.getPayload().getRepeatedInt32Count());
    assertEquals(4321, builder.getPayload().getRepeatedInt32(0));

    // Test message options.
    builder = NestedTestAllTypes.newBuilder();
    builder.getPayloadBuilder().setOptionalInt32(1000);
    builder.getPayloadBuilder().setOptionalUint32(2000);
    new FieldMaskTree().addFieldPath("payload").merge(source, builder, options);
    // Default behavior is to merge message fields.
    assertEquals(1234, builder.getPayload().getOptionalInt32());
    assertEquals(2000, builder.getPayload().getOptionalUint32());

    // Test merging unset message fields.
    NestedTestAllTypes clearedSource = source.toBuilder().clearPayload().build();
    builder = NestedTestAllTypes.newBuilder();
    new FieldMaskTree().addFieldPath("payload").merge(clearedSource, builder, options);
    assertEquals(false, builder.hasPayload());

    // Skip a message field if they are unset in both source and target.
    builder = NestedTestAllTypes.newBuilder();
    new FieldMaskTree()
        .addFieldPath("payload.optional_int32")
        .merge(clearedSource, builder, options);
    assertEquals(false, builder.hasPayload());

    // Change to replace message fields.
    options.setReplaceMessageFields(true);
    builder = NestedTestAllTypes.newBuilder();
    builder.getPayloadBuilder().setOptionalInt32(1000);
    builder.getPayloadBuilder().setOptionalUint32(2000);
    new FieldMaskTree().addFieldPath("payload").merge(source, builder, options);
    assertEquals(1234, builder.getPayload().getOptionalInt32());
    assertEquals(0, builder.getPayload().getOptionalUint32());

    // Test merging unset message fields.
    builder = NestedTestAllTypes.newBuilder();
    builder.getPayloadBuilder().setOptionalInt32(1000);
    builder.getPayloadBuilder().setOptionalUint32(2000);
    new FieldMaskTree().addFieldPath("payload").merge(clearedSource, builder, options);
    assertEquals(false, builder.hasPayload());

    // Test merging unset primitive fields.
    builder = source.toBuilder();
    builder.getPayloadBuilder().clearOptionalInt32();
    NestedTestAllTypes sourceWithPayloadInt32Unset = builder.build();
    builder = source.toBuilder();
    new FieldMaskTree()
        .addFieldPath("payload.optional_int32")
        .merge(sourceWithPayloadInt32Unset, builder, options);
    assertEquals(true, builder.getPayload().hasOptionalInt32());
    assertEquals(0, builder.getPayload().getOptionalInt32());

    // Change to clear unset primitive fields.
    options.setReplacePrimitiveFields(true);
    builder = source.toBuilder();
    new FieldMaskTree()
        .addFieldPath("payload.optional_int32")
        .merge(sourceWithPayloadInt32Unset, builder, options);
    assertEquals(true, builder.hasPayload());
    assertEquals(false, builder.getPayload().hasOptionalInt32());
  }
}
