/**
 * Tool call formatting utilities.
 *
 * Formats tool call parameters as function-call signature syntax:
 *   toolName(param1: "value", param2: 42, param3: {...})
 */

/**
 * Truncate a string to maxLength, appending "..." if truncated.
 */
export function truncate(value: string, maxLength: number): string {
  if (value.length <= maxLength) return value;
  return value.slice(0, maxLength - 3) + "...";
}

/**
 * Format a single parameter value for display in a function-call signature.
 *
 * - strings: quoted with truncation at 120 chars
 * - numbers/booleans/null: bare
 * - objects: "{...}" truncated
 * - arrays: "[...]" truncated
 */
export function formatParamValue(value: unknown): string {
  if (value === null) return "null";
  if (value === undefined) return "undefined";
  if (typeof value === "boolean") return String(value);
  if (typeof value === "number") return String(value);
  if (typeof value === "string") {
    const truncated = truncate(value, 120);
    // Only quote if it contains spaces or special chars, or if truncated
    // Always quote for consistency — function-call syntax expects it
    return `"${truncated}"`;
  }
  if (Array.isArray(value)) {
    return "[...]";
  }
  if (typeof value === "object") {
    return "{...}";
  }
  return String(value);
}

/**
 * Parse a JSON parameters string and format it as a function-call signature.
 *
 * @example
 * formatToolCallSignature("file_read", '{"path": "src/foo.ts", "recursive": true}')
 * // → 'file_read(path: "src/foo.ts", recursive: true)'
 *
 * @example
 * formatToolCallSignature("list_files", undefined)
 * // → 'list_files()'
 */
export function formatToolCallSignature(
  name: string,
  parameters?: string
): string {
  if (!parameters) return `${name}()`;

  let parsed: Record<string, unknown>;
  try {
    parsed = JSON.parse(parameters);
  } catch {
    // If it's not valid JSON, show it as a raw string argument
    return `${name}(${truncate(parameters, 200)})`;
  }

  if (typeof parsed !== "object" || parsed === null || Array.isArray(parsed)) {
    // Non-object JSON — show as single argument
    return `${name}(${formatParamValue(parsed)})`;
  }

  const entries = Object.entries(parsed);
  if (entries.length === 0) return `${name}()`;

  const params = entries
    .map(([key, val]) => `${key}: ${formatParamValue(val)}`)
    .join(", ");

  return `${name}(${params})`;
}
