// Copyright 2010-2015, Google Inc.
// All rights reserved.
//
// 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.

#include "dictionary/user_dictionary_storage.h"

#include <string>
#include <vector>

#include "base/file_stream.h"
#include "base/file_util.h"
#include "base/logging.h"
#include "base/mmap.h"
#include "base/number_util.h"
#include "base/protobuf/unknown_field_set.h"
#include "base/system_util.h"
#include "base/util.h"
#include "dictionary/user_dictionary_importer.h"
#include "dictionary/user_dictionary_util.h"
#include "testing/base/public/googletest.h"
#include "testing/base/public/gunit.h"
#include "testing/base/public/testing_util.h"

DECLARE_string(test_tmpdir);

namespace mozc {

using mozc::protobuf::UnknownField;
using mozc::protobuf::UnknownFieldSet;
using mozc::testing::SerializeUnknownFieldSetAsString;
using user_dictionary::UserDictionary;

namespace {

string GenRandomString(int size) {
  string result;
  const size_t len = Util::Random(size) + 1;
  for (int i = 0; i < len; ++i) {
    const char32 l =
        static_cast<char32>(Util::Random(static_cast<int>('~' - ' ')) + ' ');
    Util::UCS4ToUTF8Append(l, &result);
  }
  return result;
}

}   // namespace

class UserDictionaryStorageTest : public ::testing::Test {
 protected:
  virtual void SetUp() {
    backup_user_profile_directory_ = SystemUtil::GetUserProfileDirectory();
    SystemUtil::SetUserProfileDirectory(FLAGS_test_tmpdir);
    FileUtil::Unlink(GetUserDictionaryFile());
  }

  virtual void TearDown() {
    FileUtil::Unlink(GetUserDictionaryFile());
    SystemUtil::SetUserProfileDirectory(backup_user_profile_directory_);
  }

  static string GetUserDictionaryFile() {
    return FileUtil::JoinPath(FLAGS_test_tmpdir, "test.db");
  }

