<template>
    <div class="invite-manager">
        <div v-if="invite" class="active-invite-section">
            <p class="section-description">Share this code or QR with new members to let them join.</p>

            <div class="invite-display">
                <div class="qr-code-wrapper">
                    <div v-if="qrCodeUrl" class="qr-code">
                        <img :src="qrCodeUrl" alt="Household Invite QR Code" />
                    </div>
                    <div v-else class="qr-code-placeholder">
                        <Spinner size="md" />
                    </div>
                </div>
                <div class="invite-code-wrapper">
                    <span class="invite-code">{{ formattedInviteCode }}</span>
                </div>
            </div>

            <div class="invite-actions">
                <Button variant="outline" size="sm" @click="copyInvite" :disabled="!clipboardSupported">
                    <BaseIcon :name="copied ? 'heroicons:check-20-solid' : 'heroicons:clipboard-document'" />
                    <span>{{ copied ? 'Copied!' : 'Copy Code' }}</span>
                </Button>
                <Button variant="outline" size="sm" @click="copyDeepLink">
                    <BaseIcon name="heroicons:link" />
                    <span>Copy Deep Link</span>
                </Button>
                <Button variant="outline" size="sm" @click="shareInvite">
                    <BaseIcon name="heroicons:share" />
                    <span>Share Link</span>
                </Button>
            </div>

            <div class="invite-footer">
                <p class="expiry-info">Expires: {{ expiryDate }}</p>
                <Button variant="ghost" color="error" size="sm" @click="revokeInvite" :loading="revoking">
                    Revoke Invite
                </Button>
            </div>
        </div>

        <div v-else class="no-invite-section">
            <p class="section-description">Generate an invite to allow new members to join your household.</p>
            <Button @click="generateInvite" :loading="generating" full-width>
                <template #icon-left>
                    <BaseIcon name="heroicons:plus-circle-20-solid" />
                </template>
                Generate Invite Code
            </Button>
        </div>

        <Alert v-if="error" type="error" :message="error" class="mt-4" />
    </div>
</template>

<script setup lang="ts">
import { ref, onMounted, watch, computed } from 'vue'
import { useI18n } from 'vue-i18n'
import { useClipboard, useShare } from '@vueuse/core'
import QRCode from 'qrcode'
import { formatDistanceToNow, parseISO } from 'date-fns'
import { apiClient, API_ENDPOINTS } from '@/services/api'
import { Button, Spinner, Alert } from '@/components/ui'
import BaseIcon from '@/components/BaseIcon.vue'
import { useNotificationStore } from '@/stores/notifications'
import { track } from '@/utils/analytics'

interface Props {
    groupId: number
}

const props = defineProps<Props>()

interface Invite {
    code: string;
    expires_at: string;
}

const { t } = useI18n()
const notifications = useNotificationStore()

const invite = ref<Invite | null>(null)
const generating = ref(false)
const revoking = ref(false)
const error = ref<string | null>(null)
const qrCodeUrl = ref<string | null>(null)

const { copy, copied, isSupported: clipboardSupported } = useClipboard({ legacy: true, copiedDuring: 1500 })
const { share, isSupported: shareSupported } = useShare()

const deepLinkScheme = 'myapp://join/'
const inviteLink = computed(() => `${window.location.origin}/join?invite_code=${invite.value?.code}`)
const deepLink = computed(() => `${deepLinkScheme}${invite.value?.code || ''}`)

const formattedInviteCode = computed(() => {
    const code = invite.value?.code || ''
    return code.match(/.{1,4}/g)?.join('-') || code
})

const expiryDate = computed(() => {
    if (!invite.value) return ''
    return formatDistanceToNow(parseISO(invite.value.expires_at), { addSuffix: true })
})

