/**
 * Pinia store for family state management.
 *
 * Handles fetching, caching, and CRUD operations against the
 * /api/v1/families REST API.
 *
 * Part of Issue #29.
 */
import { defineStore } from 'pinia'
import axios from '@nextcloud/axios'
import { generateUrl } from '@nextcloud/router'

export const useFamiliesStore = defineStore('families', {
	state: () => ({
		/** @type {Array} List of families */
		families: [],
		/** @type {Object|null} Currently selected family */
		currentFamily: null,
		/** @type {number} Total family count */
		total: 0,
		/** @type {boolean} Loading state */
		loading: false,
		/** @type {string|null} Error message */
		error: null,
		/** @type {number} Current offset */
		offset: 0,
		/** @type {number} Items per page */
		limit: 20,
	}),

	getters: {
		hasMore: (state) => state.offset + state.limit < state.total,
		currentPage: (state) => Math.floor(state.offset / state.limit) + 1,
		totalPages: (state) => Math.ceil(state.total / state.limit),
	},

	actions: {
		/**
		 * Fetch families with pagination.
		 */
		async fetchFamilies(offset = 0) {
			this.loading = true
			this.error = null
			this.offset = offset

			try {
				const url = generateUrl('/apps/mitgliederverwaltung/api/v1/families')
				const response = await axios.get(url, {
					params: {
						limit: this.limit,
						offset: this.offset,
					},
				})

				this.families = response.data.data
				this.total = response.data.total
			} catch (err) {
				this.error = err.response?.data?.error || 'Fehler beim Laden der Familien'
				console.error('Failed to fetch families:', err)
			} finally {
				this.loading = false
			}
		},

		/**
		 * Fetch a single family by ID with linked members.
		 */
		async fetchFamily(id) {
			this.loading = true
			this.error = null

			try {
				const url = generateUrl(`/apps/mitgliederverwaltung/api/v1/families/${id}`)
				const response = await axios.get(url)
				this.currentFamily = response.data
				return response.data
			} catch (err) {
				this.error = err.response?.data?.error || 'Fehler beim Laden der Familie'
				console.error('Failed to fetch family:', err)
				throw err
			} finally {
				this.loading = false
			}
		},

		/**
		 * Search families by name.
		 */
		async searchFamilies(query) {
			this.loading = true
			this.error = null

			try {
				const url = generateUrl('/apps/mitgliederverwaltung/api/v1/families')
				const response = await axios.get(url, {
					params: { search: query },
				})

				this.families = response.data.data
				this.total = response.data.total
			} catch (err) {
				this.error = err.response?.data?.error || 'Fehler bei der Suche'
				console.error('Failed to search families:', err)
			} finally {
				this.loading = false
			}
		},

		/**
		 * Create a new family.
		 */
		async createFamily(data) {
			this.loading = true
			this.error = null

			try {
				const url = generateUrl('/apps/mitgliederverwaltung/api/v1/families')
				const response = await axios.post(url, data)
				return response.data
			} catch (err) {
				this.error = err.response?.data?.error || 'Fehler beim Erstellen der Familie'
				throw err
			} finally {
				this.loading = false
			}
		},

		/**
		 * Update an existing family.
		 */
		async updateFamily(id, data) {
			this.loading = true
			this.error = null

			try {
				const url = generateUrl(`/apps/mitgliederverwaltung/api/v1/families/${id}`)
				const response = await axios.put(url, data)
				this.currentFamily = response.data
				return response.data
			} catch (err) {
				this.error = err.response?.data?.error || 'Fehler beim Aktualisieren der Familie'
				throw err
			} finally {
				this.loading = false
			}
		},

		/**
		 * Delete a family.
		 */
		async deleteFamily(id) {
			this.loading = true
			this.error = null

			try {
				const url = generateUrl(`/apps/mitgliederverwaltung/api/v1/families/${id}`)
				await axios.delete(url)

				this.families = this.families.filter(f => f.id !== id)
				this.total = Math.max(0, this.total - 1)

				if (this.currentFamily?.id === id) {
					this.currentFamily = null
				}
			} catch (err) {
				this.error = err.response?.data?.error || 'Fehler beim Löschen der Familie'
				throw err
			} finally {
				this.loading = false
			}
		},

		/**
		 * Link a member to a family.
		 */
		async linkMember(familyId, memberId) {
			try {
				const url = generateUrl(`/apps/mitgliederverwaltung/api/v1/families/${familyId}/members/${memberId}`)
				await axios.post(url)
				// Reload the family to get updated members list
				await this.fetchFamily(familyId)
			} catch (err) {
				this.error = err.response?.data?.error || 'Fehler beim Verknüpfen des Mitglieds'
				throw err
			}
		},

		/**
		 * Unlink a member from a family.
		 */
		async unlinkMember(familyId, memberId) {
			try {
				const url = generateUrl(`/apps/mitgliederverwaltung/api/v1/families/${familyId}/members/${memberId}`)
				await axios.delete(url)
				// Reload the family to get updated members list
				await this.fetchFamily(familyId)
			} catch (err) {
				this.error = err.response?.data?.error || 'Fehler beim Entfernen des Mitglieds'
				throw err
			}
		},

		/**
		 * Navigate to a specific page.
		 */
		async goToPage(page) {
			const newOffset = (page - 1) * this.limit
			await this.fetchFamilies(newOffset)
		},

		/**
		 * Change page size and reload from page 1.
		 */
		async setLimit(newLimit) {
			this.limit = newLimit
			await this.fetchFamilies(0)
		},

		clearError() {
			this.error = null
		},
	},
})
