import { AppNode, nodeLabel, useEnv, useMessages, useProjectId, useStateStore } from "@/lib/state";
import { Button } from "./ui/button";
import { useCallback, useEffect, useState } from "react";
import { generateDodoConfig } from "@/lib/config";
import { useNodes, useReactFlow } from "@xyflow/react";
import { useToast } from "@/hooks/use-toast";

export function Actions() {
    const { toast } = useToast();
    const store = useStateStore();
    const projectId = useProjectId();
    const nodes = useNodes<AppNode>();
    const env = useEnv();
    const messages = useMessages();
    const instance = useReactFlow();
    const [ok, setOk] = useState(false);
    const [loading, setLoading] = useState(false);
    useEffect(() => {
        setOk(!messages.some((m) => m.type === "FATAL"));
    }, [messages, setOk]);
    const monitor = useCallback(async () => {
        const m = async function () {
            const resp = await fetch(`/api/project/${projectId}/status`, {
                method: "GET",
                headers: {
                    "Content-Type": "application/json",
                },
            })
            if (resp.status !== 200) {
                return;
            }
            const data: { type: string, name: string, status: string }[] = await resp.json();
            console.log(data);
            for (const n of nodes) {
                if (n.type === "network") {
                    continue;
                }
                const d = data.find((d) => n.type === d.type && nodeLabel(n) === d.name);
                if (d !== undefined) {
                    store.updateNodeData(n.id, {
                        state: d?.status,
                    });
                }
            }
            if (data.find((d) => d.status !== "success" && d.status != "failure") !== undefined) {
                setTimeout(m, 1000);
            }
        };
        setTimeout(m, 100);
    }, [projectId, nodes]);
    const deploy = useCallback(async () => {
        if (projectId == null) {
            return;
        }
        setLoading(true);
        try {
            const config = generateDodoConfig(nodes, env);
            if (config == null) {
                throw new Error("MUST NOT REACH!");
            }
            const resp = await fetch(`/api/project/${projectId}/deploy`, {
                method: "POST",
                headers: {
                    "Content-Type": "application/json",
                },
                body: JSON.stringify({
                    state: JSON.stringify(instance.toObject()),
                    config,
                }),
            });
            if (resp.ok) {
                toast({
                    title: "Deployment succeeded",
                });
                monitor();
            } else {
                toast({
                    variant: "destructive",
                    title: "Deployment failed",
                    description: await resp.text(),
                });
            }
        } catch (e) {
            console.log(e);
            toast({
                variant: "destructive",
                title: "Deployment failed",
            });
        } finally {
            setLoading(false);
        }
    }, [projectId, instance, nodes, env, setLoading]);
    const [st, setSt] = useState<string>();
    const save = useCallback(async () => {
        if (projectId == null) {
            return;
        }
        const resp = await fetch(`/api/project/${projectId}/saved`, {
            method: "POST",
            headers: {
                "Content-Type": "application/json",
            },
            body: JSON.stringify(instance.toObject()),
        });
        if (resp.ok) {
            toast({
                title: "Save succeeded",
            });
        } else {
            toast({
                variant: "destructive",
                title: "Save failed",
                description: await resp.text(),
            });
        }
    }, [projectId, instance, setSt]);
    const restoreSaved = useCallback(async () => {
        if (projectId == null) {
            return;
        }
        const resp = await fetch(`/api/project/${projectId}/saved`, {
            method: "GET",
        });
        const inst = await resp.json();
        const { x = 0, y = 0, zoom = 1 } = inst.viewport;
        store.setNodes(inst.nodes || []);
        store.setEdges(inst.edges || []);
        instance.setViewport({ x, y, zoom });
    }, [projectId, instance, st]);
    const clear = useCallback(() => {
        store.setEdges([]);
        store.setNodes([]);
        instance.setViewport({ x: 0, y: 0, zoom: 1 });
    }, [store]);
    // TODO(gio): Update store
    const deleteProject = useCallback(async () => {
        if (projectId == null) {
            return;
        }
        const resp = await fetch(`/api/project/${projectId}`, {
            method: "DELETE",
        });
        if (resp.ok) {
            clear();
            store.setProject(undefined);
            toast({
                title: "Save succeeded",
            });
        } else {
            toast({
                variant: "destructive",
                title: "Save failed",
                description: await resp.text(),
            });
        }
    }, [store, clear]);
    const [props, setProps] = useState({});
    useEffect(() => {
        if (loading) {
            setProps({ loading: true });
        } else if (ok) {
            setProps({ disabled: false });
        } else {
            setProps({ disabled: true });
        }
    }, [ok, loading, setProps]);
    return (
        <>
            <Button onClick={deploy} {...props}>Deploy</Button>
            <Button onClick={save}>Save</Button>
            <Button onClick={restoreSaved}>Restore</Button>
            <Button onClick={clear} variant="destructive">Clear</Button>
            <Button onClick={deleteProject} variant="destructive" disabled={projectId === undefined}>Delete</Button>
        </>
    )
}
