/**
 * Returns a function that resolves an id to a display label by looking it up
 * in a reactive options list. Designed for `hlm-select` value templates and
 * `hlm-select-multiple` `[itemToString]` bindings, where the form control
 * stores ids but the UI needs the human-readable label.
 *
 * Defaults to the `name` field; pass `labelKey` to use a different string
 * field.
 *
 * @example
 * // Default — T must have `name: string`
 * protected readonly clientItemToString = itemLabelOf(this.clientOptions);
 *
 * @example
 * // Custom label field
 * protected readonly langItemToString = itemLabelOf(this.langOptions, 'localName');
 */
export function itemLabelOf<T extends { id: string; name: string }>(
  options: () => T[],
): (id: string | null) => string;
export function itemLabelOf<T extends { id: string }, K extends keyof T & string>(
  options: () => T[],
  labelKey: K,
): (id: string | null) => string;
export function itemLabelOf<T extends { id: string }>(
  options: () => T[],
  labelKey: keyof T & string = 'name' as keyof T & string,
): (id: string | null) => string {
  return (id) => {
    if (!id) return '';
    const value = options().find((option) => option.id === id)?.[labelKey];
    return typeof value === 'string' ? value : '';
  };
}
