const data = {
  name: 'imgcache',
  prefix: 'imgcache_'
}
function ImgCache (vm) {
  this.vm = vm // 保存实例在其他周期使用
  this.i = 0 // 用于标记第几张图
  vm.imgCache = {
    get list () {
      return uni
        .getStorageInfoSync()
        .keys.filter((key) => key.startsWith(data.prefix))
        .map((key) => key.split(data.prefix)[1])
    },
    get (url) {
      return uni.getStorageSync(data.prefix + url)
    },
    delete (url) {
      const path = uni.getStorageSync(data.prefix + url)
      if (!path) return false
      plus.io.resolveLocalFileSystemURL(path, (entry) => {
        entry.remove()
      })
      uni.removeStorageSync(data.prefix + url)
      return true
    },
    async add (url) {
      const filename = await download(url)
      if (filename) {
        uni.setStorageSync(data.prefix + url, filename)
        return 'file://' + plus.io.convertLocalFileSystemURL(filename)
      }
      return null
    },
    clear () {
      uni
        .getStorageInfoSync()
        .keys.filter((key) => key.startsWith(data.prefix))
        .forEach((key) => {
          uni.removeStorageSync(key)
        })

      plus.io.resolveLocalFileSystemURL(`_doc/${data.name}/`, (entry) => {
        entry.removeRecursively(
          (entry) => {
            console.log(`${data.name}缓存删除成功`, entry)
          },
          (e) => {
            console.log(`${data.name}缓存删除失败`, e)
          }
        )
      })
    }
  }
}

// #ifdef APP-PLUS
ImgCache.prototype.onParse = function (node, parser) {
  // 启用本插件 && 解析图片标签 && 拥有src属性 && 是网络图片
  if (
    this.vm.ImgCache &&
    node.name === 'img' &&
    node.attrs.src &&
    /^https?:\/\//.test(node.attrs.src)
  ) {
    const src = node.attrs.src
    node.attrs.src = ''
    node.attrs.i = this.vm.imgList.length + this.i++
    parser.expose()

    async function getUrl (path) {
      if (await resolveFile(path)) return path
      const filename = await download(src)
      filename && uni.setStorageSync(data.prefix + src, filename)
      return filename
    }

    uni.getStorage({
      key: data.prefix + src,
      success: async (res) => {
        const path = await getUrl(res.data)
        const url = path
          ? 'file://' + plus.io.convertLocalFileSystemURL(path)
          : src
        node.attrs.src = url
        this.vm.imgList[node.attrs.i] = path || src
      },
      fail: async () => {
        const path = await getUrl()
        const url = path
          ? 'file://' + plus.io.convertLocalFileSystemURL(path)
          : src
        node.attrs.src = url
        this.vm.imgList[node.attrs.i] = path || src
      }
    })
  }
}

const taskQueue = new Set()

function download (url) {
  return new Promise((resolve) => {
    if (taskQueue.has(url)) return
    taskQueue.add(url)
    const suffix = /.+\.(jpg|jpeg|png|bmp|gif|webp)/.exec(url)
    const name = `${makeid(8)}_${Date.now()}${suffix ? '.' + suffix[1] : ''}`
    const task = plus.downloader.createDownload(
      url,
      { filename: `_doc/${data.name}/${name}` },
      (download, status) => {
        taskQueue.delete(url)
        resolve(status === 200 ? download.filename : null)
      }
    )
    task.start()
  })
}

// 判断文件存在
function resolveFile (url) {
  return new Promise((resolve) => {
    plus.io.resolveLocalFileSystemURL(url, resolve, () => resolve(null))
  })
}

// 生成uuid
function makeid (length) {
  let result = ''
  const characters = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz'
  for (let i = 0; i < length; i++) {
    result += characters.charAt(Math.floor(Math.random() * characters.length))
  }
  return result
}
// #endif

export default ImgCache
