<script setup lang="ts">
import { computed, ref, watch } from 'vue'
import { Search, Close } from '@icon-park/vue-next'
import { useI18n } from 'vue-i18n'
import { fetchPluginCategoryDetailInfoList, fetchPluginCategoryKeyList } from '@/apis/plugin-center'
import { useSystemLanguageStore } from '@/store/modules/system-language'

interface Props {
  isShowModal: boolean
  modalTitle: string
}

interface PluginClassificationItemInterface {
  classificationName: string
  classification: string
}

interface PluginItemInterface {
  pluginId: string
  title: string
  points: number
  description: string
  icon: string
}

interface Emits {
  (e: 'update:isShowModal', value: boolean): void
  (e: 'close'): void
}

const { t } = useI18n()

const props = defineProps<Props>()
const emit = defineEmits<Emits>()

const systemLanguageStore = useSystemLanguageStore()

const pluginIdList = defineModel<string[]>('pluginIdList', { required: true })

const pluginClassificationListLoading = ref(false)
const pluginListLoading = ref(false)
const isSearchEmptyList = ref(false)
const searchPluginQuery = ref('')

const pluginClassificationList = ref<PluginClassificationItemInterface[]>([])
const currentPluginClassification = ref<PluginClassificationItemInterface>({
  classificationName: t('common_module.all'),
  classification: '',
})
const pluginList = ref<PluginItemInterface[]>([])

const defaultPluginIconUrl = 'https://gsst-poe-sit.gz.bcebos.com/data/20250115/1736924150557.png'

const showModal = computed({
  get() {
    return props.isShowModal
  },
  set(value: boolean) {
    emit('update:isShowModal', value)
  },
})

const emptyPluginListText = computed(() => {
  return isSearchEmptyList.value ? t('common_module.search_empty_data') : t('common_module.empty_data')
})

const isAddedAgentPluginId = computed(() => (pluginId: string) => {
  return pluginIdList.value.includes(pluginId)
})

const isEnglishLanguage = computed(() => systemLanguageStore.currentLanguageInfo.key === 'en')

watch(
  () => props.isShowModal,
  (newVal) => {
    newVal && handleGetPluginClassificationList()
  },
)

async function handleGetPluginClassificationList() {
  pluginClassificationListLoading.value = true

  const res = await fetchPluginCategoryKeyList<PluginClassificationItemInterface[]>()

  if (res.code === 0) {
    pluginClassificationList.value = [
      {
        classificationName: t('common_module.all'),
        classification: '',
      },
    ]
    pluginClassificationList.value.push(...res.data)
    pluginClassificationListLoading.value = false
    await handleGetPluginList()
  }
}

async function handleGetPluginList() {
  pluginListLoading.value = true

  const payload = {
    classification: currentPluginClassification.value.classification,
    pluginIds: [],
    query: searchPluginQuery.value,
  }

  const res = await fetchPluginCategoryDetailInfoList<{ pluginInfos: PluginItemInterface[] }[]>(payload)

  if (res.code === 0) {
    pluginList.value = []

    res.data.forEach((item) => {
      item.pluginInfos.forEach((pluginItem) => {
        pluginList.value.push(pluginItem)
      })
    })

    pluginListLoading.value = false
    isSearchEmptyList.value = !!searchPluginQuery.value && pluginList.value.length === 0
  }
}

async function handleClearPluginQuery() {
  searchPluginQuery.value = ''
  await handleGetPluginList()
}

async function handleChangePluginClassification(pluginClassificationItem: PluginClassificationItemInterface) {
  currentPluginClassification.value = pluginClassificationItem

  await handleGetPluginList()
}

function handleAddAgentPlugin(pluginId: string, pluginTitle: string) {
  pluginIdList.value.push(pluginId)
  window.$message.success(
    t('personal_space_module.agent_module.agent_setting_module.agent_config_module.add_plugin_successfully', [
      pluginTitle,
    ]),
  )
}

function handleRemoveAgentPlugin(pluginId: string, pluginTitle: string) {
  pluginIdList.value = pluginIdList.value.filter((id) => id !== pluginId)

  window.$message.success(
    t('personal_space_module.agent_module.agent_setting_module.agent_config_module.remove_plugin_successfully', [
      pluginTitle,
    ]),
  )
}

function handleCloseModal() {
  emit('close')
}
</script>

