"use client";
import { useCallback, useMemo, useRef, useState } from "react";
import { getUserMessage } from "@stigmer/sdk";
import { useStigmer } from "../hooks";
import { useExecutionTarget } from "../execution-target-context";
import { useRunnerAdapter } from "../runner-adapter";
import { toProtoExecutionTarget } from "../session/execution-target";
import { workflowUsesTriggerInput } from "./workflow-uses-trigger-input";
import { useInstanceEnvKeys } from "./useInstanceEnvKeys";
/**
 * Behavior hook that orchestrates the "run a workflow" flow.
 *
 * Manages form state (trigger message, runtime env overrides, instance
 * selection), validates required fields, and calls
 * `WorkflowExecutionClient.create()` on submission. On success, the
 * consumer-provided `onSuccess` callback receives the execution ID for
 * navigation or further action.
 *
 * This hook is framework-agnostic — it works identically in Next.js,
 * Vite, Tauri, or any React environment. Navigation and toast feedback
 * are the consumer's responsibility.
 *
 * @example
 * ```tsx
 * const flow = useRunWorkflowFlow({
 *   org: "acme",
 *   workflow,
 *   instances,
 *   onSuccess: (id) => router.push(`/workflows/executions/${id}`),
 *   onError: (msg) => toast.error(msg),
 * });
 *
 * <input value={flow.triggerMessage} onChange={e => flow.setTriggerMessage(e.target.value)} />
 * <button onClick={flow.submit} disabled={flow.isSubmitting}>Run</button>
 * ```
 */
export function useRunWorkflowFlow(options) {
    const { org, workflow, instances, onSuccess, onError } = options;
    const stigmer = useStigmer();
    const contextTarget = useExecutionTarget();
    const adapter = useRunnerAdapter();
    const usesTriggerInput = useMemo(() => workflowUsesTriggerInput(workflow), [workflow]);
    const [triggerMessage, setTriggerMessage] = useState("");
    const [runtimeEnv, setRuntimeEnv] = useState({});
    const [selectedInstanceId, setSelectedInstanceId] = useState(null);
    const [showTriggerMessage, setShowTriggerMessage] = useState(usesTriggerInput);
    const [isSubmitting, setIsSubmitting] = useState(false);
    const [error, setError] = useState(null);
    const [fieldErrors, setFieldErrors] = useState({});
    const stigmerRef = useRef(stigmer);
    stigmerRef.current = stigmer;
    const onSuccessRef = useRef(onSuccess);
    onSuccessRef.current = onSuccess;
    const onErrorRef = useRef(onError);
    onErrorRef.current = onError;
    const envDeclarations = useMemo(() => (workflow.spec?.env ? { ...workflow.spec.env } : {}), [workflow.spec?.env]);
    const selectedInstance = useMemo(() => selectedInstanceId
        ? instances.find((i) => i.metadata?.id === selectedInstanceId) ?? null
        : null, [instances, selectedInstanceId]);
    const { instanceEnvKeys, isLoading: isLoadingInstanceEnvKeys } = useInstanceEnvKeys(selectedInstance, org);
    const setEnvVar = useCallback((key, value) => {
        setRuntimeEnv((prev) => ({ ...prev, [key]: value }));
        setFieldErrors((prev) => {
            if (!prev[key])
                return prev;
            const next = { ...prev };
            delete next[key];
            return next;
        });
    }, []);
    const validate = useCallback(() => {
        const errors = {};
        for (const [key, decl] of Object.entries(envDeclarations)) {
            if (!decl.optional && !runtimeEnv[key]?.trim() && !instanceEnvKeys.has(key)) {
                errors[key] = `${key} is required`;
            }
        }
        setFieldErrors(errors);
        return Object.keys(errors).length === 0;
    }, [envDeclarations, runtimeEnv, instanceEnvKeys]);
    const submit = useCallback(async () => {
        if (isSubmitting)
            return;
        if (!validate())
            return;
        setIsSubmitting(true);
        setError(null);
        try {
            const workflowName = workflow.metadata?.name || workflow.metadata?.slug || "Workflow";
            const envInput = {};
            for (const [key, value] of Object.entries(runtimeEnv)) {
                if (value.trim()) {
                    const isSecret = envDeclarations[key]?.isSecret ?? false;
                    envInput[key] = { value, isSecret };
                }
            }
            const execution = await stigmerRef.current.workflowExecution.create({
                name: `${workflowName} ${new Date().toISOString().slice(0, 19).replace("T", " ")}`,
                org,
                workflowId: selectedInstanceId
                    ? undefined
                    : workflow.metadata?.id,
                workflowInstanceId: selectedInstanceId ?? undefined,
                triggerMessage: triggerMessage || undefined,
                triggerMetadata: {
                    source: "ui",
                    timestamp: new Date().toISOString(),
                },
                runtimeEnv: Object.keys(envInput).length > 0 ? envInput : undefined,
                executionTarget: contextTarget
                    ? toProtoExecutionTarget(contextTarget)
                    : undefined,
            });
            const executionId = execution.metadata?.id;
            if (!executionId) {
                throw new Error("Execution was created but no ID was returned. Please check the executions list.");
            }
            if (adapter && contextTarget === "local") {
                await adapter.onWorkflowExecutionCreated(executionId);
            }
            onSuccessRef.current(executionId);
        }
        catch (err) {
            const message = getUserMessage(err, "Failed to start workflow execution");
            setError(message);
            onErrorRef.current?.(message);
        }
        finally {
            setIsSubmitting(false);
        }
    }, [
        isSubmitting,
        validate,
        workflow.metadata,
        org,
        selectedInstanceId,
        triggerMessage,
        runtimeEnv,
        envDeclarations,
        adapter,
        contextTarget,
    ]);
    const reset = useCallback(() => {
        setTriggerMessage("");
        setRuntimeEnv({});
        setSelectedInstanceId(null);
        setShowTriggerMessage(usesTriggerInput);
        setError(null);
        setFieldErrors({});
    }, [usesTriggerInput]);
    return {
        triggerMessage,
        setTriggerMessage,
        runtimeEnv,
        setEnvVar,
        selectedInstanceId,
        setSelectedInstanceId,
        envDeclarations,
        instanceEnvKeys,
        isLoadingInstanceEnvKeys,
        usesTriggerInput,
        showTriggerMessage,
        setShowTriggerMessage,
        fieldErrors,
        isSubmitting,
        error,
        validate,
        submit,
        reset,
    };
}
//# sourceMappingURL=useRunWorkflowFlow.js.map