<script setup>
import { useTestimonialsStore } from "@/stores/testimonialsStore";
import { useAuthStore } from "@/stores/authStore";
import { useSettingStore } from "@/stores/settingStore";
import { storeToRefs } from "pinia";
import { onMounted, ref, computed, defineAsyncComponent, watch } from "vue";
import { useRouter } from "vue-router";
import ActionButton from "@/components/ActionButton.vue";
import Paginator from "primevue/paginator";
import SearchBox from "@/components/SearchBox.vue";
import HeroSection from "@/components/HeroSection.vue";
import ConfirmationDialog from "@/components/ConfirmationDialog.vue";
import draggable from "vuedraggable";

import { showToast } from "@/composables/useStoreHelpers";

// ✅ LAZY LOADED COMPONENTS
const TestimonialForm = defineAsyncComponent(
  () => import("./TestimonialForm.vue"),
);
const TestimonialCard = defineAsyncComponent(
  () => import("@/components/TestimonialCard.vue"),
);

// ✅ STORES
const testimonialsStore = useTestimonialsStore();
const settingStore = useSettingStore();
const {
  testimonials,
  total,
  loading,
  saving,
  deleting,
  currentPage,
  rowsPerPage,
  searchTerm,
} = storeToRefs(testimonialsStore);

const authStore = useAuthStore();
const { user: authUser } = storeToRefs(authStore);
const { setting } = storeToRefs(settingStore);

const router = useRouter();

// ✅ STATE
const reordering = ref(false);
const showTestimonialForm = ref(false);
const showDeleteDialog = ref(false);
const formMode = ref("create");
const selectedTestimonial = ref(null);

const languageOptions = [
  { label: "All Languages", value: null },
  { label: "English (EN)", value: "en" },
  { label: "Hindi (HI)", value: "hi" },
  { label: "German (DE)", value: "de" },
  { label: "Albanian (SQ)", value: "sq" },
];

// ✅ COMPUTED
const testimonialsData = computed(() =>
  (Array.isArray(testimonials.value) ? testimonials.value : [])
    .map((row) => ({
      ...row,
      parent_name:
        row.selected_translation?.parent_name ??
        row.translation?.parent_name ??
        row.parent_name ??
        "",
      role:
        row.selected_translation?.role ??
        row.translation?.role ??
        row.role ??
        "",
      comment:
        row.selected_translation?.comment ??
        row.translation?.comment ??
        row.comment ??
        row.message ??
        row.content ??
        "",
      status: (
        row.selected_translation?.status ??
        row.status ??
        "draft"
      ).toLowerCase(),
      language:
        row.displayed_language ??
        row.selected_translation?.language ??
        row.translation?.language ??
        row.language ??
        "en",
    }))
    .filter(
      (row) =>
        !!row?.id && (row.parent_name || row.comment || row.translation_id),
    ),
);

const isSuperAdmin = computed(
  () => authUser.value?.data?.role === "super_admin",
);
const isFranchiseUser = computed(() =>
  ["franchise_admin", "franchise_editor"].includes(authUser.value?.data?.role),
);
const listingLanguage = computed(() => {
  if (isSuperAdmin.value) return "en";
  const configured = setting.value?.general_settings?.language_code;
  const fallback = authUser.value?.data?.franchisee?.language;
  const code = (configured || fallback || "en").toString().toLowerCase();
  return code === "english" ? "en" : code;
});

// Safe delete message
const deleteMessage = computed(() => {
  if (!selectedTestimonial.value) return "";
  return `Are you sure you want to delete the testimonial from '${selectedTestimonial.value.parent_name}'? This action cannot be undone.`;
});

// Pagination Logic
const lazyParams = computed({
  get() {
    return {
      page: currentPage.value,
      rows: rowsPerPage.value,
      search: searchTerm.value,
      sortField: "",
      sortOrder: 0,
    };
  },
  set(newParams) {
    testimonialsStore.updatePaginationParams(newParams);
  },
});

const draggableList = computed({
  get: () => testimonialsData.value,
  set: () => {},
});
const localDraggableList = ref([]);

