/*
 * Copyright 2023 KylinSoft Co., Ltd.
 *
 * This program is free software: you can redistribute it and/or modify it under
 * the terms of the GNU General Public License as published by the Free Software
 * Foundation, either version 3 of the License, or (at your option) any later
 * version.
 *
 * This program is distributed in the hope that it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
 * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License along with
 * this program. If not, see <https://www.gnu.org/licenses/>.
 */

#ifndef APPSTATUSMANAGER_H
#define APPSTATUSMANAGER_H

#include <QObject>
#include <QMap>
#include "timerwheel.h"
#include "appinfomanager.h"
#include "appcgroup.h"
#include "dbusservices/whitelistmanager.h"
#include "common.h"

class Policy;
class AppInfoManager;
class AppStatusManager : public QObject
{
    Q_OBJECT
public:
    explicit AppStatusManager(AppInfoManager *parent);

    /**
     * @brief newAppInstance
     * @param appId
     * @param forkPid
     * @param instlndex
     * @return
     */
    QString newAppInstance(const QString &appId, const QList<int> &pids);

    /**
     * @brief deleteAppCGroup
     * @param cgroupName
     * @return
     */
    bool deleteAppCGroup(const QString &cgroupName);

    void appFinished(const QString &appId, const QString &instName);

    /**
     * @brief activeAppChanged
     * @param currentAppId
     * @param preAppId
     */
    void activeAppChanged(const QString &currentAppId, 
                          const QString &currentInstName,
                          const QString &preAppId, 
                          const QString &preInstName,
                          bool preAppMinimized);

    void appWidsIsEmpty(const QString &appId, const QString &instance);

    void appStatusTimeOutCallback(timerwheel::AppData appData);

    void resourceThresholdWarning(Policy::Feature resource, Policy::ResourceUrgency level);
    void tabletModeChanged(bool isTablet);

    QString cgroupWithPid(int pid);

    bool thawApp(const QString &appId, const QString &cgroupName);

    void aboutToQuitApp();

    void initConnections();

    bool ThawApps();

private Q_SLOTS:
    void updateWhitelistAppStatus(QString desktopName);

private:
    void callMprisDbus(const QString &dbusService);
    bool setProcessResourceValue(const QString &appId,
                                 const QString &desktopFile,
                                 const QString &cgroupName,
                                 const QString &attrName,
                                 int value);

private:
    timerwheel::TimerWheel *m_timerWheel;
    QMap<QString, QMap<QString, int>> m_cgroupInfo;
    AppInfoManager *m_appInfoManager;
    AppCGroup *m_appCGroup;
    Policy *m_policy;
    WhiteListManager &m_whiteListManager = common::Singleton<WhiteListManager>::GetInstance();
};

#endif // APPSTATUSMANAGER_H
