手记

【九月打卡】第10天 jest 环境之谜、在编辑器中添加上传组件-上传校验

课程名称:web前端架构师

课程章节:第11周 第五章

主讲老师:张轩

课程内容:jest浏览器环境之谜,完成upload组件测试;在编辑器中添加上传组件-上传校验

完成upload组件图片本地预览测试

编写测试代码

it.only('test upload img and show img', async () => {
  const wrapper = mount(UploadFile, {
    props: {
      listType: 'picture'
    }
  })
  window.URL.createObjectURL = vi.fn(() => { return 'test.url' })
  const fileInput = wrapper.get('input').element
  setInputVal(fileInput)
  request.mockResolvedValueOnce({ status: 'success' })
  await wrapper.get('input').trigger('change')
  expect(request).toHaveBeenCalledTimes(0)
  expect(wrapper.get('li').classes()).toContain('upload-img')
  const firstImg = wrapper.find('li:first-child img')
  expect(firstImg.exists()).toBeTruthy()
  expect(firstImg.attributes('src')).toEqual('test.url')
})

视频中的 如果不mock window.URL.createObjectURL 会报错,而我本地的代码没有出现报错,但是无法判断图片是否可以正常预览,所以还是需要使用mock

jest 就是通过 jsdom 来模拟浏览器,但是有一部分还是不存在的,比如 window.URL.createObjectURL ,不存在的特性模拟实现一下就可以了

在编辑器中添加上传中组件

首先需要给组件加个一个 shouLIst 参数,表示是否需要展示列表,因为有时候我们需要只展示一个按钮

通用代码封装 - 上传校验

上传文件我们可能需要校验文件大小和文件格式,格式正确才能上传

我们可能会这样写

function uploadCheck (file: File, formatArr: string[], size: number): boolean {
  if (!formatArr.includes(file.type)) {
    return false
  } else if (file.size > size) {
    return false
  }
  return true
}

如果我们需要错误提示信息,可能会这样做

function uploadCheck (file: File, formatArr: string[], size: number): boolean {
  if (!formatArr.includes(file.type)) {
    toast(xxx)
    return false
  } else if (file.size > size) {
    toast(xxx)
    return false
  }
  return true
}

如果我们需要根据指定提示信息,那么可能会将提示信息当作参数传递进来,这样做这个函数就会变得越来约臃肿

function uploadCheck (file: File, formatArr: string[], size: number, msg1: string, msg2: string): boolean {
  if (!formatArr.includes(file.type)) {
    toast(msg1)
    return st
  } else if (file.size > size) {
    toast(msg2)
    return false
  }
  return true
}

我们可以将通用的内容给拆分出来

  • 我们可以将需要校验你的参数传递给函数
  • 函数内部会针对所有需要校验的参数进行处理

下面编写代码

interface CheckCondition{
  format: string[]
  size: number
}

function uploadCheck (file: File, condition: CheckCondition): {passed: boolean, err: string} {
  const { format, size } = condition
  const isValidFormat = format ? format.includes(file.type) : true
  const isValidSize = size ? (file.size > size) : true
  let err: string = ''
  if (isValidFormat) {
    err = 'format'
  }
  if (isValidSize) {
    err = 'size'
  }
  return {
    passed: isValidFormat && isValidSize,
    err
  }
}

其实有时候我们可以将参数校验的函数和信息通过参数传递进来,类似 async-validator

const descriptor = {
  name: {
    type: 'string',
    required: true,
    validator: (rule, value) => value === 'muji',
  },
  age: {
    type: 'number',
    asyncValidator: (rule, value) => {
      return new Promise((resolve, reject) => {
        if (value < 18) {
          reject('too young');  // reject with error message
        } else {
          resolve();
        }
      });
    },
  },
};
const validator = new Schema(descriptor);
validator.validate({ name: 'muji' }, (errors, fields) => {
  if (errors) {
    // validation failed, errors is an array of all errors
    // fields is an object keyed by field name with an array of
    // errors per field
    return handleErrors(errors, fields);
  }
  // validation passed
});
0人推荐
随时随地看视频
慕课网APP