<template>
  <div class="user-page flex-column card h-100 overflow-hidden">
    <div class="header-filter-form">
      <SearchForm
        :config="searchConfig"
        @search="search"
        @add="addDialog"
        @delete="deleteFn"
        v-model="searchForm"
      ></SearchForm>
    </div>
    <div class="user-content flex-1 flex-column overflow-hidden">
      <div class="user-list flex-1 overflow-hidden" v-loading="loading">
        <CustomizeTable
          v-model="tableData"
          :config="tableConfig"
          align="center"
          @getCheckboxRecords="handleCheckboxRecords"
        ></CustomizeTable>
      </div>
      <ElPagination
        v-model:current-page="currentPage"
        v-model:page-size="pageSize"
        :page-sizes="[100, 200, 300, 400, 500]"
        background
        layout="total, sizes, prev, pager, next, jumper"
        :total="total"
        style="margin: 10px auto 0; text-align: right"
        @size-change="handleSizeChange"
        @current-change="handleCurrentChange"
      ></ElPagination>
    </div>
  </div>

  <LogDialog
    :title="editForm['id'] ? '编辑申报规则' : '新增申报规则'"
    dialogWidth="1000px"
    v-model="dialogVisible"
    @close="cancelFn"
  >
    <CustomizeForm
      ref="editFormRef"
      v-model="editForm"
      :config="formConfig"
      formItemWidth="100%"
      :labelWidth="120"
    >
    </CustomizeForm>

    <template #footer>
      <div style="text-align: center">
        <ElButton @click="cancelFn">取消</ElButton>

        <ElButton type="primary" @click="save">保存</ElButton>
      </div>
    </template>
  </LogDialog>
  <LogDialog
    title="操作日志"
    v-model="logDialogVisible"
    @close="logDialogVisible = false"
  >
    <div v-for="item in logList" :key="item.id" style="margin-bottom: 8px">
      <span style="margin-right: 10px">{{ item.createTime }}</span>
      <span>{{ item.description }}</span>
    </div>
  </LogDialog>
</template>

<script setup lang="tsx">
defineOptions({
  name: 'DeclarationRule',
})
import {
  getLogisticsCustomsRuleList,
  addLogisticsCustomsRule,
  updateLogisticsCustomsRule,
  deleteLogisticsCustomsRule,
  getLogisticsLog,
  usableAllList,
} from '@/api/logistics'

import SearchForm from '@/components/SearchForm.tsx'
import LogDialog from './components/LogDialog.tsx'
import CustomizeForm from '@/components/CustomizeForm.tsx'
import CustomizeTable from '@/components/VxeTable.tsx'
import { IFormConfig } from '@/components/CustomizeForm.tsx'
import usePageList from '@/utils/hooks/usePageList'
import { useValue } from './hooks/useValue'
import { showConfirm } from '@/utils/ui'
import { debounce } from 'lodash-es'
import { AddDeclarationRuleObj } from './types/declarationRule'
import { Edit, Delete, List } from '@element-plus/icons-vue'
import { ISeachFormConfig } from '@/types/searchType'
import LogisticsWaySelect from './components/LogisticsWaySelect.tsx'
import { TableColumn } from '@/components/VxeTable'

const [searchForm] = useValue({})
const [editForm, resetEditForm] = useValue<AddDeclarationRuleObj>({
  type: 1,
  currency: 'USD',
})
const {
  loading,
  currentPage,
  pageSize,
  total,
  data: tableData,
  refresh: search,
  onCurrentPageChange: handleCurrentChange,
  onPageSizeChange: handleSizeChange,
} = usePageList({
  query: (page, pageSize) =>
    getLogisticsCustomsRuleList({
      ...searchForm.value,
      pageSize: pageSize,
      currentPage: page,
    }).then(({ data }) => {
      console.log(130, data)
      return data
    }),
})
const dialogVisible = ref(false)
const logDialogVisible = ref(false)
const editFormRef = ref<InstanceType<typeof CustomizeForm> | null>(null)
const selection = ref([])
const searchConfig = ref<ISeachFormConfig[]>([
  {
    prop: 'name',
    type: 'input',
    label: '规则名称',

    attrs: {
      clearable: true,
      placeholder: '请输入规则名称',
    },
  },
])
interface IOption {
  [key: string]: unknown
}
const mapData = ref(
  new Map<number, string[]>([
    [1, ['fixedValue', 'fixedWeight']],
    [2, ['orderPercent', 'valueUp', 'weightPercent', 'weightUp']],
  ]),
)