async function generateQrCode() {
    if (!invite.value) {
        qrCodeUrl.value = null
        return
    }
    try {
        qrCodeUrl.value = await QRCode.toDataURL(inviteLink.value, {
            errorCorrectionLevel: 'H',
            margin: 2,
            width: 160,
        })
    } catch (err) {
        console.error('Failed to generate QR code', err)
        qrCodeUrl.value = null
    }
}

async function fetchActiveInvite() {
    if (!props.groupId) return
    try {
        const { data } = await apiClient.get<Invite>(API_ENDPOINTS.GROUPS.GET_ACTIVE_INVITE(String(props.groupId)))
        invite.value = data
    } catch (err: any) {
        invite.value = null
    }
}

async function generateInvite() {
    generating.value = true
    error.value = null
    try {
        const { data } = await apiClient.post<Invite>(API_ENDPOINTS.GROUPS.CREATE_INVITE(String(props.groupId)))
        invite.value = data
        notifications.addNotification({ type: 'success', message: 'New invite generated.' })
        track('invite_generated', { groupId: props.groupId })
    } catch (err: any) {
        error.value = err?.response?.data?.detail || 'Failed to generate invite'
    } finally {
        generating.value = false
    }
}

async function revokeInvite() {
    if (!invite.value) return
    revoking.value = true
    try {
        await apiClient.delete(API_ENDPOINTS.GROUPS.REVOKE_INVITE(String(props.groupId), invite.value.code))
        notifications.addNotification({ type: 'success', message: 'Invite has been revoked.' })
        invite.value = null
        track('invite_revoked', { groupId: props.groupId })
    } catch (err) {
        notifications.addNotification({ type: 'error', message: 'Failed to revoke invite.' })
    } finally {
        revoking.value = false
    }
}

function copyInvite() {
    if (!invite.value) return
    copy(invite.value.code)
    notifications.addNotification({ type: 'info', message: 'Invite code copied to clipboard.' })
    track('invite_code_copied', { groupId: props.groupId })
}

function copyDeepLink() {
    if (!invite.value) return
    copy(deepLink.value)
    notifications.addNotification({ type: 'info', message: 'Deep link copied to clipboard.' })
    track('invite_deeplink_copied', { groupId: props.groupId })
}

function shareInvite() {
    if (!shareSupported || !invite.value) {
        notifications.addNotification({ type: 'error', message: 'Web Share API not supported in your browser.' })
        return
    }
    share({
        title: 'Join my Household!',
        text: `Use this code to join my household: ${invite.value.code}`,
        url: inviteLink.value
    })
    track('invite_shared', { groupId: props.groupId })
}

onMounted(fetchActiveInvite)

watch(() => props.groupId, fetchActiveInvite, { immediate: true })
watch(invite, generateQrCode, { immediate: true })
</script>

<style scoped>
.invite-manager {
    @apply w-full;
}

.section-description {
    @apply text-sm text-text-secondary mb-4;
}

.active-invite-section {
    @apply space-y-4;
}

.invite-display {
    @apply flex flex-col items-center gap-4 p-4 rounded-lg bg-surface-soft;
}

.qr-code-wrapper {
    @apply w-48 h-48 flex items-center justify-center bg-white dark:bg-neutral-900 rounded-lg p-2 shadow-md transition-opacity duration-150 ease-out;
}

.qr-code-placeholder {
    @apply w-full h-full flex items-center justify-center bg-neutral-100;
}

.invite-code-wrapper {
    @apply w-full text-center p-3 bg-white dark:bg-neutral-900 rounded-md border border-border-secondary;
}

.invite-code {
    @apply text-2xl font-bold tracking-widest text-primary-600 dark:text-primary-400 font-mono;
}

.invite-actions {
    @apply grid grid-cols-2 gap-3;
}

.invite-actions .button {
    @apply w-full;
}

.invite-footer {
    @apply flex items-center justify-between text-xs text-text-secondary;
}

.no-invite-section {
    @apply text-center;
}

.qr-code-enter-from {
    opacity: 0;
}

.qr-code-enter-to {
    opacity: 1;
}
</style>