/**
 * Copyright © 2020 IBM Corporation
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
#include "event.hpp"

#include "action.hpp"
#include "config_base.hpp"
#include "group.hpp"
#include "manager.hpp"

#include <fmt/format.h>

#include <nlohmann/json.hpp>
#include <phosphor-logging/log.hpp>
#include <sdbusplus/bus.hpp>

#include <algorithm>
#include <optional>

namespace phosphor::fan::control::json
{

using json = nlohmann::json;
using namespace phosphor::logging;

Event::Event(const json& jsonObj, sdbusplus::bus::bus& bus, Manager* mgr,
             std::map<configKey, std::unique_ptr<Group>>& groups,
             std::map<configKey, std::unique_ptr<Zone>>& zones) :
    ConfigBase(jsonObj),
    _bus(bus), _manager(mgr), _zones(zones)
{
    // Event could have a precondition
    if (!jsonObj.contains("precondition"))
    {
        // Event groups are optional
        if (jsonObj.contains("groups"))
        {
            setGroups(jsonObj, groups);
        }
        // Event actions are optional
        if (jsonObj.contains("actions"))
        {
            setActions(jsonObj, groups);
        }
        setTriggers(jsonObj);
    }
    else
    {
        setPrecond(jsonObj, groups);
    }
}

void Event::configGroup(Group& group, const json& jsonObj)
{
    if (!jsonObj.contains("interface") || !jsonObj.contains("property") ||
        !jsonObj["property"].contains("name"))
    {
        log<level::ERR>("Missing required group attribute",
                        entry("JSON=%s", jsonObj.dump().c_str()));
        throw std::runtime_error("Missing required group attribute");
    }

    // Get the group members' interface
    auto intf = jsonObj["interface"].get<std::string>();
    group.setInterface(intf);

    // Get the group members' property name
    auto prop = jsonObj["property"]["name"].get<std::string>();
    group.setProperty(prop);

    // Get the group members' data type
    if (jsonObj["property"].contains("type"))
    {
        std::optional<std::string> type =
            jsonObj["property"]["type"].get<std::string>();
        group.setType(type);
    }

    // Get the group members' expected value
    if (jsonObj["property"].contains("value"))
    {
        std::optional<PropertyVariantType> value =
            getJsonValue(jsonObj["property"]["value"]);
        group.setValue(value);
    }
}

void Event::setPrecond(const json& jsonObj,
                       std::map<configKey, std::unique_ptr<Group>>& groups)
{
    const auto& precond = jsonObj["precondition"];
    if (!precond.contains("name") || !precond.contains("groups") ||
        !precond.contains("triggers") || !precond.contains("events"))
    {
        log<level::ERR>("Missing required event precondition attributes",
                        entry("JSON=%s", precond.dump().c_str()));
        throw std::runtime_error(
            "Missing required event precondition attributes");
    }
    setGroups(precond, groups);
    setTriggers(precond);
}

void Event::setGroups(const json& jsonObj,
                      std::map<configKey, std::unique_ptr<Group>>& groups)
{
    for (const auto& jsonGrp : jsonObj["groups"])
    {
        if (!jsonGrp.contains("name"))
        {
            log<level::ERR>("Missing required group name attribute",
                            entry("JSON=%s", jsonGrp.dump().c_str()));
            throw std::runtime_error("Missing required group name attribute");
        }

        configKey eventProfile =
            std::make_pair(jsonGrp["name"].get<std::string>(), _profiles);
        auto grpEntry = std::find_if(
            groups.begin(), groups.end(), [&eventProfile](const auto& grp) {
                return Manager::inConfig(grp.first, eventProfile);
            });
        if (grpEntry != groups.end())
        {
            auto group = Group(*grpEntry->second);
            configGroup(group, jsonGrp);
            _groups.emplace_back(group);
        }
    }
}

void Event::setActions(const json& jsonObj,
                       std::map<configKey, std::unique_ptr<Group>>& groups)
{
    for (const auto& jsonAct : jsonObj["actions"])
    {
        if (!jsonAct.contains("name"))
        {
            log<level::ERR>("Missing required event action name",
                            entry("JSON=%s", jsonAct.dump().c_str()));
            throw std::runtime_error("Missing required event action name");
        }

        // Append action specific groups to the list of event groups for each
        // action in the event
        auto actionGroups = _groups;
        if (jsonObj.contains("groups"))
        {
            for (const auto& jsonGrp : jsonObj["groups"])
            {
                if (!jsonGrp.contains("name"))
                {
                    log<level::ERR>("Missing required group name attribute",
                                    entry("JSON=%s", jsonGrp.dump().c_str()));
                    throw std::runtime_error(
                        "Missing required group name attribute");
                }

                configKey eventProfile = std::make_pair(
                    jsonGrp["name"].get<std::string>(), _profiles);
                auto grpEntry = std::find_if(groups.begin(), groups.end(),
                                             [&eventProfile](const auto& grp) {
                                                 return Manager::inConfig(
                                                     grp.first, eventProfile);
                                             });
                if (grpEntry != groups.end())
                {
                    auto group = Group(*grpEntry->second);
                    configGroup(group, jsonGrp);
                    actionGroups.emplace_back(group);
                }
            }
        }
        if (actionGroups.empty())
        {
            log<level::DEBUG>(
                fmt::format("No groups configured for event {}'s action {} "
                            "based on the active profile(s)",
                            getName(), jsonAct["name"].get<std::string>())
                    .c_str());
        }

        // Determine list of zones action should be run against
        std::vector<std::reference_wrapper<Zone>> actionZones;
        if (!jsonObj.contains("zones"))
        {
            // No zones configured on the action results in the action running
            // against all zones matching the event's active profiles
            for (const auto& zone : _zones)
            {
                configKey eventProfile =
                    std::make_pair(zone.second->getName(), _profiles);
                auto zoneEntry = std::find_if(_zones.begin(), _zones.end(),
                                              [&eventProfile](const auto& z) {
                                                  return Manager::inConfig(
                                                      z.first, eventProfile);
                                              });
                if (zoneEntry != _zones.end())
                {
                    actionZones.emplace_back(*zoneEntry->second);
                }
            }
        }
        else
        {
            // Zones configured on the action result in the action only running
            // against those zones if they match the event's active profiles
            for (const auto& jsonZone : jsonObj["zones"])
            {
                configKey eventProfile =
                    std::make_pair(jsonZone.get<std::string>(), _profiles);
                auto zoneEntry = std::find_if(_zones.begin(), _zones.end(),
                                              [&eventProfile](const auto& z) {
                                                  return Manager::inConfig(
                                                      z.first, eventProfile);
                                              });
                if (zoneEntry != _zones.end())
                {
                    actionZones.emplace_back(*zoneEntry->second);
                }
            }
        }
        if (actionZones.empty())
        {
            log<level::DEBUG>(
                fmt::format("No zones configured for event {}'s action {} "
                            "based on the active profile(s)",
                            getName(), jsonAct["name"].get<std::string>())
                    .c_str());
        }

        // Create the action for the event
        auto actObj = ActionFactory::getAction(
            jsonAct["name"].get<std::string>(), jsonAct,
            std::move(actionGroups), std::move(actionZones));
        if (actObj)
        {
            _actions.emplace_back(std::move(actObj));
        }
    }
}

void Event::setTriggers(const json& jsonObj)
{
    if (!jsonObj.contains("triggers"))
    {
        log<level::ERR>("Missing required event triggers list",
                        entry("JSON=%s", jsonObj.dump().c_str()));
        throw std::runtime_error("Missing required event triggers list");
    }
}

} // namespace phosphor::fan::control::json