const formConfig = computed<IFormConfig[]>(() => [
  {
    prop: 'name',
    type: 'input',
    label: '规则名称',
    attrs: {
      placeholder: '请输入规则名称',
    },
    rules: [
      {
        required: true,
        message: '请输入规则名称',
      },
    ],
  },
  {
    prop: 'currency',
    type: 'select',
    label: '申报币种',
    attrs: {
      placeholder: '请选择申报币种',
      options: [{ label: 'USD', value: 'USD' }],
    },
    rules: [
      {
        required: true,
        message: '请选择申报币种',
      },
    ],
  },
  {
    prop: 'logisticsWayId',
    type: 'select',
    label: '物流方式',
    render: () => {
      return (
        <LogisticsWaySelect
          v-model={editForm.value.logisticsWayId}
          companyList={logisticsWayId.value}
        ></LogisticsWaySelect>
      )
    },

    rules: [
      {
        required: true,
        message: '请选择物流方式',
      },
    ],
  },
  {
    prop: 'type',
    type: 'select',
    label: '申报类型',
    attrs: {
      placeholder: '请选择申报类型',

      options: [
        { label: '固定', value: 1 },
        { label: '比例', value: 2 },
      ],
      onChange: (item: IOption, value: number) => {
        console.log(185, item)
        if (value === 2) {
          editForm.value.fixedValue = ''
          editForm.value.fixedWeight = ''
        } else {
          editForm.value.orderPercent = ''
          editForm.value.valueUp = ''
          editForm.value.weightPercent = ''
          editForm.value.weightUp = ''
        }
        editFormRef.value?.refashConfig(mapData.value.get(value) as string[])
        editFormRef.value?.clearValidate()
        console.log(221, editForm.value)
      },
    },
    rules: [
      {
        required: true,
        message: '请选择申报类型',
      },
    ],
  },
  {
    prop: 'fixedValue',
    type: 'amountInput',
    label: '固定金额',
    isIncludeProp: true,
    attrs: {
      placeholder: '请输入固定金额',
      hasSuffix: true,
      suffix: 'USD',
    },
    rules: [
      {
        required: true,
        message: '请输入固定金额',
        trigger: 'blur',
      },
    ],
  },
  {
    prop: 'fixedWeight',
    type: 'amountInput',
    label: '固定重量',
    isIncludeProp: true,
    attrs: {
      placeholder: '请输入固定重量',
      hasSuffix: true,
      suffix: 'g',
    },
    rules: [
      {
        required: true,
        message: '请输入固定重量',
        trigger: 'blur',
      },
    ],
  },
  {
    prop: 'orderPercent',
    type: 'amountInput',
    label: '金额百分比',
    isIncludeProp: true,
    attrs: {
      placeholder: '请输入金额百分比',
      trigger: 'blur',
      hasSuffix: true,
      suffix: '%',
    },
    rules: [
      {
        required: true,
        message: '请输入金额百分比',
        trigger: 'blur',
      },
    ],
  },

  {
    prop: 'valueUp',
    type: 'amountInput',
    label: '申报价值上限',
    isIncludeProp: true,
    attrs: {
      placeholder: '请输入申报价值上限',
      hasSuffix: true,
      suffix: 'USD',
    },
    rules: [
      {
        required: true,
        message: '请输入申报价值上限',
        trigger: 'blur',
      },
    ],
  },
  {
    prop: 'weightPercent',
    type: 'amountInput',
    label: '重量百分比',
    isIncludeProp: true,
    attrs: {
      placeholder: '请输入重量百分比',
      hasSuffix: true,
      suffix: '%',
    },
    rules: [
      {
        required: true,
        message: '请输入重量百分比',
        trigger: 'blur',
      },
    ],
  },
  {
    prop: 'weightUp',
    type: 'amountInput',
    label: '申报重量上限',
    isIncludeProp: true,
    attrs: {
      placeholder: '请输入申报重量上限',
      hasSuffix: true,
      suffix: 'g',
    },
    rules: [
      {
        required: true,
        message: '请输入申报重量上限',
        trigger: 'blur',
      },
    ],
  },
  {
    prop: 'remark',
    type: 'input',
    label: '备注',
    fixed: 'last',
    attrs: {
      placeholder: '请输入备注',
      type: 'textarea',
      rows: 4,
    },
  },
])

