"use client";
import { useCallback, useEffect, useMemo, useRef, useState } from "react";
import { toError } from "../internal/toError.js";
import { loadEntryFiles, peekEntryListing } from "./workspaceListingCache.js";
const EMPTY_TREE = [];
/**
 * Behavior hook that fetches and caches a file listing for a single
 * workspace entry, converting it into a {@link TreeNode} hierarchy.
 *
 * - Calls the platform-injected `lister` (via the shared
 *   {@link loadEntryFiles} cache) when the
 *   entry changes.
 * - Reads the shared listing cache so tab switches, re-expands, and the search
 *   surface are instant without re-fetching (one cache, keyed by `entry.id`).
 * - Returns an empty tree and skips the call when `lister` is
 *   `undefined` (graceful degradation — DD-011 opt-in).
 * - Memoizes the return value for referential stability (DD-010).
 *
 * @example
 * ```tsx
 * const { tree, isLoading, error, truncated, refresh } = useWorkspaceFiles({
 *   entry: selectedEntry,
 *   lister: workspaceFileLister,
 * });
 * ```
 */
export function useWorkspaceFiles({ entry, lister, }) {
    const [isLoading, setIsLoading] = useState(false);
    const [error, setError] = useState(null);
    const [tree, setTree] = useState(EMPTY_TREE);
    const [truncated, setTruncated] = useState(false);
    const fetchIdRef = useRef(0);
    const fetchFiles = useCallback(async (target, bustCache) => {
        if (!lister)
            return;
        if (!bustCache) {
            const cached = peekEntryListing(target.id);
            if (cached) {
                setTree(cached.tree);
                setTruncated(cached.truncated);
                setError(null);
                setIsLoading(false);
                return;
            }
        }
        const id = ++fetchIdRef.current;
        setIsLoading(true);
        setError(null);
        try {
            const listing = await loadEntryFiles(target, lister, { bustCache });
            if (fetchIdRef.current !== id)
                return;
            if (listing === null) {
                setTree(EMPTY_TREE);
                setTruncated(false);
                setIsLoading(false);
                return;
            }
            setTree(listing.tree);
            setTruncated(listing.truncated);
            setIsLoading(false);
        }
        catch (err) {
            if (fetchIdRef.current !== id)
                return;
            setError(toError(err));
            setTree(EMPTY_TREE);
            setTruncated(false);
            setIsLoading(false);
        }
    }, [lister]);
    useEffect(() => {
        if (!entry || !lister) {
            setTree(EMPTY_TREE);
            setTruncated(false);
            setIsLoading(false);
            setError(null);
            return;
        }
        fetchFiles(entry, false);
    }, [entry, lister, fetchFiles]);
    const refresh = useCallback(() => {
        if (entry && lister) {
            fetchFiles(entry, true);
        }
    }, [entry, lister, fetchFiles]);
    return useMemo(() => ({ tree, isLoading, error, truncated, refresh }), [tree, isLoading, error, truncated, refresh]);
}
//# sourceMappingURL=useWorkspaceFiles.js.map