<template>
  <div class="filter-builder">
    <div
      v-for="(condition, idx) in conditions"
      :key="idx"
      class="filter-builder__row"
    >
      <a-select
        v-model:value="condition.field_id"
        placeholder="选择字段"
        style="width: 140px"
        @change="onFieldChange(idx)"
      >
        <a-select-option
          v-for="f in fields"
          :key="f.id"
          :value="f.id"
        >
          {{ f.name }}
        </a-select-option>
      </a-select>

      <a-select
        v-model:value="condition.op"
        placeholder="操作符"
        style="width: 120px"
      >
        <a-select-option
          v-for="op in availableOps(condition.field_id)"
          :key="op.value"
          :value="op.value"
        >
          {{ op.label }}
        </a-select-option>
      </a-select>

      <a-input
        v-if="getValueInputType(condition.field_id) === 'text'"
        v-model:value="condition.value"
        placeholder="值"
        style="width: 160px"
      />
      <a-input-number
        v-else-if="getValueInputType(condition.field_id) === 'number'"
        v-model:value="condition.value"
        placeholder="数值"
        style="width: 160px"
      />
      <a-date-picker
        v-else-if="getValueInputType(condition.field_id) === 'date'"
        :value="condition.value as string | undefined"
        @change="(_, dateString) => condition.value = dateString"
        style="width: 160px"
      />

      <a-button type="text" danger :icon="h(DeleteOutlined)" @click="removeCondition(idx)" />
    </div>

    <a-button type="dashed" block :icon="h(PlusOutlined)" @click="addCondition">
      添加筛选条件
    </a-button>
  </div>
</template>

<script setup lang="ts">
import { ref, watch, h } from 'vue'
import {
  Button as AButton,
  Select as ASelect,
  Input as AInput,
  InputNumber as AInputNumber,
  DatePicker as ADatePicker,
} from 'ant-design-vue'
import { DeleteOutlined, PlusOutlined } from '@ant-design/icons-vue'
import type { IBitableField, FieldType } from '@/api/bitable'

interface FilterCondition {
  field_id: string
  op: string
  // Value type varies by field type: string for text, number for number, string(ISO) for date
  value: string | number | undefined
}

const props = defineProps<{
  fields: IBitableField[]
  modelValue?: FilterCondition[]
}>()

const emit = defineEmits<{
  (e: 'update:modelValue', conditions: FilterCondition[]): void
}>()

const conditions = ref<FilterCondition[]>(props.modelValue ? [...props.modelValue] : [])

watch(conditions, (val) => {
  emit('update:modelValue', val)
}, { deep: true })

function addCondition(): void {
  conditions.value.push({ field_id: '', op: 'eq', value: undefined })
}

function removeCondition(idx: number): void {
  conditions.value.splice(idx, 1)
}

function onFieldChange(idx: number): void {
  // Reset op to first available for the new field type
  const condition = conditions.value[idx]
  const ops = availableOps(condition.field_id)
  if (ops.length > 0 && !ops.some((o) => o.value === condition.op)) {
    condition.op = ops[0].value
  }
  condition.value = undefined
}

function getField(field_id: string): IBitableField | undefined {
  return props.fields.find((f) => f.id === field_id)
}

function availableOps(field_id: string): { value: string; label: string }[] {
  const field = getField(field_id)
  if (!field) return [{ value: 'eq', label: '等于' }]

  const type = field.field_type as FieldType
  switch (type) {
    case 'number':
      return [
        { value: 'eq', label: '等于' },
        { value: 'ne', label: '不等于' },
        { value: 'gt', label: '大于' },
        { value: 'lt', label: '小于' },
        { value: 'gte', label: '大于等于' },
        { value: 'lte', label: '小于等于' },
      ]
    case 'date':
      return [
        { value: 'eq', label: '等于' },
        { value: 'gt', label: '之后' },
        { value: 'lt', label: '之前' },
      ]
    case 'text':
    default:
      return [
        { value: 'eq', label: '等于' },
        { value: 'ne', label: '不等于' },
        { value: 'contains', label: '包含' },
        { value: 'is_empty', label: '为空' },
      ]
  }
}

function getValueInputType(field_id: string): 'text' | 'number' | 'date' | null {
  const field = getField(field_id)
  if (!field) return 'text'
  const type = field.field_type as FieldType
  switch (type) {
    case 'number':
      return 'number'
    case 'date':
      return 'date'
    default:
      return 'text'
  }
}

defineExpose({
  getConditions: () => conditions.value,
})
</script>

<style scoped>
.filter-builder__row {
  display: flex;
  gap: 8px;
  margin-bottom: 8px;
  align-items: center;
}
</style>
