import { Component, inject } from '@angular/core'
import { NonNullableFormBuilder, ReactiveFormsModule, Validators } from '@angular/forms'
import { RouterLink } from '@angular/router'
import { DefaultService, ReservationSettings } from '@api-client/angular'
import { LoadingButtonDirective } from '@frontend/shared'
import { HotToastService } from '@ngxpert/hot-toast'
import { TranslocoDirective } from '@jsverse/transloco'
import { UntilDestroy, untilDestroyed } from '@ngneat/until-destroy'
import { range } from 'es-toolkit/compat'
import { finalize } from 'rxjs'
import { I18nService } from '../../../core'
import { LucideChevronLeft } from '@lucide/angular'

function parseTimeText(text: string): { hours: number; minutes: number } {
	const [hours, minutes] = text.split(':').map(Number)
	return { hours, minutes }
}

function formatTimeText(time: { hours: number; minutes: number }): string {
	return `${String(time.hours).padStart(2, '0')}:${String(time.minutes).padStart(2, '0')}`
}

@UntilDestroy({ checkProperties: true })
@Component({
	selector: 'kadi-reservation-settings',
	templateUrl: './reservation-settings.component.html',
	imports: [TranslocoDirective, RouterLink, ReactiveFormsModule, LoadingButtonDirective, LucideChevronLeft],
})
export class ReservationSettingsComponent {
	private readonly _toast = inject(HotToastService)
	private readonly _i18nService = inject(I18nService)
	private readonly _apiService = inject(DefaultService)
	private readonly _formBuilder = inject(NonNullableFormBuilder)

	settings: ReservationSettings | undefined
	defaultReservationTimeOptions = range(1, 7).map((val) => val * 30)
	loading = false

	form = this._formBuilder.group({
		autoApproveReservations: this._formBuilder.group({
			enabled: this._formBuilder.control(false, { validators: Validators.required }),
			guestLimitOverall: this._formBuilder.control(0),
			guestLimitPerReservation: this._formBuilder.control(0),
		}),
		defaultReservationTime: this._formBuilder.control(30, { validators: [Validators.required, Validators.min(30)] }),
		dashboardReservationTimeLimit: this._formBuilder.control(1, {
			validators: [Validators.required, Validators.min(1)],
		}),
		// "HH:mm" string, empty = no cutoff (mapped to lastReservationTime)
		lastReservationTimeText: this._formBuilder.control(''),
	})

	constructor() {
		this.loadSettings()
	}

	save() {
		if (this.form.invalid) return

		this.loading = true
		const { lastReservationTimeText, ...rest } = this.form.getRawValue()
		const reservation = {
			...rest,
			// null (not undefined) so clearing survives JSON.stringify AND the
			// shallow settings merge — undefined keys vanish from the payload
			// and the old value would silently stay in the database
			lastReservationTime: lastReservationTimeText ? parseTimeText(lastReservationTimeText) : null,
		}
		this._apiService
			.settingsControllerSave({ reservation })
			.pipe(
				untilDestroyed(this),
				finalize(() => (this.loading = false)),
				this._toast.observe({
					success: this._i18nService.translate('update_settings_success'),
				}),
			)
			.subscribe({
				next: () => {
					this.form.markAsPristine()
				},
			})
	}

	private loadSettings(): void {
		this._apiService
			.settingsControllerFind()
			.pipe(untilDestroyed(this))
			.subscribe(({ reservation }) => {
				this.settings = reservation
				if (reservation) {
					this.form.patchValue(reservation)
					const cutoff = (reservation as ReservationSettings & { lastReservationTime?: { hours: number; minutes: number } })
						.lastReservationTime
					if (cutoff) {
						this.form.controls.lastReservationTimeText.setValue(formatTimeText(cutoff))
					}
				}
			})
	}
}
