"use client";
// Headless presentation layer for tool calls.
//
// useToolPresentation turns a ToolCall into everything a renderer needs — kind,
// label, primary argument, a normalized result view, and a one-line summary —
// without rendering anything. Styled components (ToolCallItem, ToolCallDetail)
// consume it; platform builders can consume it to build their own tool UI.
//
// The registry lets a consumer override the label or summary for a ToolKind
// (e.g. a product that wants "Run command" instead of "Shell") without forking
// the components. Result interpretation stays in @stigmer/sdk; this is the React
// presentation seam.
import { useMemo } from "react";
import { resolveToolKind, normalizeToolResult } from "@stigmer/sdk";
import { resolveToolCategoryFromCall, extractPrimaryArg, defaultDisclosureForCategory, isRunGroupableCategory, } from "./tool-categories.js";
import { summarizeResultView } from "./ResultView.js";
const registry = new Map();
/**
 * Registers a custom presenter for a {@link ToolKind}, overriding the default
 * label and/or summary. Call once at app startup. This is the extension point
 * for platform builders embedding the execution UI who want product-specific
 * wording without forking the components.
 *
 * Returns a disposer that unregisters the presenter, restoring the previous one
 * for that kind (or the default). Most apps register once at startup and ignore
 * it; tests and dynamic hosts use it to avoid leaking global state.
 *
 * @example
 * ```ts
 * import { registerToolPresenter, ToolKind } from "@stigmer/react";
 *
 * const dispose = registerToolPresenter(ToolKind.SHELL, {
 *   label: () => "Run command",
 *   summary: (_tc, result) =>
 *     result.type === "terminal" && result.exitCode ? `failed (${result.exitCode})` : null,
 * });
 * // later: dispose();
 * ```
 */
export function registerToolPresenter(kind, presenter) {
    const previous = registry.get(kind);
    registry.set(kind, presenter);
    return () => {
        if (previous === undefined) {
            registry.delete(kind);
        }
        else {
            registry.set(kind, previous);
        }
    };
}
/** Returns the registered presenter for a kind, if any. */
export function getToolPresenter(kind) {
    return registry.get(kind);
}
/**
 * Resolves whether a tool call participates in run-grouping, honouring a
 * registered {@link ToolPresenter.runGroupable} override before the
 * category default ({@link isRunGroupableCategory}).
 *
 * This is the non-hook twin of the `runGroupable` field in
 * {@link useToolPresentation}, so the pure `segmentToolCalls` layout pass and
 * the component layer share one source of truth (and honour the same override).
 */
export function resolveRunGroupable(toolCall) {
    const kind = resolveToolKind(toolCall);
    const override = registry.get(kind)?.runGroupable;
    if (override)
        return override(toolCall);
    return isRunGroupableCategory(resolveToolCategoryFromCall(toolCall).category);
}
/**
 * Resolves the complete, render-ready presentation for a tool call.
 *
 * Headless and memoized: the returned object is referentially stable across
 * renders for the same `toolCall`, so it is safe to depend on in `React.memo`
 * leaves of the streaming thread.
 */
export function useToolPresentation(toolCall) {
    return useMemo(() => {
        const kind = resolveToolKind(toolCall);
        const categoryInfo = resolveToolCategoryFromCall(toolCall);
        const result = normalizeToolResult(toolCall);
        const override = registry.get(kind);
        const label = override?.label?.(toolCall) ?? categoryInfo.label;
        const resultSummary = override?.summary?.(toolCall, result) ?? summarizeResultView(result);
        const disclosure = override?.disclosure?.(toolCall, result) ??
            defaultDisclosureForCategory(categoryInfo.category);
        const runGroupable = override?.runGroupable?.(toolCall) ??
            isRunGroupableCategory(categoryInfo.category);
        return {
            kind,
            category: categoryInfo.category,
            label,
            primaryArg: extractPrimaryArg(toolCall),
            result,
            resultSummary,
            disclosure,
            runGroupable,
        };
    }, [toolCall]);
}
//# sourceMappingURL=tool-presenter.js.map