#include "bell_sender.h"

#include <yandex/maps/wiki/common/secrets.h>

#include <maps/libs/log8/include/log8.h>

#include <util/string/strip.h>
#include <util/system/env.h>

namespace maps::wiki::notifications_dispatcher {

namespace secrets = maps::wiki::common::secrets;

namespace {

const TString SUP_TOKEN_ENV = "SUP_TOKEN";

}  // namespace

void BellSender::sendGroupedNotification(
    GroupedNotificationGateway& gng,
    social::SentNotificationGateway& sentNotificationGateway,
    const BellNotificationConfig& notificationConfig,
    GroupedNotification& notification
) {
    notification.pending = false;
    gng.update(notification);

    auto pushId = bellClient_.push(notificationConfig.makeBellPushInfo(notification));

    auto sentNotification = notificationConfig.makeSentNotificationEntry(notification, pushId);
    sentNotificationGateway.insert(sentNotification);
}

void BellSender::sendPendingGroupedNotifications(Grouper& grouper, const BellNotificationConfig& notificationConfig) {
    auto slaveTxnSocial = socialPool_.slaveTransaction();
    auto pendingNotifications = grouper.getPendingNotifications(
        *slaveTxnSocial,
        notificationConfig.grouperNotificationType(),
        whitelist_);

    INFO() << "Notifying " << pendingNotifications.size() << " users with Bell";

    // Each notification is sent inside it's own transaction
    for (auto& notification : pendingNotifications) {
        auto txnSocial = socialPool_.masterWriteableTransaction();

        GroupedNotificationGateway gng{*txnSocial};
        social::SentNotificationGateway sentNotificationGateway{*txnSocial};

        sendGroupedNotification(gng, sentNotificationGateway, notificationConfig, notification);

        txnSocial->commit();
    }
}

bell_client::Configuration BellSender::makeBellConfig(const common::ExtendedXmlDoc& cfg) {
    std::string supToken = Strip(GetEnv(SUP_TOKEN_ENV));
    if (supToken.empty()) {
        supToken = secrets::tokenByKey(secrets::Key::RobotWikimapSupToken);
    }

    auto bellNode = cfg.node("/config/services/tasks/notifications-dispatcher/bell-client");
    bell_client::Configuration config(
        bellNode.attr<std::string>("base-url"),
        supToken,
        bellNode.attr<std::string>("project"),  // nmaps -- registered in SUP
        bellNode.attr<std::string>("service"));  // map_editor -- key for Tanker

    return config;
}

}  // maps::wiki::notifications_dispatcher