const tableConfig = ref<TableColumn[]>([
  {
    prop: 'name',
    label: '规则名称',
  },
  {
    prop: 'currency',
    label: '申报币种',
  },

  {
    prop: 'type',
    label: '申报类型',
    render: {
      default: ({ row }: { row: AddDeclarationRuleObj }) => (
        <span>{row.type === 1 ? '固定' : '比例'}</span>
      ),
    },
  },
  {
    prop: 'logisticsWayId',
    label: '物流方式',
    attrs: {
      width: 300,
    },
    render: {
      default: ({ row }: { row: AddDeclarationRuleObj }) =>
        row.logisticsWay ? (
          <span>
            {logisticsWayId.value
              .map((el: { id: number; name: string }) => {
                if (row.logisticsWay?.split(',')?.includes(el.id.toString())) {
                  return el.name
                }
              })
              .filter((el) => el !== undefined)
              .join(',')}
          </span>
        ) : (
          <span>{''}</span>
        ),
    },
  },
  {
    prop: 'fixedValue',
    label: '固定金额',
  },
  {
    prop: 'fixedWeight',
    label: '固定重量',
  },
  {
    prop: 'orderPercent',
    label: '订单总金额百分比',
  },
  {
    prop: 'valueUp',
    label: '申报价值上限',
  },
  {
    prop: 'weightPercent',
    label: '按原订单报关重量',
  },
  {
    prop: 'weightUp',
    label: '申报重量上限',
  },
  {
    prop: 'remark',
    label: '备注',
  },

  {
    prop: 'opeare',
    label: '操作',
    attrs: {
      align: 'center',
    },
    render: {
      default: ({ row }: { row: AddDeclarationRuleObj }) => (
        <div>
          <el-icon
            size="24"
            title="编辑"
            color="#EF6C00"
            style="cursor: pointer; vertical-align: middle"
            onclick={() => editRule(row)}
          >
            <Edit />
          </el-icon>
          <el-icon
            size="24"
            title="删除"
            color="#f56c6c"
            style="cursor: pointer; vertical-align: middle"
            onclick={() => deleteRule(row)}
          >
            <Delete />
          </el-icon>
          <el-icon
            size="24"
            title="日志"
            color="#008aff"
            style="cursor: pointer; vertical-align: middle"
            onclick={() => showLog(row)}
          >
            <List />
          </el-icon>
        </div>
      ),
    },
  },
])

// const loading = ref(false)

/**
 * @description: 取消按钮
 */
function cancelFn() {
  dialogVisible.value = false
  editFormRef.value?.resetFields()
  resetEditForm()
}

/**
 * @description: 编辑按钮
 */
async function editRule(item: AddDeclarationRuleObj) {
  try {
    editForm.value = { ...item }
    console.log(477, item)

    editForm.value.logisticsWayId = item.logisticsWay
      ?.split(',')
      .map((el) => Number(el))

    dialogVisible.value = true
    nextTick(() => {
      editFormRef.value?.refashConfig(
        mapData.value.get(item.type as number) as string[],
      )
    })
    console.log(493, editForm.value)
  } catch (e) {
    console.log(e)
  }
}

/**
 * @description: 检查数据
 */
