<script setup lang="ts">
import { CopyDocument, Edit, Plus, Refresh } from '@element-plus/icons-vue'
import { ElMessage, ElMessageBox } from 'element-plus'
import { computed, onMounted, ref } from 'vue'
import { useRoute } from 'vue-router'

import {
  fetchSellerListings,
  offlineListing,
  submitListingReview,
  type Listing,
} from '@/features/listings'
import { formatCent, formatMoneyWithSymbol } from '@/shared/utils/money'
import { listingReviewStatusLabel, listingStatusLabel } from '@/shared/utils/statusLabels'
import { formatListingCode, getListingSellerPrice } from '@/shared/utils/listingDisplay'

const loading = ref(false)
const submittingID = ref<number | null>(null)
const offliningID = ref<number | null>(null)
const listings = ref<Listing[]>([])
const statusFilter = ref('all')
const route = useRoute()

const displayListings = computed(() => {
  if (statusFilter.value === 'all') return listings.value
  if (statusFilter.value === 'pending') return listings.value.filter(item => isPendingReview(item))
  return listings.value.filter(item => item.status === statusFilter.value)
})

const stats = computed(() => [
  { key: 'all', label: '全部发布', value: listings.value.length },
  {
    key: 'published',
    label: '已上架',
    value: listings.value.filter(item => item.status === 'published').length,
  },
  {
    key: 'pending',
    label: '待审核',
    value: listings.value.filter(item => isPendingReview(item)).length,
  },
  {
    key: 'offline',
    label: '已下架',
    value: listings.value.filter(item => item.status === 'offline').length,
  },
])

onMounted(loadListings)

async function loadListings() {
  loading.value = true
  try {
    listings.value = await fetchSellerListings()
  } finally {
    loading.value = false
  }
}

async function submitReview(row: Listing) {
  submittingID.value = row.id
  try {
    const listing = await submitListingReview(row.id)
    replaceListing(listing)
    ElMessage.success(
      listing.status === 'published' && listing.review_status === 'approved'
        ? '已上架'
        : '已提交审核，等待后台处理'
    )
  } finally {
    submittingID.value = null
  }
}

async function offline(row: Listing) {
  try {
    await ElMessageBox.confirm(
      `确认下架「${row.title}」吗？下架后后台待审列表会同步移除。`,
      '下架确认',
      {
        confirmButtonText: '确认下架',
        cancelButtonText: '取消',
        type: 'warning',
      }
    )
  } catch {
    return
  }
  offliningID.value = row.id
  try {
    const listing = await offlineListing(row.id)
    replaceListing(listing)
    ElMessage.success('已下架')
  } finally {
    offliningID.value = null
  }
}

function replaceListing(next: Listing) {
  const index = listings.value.findIndex(item => item.id === next.id)
  if (index >= 0) {
    listings.value.splice(index, 1, next)
  } else {
    listings.value.unshift(next)
  }
}

function listingPrice(row: Listing) {
  return formatMoneyWithSymbol(getListingSellerPrice(row))
}

async function copyListingCode(row: Listing) {
  try {
    await navigator.clipboard.writeText(formatListingCode(row))
    ElMessage.success('商品编号已复制')
  } catch {
    ElMessage.error('复制失败')
  }
}

function coinText(row: Listing) {
  const coinM = Number(row.haf_coin_amount || 0) / 1000000
  return Number.isInteger(coinM) ? `${coinM}M` : `${coinM.toFixed(2)}M`
}

function canSubmit(row: Listing) {
  return !isPendingReview(row) && row.status !== 'rented' && row.status !== 'published'
}

function canEdit(row: Listing) {
  return !isPendingReview(row) && row.status !== 'rented' && row.status !== 'published'
}

function canOffline(row: Listing) {
  return row.status !== 'rented' && row.status !== 'offline'
}

function editPath(row: Listing) {
  return route.path.startsWith('/m/')
    ? `/m/seller/listings/${row.id}/edit`
    : `/seller/listings/${row.id}/edit`
}

function statusTone(status: string) {
  const tones: Record<string, string> = {
    published: 'success',
    draft: 'info',
    offline: 'muted',
    rented: 'warning',
    abnormal: 'danger',
  }
  return tones[status] || 'info'
}

function reviewTone(status: string) {
  const tones: Record<string, string> = {
    approved: 'success',
    pending: 'warning',
    rejected: 'danger',
    none: 'muted',
  }
  return tones[status] || 'info'
}

