<script lang="ts">
	import { CreateRevenueStore, UpdateRevenueStore } from '$houdini';
	import { offCanvas } from '$lib/stores/offCanvas.svelte';
	import type { GetAccount$result } from '$houdini';
	import IconSpinner from '$lib/components/icons/IconSpinner.svelte';
	import { fromGlobalId } from '$lib/utils/relay';

	type Revenue = NonNullable<GetAccount$result['account']>['revenues'][number];

	interface WaveProduct {
		id: string;
		name: string;
		description: string | null;
		unitPrice: number | string;
		isArchived: boolean;
	}

	interface Props {
		accountId: string;
		revenue?: Revenue;
		waveProducts?: WaveProduct[];
		onSuccess?: () => void;
		onCancel?: () => void;
	}

	let { accountId, revenue, waveProducts = [], onSuccess, onCancel }: Props = $props();

	let isEdit = $derived(!!revenue);
	let submitting = $state(false);
	let error = $state('');

	let amount = $state(revenue?.amount?.toString() ?? '');
	let startDate = $state(revenue?.startDate ?? '');
	let endDate = $state(revenue?.endDate ?? '');
	let waveServiceId = $state(revenue?.waveServiceId ?? '');

	// Find currently linked product for display
	let linkedProduct = $derived(
		waveServiceId ? waveProducts.find((p) => fromGlobalId(p.id) === waveServiceId) : null
	);

	const createStore = new CreateRevenueStore();
	const updateStore = new UpdateRevenueStore();

	async function handleSubmit(e: SubmitEvent) {
		e.preventDefault();
		submitting = true;
		error = '';

		try {
			const parsedAmount = parseFloat(amount);
			if (isNaN(parsedAmount) || parsedAmount < 0) {
				error = 'Please provide a valid amount';
				return;
			}

			if (!startDate) {
				error = 'Please provide a start date';
				return;
			}

			if (isEdit && revenue) {
				const res = await updateStore.mutate({
					input: {
						id: revenue.id,
						amount: parsedAmount,
						startDate,
						endDate: endDate || null,
						waveServiceId: waveServiceId || ''
					}
				});
				if (res.errors?.length) {
					error = res.errors.map((e) => e.message).join(', ');
					return;
				}
			} else {
				const res = await createStore.mutate({
					input: {
						accountId,
						amount: parsedAmount,
						startDate,
						endDate: endDate || null,
						waveServiceId: waveServiceId || ''
					}
				});
				if (res.errors?.length) {
					error = res.errors.map((e) => e.message).join(', ');
					return;
				}
			}

			offCanvas.closeRight();
			onSuccess?.();
		} catch (err) {
			error = err instanceof Error ? err.message : 'Failed to save revenue';
		} finally {
			submitting = false;
		}
	}

	function handleCancel() {
		offCanvas.closeRight();
		onCancel?.();
	}
</script>

<div class="min-w-0 space-y-6">
	{#if error}
		<div class="alert-error">
			{error}
		</div>
	{/if}

	<form class="space-y-4" onsubmit={handleSubmit}>
		<div>
			<label for="amount" class="mb-1.5 block text-sm font-medium text-theme">
				Monthly Revenue <span class="text-red-500">*</span>
			</label>
			<div class="relative">
				<span class="absolute top-1/2 left-3 -translate-y-1/2 text-theme-muted">$</span>
				<input
					id="amount"
					type="number"
					step="0.01"
					min="0"
					bind:value={amount}
					disabled={submitting}
					placeholder="0.00"
					class="placeholder-theme-muted w-full rounded-lg border border-theme bg-theme py-2 pr-3 pl-7 text-theme focus:border-primary-500 focus:ring-1 focus:ring-primary-500 disabled:cursor-not-allowed disabled:opacity-50"
				/>
			</div>
		</div>

		<div class="grid grid-cols-2 gap-4">
			<div>
				<label for="startDate" class="mb-1.5 block text-sm font-medium text-theme">
					Start Date <span class="text-red-500">*</span>
				</label>
				<input
					id="startDate"
					type="date"
					bind:value={startDate}
					disabled={submitting}
					class="w-full rounded-lg border border-theme bg-theme px-3 py-2 text-theme focus:border-primary-500 focus:ring-1 focus:ring-primary-500 disabled:cursor-not-allowed disabled:opacity-50"
				/>
			</div>

			<div>
				<label for="endDate" class="mb-1.5 block text-sm font-medium text-theme"> End Date </label>
				<input
					id="endDate"
					type="date"
					bind:value={endDate}
					disabled={submitting}
					class="w-full rounded-lg border border-theme bg-theme px-3 py-2 text-theme focus:border-primary-500 focus:ring-1 focus:ring-primary-500 disabled:cursor-not-allowed disabled:opacity-50"
				/>
			</div>
		</div>

		<p class="text-xs text-theme-muted">
			Leave end date empty to mark this as the current revenue rate.
		</p>

		{#if waveProducts.length > 0}
			<div class="border-t border-theme pt-4">
				<label for="waveProduct" class="mb-1.5 block text-sm font-medium text-theme">
					Wave Product
				</label>
				<select
					id="waveProduct"
					bind:value={waveServiceId}
					disabled={submitting}
					class="w-full rounded-lg border border-theme bg-theme px-3 py-2 text-theme focus:border-primary-500 focus:ring-1 focus:ring-primary-500 disabled:cursor-not-allowed disabled:opacity-50"
				>
					<option value="">No linked product</option>
					{#each waveProducts as product (product.id)}
						{@const decodedId = fromGlobalId(product.id)}
						<option value={decodedId}>
							{product.name} (${Number(product.unitPrice).toFixed(2)})
						</option>
					{/each}
				</select>
				{#if linkedProduct}
					<p class="mt-1 text-xs text-theme-muted">
						Currently linked to: {linkedProduct.name}
					</p>
				{/if}
			</div>
		{/if}

		<div class="flex items-center gap-3 pt-4">
			<button
				type="submit"
				disabled={submitting}
				class="flex-1 rounded-lg bg-primary-500 px-4 py-2 font-medium text-white transition-colors hover:bg-primary-600 disabled:cursor-not-allowed disabled:opacity-50"
			>
				{#if submitting}
					<span class="flex items-center justify-center gap-2">
						<IconSpinner class="h-4 w-4" />
						<span>{isEdit ? 'Saving...' : 'Creating...'}</span>
					</span>
				{:else}
					{isEdit ? 'Save Changes' : 'Add Revenue'}
				{/if}
			</button>
			<button
				type="button"
				onclick={handleCancel}
				disabled={submitting}
				class="rounded-lg border border-theme bg-theme px-4 py-2 font-medium text-theme transition-colors hover:bg-black/5 disabled:cursor-not-allowed disabled:opacity-50 dark:hover:bg-white/10"
			>
				Cancel
			</button>
		</div>
	</form>
</div>