watch(
  testimonialsData,
  (rows) => {
    localDraggableList.value = Array.isArray(rows) ? [...rows] : [];
  },
  { immediate: true },
);

// ✅ METHODS
onMounted(async () => {
  await settingStore.getSetting();
  await loadTestimonialsLazy();
});

const loadTestimonialsLazy = async () => {
  try {
    await testimonialsStore.fetchTestimonialsLazy({
      page: lazyParams.value.page,
      rows: lazyParams.value.rows,
      sortField: lazyParams.value.sortField,
      sortOrder: lazyParams.value.sortOrder,
      search: lazyParams.value.search,
      language: listingLanguage.value,
    });
  } catch (error) {
    console.error("Failed to load testimonials:", error);
  }
};

const onPage = (event) => {
  testimonialsStore.updatePaginationParams({
    page: event.page + 1,
    rows: event.rows,
  });
};

const handleSearch = (term) => {
  testimonialsStore.updatePaginationParams({ page: 1, search: term });
};

const handleClearSearch = () => {
  testimonialsStore.updatePaginationParams({ page: 1, search: "" });
};

// CRUD
const createTestimonial = () => {
  router.push({ name: "testimonial-add" });
};

const editTestimonial = (testimonial) => {
  router.push({ name: "testimonial-edit", params: { id: testimonial.id } });
};

const confirmDeleteTestimonial = (testimonial) => {
  selectedTestimonial.value = testimonial;
  showDeleteDialog.value = true;
};

const togglingStatus = ref(new Set());
const handleToggleStatus = async (testimonial) => {
  if (togglingStatus.value.has(testimonial.id)) return;
  // Because the v-model binds direct to boolean mapping inside the UI or toggle component toggles the value,
  // on custom list/cards, it depends if the v-model changed it before the emit. We toggle explicitly here to be safe and use that.
  const isCurrentlyActive = !!testimonial.is_enabled;
  const nextEnabled = !isCurrentlyActive;
  const original = testimonial.is_enabled;

  // Optimistically set to new status to make UI snappy
  testimonial.is_enabled = nextEnabled;

  try {
    togglingStatus.value.add(testimonial.id);
    await testimonialsStore.updateTestimonial(testimonial.id, {
      is_enabled: nextEnabled,
      status: testimonial.status || "draft",
    });
    // The store should optimally reload or we trigger a manual reload:
    // await loadTestimonialsLazy(); // uncomment if you prefer wait for reload
  } catch (error) {
    showToast("error", "", "Failed to toggle status");
    // Revert on failure
    testimonial.is_enabled = original;
  } finally {
    togglingStatus.value.delete(testimonial.id);
  }
};

const handleSaveTestimonial = async (formData) => {
  try {
    const result =
      formMode.value === "create"
        ? await testimonialsStore.createTestimonial(formData)
        : await testimonialsStore.updateTestimonial(
            selectedTestimonial.value.id,
            formData,
          );
    if (result?.success !== false) showTestimonialForm.value = false;
  } catch (error) {
    console.error("Save error:", error);
  }
};

const handleDeleteTestimonial = async () => {
  try {
    const result = await testimonialsStore.deleteTestimonial(
      selectedTestimonial.value.id,
    );
    if (result?.success !== false) {
      showDeleteDialog.value = false;
      selectedTestimonial.value = null;
    }
  } catch (error) {
    console.error("Delete error:", error);
  }
};

const handleCancelForm = () => {
  showTestimonialForm.value = false;
  selectedTestimonial.value = null;
  testimonialsStore.clearSelectedTestimonial();
};

const handleCancelDelete = () => {
  showDeleteDialog.value = false;
  selectedTestimonial.value = null;
};

// Drag
const onDragEnd = async (event) => {
  if (reordering.value) return;
  reordering.value = true;
  try {
    const newOrder = localDraggableList.value.map((item, index) => ({
      ...item,
      order_no: index + 1,
    }));
    if (newOrder.length) {
      await testimonialsStore.reorderTestimonialsOrder(newOrder);
    }
  } catch (e) {
    await loadTestimonialsLazy();
  } finally {
    reordering.value = false;
  }
};
</script>

