/*
 *  Copyright (c) 2011 The WebRTC project authors. All Rights Reserved.
 *
 *  Use of this source code is governed by a BSD-style license
 *  that can be found in the LICENSE file in the root of the source
 *  tree. An additional intellectual property rights grant can be found
 *  in the file PATENTS.  All contributing project authors may
 *  be found in the AUTHORS file in the root of the source tree.
 */

#include "webrtc/system_wrappers/include/data_log.h"

#include <map>
#include <string>

#include "webrtc/system_wrappers/include/data_log_c.h"
#include "webrtc/system_wrappers/source/data_log_c_helpers_unittest.h"
#include "webrtc/test/gtest.h"

using ::webrtc::DataLog;

// A class for storing the values expected from a log table column when
// verifying a log table file.
struct ExpectedValues {
 public:
  ExpectedValues()
    : values(),
      multi_value_length(1) {
  }

  ExpectedValues(std::vector<std::string> expected_values,
                 int expected_multi_value_length)
    : values(expected_values),
      multi_value_length(expected_multi_value_length) {
  }

  std::vector<std::string> values;
  int multi_value_length;
};

typedef std::map<std::string, ExpectedValues> ExpectedValuesMap;

// A static class used for parsing and verifying data log files.
class DataLogParser {
 public:
  // Verifies that the log table stored in the file "log_file" corresponds to
  // the cells and columns specified in "columns".
  static int VerifyTable(FILE* log_file, const ExpectedValuesMap& columns) {
    int row = 0;
    char line_buffer[kMaxLineLength];
    char* ret = fgets(line_buffer, kMaxLineLength, log_file);
    EXPECT_FALSE(ret == NULL);
    if (ret == NULL)
      return -1;

    std::string line(line_buffer, kMaxLineLength);
    VerifyHeader(line, columns);
    while (fgets(line_buffer, kMaxLineLength, log_file) != NULL) {
      line = std::string(line_buffer, kMaxLineLength);
      size_t line_position = 0;

      for (ExpectedValuesMap::const_iterator it = columns.begin();
           it != columns.end(); ++it) {
        std::string str = ParseElement(line, &line_position,
                                       it->second.multi_value_length);
        EXPECT_EQ(str, it->second.values[row]);
        if (str != it->second.values[row])
          return -1;
      }
      ++row;
    }
    return 0;
  }

  // Verifies the table header stored in "line" to correspond with the header
  // specified in "columns".
  static int VerifyHeader(const std::string& line,
                          const ExpectedValuesMap& columns) {
    size_t line_position = 0;
    for (ExpectedValuesMap::const_iterator it = columns.begin();
         it != columns.end(); ++it) {
      std::string str = ParseElement(line, &line_position,
                                     it->second.multi_value_length);
      EXPECT_EQ(str, it->first);
      if (str != it->first)
        return -1;
    }
    return 0;
  }

  // Parses out and returns one element from the string "line", which contains
  // one line read from a log table file. An element can either be a column
  // header or a cell of a row.
  static std::string ParseElement(const std::string& line,
                                  size_t* line_position,
                                  int multi_value_length) {
    std::string parsed_cell;
    parsed_cell = "";
    for (int i = 0; i < multi_value_length; ++i) {
      size_t next_separator = line.find(',', *line_position);
      EXPECT_NE(next_separator, std::string::npos);
      if (next_separator == std::string::npos)
        break;
      parsed_cell += line.substr(*line_position,
                                 next_separator - *line_position + 1);
      *line_position = next_separator + 1;
    }
    return parsed_cell;
  }

  // This constant defines the maximum line length the DataLogParser can
  // parse.
  enum { kMaxLineLength = 100 };
};

TEST(TestDataLog, CreateReturnTest) {
  for (int i = 0; i < 10; ++i)
    ASSERT_EQ(DataLog::CreateLog(), 0);
  ASSERT_EQ(DataLog::AddTable(DataLog::Combine("a proper table", 1)), 0);
  for (int i = 0; i < 10; ++i)
    DataLog::ReturnLog();
  ASSERT_LT(DataLog::AddTable(DataLog::Combine("table failure", 1)), 0);
}