 private:
  string backup_user_profile_directory_;
};

TEST_F(UserDictionaryStorageTest, FileTest) {
  UserDictionaryStorage storage(GetUserDictionaryFile());
  EXPECT_EQ(storage.filename(), GetUserDictionaryFile());
  EXPECT_FALSE(storage.Exists());
}

TEST_F(UserDictionaryStorageTest, LockTest) {
  UserDictionaryStorage storage1(GetUserDictionaryFile());
  UserDictionaryStorage storage2(GetUserDictionaryFile());

  EXPECT_FALSE(storage1.Save());
  EXPECT_FALSE(storage2.Save());

  EXPECT_TRUE(storage1.Lock());
  EXPECT_FALSE(storage2.Lock());
  EXPECT_TRUE(storage1.Save());
  EXPECT_FALSE(storage2.Save());

  EXPECT_TRUE(storage1.UnLock());
  EXPECT_FALSE(storage1.Save());
  EXPECT_FALSE(storage2.Save());

  EXPECT_TRUE(storage2.Lock());
  EXPECT_FALSE(storage1.Save());
  EXPECT_TRUE(storage2.Save());
}

TEST_F(UserDictionaryStorageTest, BasicOperationsTest) {
  UserDictionaryStorage storage(GetUserDictionaryFile());
  EXPECT_FALSE(storage.Load());

  const size_t kDictionariesSize = 3;
  uint64 id[kDictionariesSize];

  const size_t dict_size = storage.dictionaries_size();

  for (size_t i = 0; i < kDictionariesSize; ++i) {
    EXPECT_TRUE(storage.CreateDictionary(
        "test" + NumberUtil::SimpleItoa(static_cast<uint32>(i)),
        &id[i]));
    EXPECT_EQ(i + 1 + dict_size, storage.dictionaries_size());
  }

  for (size_t i = 0; i < kDictionariesSize; ++i) {
    EXPECT_EQ(i + dict_size, storage.GetUserDictionaryIndex(id[i]));
    EXPECT_EQ(-1, storage.GetUserDictionaryIndex(id[i] + 1));
  }

  for (size_t i = 0; i < kDictionariesSize; ++i) {
    EXPECT_EQ(storage.mutable_dictionaries(i + dict_size),
              storage.GetUserDictionary(id[i]));
    EXPECT_EQ(NULL, storage.GetUserDictionary(id[i] + 1));
  }

  // empty
  EXPECT_FALSE(storage.RenameDictionary(id[0], ""));

  // duplicated
  uint64 tmp_id = 0;
  EXPECT_FALSE(storage.CreateDictionary("test0", &tmp_id));
  EXPECT_EQ(UserDictionaryStorage::DUPLICATED_DICTIONARY_NAME,
            storage.GetLastError());

  // invalid id
  EXPECT_FALSE(storage.RenameDictionary(0, ""));

  // duplicated
  EXPECT_FALSE(storage.RenameDictionary(id[0], "test1"));
  EXPECT_EQ(UserDictionaryStorage::DUPLICATED_DICTIONARY_NAME,
            storage.GetLastError());

  // no name
  EXPECT_TRUE(storage.RenameDictionary(id[0], "test0"));

  EXPECT_TRUE(storage.RenameDictionary(id[0], "renamed0"));
  EXPECT_EQ("renamed0", storage.GetUserDictionary(id[0])->name());

  // invalid id
  EXPECT_FALSE(storage.DeleteDictionary(0));

  EXPECT_TRUE(storage.DeleteDictionary(id[1]));
  EXPECT_EQ(kDictionariesSize + dict_size - 1, storage.dictionaries_size());
}

TEST_F(UserDictionaryStorageTest, DeleteTest) {
  UserDictionaryStorage storage(GetUserDictionaryFile());
  EXPECT_FALSE(storage.Load());

  // repeat 10 times
  for (int i = 0; i < 10; ++i) {
    storage.Clear();
    vector<uint64> ids(100);
    for (size_t i = 0; i < ids.size(); ++i) {
      EXPECT_TRUE(storage.CreateDictionary(
          "test" + NumberUtil::SimpleItoa(static_cast<uint32>(i)),
          &ids[i]));
    }

    vector<uint64> alive;
    for (size_t i = 0; i < ids.size(); ++i) {
      if (Util::Random(3) == 0) {   // 33%
        EXPECT_TRUE(storage.DeleteDictionary(ids[i]));
        continue;
      }
      alive.push_back(ids[i]);
    }

    EXPECT_EQ(alive.size(), storage.dictionaries_size());

    for (size_t i = 0; i < alive.size(); ++i) {
      EXPECT_EQ(alive[i], storage.dictionaries(i).id());
    }
  }
}

TEST_F(UserDictionaryStorageTest, ExportTest) {
  UserDictionaryStorage storage(GetUserDictionaryFile());
  uint64 id = 0;

  EXPECT_TRUE(storage.CreateDictionary("test", &id));

  UserDictionaryStorage::UserDictionary *dic =
      storage.GetUserDictionary(id);

  for (size_t i = 0; i < 1000; ++i) {
    UserDictionaryStorage::UserDictionaryEntry *entry = dic->add_entries();
    const string prefix = NumberUtil::SimpleItoa(static_cast<uint32>(i));
    // set empty fields randomly
    entry->set_key(prefix + "key");
    entry->set_value(prefix + "value");
    // "名詞"
    entry->set_pos(UserDictionary::NOUN);
    entry->set_comment(prefix + "comment");
  }

  const string export_file = FileUtil::JoinPath(FLAGS_test_tmpdir,
                                                "export.txt");

  EXPECT_FALSE(storage.ExportDictionary(id + 1, export_file));
  EXPECT_TRUE(storage.ExportDictionary(id, export_file));

  string file_string;
  // Copy whole contents of the file into |file_string|.
  {
    InputFileStream ifs(export_file.c_str());
    CHECK(ifs);
    ifs.seekg(0, std::ios::end);
    file_string.resize(ifs.tellg());
    ifs.seekg(0, std::ios::beg);
    ifs.read(&file_string[0], file_string.size());
    ifs.close();
  }
  UserDictionaryImporter::StringTextLineIterator iter(file_string);

  UserDictionaryStorage::UserDictionary dic2;
  EXPECT_EQ(UserDictionaryImporter::IMPORT_NO_ERROR,
            UserDictionaryImporter::ImportFromTextLineIterator(
                UserDictionaryImporter::MOZC,
                &iter, &dic2));

  dic2.set_id(id);
  dic2.set_name("test");

  EXPECT_EQ(dic2.DebugString(), dic->DebugString());
}

TEST_F(UserDictionaryStorageTest, SerializeTest) {
  // repeat 20 times
  for (int i = 0; i < 20; ++i) {
    FileUtil::Unlink(GetUserDictionaryFile());
    UserDictionaryStorage storage1(GetUserDictionaryFile());

    {
      EXPECT_FALSE(storage1.Load());
      const size_t dic_size = Util::Random(50) + 1;

      for (size_t i = 0; i < dic_size; ++i) {
        uint64 id = 0;
        EXPECT_TRUE(
            storage1.CreateDictionary(
                "test" + NumberUtil::SimpleItoa(static_cast<uint32>(i)), &id));
        const size_t entry_size = Util::Random(100) + 1;
        for (size_t j = 0; j < entry_size; ++j) {
          UserDictionaryStorage::UserDictionary *dic =
              storage1.mutable_dictionaries(i);
          UserDictionaryStorage::UserDictionaryEntry *entry =
              dic->add_entries();
          entry->set_key(GenRandomString(10));
          entry->set_value(GenRandomString(10));
          entry->set_pos(UserDictionary::NOUN);
          entry->set_comment(GenRandomString(10));
        }
      }

      EXPECT_TRUE(storage1.Lock());
      EXPECT_TRUE(storage1.Save());
      EXPECT_TRUE(storage1.UnLock());
    }

    UserDictionaryStorage storage2(GetUserDictionaryFile());
    {
      EXPECT_TRUE(storage2.Load());
    }

    EXPECT_EQ(storage1.DebugString(), storage2.DebugString());
  }
}

TEST_F(UserDictionaryStorageTest, GetUserDictionaryIdTest) {
  UserDictionaryStorage storage(GetUserDictionaryFile());
  EXPECT_FALSE(storage.Load());

  const size_t kDictionariesSize = 3;
  uint64 id[kDictionariesSize];
  EXPECT_TRUE(storage.CreateDictionary("testA", &id[0]));
  EXPECT_TRUE(storage.CreateDictionary("testB", &id[1]));

  uint64 ret_id[kDictionariesSize];
  EXPECT_TRUE(storage.GetUserDictionaryId("testA", &ret_id[0]));
  EXPECT_TRUE(storage.GetUserDictionaryId("testB", &ret_id[1]));
  EXPECT_FALSE(storage.GetUserDictionaryId("testC", &ret_id[2]));

  EXPECT_EQ(ret_id[0], id[0]);
  EXPECT_EQ(ret_id[1], id[1]);
}

TEST_F(UserDictionaryStorageTest, ConvertSyncDictionariesToNormalDictionaries) {
  // "名詞"
  const UserDictionary::PosType kPos = UserDictionary::NOUN;

  const struct TestData {
    bool is_sync_dictionary;
    bool is_removed_dictionary;
    bool has_normal_entry;
    bool has_removed_entry;
    string dictionary_name;
  } test_data[] = {
    { false, false, false, false, "non-sync dictionary (empty)" },
    { false, false, true, false, "non-sync dictionary (normal entry)" },
    { true, false, false, false, "sync dictionary (empty)" },
    { true, false, false, true, "sync dictionary (removed entry)" },
    { true, false, true, false, "sync dictionary (normal entry)" },
    { true, false, true, true, "sync dictionary (normal & removed entries)" },
    { true, true, false, false, "removed sync dictionary (empty)" },
    { true, true, false, true, "removed sync dictionary (removed entry)" },
    { true, true, true, false, "removed sync dictionary (normal entry)" },
    { true, true, true, true,
      "removed sync dictionary (normal & removed entries)" },
    { true, false, true, false,
      UserDictionaryStorage::default_sync_dictionary_name() },
  };

  UserDictionaryStorage storage(GetUserDictionaryFile());
  EXPECT_FALSE(storage.Load())
      << "At first, we expect there is not user dictionary file.";
  EXPECT_FALSE(storage.ConvertSyncDictionariesToNormalDictionaries())
      << "No sync dictionary available.";

  for (size_t i = 0; i < arraysize(test_data); ++i) {
    SCOPED_TRACE(Util::StringPrintf("add %d", static_cast<int>(i)));
    const TestData &data = test_data[i];
    CHECK(data.is_sync_dictionary ||
          !(data.is_removed_dictionary || data.has_removed_entry))
        << "Non-sync dictionary should NOT have removed dictionary / entry.";

    uint64 dict_id = 0;
    ASSERT_TRUE(storage.CreateDictionary(data.dictionary_name, &dict_id));
    UserDictionaryStorage::UserDictionary *dict =
        storage.mutable_dictionaries(storage.GetUserDictionaryIndex(dict_id));
    dict->set_syncable(data.is_sync_dictionary);
    dict->set_removed(data.is_removed_dictionary);
    if (data.has_normal_entry) {
      UserDictionaryStorage::UserDictionaryEntry *entry = dict->add_entries();
      entry->set_key("normal");
      entry->set_value("normal entry");
      entry->set_pos(kPos);
    }
    if (data.has_removed_entry) {
      UserDictionaryStorage::UserDictionaryEntry *entry = dict->add_entries();
      entry->set_key("removed");
      entry->set_value("removed entry");
      entry->set_pos(kPos);
      entry->set_removed(true);
    }
  }
  EXPECT_EQ(9, UserDictionaryStorage::CountSyncableDictionaries(storage));

  ASSERT_TRUE(storage.ConvertSyncDictionariesToNormalDictionaries());

  // "同期用辞書"
  const char *kDictionaryNameConvertedFromSyncableDictionary =
      "\xE5\x90\x8C\xE6\x9C\x9F\xE7\x94\xA8\xE8\xBE\x9E\xE6\x9B\xB8";
  const struct ExpectedData {
    bool has_normal_entry;
    string dictionary_name;
  } expected_data[] = {
    { false, "non-sync dictionary (empty)" },
    { true, "non-sync dictionary (normal entry)" },
    { true, "sync dictionary (normal entry)" },
    { true, "sync dictionary (normal & removed entries)" },
    { true, kDictionaryNameConvertedFromSyncableDictionary },
  };

  EXPECT_EQ(0, UserDictionaryStorage::CountSyncableDictionaries(storage));
  ASSERT_EQ(arraysize(expected_data), storage.dictionaries_size());
  for (size_t i = 0; i < arraysize(expected_data); ++i) {
    SCOPED_TRACE(Util::StringPrintf("verify %d", static_cast<int>(i)));
    const ExpectedData &expected = expected_data[i];
    const UserDictionaryStorage::UserDictionary &dict = storage.dictionaries(i);

    EXPECT_EQ(expected.dictionary_name, dict.name());
    EXPECT_FALSE(dict.syncable());
    EXPECT_FALSE(dict.removed());
    if (expected.has_normal_entry) {
      ASSERT_EQ(1, dict.entries_size());
      EXPECT_EQ("normal", dict.entries(0).key());
    } else {
      EXPECT_EQ(0, dict.entries_size());
    }
  }

  // Test duplicated dictionary name.
  storage.Clear();
  {
    uint64 dict_id = 0;
    storage.CreateDictionary(
        UserDictionaryStorage::default_sync_dictionary_name(), &dict_id);
    storage.CreateDictionary(
        kDictionaryNameConvertedFromSyncableDictionary, &dict_id);
    ASSERT_EQ(2, storage.dictionaries_size());
    UserDictionaryStorage::UserDictionary *dict;
    dict = storage.mutable_dictionaries(0);
    dict->set_syncable(true);
    dict->add_entries()->set_key("0");
    dict = storage.mutable_dictionaries(1);
    dict->set_syncable(false);
    dict->add_entries()->set_key("1");
  }
  ASSERT_TRUE(storage.ConvertSyncDictionariesToNormalDictionaries());
  EXPECT_EQ(0, UserDictionaryStorage::CountSyncableDictionaries(storage));
  EXPECT_EQ(2, storage.dictionaries_size());
  EXPECT_EQ(Util::StringPrintf("%s_1",
                               kDictionaryNameConvertedFromSyncableDictionary),
            storage.dictionaries(0).name());
  EXPECT_EQ(kDictionaryNameConvertedFromSyncableDictionary,
            storage.dictionaries(1).name());
}

TEST_F(UserDictionaryStorageTest, AddToAutoRegisteredDictionary) {
  {
    UserDictionaryStorage storage(GetUserDictionaryFile());
    EXPECT_EQ(0, storage.dictionaries_size());
    EXPECT_TRUE(storage.AddToAutoRegisteredDictionary(
        "key1", "value1", UserDictionary::NOUN));
    EXPECT_EQ(1, storage.dictionaries_size());
    EXPECT_EQ(1, storage.dictionaries(0).entries_size());
    const UserDictionaryStorage::UserDictionaryEntry &entry1 =
        storage.dictionaries(0).entries(0);
    EXPECT_EQ("key1", entry1.key());
    EXPECT_EQ("value1", entry1.value());
    EXPECT_EQ(UserDictionary::NOUN, entry1.pos());
    EXPECT_TRUE(entry1.auto_registered());

    EXPECT_TRUE(storage.AddToAutoRegisteredDictionary(
        "key2", "value2", UserDictionary::NOUN));
    EXPECT_EQ(1, storage.dictionaries_size());
    EXPECT_EQ(2, storage.dictionaries(0).entries_size());
    const UserDictionaryStorage::UserDictionaryEntry &entry2 =
        storage.dictionaries(0).entries(1);
    EXPECT_EQ("key2", entry2.key());
    EXPECT_EQ("value2", entry2.value());
    EXPECT_EQ(UserDictionary::NOUN, entry2.pos());
    EXPECT_TRUE(entry1.auto_registered());
  }

  {
    FileUtil::Unlink(GetUserDictionaryFile());
    UserDictionaryStorage storage(GetUserDictionaryFile());
    storage.Lock();
    // Already locked.
    EXPECT_FALSE(storage.AddToAutoRegisteredDictionary(
        "key", "value", UserDictionary::NOUN));
  }
}

#ifndef OS_ANDROID
// This is a test to check if the data stored by the new binary can be read
// by an older binary, considering the Dev -> Stable converting users.
// We can remove when the new Stable binary which supports reading new format
// is spread enough.
TEST_F(UserDictionaryStorageTest, BackwardCompatibilityTest) {
  {
    UserDictionaryStorage storage(GetUserDictionaryFile());
    // Add dummy entry.
    {
      UserDictionary *dictionary = storage.add_dictionaries();
      UserDictionary::Entry *entry = dictionary->add_entries();
      entry->set_key("key");
      entry->set_value("value");
      entry->set_comment("comment");
      entry->set_pos(UserDictionary::NOUN);
    }

    ASSERT_TRUE(storage.Lock());
    ASSERT_TRUE(storage.Save());
    ASSERT_TRUE(storage.UnLock());
  }

  // Make sure that the deprecated field is filled (in string).
  UserDictionaryStorage storage(GetUserDictionaryFile());
  ASSERT_TRUE(storage.LoadWithoutMigration());

  ASSERT_EQ(1, storage.dictionaries_size());
  const UserDictionary &dictionary = storage.dictionaries(0);
  ASSERT_EQ(1, dictionary.entries_size());
  const UserDictionary::Entry &entry = dictionary.entries(0);
  const UnknownFieldSet &unknown_field_set = entry.unknown_fields();
  ASSERT_EQ(1, unknown_field_set.field_count());
  const UnknownField &unknown_field = unknown_field_set.field(0);
  EXPECT_EQ(3, unknown_field.number());
  EXPECT_EQ(UnknownField::TYPE_LENGTH_DELIMITED, unknown_field.type());
  EXPECT_EQ("\xE5\x90\x8D\xE8\xA9\x9E", unknown_field.length_delimited());
}
#endif

TEST_F(UserDictionaryStorageTest, Export) {
  const int kDummyDictionaryId = 10;
  const string kPath = FileUtil::JoinPath(FLAGS_test_tmpdir, "exported_file");

  {
    UserDictionaryStorage storage(GetUserDictionaryFile());
    {
      UserDictionary *dictionary = storage.add_dictionaries();
      dictionary->set_id(kDummyDictionaryId);
      UserDictionary::Entry *entry = dictionary->add_entries();
      entry->set_key("key");
      entry->set_value("value");
      entry->set_pos(UserDictionary::NOUN);
      entry->set_comment("comment");
    }
    storage.ExportDictionary(kDummyDictionaryId, kPath);
  }

  Mmap mapped_data;
  ASSERT_TRUE(mapped_data.Open(kPath.c_str()));

  // Make sure the exported format, especially that the pos is exported in
  // Japanese.
  // "key value 名詞 comment" separted by a tab character.
#ifdef OS_WIN
  EXPECT_EQ("key\tvalue\t\xE5\x90\x8D\xE8\xA9\x9E\tcomment\r\n",
            string(mapped_data.begin(), mapped_data.size()));
#else
  EXPECT_EQ("key\tvalue\t\xE5\x90\x8D\xE8\xA9\x9E\tcomment\n",
            string(mapped_data.begin(), mapped_data.size()));
#endif  // OS_WIN
}

namespace {

enum SerializedPosType {
  NEW_ENUM_POS,
  LEGACY_STRING_POS,
  LEGACY_ENUM_POS,
};

void AddTestDummyUserDictionary(
    SerializedPosType serialized_pos_type, UnknownFieldSet *storage) {
  UnknownFieldSet dictionary;
  for (int i = UserDictionary::PosType_MIN;
       i <= UserDictionary::PosType_MAX; ++i) {
    UnknownFieldSet entry;
    entry.AddLengthDelimited(1, Util::StringPrintf("key%d", i));
    entry.AddLengthDelimited(2, Util::StringPrintf("value%d", i));
    switch (serialized_pos_type) {
      case NEW_ENUM_POS:
        entry.AddVarint(5, i);
        break;
      case LEGACY_STRING_POS:
        entry.AddLengthDelimited(
            3,
            UserDictionaryUtil::GetStringPosType(
                static_cast<UserDictionary::PosType>(i)));
        break;
      case LEGACY_ENUM_POS:
        entry.AddVarint(3, i);
        break;
      default:
        LOG(FATAL) << "Unknown serialized pos type: " << serialized_pos_type;
    }
    entry.AddLengthDelimited(4, Util::StringPrintf("comment%d", i));
    dictionary.AddLengthDelimited(
        4, SerializeUnknownFieldSetAsString(entry));
  }
  storage->AddLengthDelimited(
      2, SerializeUnknownFieldSetAsString(dictionary));
}

void WriteToFile(const string &value, const string &filepath) {
  OutputFileStream stream(filepath.c_str(), ios::out|ios::binary|ios::trunc);
  stream.write(value.data(), value.size());
}

}  // namespace

class UserDictionaryStorageMigrationTest
    : public UserDictionaryStorageTest,
      public ::testing::WithParamInterface<SerializedPosType> {
};

TEST_P(UserDictionaryStorageMigrationTest, Load) {
  {
    // Create serialized user dictionary data directly.
    UnknownFieldSet storage;
    AddTestDummyUserDictionary(GetParam(), &storage);
    WriteToFile(SerializeUnknownFieldSetAsString(storage),
                GetUserDictionaryFile());
  }

  UserDictionaryStorage storage(GetUserDictionaryFile());
  ASSERT_TRUE(storage.Load());

  ASSERT_EQ(1, storage.dictionaries_size()) << storage.Utf8DebugString();
  const UserDictionary &dictionary = storage.dictionaries(0);
  ASSERT_EQ(UserDictionary::PosType_MAX - UserDictionary::PosType_MIN + 1,
            dictionary.entries_size())
      << dictionary.Utf8DebugString();
  for (int i = 0; i < dictionary.entries_size(); ++i) {
    const int id = UserDictionary::PosType_MIN + i;
    const UserDictionary::Entry &entry = dictionary.entries(i);
    EXPECT_EQ(Util::StringPrintf("key%d", id), entry.key())
        << entry.Utf8DebugString();
    EXPECT_EQ(Util::StringPrintf("value%d", id), entry.value())
        << entry.Utf8DebugString();
    EXPECT_EQ(id, entry.pos()) << entry.Utf8DebugString();
    EXPECT_EQ(Util::StringPrintf("comment%d", id), entry.comment())
        << entry.Utf8DebugString();
  }
}

TEST_P(UserDictionaryStorageMigrationTest, LoadWithoutMigration) {
  {
    // Create serialized user dictionary data directly.
    UnknownFieldSet storage;
    AddTestDummyUserDictionary(GetParam(), &storage);
    WriteToFile(SerializeUnknownFieldSetAsString(storage),
                GetUserDictionaryFile());
  }

  UserDictionaryStorage storage(GetUserDictionaryFile());
  ASSERT_TRUE(storage.LoadWithoutMigration());

  ASSERT_EQ(1, storage.dictionaries_size()) << storage.Utf8DebugString();
  const UserDictionary &dictionary = storage.dictionaries(0);
  ASSERT_EQ(UserDictionary::PosType_MAX - UserDictionary::PosType_MIN + 1,
            dictionary.entries_size())
      << dictionary.Utf8DebugString();
  for (int i = 0; i < dictionary.entries_size(); ++i) {
    const int id = UserDictionary::PosType_MIN + i;
    const UserDictionary::Entry &entry = dictionary.entries(i);
    EXPECT_EQ(Util::StringPrintf("key%d", id), entry.key())
        << entry.Utf8DebugString();
    EXPECT_EQ(Util::StringPrintf("value%d", id), entry.value())
        << entry.Utf8DebugString();
    switch (GetParam()) {
      case NEW_ENUM_POS:
        ASSERT_TRUE(entry.has_pos());
        EXPECT_EQ(id, entry.pos());
        break;
      case LEGACY_STRING_POS: {
        const UnknownFieldSet &unknown_field_set = entry.unknown_fields();
        ASSERT_EQ(1, unknown_field_set.field_count());
        const UnknownField &unknown_field = unknown_field_set.field(0);
        EXPECT_EQ(UnknownField::TYPE_LENGTH_DELIMITED, unknown_field.type());
        EXPECT_EQ(3, unknown_field.number());
        EXPECT_EQ(
            UserDictionaryUtil::GetStringPosType(
                static_cast<UserDictionary::PosType>(id)),
            unknown_field.length_delimited());
        break;
      }
      case LEGACY_ENUM_POS: {
        const UnknownFieldSet &unknown_field_set = entry.unknown_fields();
        ASSERT_EQ(1, unknown_field_set.field_count());
        const UnknownField &unknown_field = unknown_field_set.field(0);
        EXPECT_EQ(UnknownField::TYPE_VARINT, unknown_field.type());
        EXPECT_EQ(3, unknown_field.number());
        EXPECT_EQ(id, unknown_field.varint());
        break;
      }
      default:
        LOG(FATAL) << "Unknown serialized pos type: " << GetParam();
    }
    EXPECT_EQ(Util::StringPrintf("comment%d", id), entry.comment())
        << entry.Utf8DebugString();
  }
}

INSTANTIATE_TEST_CASE_P(
    UserDictionaryStorageProtoMigration,
    UserDictionaryStorageMigrationTest,
    ::testing::Values(NEW_ENUM_POS, LEGACY_STRING_POS, LEGACY_ENUM_POS));

}  // namespace mozc
