<script setup lang="ts">
import { onMounted, onUnmounted, ref } from 'vue'
import { ApiError, api } from '../lib/api'
import type { Connection } from '../lib/types'
import { useToast } from '../stores/toast'
import GlassCard from './GlassCard.vue'

const toast = useToast()
const connections = ref<Connection[] | null>(null)
const syncing = ref(false)
const busy = ref(false)

const showCalDAV = ref(false)
const showICS = ref(false)

const caldav = ref({ server_url: 'https://caldav.icloud.com', username: '', password: '', calendar_path: '', display_name: '' })
const ics = ref({ url: '', display_name: '' })

let pollTimer: ReturnType<typeof setTimeout> | null = null

const providerLabel: Record<Connection['provider'], string> = {
  google: 'Google',
  caldav: 'CalDAV / iCloud',
  ics: 'ICS-Abo',
}
const providerIcon: Record<Connection['provider'], string> = {
  google: '🇬',
  caldav: '☁️',
  ics: '📡',
}

async function load() {
  try {
    connections.value = await api.connections()
  } catch (e) {
    toast.error(e instanceof ApiError ? e.message : 'Laden fehlgeschlagen')
  }
}

function schedulePoll() {
  pollTimer = setTimeout(load, 3500)
}

onMounted(() => {
  load()
  schedulePoll()
})
onUnmounted(() => {
  if (pollTimer) clearTimeout(pollTimer)
})

async function syncNow() {
  syncing.value = true
  try {
    connections.value = await api.syncNow()
    toast.ok('Kalender synchronisiert')
  } catch (e) {
    toast.error(e instanceof ApiError ? e.message : 'Sync fehlgeschlagen')
  } finally {
    syncing.value = false
  }
}

async function connectGoogle() {
  try {
    const { url } = await api.googleStart()
    location.href = url
  } catch (e) {
    toast.error(e instanceof ApiError ? e.message : 'Google-Start fehlgeschlagen')
  }
}

async function submitCalDAV() {
  busy.value = true
  try {
    await api.connectCalDAV({
      server_url: caldav.value.server_url,
      username: caldav.value.username,
      password: caldav.value.password,
      calendar_path: caldav.value.calendar_path || undefined,
      display_name: caldav.value.display_name || undefined,
    })
    toast.ok('Kalender verbunden – erste Synchronisierung läuft.')
    showCalDAV.value = false
    caldav.value.username = ''
    caldav.value.password = ''
    await load()
    schedulePoll()
  } catch (e) {
    toast.error(e instanceof ApiError ? e.message : 'Verbinden fehlgeschlagen')
  } finally {
    busy.value = false
  }
}

async function submitICS() {
  busy.value = true
  try {
    await api.connectICS({ url: ics.value.url, display_name: ics.value.display_name || undefined })
    toast.ok('ICS-Kalender verbunden.')
    showICS.value = false
    ics.value.url = ''
    ics.value.display_name = ''
    await load()
  } catch (e) {
    toast.error(e instanceof ApiError ? e.message : 'Verbinden fehlgeschlagen')
  } finally {
    busy.value = false
  }
}

async function remove(conn: Connection) {
  if (!confirm(`„${conn.display_name}“ wirklich entfernen?`)) return
  try {
    await api.deleteConnection(conn.id)
    connections.value = (connections.value ?? []).filter((c) => c.id !== conn.id)
    toast.ok('Verbindung entfernt')
  } catch (e) {
    toast.error(e instanceof ApiError ? e.message : 'Löschen fehlgeschlagen')
  }
}

function syncedAgo(ts: number | null): string {
  if (!ts) return 'wird synchronisiert…'
  const s = Math.max(0, Math.round(Date.now() / 1000 - ts))
  if (s < 60) return `vor ${s}s`
  if (s < 3600) return `vor ${Math.round(s / 60)} Min.`
  return `vor ${Math.round(s / 3600)} Std.`
}
</script>