TEST(TestDataLog, VerifyCombineMethod) {
  EXPECT_EQ(std::string("a proper table_1"),
            DataLog::Combine("a proper table", 1));
}

TEST(TestDataLog, VerifySingleTable) {
  DataLog::CreateLog();
  DataLog::AddTable(DataLog::Combine("table", 1));
  DataLog::AddColumn(DataLog::Combine("table", 1), "arrival", 1);
  DataLog::AddColumn(DataLog::Combine("table", 1), "timestamp", 1);
  DataLog::AddColumn(DataLog::Combine("table", 1), "size", 5);
  uint32_t sizes[5] = {1400, 1500, 1600, 1700, 1800};
  for (int i = 0; i < 10; ++i) {
    DataLog::InsertCell(DataLog::Combine("table", 1), "arrival",
                        static_cast<double>(i));
    DataLog::InsertCell(DataLog::Combine("table", 1), "timestamp",
                        static_cast<int64_t>(4354 + i));
    DataLog::InsertCell(DataLog::Combine("table", 1), "size", sizes, 5);
    DataLog::NextRow(DataLog::Combine("table", 1));
  }
  DataLog::ReturnLog();
  // Verify file
  FILE* table = fopen("table_1.txt", "r");
  ASSERT_FALSE(table == NULL);
  // Read the column names and verify with the expected columns.
  // Note that the columns are written to file in alphabetical order.
  // Data expected from parsing the file
  const int kNumberOfRows = 10;
  std::string string_arrival[kNumberOfRows] = {
    "0,", "1,", "2,", "3,", "4,",
    "5,", "6,", "7,", "8,", "9,"
  };
  std::string string_timestamp[kNumberOfRows] = {
    "4354,", "4355,", "4356,", "4357,",
    "4358,", "4359,", "4360,", "4361,",
    "4362,", "4363,"
  };
  std::string string_sizes = "1400,1500,1600,1700,1800,";
  ExpectedValuesMap expected;
  expected["arrival,"] = ExpectedValues(
                           std::vector<std::string>(string_arrival,
                                                    string_arrival +
                                                    kNumberOfRows),
                           1);
  expected["size[5],,,,,"] = ExpectedValues(
                               std::vector<std::string>(10, string_sizes), 5);
  expected["timestamp,"] = ExpectedValues(
                             std::vector<std::string>(string_timestamp,
                                                      string_timestamp +
                                                      kNumberOfRows),
                             1);
  ASSERT_EQ(DataLogParser::VerifyTable(table, expected), 0);
  fclose(table);
}