function effectiveReviewStatus(row: Listing) {
  return row.status === 'offline' ? 'none' : row.review_status
}

function isPendingReview(row: Listing) {
  return row.status !== 'offline' && row.review_status === 'pending'
}
</script>

<template>
  <section class="page seller-listings-page">
    <div class="seller-hero">
      <div>
        <p class="eyebrow">Seller</p>
        <h1>我的发布</h1>
        <p>查看账号状态、审核进度，并管理上架与下架。</p>
      </div>
      <div class="hero-actions">
        <el-button :icon="Refresh" :loading="loading" @click="loadListings">刷新</el-button>
        <RouterLink to="/seller/listings/create">
          <el-button type="primary" :icon="Plus">发布账号</el-button>
        </RouterLink>
      </div>
    </div>

    <div class="seller-stats">
      <button
        v-for="item in stats"
        :key="item.key"
        type="button"
        class="stat-card"
        :class="{ active: statusFilter === item.key }"
        @click="statusFilter = item.key"
      >
        <span>{{ item.label }}</span>
        <strong>{{ item.value }}</strong>
      </button>
    </div>

    <div v-loading="loading" class="listing-card-panel">
      <el-empty v-if="!displayListings.length" description="暂无符合条件的发布" />

      <article v-for="item in displayListings" :key="item.id" class="listing-card">
        <div class="listing-main">
          <div class="listing-title-row">
            <div class="listing-title-main">
              <button class="listing-code-chip" type="button" @click="copyListingCode(item)">
                编号 {{ formatListingCode(item) }}
                <el-icon><CopyDocument /></el-icon>
              </button>
              <h3>{{ item.title }}</h3>
            </div>
            <div class="listing-tags">
              <span class="status-pill" :class="statusTone(item.status)">{{
                listingStatusLabel(item.status)
              }}</span>
              <span class="status-pill" :class="reviewTone(effectiveReviewStatus(item))">
                {{ listingReviewStatusLabel(effectiveReviewStatus(item)) }}
              </span>
            </div>
          </div>

          <div class="listing-meta-grid">
            <div>
              <span>区服</span>
              <strong>{{ item.server_region || '-' }}</strong>
            </div>
            <div>
              <span>哈夫币</span>
              <strong>{{ coinText(item) }}</strong>
            </div>
            <div>
              <span>价格</span>
              <strong class="price-text">{{ listingPrice(item) }}</strong>
            </div>
            <div>
              <span>押金</span>
              <strong>¥{{ formatCent(item.deposit_amount_cent) }}</strong>
            </div>
          </div>

          <p v-if="item.review_reason" class="review-reason">{{ item.review_reason }}</p>
        </div>

        <div class="listing-actions">
          <RouterLink v-if="canEdit(item)" :to="editPath(item)">
            <el-button :icon="Edit">编辑</el-button>
          </RouterLink>
          <el-button
            :disabled="!canSubmit(item)"
            :loading="submittingID === item.id"
            @click="submitReview(item)"
          >
            提审
          </el-button>
          <el-button
            type="danger"
            plain
            :disabled="!canOffline(item)"
            :loading="offliningID === item.id"
            @click="offline(item)"
          >
            下架
          </el-button>
        </div>
      </article>
    </div>
  </section>
</template>

<style scoped>
.seller-listings-page {
  display: grid;
  gap: 18px;
}