async function checkData() {
  const [isValid, postData] = await Promise.all([
    new Promise<boolean>((resolve) => {
      editFormRef.value
        ?.validate()
        .then(() => resolve(true))
        .catch((err) => {
          resolve(false)
          console.log(err)
        })
    }),
    new Promise<AddDeclarationRuleObj>((resolve) => {
      const params = { ...editForm.value }
      params.logisticsWay = params.logisticsWayId?.join(',')
      resolve(params)
    }),
  ])
  return { isValid, postData }
}

/**
 * @description: 保存按钮
 */
const save = debounce(async () => {
  const { isValid, postData } = await checkData()
  if (isValid) {
    try {
      if (!postData.id) {
        await addLogisticsCustomsRule({
          ...postData,
        })
      } else {
        await updateLogisticsCustomsRule({
          ...postData,
        })
      }
      ElMessage({
        message: postData.id ? '更新成功' : '新增成功',
        type: 'success',
      })

      cancelFn()
      search()
    } catch (e) {
      return
    }
  }
}, 400)

/**
 * @description: 新增按钮打开弹窗
 */
function addDialog() {
  dialogVisible.value = true
  nextTick(() => {
    console.log(999)
    editFormRef.value?.refashConfig(mapData.value.get(1))
  })
}

/**
 * @description: 获取选中数据
 */
function handleCheckboxRecords(value: never[]) {
  console.log(351, value)
  selection.value = value
}

/**
 * @description: 多选删除按钮
 */
async function deleteFn() {
  if (!selection.value.length) {
    return ElMessage({
      message: '请选择申报规则',
      type: 'warning',
    })
  }
  try {
    await showConfirm('是否删除申报规则', {
      confirmButtonText: '确认',
      cancelButtonText: '取消',
      type: 'warning',
    })
  } catch {
    return
  }
  try {
    const ids = {
      ids: selection.value.map((item: IOption) => item.id).join(','),
    }
    await deleteLogisticsCustomsRule(ids)
    ElMessage({
      message: '删除成功',
      type: 'success',
    })
    search()
  } catch (e) {
    search()
    // showError(e)
  }
}

/**
 * @description: 单个删除按钮
 */
async function deleteRule(item: AddDeclarationRuleObj) {
  try {
    await showConfirm('是否删除申报规则', {
      confirmButtonText: '确认',
      cancelButtonText: '取消',
      type: 'warning',
    })
  } catch {
    return
  }
  try {
    const ids = { ids: [item.id].join(',') }
    await deleteLogisticsCustomsRule(ids)
    ElMessage({
      message: '删除成功',
      type: 'success',
    })
    search()
  } catch (e) {
    search()
    // showError(e)
  }
}

/**
 * @description: 日志弹窗
 */
interface LogList {
  id?: number
  createTime?: string
  description?: string
}
const logList = ref<LogList[]>([])

async function showLog(row: AddDeclarationRuleObj) {
  logDialogVisible.value = true
  try {
    const { data } = await getLogisticsLog({
      logType: 'logistics_customs_rule',
      relaId: row.id as number,
    })
    logList.value = data
  } catch (error) {
    console.log(error)
  }
}

onMounted(() => {
  getAllList()
})
/**
 * @description: 获取物流方式列表
 */
const logisticsWayId = ref([])
async function getAllList() {
  try {
    const res = await Promise.allSettled([usableAllList()])
    res.forEach(
      (item: PromiseSettledResult<{ code: number; data: never[] }>, index) => {
        if (item?.status === 'fulfilled') {
          if (item.value.code === 200) {
            if (index == 0) {
              logisticsWayId.value = [...(item.value.data || [])]
            }
          }
        }
      },
    )
  } catch (error) {
    console.log(error)
  }
}
</script>

<style lang="scss" scoped>
.header-filter-form {
  margin-bottom: 20px;

  :deep(.el-form-item) {
    margin-right: 14px;
    margin-bottom: 10px;
  }
}
.user-operate-btn {
  margin-bottom: 10px;
}
.dialog-footer {
  text-align: center;
}
</style>