<template>
  <div class="testimonials-page-container">
    <HeroSection
      title="Testimonials"
      subtitle="Manage customer testimonials and feedback"
      icon="pi pi-comments"
    />

    <div class="content-wrapper">
      <div class="page-content">
        <div class="toolbar">
          <div class="search-section">
            <SearchBox
              :model-value="lazyParams.search"
              placeholder="Search testimonials..."
              :loading="loading"
              size="medium"
              @search="handleSearch"
              @clear="handleClearSearch"
            />
          </div>

          <div class="action-buttons">
            <ActionButton
              label="New Testimonial"
              icon="pi pi-plus"
              size="medium"
              @click="createTestimonial"
              class="create-button"
            />
          </div>
        </div>

        <div class="cards-container">
          <div v-if="loading" class="loading-cards">
            <div v-for="n in 6" :key="n" class="skeleton-card-wrapper">
              <div class="skeleton-header">
                <div class="skeleton-avatar"></div>
                <div class="skeleton-info">
                  <div class="skeleton-line title"></div>
                  <div class="skeleton-line subtitle"></div>
                </div>
              </div>
              <div class="skeleton-body">
                <div class="skeleton-line text full"></div>
                <div class="skeleton-line text full"></div>
                <div class="skeleton-line text three-quarter"></div>
              </div>
              <div class="skeleton-footer">
                <div class="skeleton-line date"></div>
                <div class="skeleton-badge"></div>
              </div>
            </div>
          </div>

          <div v-else-if="testimonialsData.length === 0" class="no-data">
            <i class="pi pi-comments" />
            <h3>No Testimonials Found</h3>
            <p>Get started by adding your first testimonial.</p>
          </div>

          <div v-else>
            <draggable
              :list="localDraggableList"
              item-key="id"
              class="testimonials-grid"
              handle=".drag-handle"
              :disabled="reordering"
              ghost-class="drag-ghost"
              @end="onDragEnd"
            >
              <template #item="{ element: testimonial }">
                <div
                  v-if="testimonial"
                  class="card-wrapper"
                  :data-id="testimonial.id"
                >
                  <TestimonialCard
                    :testimonial="testimonial"
                    :can-delete="
                      isSuperAdmin ||
                      (isFranchiseUser &&
                        (!testimonial.is_global ||
                          !!testimonial.parent_testimonials_id))
                    "
                    @edit="editTestimonial"
                    @delete="confirmDeleteTestimonial"
                    @toggle-status="handleToggleStatus"
                  />
                </div>
              </template>
            </draggable>
          </div>

          <div v-if="total > 0" class="cards-pagination">
            <Paginator
              :rows="lazyParams.rows"
              :total-records="total"
              @page="onPage"
            />
          </div>
        </div>
      </div>
    </div>

    <ConfirmationDialog
      v-model:visible="showDeleteDialog"
      title="Delete Testimonial"
      :message="deleteMessage"
      :item="selectedTestimonial"
      :loading="deleting"
      @confirm="handleDeleteTestimonial"
      @cancel="handleCancelDelete"
    />
  </div>
</template>

<style scoped>
.content-wrapper {
  max-width: 1400px;
  margin: -4.5rem auto 0;
  padding: 0 1.5rem;
  position: relative;
  z-index: 10;
}

.page-content {
  background: rgb(var(--v-theme-surface));
  color: rgb(var(--v-theme-on-surface));
  border-radius: 12px;
  box-shadow: 0 10px 40px rgba(0, 0, 0, 0.1);
  overflow: hidden;
}

.toolbar {
  padding: 1.5rem;
  border-bottom: 1px solid rgba(var(--v-border-color), var(--v-border-opacity));
  display: flex;
  justify-content: space-between;
  align-items: center;
  gap: 1rem;
}

.search-section {
  display: flex;
  gap: 1rem;
  flex: 1;
  max-width: 600px;
}

.action-buttons {
  display: flex;
  gap: 0.75rem;
  align-items: center;
}

/* ========== GRID ========== */
.cards-container {
  padding: 2rem;
  background: rgb(var(--v-theme-background));
}

