import Quickshell
import Quickshell.Io
import QtQuick

import qs.config
import qs.services

ShellRoot {
    id: root

    function notification(idValue: int, desktopEntryValue: string, appNameValue: string): var {
        const closeHandlers = [];
        return {
            id: idValue,
            desktopEntry: desktopEntryValue,
            appName: appNameValue,
            appIcon: "",
            transient: false,
            lastGeneration: false,
            tracked: false,
            dismissed: false,
            closed: {
                connect: callback => closeHandlers.push(callback)
            },
            dismiss: function() {
                this.dismissed = true;
                for (const callback of closeHandlers)
                    callback();
            }
        };
    }

    function resetNotifications(): void {
        Notifs.history = [];
        Notifs.popups = [];
        Notifs.unreadCount = 0;
        Notifs.doNotDisturb = false;
    }

    function reset(): void {
        root.resetNotifications();
        Notifs.fallbackAppRules = {};
        Notifs.rememberedApplications = {};
        DesktopPreferences.set("notificationAppRules", {});
    }

    IpcHandler {
        target: "notification-app-rules-test"

        function exercise(): string {
            root.reset();

            const signal = root.notification(1, "org.signal.Signal.desktop", "Signal");
            Notifs.handleNotification(signal);
            const appId = Notifs.notificationAppId(signal);
            const initialRules = DesktopPreferences.get("notificationAppRules");

            const fallback = root.notification(6, "", "Fallback Terminal");
            Notifs.handleNotification(fallback);
            const fallbackId = Notifs.notificationAppId(fallback);
            const fallbackApplication = Notifs.applications.find(app => app.id === fallbackId);

            root.resetNotifications();
            Notifs.setAppRule(appId, { enabled: false });
            const muted = root.notification(2, "org.signal.Signal.desktop", "Signal");
            Notifs.handleNotification(muted);
            const mutedResult = {
                tracked: muted.tracked,
                history: Notifs.history.length,
                popups: Notifs.popups.length,
                unread: Notifs.unreadCount
            };

            root.reset();
            Notifs.doNotDisturb = true;
            const dnd = root.notification(3, "org.signal.Signal.desktop", "Signal");
            Notifs.handleNotification(dnd);

            Notifs.setAppRule("org.privacy.App.desktop", {
                showOnLockScreen: false,
                showContentOnLockScreen: false
            });
            const privateNotification = root.notification(4, "org.privacy.App.desktop", "Private");

            return JSON.stringify({
                appId: appId,
                initialRules: initialRules,
                fallback: {
                    id: fallbackId,
                    application: fallbackApplication
                },
                muted: mutedResult,
                dnd: {
                    tracked: dnd.tracked,
                    history: Notifs.history.length,
                    popups: Notifs.popups.length,
                    unread: Notifs.unreadCount
                },
                privacy: {
                    visible: Notifs.shouldShowOnLockScreen(privateNotification),
                    content: Notifs.shouldShowContentOnLockScreen(privateNotification)
                }
            });
        }

        function persist(): string {
            root.reset();
            const notification = root.notification(5, "org.persist.App.desktop", "Persist");
            Notifs.handleNotification(notification);
            Notifs.setAppRule("org.persist.App.desktop", {
                enabled: false,
                showOnLockScreen: true,
                showContentOnLockScreen: false
            });
            return JSON.stringify(DesktopPreferences.get("notificationAppRules"));
        }

        function restored(): string {
            return JSON.stringify(DesktopPreferences.get("notificationAppRules"));
        }

        function applications(): string {
            return JSON.stringify(Notifs.applications);
        }
    }
}