<template>
  <div class="col">
    <GlassCard title="Kalender hinzufügen" subtitle="WannPassts liest nur frei/belegt – nie Termindetails.">
      <div class="row add-row">
        <button class="btn" @click="connectGoogle">🇬 Google Kalender</button>
        <button class="btn" @click="showCalDAV = !showCalDAV; showICS = false">☁️ iCloud / CalDAV</button>
        <button class="btn" @click="showICS = !showICS; showCalDAV = false">📡 ICS-Link</button>
      </div>

      <transition name="fade">
        <form v-if="showCalDAV" class="glass-soft form" @submit.prevent="submitCalDAV">
          <p class="muted small" style="margin: 0 0 4px">
            Für iCloud: <strong>Apple-ID</strong> als Benutzername und ein
            <a href="https://appleid.apple.com/account/manage" target="_blank" rel="noopener">App-spezifisches Passwort</a>
            (Konto → Anmeldung und Sicherheit). Auch Fastmail, Nextcloud &amp; Co. funktionieren.
          </p>
          <div class="form-grid">
            <label class="field">
              <span>Server</span>
              <input v-model="caldav.server_url" required class="input" />
            </label>
            <label class="field">
              <span>Benutzername</span>
              <input v-model="caldav.username" required class="input" autocomplete="username" />
            </label>
            <label class="field">
              <span>Passwort (App-spezifisch)</span>
              <input v-model="caldav.password" type="password" required class="input" autocomplete="current-password" />
            </label>
            <label class="field">
              <span>Kalender-Pfad (optional)</span>
              <input v-model="caldav.calendar_path" class="input" placeholder="wird automatisch erkannt" />
            </label>
            <label class="field">
              <span>Anzeigename (optional)</span>
              <input v-model="caldav.display_name" class="input" placeholder="z. B. Privatkalender" />
            </label>
          </div>
          <button class="btn btn-primary" type="submit" :disabled="busy">
            {{ busy ? 'Verbinde…' : 'Verbinden' }}
          </button>
        </form>
      </transition>

      <transition name="fade">
        <form v-if="showICS" class="glass-soft form" @submit.prevent="submitICS">
          <p class="muted small" style="margin: 0 0 4px">
            Funktioniert mit jedem öffentlichen ICS/webcal-Link, z. B. der „privaten Adresse im
            iCal-Format“ eines Google-Kalenders oder Ferien-/Schichtplänen.
          </p>
          <label class="field">
            <span>ICS-URL</span>
            <input v-model="ics.url" required class="input" placeholder="https://…/kalender.ics" />
          </label>
          <label class="field">
            <span>Anzeigename (optional)</span>
            <input v-model="ics.display_name" class="input" placeholder="z. B. Schichtplan" />
          </label>
          <button class="btn btn-primary" type="submit" :disabled="busy">
            {{ busy ? 'Prüfe…' : 'Hinzufügen' }}
          </button>
        </form>
      </transition>
    </GlassCard>

    <GlassCard title="Verbundene Kalender">
      <template #header>
        <button class="btn btn-sm" :disabled="syncing" @click="syncNow">
          {{ syncing ? 'Synchronisiere…' : '↻ Jetzt synchronisieren' }}
        </button>
      </template>

      <div v-if="connections === null" class="skeleton" style="height: 72px"></div>
      <p v-else-if="connections.length === 0" class="muted small" style="margin: 0">
        Noch kein Kalender verbunden. Oben einen hinzufügen – ohne Kalender sind alle Zeiten frei.
      </p>
      <div v-else class="col conn-list">
        <div v-for="c in connections" :key="c.id" class="glass-soft conn">
          <span class="conn-icon">{{ providerIcon[c.provider] }}</span>
          <div class="grow">
            <div class="row">
              <strong>{{ c.display_name }}</strong>
              <span class="badge">{{ providerLabel[c.provider] }}</span>
            </div>
            <div class="row small">
              <span :class="c.last_error ? 'err' : 'muted'">
                {{ c.last_error ? '⚠ ' + c.last_error : '✓ synchronisiert ' + syncedAgo(c.last_synced_ts) }}
              </span>
            </div>
          </div>
          <button class="btn btn-sm btn-danger" @click="remove(c)">Entfernen</button>
        </div>
      </div>
    </GlassCard>
  </div>
</template>

<style scoped>
.add-row { flex-wrap: wrap; }
.form { padding: 18px; display: flex; flex-direction: column; gap: 14px; }
.form-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(220px, 1fr)); gap: 12px; }
.form a { color: var(--accent); }
.conn { display: flex; align-items: center; gap: 14px; padding: 14px 16px; }
.conn-icon { font-size: 22px; }
.err { color: var(--danger); }
a { color: var(--accent); text-decoration: none; }
a:hover { text-decoration: underline; }
</style>