.seller-hero {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 20px;
  padding: 26px 28px;
  border: 1px solid #e7edf7;
  border-radius: 22px;
  background: linear-gradient(135deg, #ffffff 0%, #f7fbff 58%, #eef6ff 100%);
  box-shadow: 0 14px 36px rgba(15, 23, 42, 0.06);
}

.seller-hero h1 {
  margin: 0;
  color: #0f172a;
  font-size: 34px;
}

.seller-hero p:last-child {
  margin: 10px 0 0;
  color: #64748b;
  font-weight: 700;
}

.hero-actions {
  display: flex;
  flex-wrap: wrap;
  gap: 10px;
  justify-content: flex-end;
}

.seller-stats {
  display: grid;
  grid-template-columns: repeat(4, minmax(0, 1fr));
  gap: 12px;
}

.stat-card {
  display: flex;
  align-items: center;
  justify-content: space-between;
  min-height: 76px;
  padding: 16px 18px;
  border: 1px solid #e6ebf2;
  border-radius: 18px;
  background: #fff;
  color: #64748b;
  cursor: pointer;
  box-shadow: 0 10px 24px rgba(15, 23, 42, 0.04);
  transition:
    transform 0.18s ease,
    border-color 0.18s ease,
    box-shadow 0.18s ease;
}

.stat-card span {
  font-size: 13px;
  font-weight: 800;
}

.stat-card strong {
  color: #0f172a;
  font-size: 24px;
}

.stat-card.active,
.stat-card:hover {
  border-color: #409eff;
  box-shadow: 0 12px 28px rgba(64, 158, 255, 0.14);
  transform: translateY(-1px);
}

.listing-card-panel {
  display: grid;
  min-height: 220px;
  gap: 12px;
}

.listing-card {
  display: grid;
  grid-template-columns: minmax(0, 1fr) auto;
  gap: 18px;
  align-items: center;
  padding: 18px;
  border: 1px solid #e7edf5;
  border-radius: 18px;
  background: #fff;
  box-shadow: 0 10px 28px rgba(15, 23, 42, 0.05);
}

.listing-main {
  min-width: 0;
}

.listing-title-row {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 12px;
}

.listing-title-main {
  display: grid;
  min-width: 0;
  gap: 6px;
}

.listing-code-chip {
  display: inline-flex;
  width: fit-content;
  align-items: center;
  gap: 5px;
  padding: 4px 9px;
  border: 1px solid #dbeafe;
  border-radius: 999px;
  background: #eff6ff;
  color: #2563eb;
  font-size: 12px;
  font-weight: 800;
  cursor: pointer;
}

.listing-title-row h3 {
  min-width: 0;
  margin: 0;
  overflow: hidden;
  color: #1f2937;
  font-size: 16px;
  line-height: 1.45;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.listing-tags {
  display: flex;
  flex-wrap: wrap;
  gap: 6px;
  justify-content: flex-end;
}

.status-pill {
  display: inline-flex;
  align-items: center;
  min-height: 24px;
  padding: 0 9px;
  border-radius: 999px;
  background: #eef2f7;
  color: #64748b;
  font-size: 12px;
  font-weight: 800;
}

.status-pill.success {
  background: #ecfdf3;
  color: #15803d;
}

.status-pill.warning {
  background: #fff7ed;
  color: #c2410c;
}

.status-pill.danger {
  background: #fef2f2;
  color: #dc2626;
}

.status-pill.info {
  background: #eff6ff;
  color: #2563eb;
}

.status-pill.muted {
  background: #f1f5f9;
  color: #64748b;
}

.listing-meta-grid {
  display: grid;
  grid-template-columns: repeat(4, minmax(110px, 1fr));
  gap: 10px;
  margin-top: 14px;
}

.listing-meta-grid div {
  display: grid;
  gap: 4px;
  padding: 10px 12px;
  border-radius: 12px;
  background: #f8fafc;
}

.listing-meta-grid span {
  color: #94a3b8;
  font-size: 12px;
  font-weight: 800;
}

.listing-meta-grid strong {
  color: #334155;
  font-size: 14px;
}

.price-text {
  color: #f97316 !important;
}

.review-reason {
  margin: 12px 0 0;
  padding: 10px 12px;
  border-radius: 12px;
  background: #fff7ed;
  color: #b45309;
  font-size: 13px;
  font-weight: 700;
  line-height: 1.6;
}

.listing-actions {
  display: flex;
  gap: 8px;
  justify-content: flex-end;
}

@media (max-width: 900px) {
  .seller-hero,
  .listing-title-row {
    flex-direction: column;
  }

  .listing-card {
    grid-template-columns: 1fr;
  }

  .hero-actions,
  .listing-actions,
  .listing-tags {
    justify-content: flex-start;
  }

  .seller-stats {
    grid-template-columns: repeat(2, minmax(0, 1fr));
  }

  .listing-meta-grid {
    grid-template-columns: repeat(2, minmax(0, 1fr));
  }
}

@media (max-width: 560px) {
  .seller-hero {
    padding: 20px;
  }

  .seller-stats,
  .listing-meta-grid {
    grid-template-columns: 1fr;
  }

  .listing-actions {
    display: grid;
    grid-template-columns: 1fr 1fr;
  }
}
</style>
