import type { components } from '$lib/generated/api';
import { createTypeahead } from '$lib/shared/hooks/useTypeahead.svelte';
import { formatDocumentDate, type DatePrecision } from '$lib/shared/utils/documentDate';
import { getLocale } from '$lib/paraglide/runtime.js';

type DocumentListItem = components['schemas']['DocumentListItem'];

/**
 * Chip/dedup contract for document pickers. `metaDatePrecision`/`metaDateEnd`
 * are optional: the typeahead always populates them, but a TimelineEvent's
 * DocumentRef (#781) carries only id/title/documentDate — formatDocumentOption
 * degrades gracefully (bare title or plain date) when precision is absent.
 */
export type DocumentOption = Pick<DocumentListItem, 'id' | 'title' | 'documentDate'> &
	Partial<Pick<DocumentListItem, 'metaDatePrecision' | 'metaDateEnd'>>;

export function createDocumentTypeahead() {
	return createTypeahead<DocumentOption>({
		// Intentional bare browser fetch (matches the Geschichte editor): in dev the
		// Vite proxy forwards /api and injects the auth header; in prod the app is
		// same-origin so the auth cookie travels automatically. An internal
		// +server.ts proxy would add complexity with no practical security benefit.
		fetchUrl: (q) =>
			fetch(`/api/documents/search?q=${encodeURIComponent(q)}&size=10`)
				.then((r) => {
					// Without this check a 401/500 parses as JSON without `items` and
					// renders as "no results" — errors must reach the hook's error state.
					if (!r.ok) throw new Error(`document search failed: ${r.status}`);
					return r.json();
				})
				.then((b: { items: DocumentListItem[] }) =>
					b.items.map((it) => ({
						id: it.id,
						title: it.title,
						documentDate: it.documentDate,
						metaDatePrecision: it.metaDatePrecision,
						metaDateEnd: it.metaDateEnd
					}))
				)
	});
}

export function formatDocumentOption(doc: DocumentOption): string {
	if (!doc.documentDate) return doc.title;
	// A DocumentRef (#781 timeline chips) carries documentDate but no precision —
	// default to DAY so the full date renders, rather than the UNKNOWN fallback
	// formatDocumentDate would otherwise hit for an undefined precision.
	const label = formatDocumentDate(
		doc.documentDate,
		(doc.metaDatePrecision as DatePrecision) ?? 'DAY',
		doc.metaDateEnd,
		null,
		getLocale()
	);
	return `${doc.title} · ${label}`;
}