/* ✅ 2 Columns Grid (Wider Cards) */
.testimonials-grid,
.loading-cards {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(500px, 1fr));
  gap: 1.5rem;
}

.card-wrapper {
  transition: transform 0.2s;
}

/* ========== BUTTONS ========== */
.translate-btn {
  background: rgb(var(--v-theme-primary)) !important;
  border: 1px solid rgb(var(--v-theme-primary)) !important;
  color: rgb(var(--v-theme-on-primary)) !important;
}

.translate-btn:hover {
  filter: brightness(0.9);
}

.create-button {
  background: rgb(var(--v-theme-primary));
  color: rgb(var(--v-theme-on-primary));
  border: none;
}

.create-button:hover {
  filter: brightness(0.9);
}

/* ========== PREMIUM SHIMMER SKELETON ========== */
.skeleton-card-wrapper {
  background: rgb(var(--v-theme-surface));
  border: 1px solid rgba(var(--v-border-color), var(--v-border-opacity));
  border-radius: 12px;
  padding: 1.25rem;
  display: flex;
  flex-direction: column;
  height: 240px;
  border-left: 4px solid rgba(var(--v-theme-on-surface), 0.12); /* Mimic active border dynamically */
}

/* Shimmer Animation Base */
.skeleton-avatar,
.skeleton-line,
.skeleton-badge {
  background: rgba(
    var(--v-theme-on-surface),
    0.05
  ); /* Auto-adapts based on light/dark mode */
  position: relative;
  overflow: hidden;
}

/* The sweeping shine effect */
.skeleton-avatar::after,
.skeleton-line::after,
.skeleton-badge::after {
  content: "";
  position: absolute;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
  background: linear-gradient(
    90deg,
    transparent 0%,
    rgba(var(--v-theme-on-surface), 0.08) 50%,
    transparent 100%
  );
  transform: translateX(-100%);
  animation: shimmer 1.5s infinite;
}

@keyframes shimmer {
  100% {
    transform: translateX(100%);
  }
}

/* Structure */
.skeleton-header {
  display: flex;
  align-items: center;
  gap: 0.75rem;
  margin-bottom: 1.5rem;
}

.skeleton-avatar {
  width: 42px;
  height: 42px;
  border-radius: 50%;
}

.skeleton-info {
  flex: 1;
  display: flex;
  flex-direction: column;
  gap: 0.5rem;
}

.skeleton-line {
  border-radius: 4px;
  height: 0.8rem;
}

.skeleton-line.title {
  width: 60%;
  height: 1rem;
}
.skeleton-line.subtitle {
  width: 40%;
}
.skeleton-line.text {
  margin-bottom: 0.5rem;
}
.skeleton-line.full {
  width: 100%;
}
.skeleton-line.three-quarter {
  width: 75%;
}
.skeleton-line.date {
  width: 30%;
}

.skeleton-body {
  flex: 1;
  margin-bottom: 1.5rem;
}

.skeleton-footer {
  display: flex;
  justify-content: space-between;
  align-items: center;
  border-top: 1px solid rgba(var(--v-border-color), var(--v-border-opacity));
  padding-top: 1rem;
}

.skeleton-badge {
  width: 40px;
  height: 20px;
  border-radius: 6px;
}

/* ========== UTILS ========== */
.no-data {
  text-align: center;
  padding: 4rem;
  color: rgba(var(--v-theme-on-surface), 0.6);
}

.no-data i {
  font-size: 3rem;
  margin-bottom: 1rem;
  color: rgba(var(--v-theme-on-surface), 0.2);
}

.cards-pagination {
  margin-top: 2rem;
  display: flex;
  justify-content: center;
}

/* Transitions */
.fade-enter-active,
.fade-leave-active {
  transition: opacity 0.3s ease;
}
.fade-enter-from,
.fade-leave-to {
  opacity: 0;
}

@media (max-width: 1100px) {
  .testimonials-grid,
  .loading-cards {
    grid-template-columns: 1fr;
  }
}

@media (max-width: 768px) {
  .toolbar {
    flex-direction: column;
  }
  .search-section {
    flex-direction: column;
    width: 100%;
  }
}
</style>
