<template>
  <Sidebar>
    <SidebarContent class="gap-0 bg-white">
      <div class="flex-none">
        <!-- Title -->
        <div class="flex items-center h-15 px-4 border-b-1">
          <h1 className="text-2xl font-semibold tracking-tight">Traces</h1>
        </div>

        <!-- Local trace -->
        <div class="px-4 py-6 border-b-1 h-[200px]">
          <div class="flex justify-between">
            <div class="flex items-center gap-2 mb-1 font-semibold">
              <Clipboard :size="20" />
              Local trace
            </div>
            <Tooltip :delay-duration="500">
              <TooltipTrigger as-child>
                <div
                  v-if="tracesStore.localTrace"
                  class="w-6 h-6 rounded-md bg-accent flex items-center justify-center cursor-pointer"
                  @click="removeLocalTrace"
                >
                  <X :size="12" />
                </div>
              </TooltipTrigger>
              <TooltipContent>Remove local trace</TooltipContent>
            </Tooltip>
          </div>

          <div class="pt-1 h-[90px]">
            <Alert v-if="!tracesStore.localTrace" class="mb-3 rounded-sm py-[14px]">
              <MessageSquareDashed class="opacity-60" />
              <AlertTitle class="opacity-60"> No local trace found </AlertTitle>
              <AlertDescription>Please paste a new trace.</AlertDescription>
            </Alert>
            <div v-else @click="tracesStore.selectedTraceId = tracesStore.localTrace.id">
              <TraceCard
                :trace="tracesStore.localTrace"
                :is-selected="tracesStore.localTrace.id == tracesStore.selectedTraceId"
              />
            </div>
          </div>

          <Dialog v-model:open="dialogOpen">
            <DialogTrigger class="w-full">
              <Button size="sm" class="text-sm w-full sm:mt-2">
                <ClipboardPaste :size="16" /> Paste new trace
              </Button>
            </DialogTrigger>
            <DialogContent class="rounded-sm min-w-[600px]">
              <DialogHeader>
                <DialogTitle>Add a local trace</DialogTitle>
                <DialogDescription>
                  Paste a JSON trace.
                  <Textarea class="my-4 h-[300px] resize-none break-all" v-model="pastedJson" />
                  <div v-if="pasteError !== ''">
                    <Alert variant="destructive" class="rounded-sm border-red-300">
                      <AlertCircle class="w-4 h-4" />
                      <AlertTitle>Error</AlertTitle>
                      <AlertDescription>
                        {{ pasteError }}
                      </AlertDescription>
                    </Alert>
                  </div>
                </DialogDescription>
              </DialogHeader>

              <DialogFooter>
                <DialogClose as-child>
                  <Button variant="outline">Close</Button>
                </DialogClose>
                <Button @click="addLocalTrace">Add trace</Button>
              </DialogFooter>
            </DialogContent>
          </Dialog>
        </div>

        <!-- Dataset traces -->
        <div class="p-4">
          <div class="flex mb-4 font-semibold justify-between">
            <div class="flex gap-2 items-center">
              <Database :size="20" />
              <p>Dataset traces</p>
            </div>
            <div>
              <Tooltip :delay-duration="500">
                <TooltipTrigger as-child>
                  <Button variant="outline" class="ml-2" @click="reloadDatasetTraces">
                    <RefreshCcw :size="20" />
                  </Button>
                </TooltipTrigger>
                <TooltipContent>Reload dataset traces</TooltipContent>
              </Tooltip>
            </div>
          </div>

          <!-- Dataset traces filters -->
          <TracesFilters />
        </div>
      </div>

      <TracesList />
    </SidebarContent>
  </Sidebar>
</template>

<script setup lang="ts">
import {
  AlertCircle,
  Clipboard,
  ClipboardPaste,
  Database,
  MessageSquareDashed,
  RefreshCcw,
  X
} from 'lucide-vue-next'
import { ref, type Ref } from 'vue'
import { toast } from 'vue-sonner'

import { API } from '@/Api'
import { WT1iser } from '@/common/wt1'
import TracesFilters from '@/components/app-sidebar/traces-filters/TracesFilters.vue'
import { Alert, AlertTitle, AlertDescription } from '@/components/ui/alert'
import { Button } from '@/components/ui/button'
import {
  Dialog,
  DialogClose,
  DialogContent,
  DialogDescription,
  DialogFooter,
  DialogHeader,
  DialogTitle,
  DialogTrigger
} from '@/components/ui/dialog'
import { Textarea } from '@/components/ui/textarea'
import { Sidebar, SidebarContent } from '@/components/ui/sidebar'
import { Tooltip, TooltipContent, TooltipTrigger } from '@/components/ui/tooltip'
import { useTracesStore } from '@/stores/traces'
import { getLocalTraceItemName, removeTraceFromLS } from '@/utils/localStorage'
import { prepareTrace } from '@/utils/prepareTrace'

import TracesList from './TracesList.vue'
import TraceCard from './TraceCard.vue'

const tracesStore = useTracesStore()
const pastedJson: Ref<string> = ref('')
const pasteError: Ref<string> = ref('')
const dialogOpen: Ref<boolean> = ref(false)

function addLocalTrace() {
  const { trace, error } = prepareTrace(pastedJson.value)

  if (error) {
    pasteError.value = error
  } else if (trace) {
    // update store & local storage
    localStorage.setItem(getLocalTraceItemName(window.location.href), JSON.stringify(trace))
    tracesStore.localTrace = trace

    // reset UI elements
    pastedJson.value = ''
    pasteError.value = ''
    dialogOpen.value = false

    // trigger actions
    tracesStore.selectedTraceId = trace.id
    WT1iser.addTrace()
  }
}

function removeLocalTrace() {
  removeTraceFromLS()

  tracesStore.localTrace = null
  tracesStore.selectedTraceId = null
}

async function reloadDatasetTraces() {
  WT1iser.reloadTraces()
  tracesStore.isLoadingList = true
  tracesStore.selectedTraceId = null

  try {
    // force the refresh of the traces list in the backend
    await API.reloadTraces()

    // fetch the traces list & reset filters based on new traces
    tracesStore.datasetTraces = await API.listTraces()
    tracesStore.setupFilters()

    toast.success('Traces reloaded successfully')
  } catch (err) {
    console.error('Error loading traces:', err)
    toast.error("Couldn't reload traces, please try again later.")
  } finally {
    tracesStore.isLoadingList = false
  }
}
</script>
