#ifndef __KMCRUN_H__
#define __KMCRUN_H__

#include <string>
#include <optional>
#include <vector>
#include <map>
#include <variant>
#include <nlohmann/json.hpp>

#include "common/KMLogger.h"

class KMCrun final
{
public:
    KMCrun() = default;
    virtual ~KMCrun() = default;

public:
    /**
     * @brief 执行run命令 
     * @param options 命令行参数
     * @return true 成功 false 失败
     */
    static bool exec(const std::vector<std::string> &options);

    /**
     * @brief 执行run命令 
     * @param options 命令行参数
     * @param output 输出
     * @return true 成功 false 失败
     */
    template<typename T>
    static bool exec(const std::vector<std::string> &options, T &output)
    {
        std::vector<const char *> args;
        if (!getArgs(options, args))
            return false;

        bool ret = false;
        std::variant<bool, std::string> varOutput = std::string("");
        if (!(ret = doCmd(args, varOutput)))
            return ret;

        std::string outputStr = std::get<std::string>(varOutput);
        if (outputStr.empty())
        {
            output = {};
            return true;
        }

        try
        {
            nlohmann::json j = nlohmann::json::parse(outputStr);
            output = j;
        }
        catch (const std::exception &e)
        {
            KMError("json pase error: " + std::string(e.what()));
            return false;
        }

        return ret;
    }

private:
    /**
     * @brief 执行命令
     * @param processArgs 进程参数
     * @param output 输出
     * @return true 成功 false 失败
     */
    static bool doCmd(const std::vector<const char *> &processArgs, std::variant<bool, std::string> &output);

    /**
     * @brief 获取进程参数
     * @param options 命令行参数
     * @param args 进程参数
     * @return true 成功 false 失败
     */
    static bool getArgs(const std::vector<std::string> &options, std::vector<const char *> &args);
};

#endif // __KMCRUN_H__