TEST(TestDataLog, VerifyMultipleTables) {
  DataLog::CreateLog();
  DataLog::AddTable(DataLog::Combine("table", 2));
  DataLog::AddTable(DataLog::Combine("table", 3));
  DataLog::AddColumn(DataLog::Combine("table", 2), "arrival", 1);
  DataLog::AddColumn(DataLog::Combine("table", 2), "timestamp", 1);
  DataLog::AddColumn(DataLog::Combine("table", 2), "size", 1);
  DataLog::AddTable(DataLog::Combine("table", 4));
  DataLog::AddColumn(DataLog::Combine("table", 3), "timestamp", 1);
  DataLog::AddColumn(DataLog::Combine("table", 3), "arrival", 1);
  DataLog::AddColumn(DataLog::Combine("table", 4), "size", 1);
  for (int32_t i = 0; i < 10; ++i) {
    DataLog::InsertCell(DataLog::Combine("table", 2), "arrival",
                        static_cast<int32_t>(i));
    DataLog::InsertCell(DataLog::Combine("table", 2), "timestamp",
                        static_cast<int32_t>(4354 + i));
    DataLog::InsertCell(DataLog::Combine("table", 2), "size",
                        static_cast<int32_t>(1200 + 10 * i));
    DataLog::InsertCell(DataLog::Combine("table", 3), "timestamp",
                        static_cast<int32_t>(4354 + i));
    DataLog::InsertCell(DataLog::Combine("table", 3), "arrival",
                        static_cast<int32_t>(i));
    DataLog::InsertCell(DataLog::Combine("table", 4), "size",
                        static_cast<int32_t>(1200 + 10 * i));
    DataLog::NextRow(DataLog::Combine("table", 4));
    DataLog::NextRow(DataLog::Combine("table", 2));
    DataLog::NextRow(DataLog::Combine("table", 3));
  }
  DataLog::ReturnLog();

  // Data expected from parsing the file
  const int kNumberOfRows = 10;
  std::string string_arrival[kNumberOfRows] = {
    "0,", "1,", "2,", "3,", "4,",
    "5,", "6,", "7,", "8,", "9,"
  };
  std::string string_timestamp[kNumberOfRows] = {
    "4354,", "4355,", "4356,", "4357,",
    "4358,", "4359,", "4360,", "4361,",
    "4362,", "4363,"
  };
  std::string string_size[kNumberOfRows] = {
    "1200,", "1210,", "1220,", "1230,",
    "1240,", "1250,", "1260,", "1270,",
    "1280,", "1290,"
  };

  // Verify table 2
  {
    FILE* table = fopen("table_2.txt", "r");
    ASSERT_FALSE(table == NULL);
    ExpectedValuesMap expected;
    expected["arrival,"] = ExpectedValues(
                             std::vector<std::string>(string_arrival,
                                                      string_arrival +
                                                      kNumberOfRows),
                             1);
    expected["size,"] = ExpectedValues(
                          std::vector<std::string>(string_size,
                                                   string_size + kNumberOfRows),
                          1);
    expected["timestamp,"] = ExpectedValues(
                               std::vector<std::string>(string_timestamp,
                                                        string_timestamp +
                                                        kNumberOfRows),
                               1);
    ASSERT_EQ(DataLogParser::VerifyTable(table, expected), 0);
    fclose(table);
  }

  // Verify table 3
  {
    FILE* table = fopen("table_3.txt", "r");
    ASSERT_FALSE(table == NULL);
    ExpectedValuesMap expected;
    expected["arrival,"] = ExpectedValues(
                             std::vector<std::string>(string_arrival,
                                                      string_arrival +
                                                      kNumberOfRows),
                             1);
    expected["timestamp,"] = ExpectedValues(
                               std::vector<std::string>(string_timestamp,
                                                        string_timestamp +
                                                        kNumberOfRows),
                               1);
    ASSERT_EQ(DataLogParser::VerifyTable(table, expected), 0);
    fclose(table);
  }

  // Verify table 4
  {
    FILE* table = fopen("table_4.txt", "r");
    ASSERT_FALSE(table == NULL);
    ExpectedValuesMap expected;
    expected["size,"] = ExpectedValues(
                          std::vector<std::string>(string_size,
                                                   string_size +
                                                   kNumberOfRows),
                          1);
    ASSERT_EQ(DataLogParser::VerifyTable(table, expected), 0);
    fclose(table);
  }
}

TEST(TestDataLogCWrapper, VerifyCWrapper) {
  // Simply call all C wrapper log functions through the C helper unittests.
  // Main purpose is to make sure that the linkage is correct.

  EXPECT_EQ(0, WebRtcDataLogCHelper_TestCreateLog());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestCombine());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestAddTable());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestAddColumn());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestInsertCell_int());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestInsertArray_int());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestNextRow());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestInsertCell_float());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestInsertArray_float());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestNextRow());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestInsertCell_double());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestInsertArray_double());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestNextRow());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestInsertCell_int32());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestInsertArray_int32());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestNextRow());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestInsertCell_uint32());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestInsertArray_uint32());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestNextRow());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestInsertCell_int64());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestInsertArray_int64());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestNextRow());
  EXPECT_EQ(0, WebRtcDataLogCHelper_TestReturnLog());
}
