// Copyright (c) 2014 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "base/trace_event/trace_event_argument.h"

#include <stddef.h>

#include <utility>

#include "base/memory/ptr_util.h"
#include "base/values.h"
#include "testing/gtest/include/gtest/gtest.h"

namespace base {
namespace trace_event {

TEST(TraceEventArgumentTest, FlatDictionary) {
  std::unique_ptr<TracedValue> value(new TracedValue());
  value->SetBoolean("bool", true);
  value->SetDouble("double", 0.0);
  value->SetInteger("int", 2014);
  value->SetString("string", "string");
  std::string json = "PREFIX";
  value->AppendAsTraceFormat(&json);
  EXPECT_EQ(
      "PREFIX{\"bool\":true,\"double\":0.0,\"int\":2014,\"string\":\"string\"}",
      json);
}

TEST(TraceEventArgumentTest, NoDotPathExpansion) {
  std::unique_ptr<TracedValue> value(new TracedValue());
  value->SetBoolean("bo.ol", true);
  value->SetDouble("doub.le", 0.0);
  value->SetInteger("in.t", 2014);
  value->SetString("str.ing", "str.ing");
  std::string json;
  value->AppendAsTraceFormat(&json);
  EXPECT_EQ(
      "{\"bo.ol\":true,\"doub.le\":0.0,\"in.t\":2014,\"str.ing\":\"str.ing\"}",
      json);
}

TEST(TraceEventArgumentTest, Hierarchy) {
  std::unique_ptr<TracedValue> value(new TracedValue());
  value->BeginArray("a1");
  value->AppendInteger(1);
  value->AppendBoolean(true);
  value->BeginDictionary();
  value->SetInteger("i2", 3);
  value->EndDictionary();
  value->EndArray();
  value->SetBoolean("b0", true);
  value->SetDouble("d0", 0.0);
  value->BeginDictionary("dict1");
  value->BeginDictionary("dict2");
  value->SetBoolean("b2", false);
  value->EndDictionary();
  value->SetInteger("i1", 2014);
  value->SetString("s1", "foo");
  value->EndDictionary();
  value->SetInteger("i0", 2014);
  value->SetString("s0", "foo");
  std::string json;
  value->AppendAsTraceFormat(&json);
  EXPECT_EQ(
      "{\"a1\":[1,true,{\"i2\":3}],\"b0\":true,\"d0\":0.0,\"dict1\":{\"dict2\":"
      "{\"b2\":false},\"i1\":2014,\"s1\":\"foo\"},\"i0\":2014,\"s0\":"
      "\"foo\"}",
      json);
}

TEST(TraceEventArgumentTest, LongStrings) {
  std::string kLongString = "supercalifragilisticexpialidocious";
  std::string kLongString2 = "0123456789012345678901234567890123456789";
  char kLongString3[4096];
  for (size_t i = 0; i < sizeof(kLongString3); ++i)
    kLongString3[i] = 'a' + (i % 25);
  kLongString3[sizeof(kLongString3) - 1] = '\0';

  std::unique_ptr<TracedValue> value(new TracedValue());
  value->SetString("a", "short");
  value->SetString("b", kLongString);
  value->BeginArray("c");
  value->AppendString(kLongString2);
  value->AppendString("");
  value->BeginDictionary();
  value->SetString("a", kLongString3);
  value->EndDictionary();
  value->EndArray();

  std::string json;
  value->AppendAsTraceFormat(&json);
  EXPECT_EQ("{\"a\":\"short\",\"b\":\"" + kLongString + "\",\"c\":[\"" +
                kLongString2 + "\",\"\",{\"a\":\"" + kLongString3 + "\"}]}",
            json);
}

TEST(TraceEventArgumentTest, PassBaseValue) {
  Value int_value(42);
  Value bool_value(true);
  Value double_value(42.0f);

  auto dict_value = WrapUnique(new DictionaryValue);
  dict_value->SetBoolean("bool", true);
  dict_value->SetInteger("int", 42);
  dict_value->SetDouble("double", 42.0f);
  dict_value->SetString("string", std::string("a") + "b");
  dict_value->SetString("string", std::string("a") + "b");

  auto list_value = WrapUnique(new ListValue);
  list_value->AppendBoolean(false);
  list_value->AppendInteger(1);
  list_value->AppendString("in_list");
  list_value->Append(std::move(dict_value));

  std::unique_ptr<TracedValue> value(new TracedValue());
  value->BeginDictionary("outer_dict");
  value->SetValue("inner_list", std::move(list_value));
  value->EndDictionary();

  dict_value.reset();
  list_value.reset();

  std::string json;
  value->AppendAsTraceFormat(&json);
  EXPECT_EQ(
      "{\"outer_dict\":{\"inner_list\":[false,1,\"in_list\",{\"bool\":true,"
      "\"double\":42.0,\"int\":42,\"string\":\"ab\"}]}}",
      json);
}

TEST(TraceEventArgumentTest, PassTracedValue) {
  auto dict_value = std::make_unique<TracedValue>();
  dict_value->SetInteger("a", 1);

  auto nested_dict_value = std::make_unique<TracedValue>();
  nested_dict_value->SetInteger("b", 2);
  nested_dict_value->BeginArray("c");
  nested_dict_value->AppendString("foo");
  nested_dict_value->EndArray();

  dict_value->SetValue("e", *nested_dict_value);

  // Check the merged result.
  std::string json;
  dict_value->AppendAsTraceFormat(&json);
  EXPECT_EQ("{\"a\":1,\"e\":{\"b\":2,\"c\":[\"foo\"]}}", json);

  // Check that the passed nestd dict was left unouthced.
  json = "";
  nested_dict_value->AppendAsTraceFormat(&json);
  EXPECT_EQ("{\"b\":2,\"c\":[\"foo\"]}", json);

  // And that it is still usable.
  nested_dict_value->SetInteger("f", 3);
  nested_dict_value->BeginDictionary("g");
  nested_dict_value->EndDictionary();
  json = "";
  nested_dict_value->AppendAsTraceFormat(&json);
  EXPECT_EQ("{\"b\":2,\"c\":[\"foo\"],\"f\":3,\"g\":{}}", json);
}

}  // namespace trace_event
}  // namespace base