<template>
  <n-modal
    v-model:show="showModal"
    class="h-[700px] w-[954px] rounded-[10px] bg-white"
    :auto-focus="false"
    @after-leave="handleCloseModal"
  >
    <div class="flex">
      <div class="w-[218px] flex-shrink-0 p-6 shadow-[0_2px_8px_0_rgba(0,0,0,0.1)]">
        <p class="text-[18px] leading-none text-[#333]">{{ modalTitle }}</p>

        <n-input
          v-model:value="searchPluginQuery"
          :placeholder="t('common_module.search')"
          class="my-[18px]"
          clearable
          @clear="handleClearPluginQuery"
          @keyup.enter="handleGetPluginList"
        >
          <template #prefix>
            <Search theme="outline" size="16" fill="#999" class="cursor-pointer" />
          </template>
        </n-input>

        <n-scrollbar v-if="!pluginClassificationListLoading" style="max-height: calc(100% - 86px)">
          <ul class="flex flex-col gap-[2px]">
            <li
              v-for="pluginClassificationItem in pluginClassificationList"
              :key="pluginClassificationItem.classification"
              :class="
                currentPluginClassification.classification === pluginClassificationItem.classification
                  ? 'text-theme-color bg-active-color'
                  : 'text-[#333]'
              "
              class="hover:bg-active-color rounded-theme flex h-10 w-full cursor-pointer items-center px-[13px]"
              @click="handleChangePluginClassification(pluginClassificationItem)"
            >
              <n-ellipsis>
                {{ pluginClassificationItem.classificationName }}
              </n-ellipsis>
            </li>
          </ul>
        </n-scrollbar>

        <div v-show="pluginClassificationListLoading" class="flex flex-col gap-[2px]">
          <n-skeleton v-for="i in 3" :key="i" height="40px" width="100%" class="rounded-theme" />
        </div>
      </div>

      <div class="flex-1 overflow-hidden p-6">
        <div class="mb-[18px] flex items-center justify-between">
          <span>{{ currentPluginClassification.classificationName }}</span>
          <div
            class="rounded-theme cursor-pointer p-[3px] hover:bg-[#dedede]"
            @click="emit('update:isShowModal', false)"
          >
            <Close theme="outline" size="16" fill="#666" />
          </div>
        </div>

        <n-virtual-list
          v-show="!pluginListLoading && pluginList.length > 0"
          style="max-height: 612px"
          :item-size="106"
          :items="pluginList"
          key-field="pluginId"
          items-style="padding-right: 12px;"
        >
          <template #default="{ item }: { item: PluginItemInterface }">
            <div
              :key="item.pluginId"
              class="border-inactive-border-color mb-4.5 hover:border-theme-color flex h-[88px] items-center gap-[14px] overflow-hidden rounded-[10px] border px-5 last:mb-0 hover:bg-[#F6F7FF]"
            >
              <div
                class="h-[38px] w-[38px] flex-shrink-0 bg-contain bg-center bg-no-repeat"
                :style="
                  item.icon
                    ? { backgroundImage: `url(${item.icon})` }
                    : { backgroundImage: `url(${defaultPluginIconUrl})` }
                "
              />

              <div class="flex flex-1 items-center justify-between gap-[14px] overflow-hidden">
                <div class="flex h-full flex-1 flex-col justify-between overflow-hidden">
                  <div class="w-full text-[14px]">
                    <n-ellipsis class="w-full text-[#333]" :tooltip="{ 'content-style': 'max-width: 600px;' }">
                      {{ item.title }}
                    </n-ellipsis>
                  </div>

                  <div class="w-full text-[12px]">
                    <n-ellipsis class="w-full text-[#333]" :tooltip="{ 'content-style': 'max-width: 600px;' }">
                      {{ item.description }}
                    </n-ellipsis>
                  </div>
                </div>

                <div class="flex flex-shrink-0 items-center gap-[14px]">
                  <span class="text-[12px] text-[#999]">
                    {{ t('common_module.points_per_time', { count: (item.points * 1).toFixed(2) }) }}
                  </span>

                  <n-button
                    v-show="!isAddedAgentPluginId(item.pluginId)"
                    type="primary"
                    :border="false"
                    class="h-[34px]!"
                    :class="isEnglishLanguage ? 'w-[86px]!' : 'px-5!'"
                    @click="handleAddAgentPlugin(item.pluginId, item.title)"
                  >
                    {{ t('common_module.add') }}
                  </n-button>

                  <n-button
                    v-show="isAddedAgentPluginId(item.pluginId)"
                    type="error"
                    ghost
                    class="h-[34px]!"
                    :class="isEnglishLanguage ? 'w-[86px]!' : 'px-5!'"
                    @click="handleRemoveAgentPlugin(item.pluginId, item.title)"
                  >
                    {{ t('common_module.remove') }}
                  </n-button>
                </div>
              </div>
            </div>
          </template>
        </n-virtual-list>

        <div v-show="pluginListLoading" class="flex flex-col gap-[14px]">
          <n-skeleton v-for="i in 3" :key="i" height="88px" width="100%" class="rounded-[10px]" />
        </div>

        <div v-show="!pluginListLoading && pluginList.length === 0" class="flex h-full items-center justify-center">
          <div class="flex flex-col items-center justify-center">
            <div
              class="mb-5 h-[68px] w-[68px]"
              :class="isSearchEmptyList ? 'bg-px-search_empty_list-png' : 'bg-px-empty_list-png'"
            />
            <p class="text-gray-font-color select-none">{{ emptyPluginListText }}</p>
          </div>
        </div>
      </div>
    </div>

    <template #footer />
  </n-modal>
</template>
