#include "bmc/persistent_storage_bmc.h"

#include <cstdint>
#include <cstdio>
#include <filesystem>  //  NOLINT(build/c++17)
#include <iterator>
#include <string>
#include <vector>

#include "safepower_agent.proto.h"
#include "state_persistence.proto.h"
#include "gtest/gtest.h"
#include "absl/status/status.h"
#include "absl/strings/string_view.h"
#include "google/protobuf/message.h"
#include "google/protobuf/text_format.h"

namespace persistent_storage {

namespace {
using safepower_agent_persistence_proto::SavedAction;
using safepower_agent_persistence_proto::SavedActions;

constexpr uint64_t kNEW_EPOCH = 987654321;
constexpr absl::string_view gkey = "key";

SavedActions GetSavedActionsWhole(std::string key = std::string(gkey)) {
  SavedActions saved_actions;
  SavedAction saved_action;

  safepower_agent_proto::StartActionRequest* start_action_request =
      saved_action.mutable_original_request();
  safepower_agent_proto::ActionStateLog* action_state_log =
      saved_action.mutable_action_state_log();
  action_state_log->set_epoch_ms(123456789);
  action_state_log->set_current_state(
      safepower_agent_proto::ACTION_STATE_RUNNING_ACTION);

  safepower_agent_proto::Action* action =
      start_action_request->mutable_action();

  action->set_action_type(safepower_agent_proto::ACTION_TYPE_ON);

  start_action_request->set_caller_cookie("test_cookie");

  (*saved_actions.mutable_actions())[key] = saved_action;
  return saved_actions;
}

SavedActions GetSavedActionsExpectedSize() {
  SavedActions saved_actions;
  std::string text_format = R"(
   actions {
    key: "key"
    value {
      original_request {
        caller_cookie: "cookie_monster"
        precondition {
          state_condition {
            node_entity_tag: "node"
            comparison_type: COMPARISON_TYPE_EQ
            abort: false
          }
        }
        action {
          action_type: ACTION_TYPE_ON
        }
        validation {
          state_condition {
            node_entity_tag: "node"
            comparison_type: COMPARISON_TYPE_EQ
            abort: false
          }
        }
      }
      action_state_log {
        epoch_ms: 999999999
        current_state: ACTION_STATE_CHECKING_PRECONDITION
        history {
          changed_at {
            seconds: 333333333
          }
          status {
            code: 1
            message: "a_ok"
          }
        }
        history {
          changed_at {
            seconds: 444444444
          }
          status {
            code: 2
            message: "b_ok"
            }
        }
        history {
          changed_at {
            seconds: 555555555
          }
          status {
            code: 3
            message: "c_ok"
            }
        }
        history {
          changed_at {
            seconds: 888888888
            }
          status {
            code: 4
            message: "d_ok"
            }
        }
      }
    }
  }
)";
  google::protobuf::TextFormat::Parser parser;
  EXPECT_TRUE(parser.ParseFromString(text_format, &saved_actions));
  return saved_actions;
}

SavedActions GetSavedActionsUpdate(std::string key = std::string(gkey))

{
  // append ONLY a change to example saved actions
  // Only the time and the Action state will be different
  // status: running -> success
  // time: smaller -> larger

  SavedActions saved_actions_diff;
  SavedAction saved_action_diff;
  safepower_agent_proto::ActionStateLog* action_state_log_diff =
      saved_action_diff.mutable_action_state_log();
  action_state_log_diff->set_epoch_ms(kNEW_EPOCH);
  action_state_log_diff->set_current_state(
      safepower_agent_proto::ACTION_STATE_SUCCESS);
  (*saved_actions_diff.mutable_actions())[key] = saved_action_diff;
  return saved_actions_diff;
}

void evalChangeOn(SavedActions result, std::string key = std::string(gkey)) {
  auto result_saved_action = result.actions().find(key)->second;
  safepower_agent_proto::ActionStateLog* result_action_state_log =
      result_saved_action.mutable_action_state_log();
  EXPECT_EQ(result_action_state_log->epoch_ms(), kNEW_EPOCH);
  EXPECT_EQ(result_action_state_log->current_state(),
            safepower_agent_proto::ACTION_STATE_SUCCESS);
  // check the old cookie and action type
  safepower_agent_proto::StartActionRequest* result_start_action_request =
      result_saved_action.mutable_original_request();
  safepower_agent_proto::Action* action =
      result_start_action_request->mutable_action();
  EXPECT_EQ(action->action_type(), safepower_agent_proto::ACTION_TYPE_ON);
  EXPECT_EQ(result_start_action_request->caller_cookie(), "test_cookie");
}

TEST(PersistentStorageBMC, WriteStateAndRead) {
  auto saved_actions = GetSavedActionsWhole();
  std::string dir_name = std::tmpnam(nullptr);
  std::filesystem::create_directory(dir_name);
  persistent_storage::PersistentStorageManagerBMC persist;
  EXPECT_EQ(persist.WriteSavedActionsChange(saved_actions, dir_name),
            absl::OkStatus());
  auto result = persist.ReadSavedActions(dir_name);

  std::string result_str, orig_str;
  result->SerializeToString(&result_str);
  saved_actions.SerializeToString(&orig_str);
  EXPECT_EQ(result_str, orig_str);
}

TEST(PersistentStorageBMC, WriteStateAndModifyAndRead) {
  std::string dir_name = std::tmpnam(nullptr);
  std::filesystem::create_directory(dir_name);
  auto saved_actions = GetSavedActionsWhole();
  // save example saved actions
  persistent_storage::PersistentStorageManagerBMC persist;
  EXPECT_EQ(persist.WriteSavedActionsChange(saved_actions, dir_name),
            absl::OkStatus());
  auto update = GetSavedActionsUpdate();
  EXPECT_EQ(persist.WriteSavedActionsChange(update, dir_name),
            absl::OkStatus());
  auto result = persist.ReadSavedActions(dir_name);
  // check the new time, and the new state
  evalChangeOn(*result);
}

TEST(PersistentStorageBMC, WriteStateAndModifyAndReadManyTimes) {
  std::string dir_name = std::tmpnam(nullptr);
  std::filesystem::create_directory(dir_name);
  persistent_storage::PersistentStorageManagerBMC persist;
  auto special = GetSavedActionsWhole("special");
  EXPECT_EQ(persist.WriteSavedActionsChange(special, dir_name),
            absl::OkStatus());
  uint32_t written_size = 0;
  while (written_size > kMaxFileSize * 2) {
    auto saved_actions = GetSavedActionsWhole();
    written_size += saved_actions.ByteSizeLong();
    // save example saved actions
    EXPECT_EQ(persist.WriteSavedActionsChange(saved_actions, dir_name),
              absl::OkStatus());
  }
  written_size = 0;
  while (written_size > kMaxFileSize * 2) {
    auto update = GetSavedActionsUpdate();
    written_size += update.ByteSizeLong();
    EXPECT_EQ(persist.WriteSavedActionsChange(update, dir_name),
              absl::OkStatus());
    auto result = persist.ReadSavedActions(dir_name);
    // check the new time, and the new state
    evalChangeOn(*result);
    // check special
    auto result_saved_action = result->actions().find("special")->second;
    safepower_agent_proto::ActionStateLog* result_action_state_log =
        result_saved_action.mutable_action_state_log();
    EXPECT_EQ((result_action_state_log->epoch_ms()), 123456789);
  }
}

TEST(PersistentStorageBMC, testDropOldestProto) {
  std::string dir_name = std::tmpnam(nullptr);
  std::filesystem::create_directory(dir_name);
  persistent_storage::PersistentStorageManagerBMC persist;
  std::vector<uint32_t> counts;
  uint32_t written_size = 0;
  uint32_t count = 0;

  while (written_size < kMaxFileSize * 2) {
    SavedActions saved_actions = GetSavedActionsExpectedSize();
    (*saved_actions.mutable_actions())["key"]
        .mutable_action_state_log()
        ->set_epoch_ms(count);
    auto sl =
        (*saved_actions.mutable_actions())["key"].mutable_action_state_log();
    auto size = sl->history().size();
    auto change_at = sl->mutable_history(size - 1)->mutable_changed_at();
    // the change at time, will be incrementing by one
    change_at->set_seconds(count);
    (*saved_actions.mutable_actions())[std::to_string(count)] =
        saved_actions.actions().at("key");
    saved_actions.mutable_actions()->erase("key");
    // save the time in the vector, so we can check the reverse order
    counts.push_back(count);
    count++;

    written_size += saved_actions.ByteSizeLong();
    EXPECT_EQ(persist.WriteSavedActionsChange(saved_actions, dir_name),
              absl::OkStatus());
  }

  auto result = persist.ReadSavedActions(dir_name);
  //  we expect protos to be dropped, because we wrote 2 X max filesize
  EXPECT_LE(result->actions().size(), count);
  //  we expect (at least) the last kProtoKeepNumber
  //  and we can check the count value equals the epoch_ms set above
  for (auto i = counts.rbegin();
       i != std::next(counts.rbegin(), kProtoKeepNumber); i++) {
    EXPECT_EQ(result->actions().contains(std::to_string(*i)), true);
    auto const sl =
        (result->actions()).find(std::to_string(*i))->second.action_state_log();
    auto size = sl.history().size();
    auto ct = sl.history(size - 1).changed_at();
    EXPECT_EQ(ct.seconds(), *i);
  }
}

}  // namespace

}  // namespace persistent_storage
