import { onPullDownRefresh, onReachBottom } from '@dcloudio/uni-app'
import { computed, onMounted, ref } from 'vue'

interface PaginationRequest {
  pageIndex?: number
  pageSize?: number
  [key: string]: any
}

function useListPageRequest(
  request: (params: PaginationRequest) => Promise<any>,
  options: {
    autoBind?: boolean
    autoRequest?: boolean
  } = {},
) {
  const { autoBind = true, autoRequest = true } = options
  const list = ref<any[]>([])
  // 加载中
  const loading = ref(false)
  // 加载更多中
  const moreLoading = ref(false)
  // 全部数据加载完成
  const totalPage = ref(0)
  const finished = computed(() => totalPage.value <= pagingParams.value.pageIndex)
  const pagingParams = ref<PaginationRequest>({
    pageIndex: 1,
    pageSize: 10,
  })
  const getPagingParams = computed(() => {
    return {
      ...pagingParams.value,
    }
  })
  let customParams: PaginationRequest = {}

  const statusLoading = computed(() => {
    if (moreLoading.value || loading.value) {
      return 'loading'
    }
    if (finished.value) {
      return 'noMore'
    }
    return 'more'
  })

  const loadData = async () => {
    const { data } = await request({
      ...getPagingParams.value,
      ...customParams,
    })
    totalPage.value = data.count ? Math.ceil(data.count / pagingParams.value.pageSize!) : 0
    list.value.push(...data.list)
  }

  const onReload = async (params?: AnyObject) => {
    loading.value = true
    pagingParams.value.pageIndex = 1
    if (params) {
      customParams = params
    }
    try {
      await loadData()
    } finally {
      loading.value = false
    }
  }
  const onMore = async () => {
    if (finished.value) {
      return
    }
    pagingParams.value.pageIndex = pagingParams.value.pageIndex! + 1
    moreLoading.value = true
    try {
      await loadData()
    } finally {
      moreLoading.value = false
    }
  }

  if (autoRequest) {
    onMounted(onReload)
  }
  if (autoBind) {
    onPullDownRefresh(async () => {
      await onReload()
      uni.stopPullDownRefresh()
    })
    onReachBottom(onMore)
  }

  return {
    list,
    loading,
    moreLoading,
    finished,
    statusLoading,
    totalPage,

    onReload,
    onMore,
  }
}

export { useListPageRequest }
