/*
 * GlobalConfigHandler.h
 *
 *  Created on: May 3, 2022
 *      Author: Jona Petri (IRS)
 */

#ifndef MISSION_UTILITY_GLOBALCONFIGHANDLER_H_
#define MISSION_UTILITY_GLOBALCONFIGHANDLER_H_

#include <fsfw/action/ActionHelper.h>
#include <fsfw/action/HasActionsIF.h>
#include <fsfw/objectmanager/SystemObject.h>
#include <fsfw/serviceinterface/ServiceInterfaceStream.h>
#include <fsfw/storagemanager/StorageManagerIF.h>
#include <fsfw/tasks/ExecutableObjectIF.h>
#include <mission/memory/NvmParameterBase.h>

#include <sstream>
#include <string>

#include "GlobalConfigFileDefinitions.h"
#include "OBSWConfig.h"
#include "fsfw/parameters/HasParametersIF.h"
#include "fsfw/parameters/ParameterHelper.h"

static std::map<ParamIds, std::string> PARAM_KEY_MAP = {
    {PARAM0, "Parameter0"},
    {PARAM1, "Parameter1"},
};
/*
 * Idea: This class is intended to be used as a subclass for the Core Controller.
 * Its tasks is managing a configuration JSON file containing config values important for various
 * object. If some function to read or write a config value is called, a mutex should be used so
 * only one call is done at a time.
 */
class GlobalConfigHandler : public SystemObject,
                            public ExecutableObjectIF,
                            public NVMParameterBase {
 public:
  GlobalConfigHandler(object_id_t objectId, std::string configFilePath);
  virtual ~GlobalConfigHandler();

  static const uint8_t SUBSYSTEM_ID = SUBSYSTEM_ID::CONFIGHANDLER;

  static constexpr Event SET_CONFIGFILEVALUE_FAILED = MAKE_EVENT(1, severity::MEDIUM);
  static constexpr Event GET_CONFIGFILEVALUE_FAILED = MAKE_EVENT(2, severity::MEDIUM);
  static constexpr Event INSERT_CONFIGFILEVALUE_FAILED = MAKE_EVENT(3, severity::MEDIUM);
  static constexpr Event WRITE_CONFIGFILE_FAILED = MAKE_EVENT(4, severity::MEDIUM);
  static constexpr Event READ_CONFIGFILE_FAILED = MAKE_EVENT(5, severity::MEDIUM);

  ReturnValue_t performOperation(uint8_t operationCode);

  ReturnValue_t initialize();

  template <typename T>
  ReturnValue_t setConfigFileValue(ParamIds paramID, T data);
  template <typename T>
  ReturnValue_t getConfigFileValue(ParamIds paramID, T& data);

  ReturnValue_t ResetConfigFile();
  ReturnValue_t WriteConfigFile();
  std::string getConfigFileName();

 private:
  static MutexIF* CONFIG_LOCK;

  ReturnValue_t lockConfigFile();
  ReturnValue_t unlockConfigFile();
  ReturnValue_t resetConfigFileValues();

  ReturnValue_t setConfigFileName(std::string configFileName);

  ReturnValue_t ReadConfigFile();

  MessageQueueIF* commandQueue;
};

#endif /* MISSION_UTILITY_GLOBALCONFIGHANDLER_H_ */