/*
 * Copyright (c) KylinSoft  Co., Ltd. 2024. All rights reserved.
 *
 * kaiming is licensed under the GPL v2.0+.
 *
 * See the LICENSE file for more details.
 */

#ifndef __KMRUNNER_H__
#define __KMRUNNER_H__

#include "common/KMSubCommand.h"

/**
 * @brief 开明包运行功能封装
 */
class KMRunner final : public KMSubCommand
{
    DECLARE_DYNCREATE(KMRunner);

public:
    KMRunner();
    ~KMRunner() override = default;

    /**
     * @brief 开明子命令运行
     * @param argc 参数个数
     * @param argv 参数列表
     * @return 0 成功 非0 失败
     */
    int dispose(int argc, char **argv) override;

    /**
     * @brief 开始运行
     * @return true 成功 false 失败
     */
    bool start();

private:
    /**
     * @brief 解析命令行参数
     * @param argc 参数个数
     * @param argv 参数列表
     * @return true 成功 false 失败
     */
    bool parseArgs(int argc, char **argv);

    /**
     * @brief 获取app,base,runtime目录
     * @return true 成功 false 失败
     */
    bool getLayersDirs();

    /**
     * @brief 创建appdate子目录
     * @return true 成功 false 失败
     */
    bool ensureAppDataDir();

    /**
     * @brief 挂载app,base,runtime目录
     * @return true 成功 false 失败
     */
    bool mountLayers();

    /**
     * @brief 挂载基础路径
     * @return true 成功 false 失败
     */
    bool mountBase();

    /**
     * @brief 挂载数据配置路径
     * @return true 成功 false 失败
     */
    bool mountData();

    /**
     * @brief 权限管控
     * @return true 成功 false 失败
     */
    bool permissionControl();

    /**
     * @brief 生成ld.so.cache
     * @return true 成功 false 失败
     */
    bool genLdsocache();

    /**
     * @brief 设置process
     * @return true 成功 false 失败
     */
    bool setProcessCmd();

    /**
     * @brief 挂载dev设备
     * @return true 成功 false 失败
     */
    bool mountDev();

    /**
     * @brief 设置网络访问权限
     * @return true 成功 false 失败
     */
    bool setNetwork();

    /**
     * @brief 挂载指定目录
     * @return true 成功 false 失败
     */
    bool mountFileSystem();

    /**
     * @brief 挂载自动启动目录
     * @return true 成功 false 失败
     */
    bool mountAutoStart();

    /**
     * @brief 管控设备文件
     * @return true 成功 false 失败
     */
    bool permDev(std::string const &dev);

    /**
     * @brief 设置process的cap能力
     * @param cap 能力列表
     * @return true 成功 false 失败
     */
    bool setProcessCap(const std::vector<int> &cap);

    /**
     * @brief 挂载socket
     * @return true 成功 false 失败
     */
    bool mountSocket();

    /**
     * @brief 挂载share,包含字体,icon等
     * @return true 成功 false 失败
     */
    bool mountShare();

    /**
     * @brief 挂载共享目录
     * @return true 成功 false 失败
     */
    bool mountShareData();

    /**
     * @brief 挂载etc目录
     * @return true 成功 false 失败
     */
    bool mountEtc();

    /**
     * @brief 挂载许可
     *@ return true 成功 false 失败
     */
    bool mountXauthority();

    /**
     * @brief 挂载pulseaudio配置
     * @return true 成功 false 失败
     */
    bool mountPulseaudio();

    /**
     * @brief 挂载dbus配置
     * @return true 成功 false 失败
     */
    bool mountDbus();

    /**
     * @brief 挂载xdg-open,解决xdg-open穿透问题
     */
    void mountXdgOpen();

    /**
     * @brief 挂载x11-wayland兼容层
     */
    void mountX11Wayland();

    /**
     * @brief : 挂载x11
     * @return true 成功 false 失败
     */
    bool mountX11();

    /**
     * @brief 挂载wayland
     * @return true 成功 false 失败
     */
    bool mountWayland();

    /**
     * @brief 挂载journal配置
     */
    void mountJournal();

    /**
     * @brief 挂载GSSProxy配置
     */
    void mountGssproxy();

    /**
     * @brief 挂载resolved配置
     */
    void mountResolved();

    /**
     * @brief 组装运行命令
     * @return true 成功 false 失败
     */
    bool assembleCommand();

    /**
     * @brief 组装运行环境变量
     * @return true 成功 false 失败
     */
    bool assembleProcEnv();

    /**
     * @brief 设置进程运行命令
     * @return true 成功 false 失败
     */
    bool setProcessCmdArgs();

    /**
     * @brief 追加lowerdir
     * @param lowerdir lowerdir
     * @param dir 追加的目录
     */
    void appendLowerDir(std::string &lowerdir, const std::string &dir) const;

    /**
     * @brief 叠加目录
     * @param dir overlay目录路径
     * @param isOverlayHost 是否叠加宿主机目录
     */
    void overlayDir(const std::string &dir, bool isOverlayHost = true);

    /**
     * @brief 挂载dconf目录
     * @return true 成功 false 失败
     */
    bool mountDconf();

    /**
     *@brief 获取appdata路径
     *@return true 成功 false 失败
     */
    bool getAppDataPath();

    /**
     *@brief 解析dbus地址
     *@return string 路径
     */
    std::string pathFromAddress(const std::string &address) const;

    /**
     * @brief 生成ldso配置文件
     * @return true 成功 false 失败
     */
    bool genLdconfig();

    /**
     * @brief 检查当前系统是否支持 `userxattr` 文件系统特性
     * @return bool 如果支持 `userxattr` 特性则返回 `true`，否则返回 `false`。
     */
    bool supportsUserXAttr();

    /**
     * @brief 提权
     * @return true 成功 false 失败
     */
    bool privileged();

    /**
     * @brief 挂载指定目
     */
    void mountDir(const std::string &hostDir, const std::string &containDir, const std::string &type, std::vector<std::string> options);
    
    /**
     * @brief 检查内核配置文件中是否设置了 CONFIG_OVERLAY_FS_INDEX=y
     */
    bool isOverlayFsIndexOff();

    /**
     * @brief 判断是否有蓝牙权限
     */
    bool bluetoothRestricted();
private:
    class Private;
    std::shared_ptr<Private> d_ptr;
};

#endif // KMRUNNER_H
