java返回文件流和返回Json混用

遇到一个需求,前端上传Excel文件,后端校验校验不通过直接返回并下载带有失败信息的Excel文件,如果是其他情况则返回相应的Json提示信息。

前后端用于处理Java上传文件后成功和失败返回Json信息,校验失败放回文件流并下载。

一个接口兼顾Json返回和文件流返回

1、vue前端请求处理:

// 封装axios的下载数据流转换成excel
export function DownLoadToExcel(url, data = {}, fileName) {
  fileName = fileName + '.xls'
  return new Promise((resolve, reject) => {
    axios
      .post(url, data, {
        // 必须设置不然Excel下载后打不开
        responseType: 'blob',
        dataType: 'json',
        headers: { 'Content-Type': 'application/json; application/vnd.ms-excel' }
      })
      .then(response => {
        resolve(response)
      })
      .catch(error => {
        console.log(error)
        reject(error)
      })
  })
}

2、前端上传附件方法处理:

uploads() {
  let formdata = new FormData()
  formdata.append('file', this.file)
  this.loadingStatus = true
  this.$http.DownLoadToExcel(this.uploadUrl, formdata, this.file.name).then(res => {
    const resData = res.data
    let that = this
    // 处理返回是Json的数据
    if (resData.type === 'application/json') {
      // 说明是普通对象数据,读取信息
      const fileReader = new FileReader()
      fileReader.onloadend = () => {
        debugger
        try {
          const jsonData = JSON.parse(fileReader.result)
          // 后台信息
          console.log(jsonData)
          debugger
          if (jsonData.code === 200) {
            debugger
            that.tips.class = this.tips.successClass
            that.tips.message = '文件导入成功!'
            that.$emit('fileUploadSuccess')
          } else {
            that.tips.class = that.tips.failClass
            that.tips.message = jsonData.message
          }
        } catch (err) {
          console.log(err)
        }
      }
      fileReader.readAsText(res.data)
    } else {
      // 校验错误时直接下载校验错误Excel
      const blob = new Blob([res.data], {
        type: 'application/vnd.ms-excel'
      })
      if ('download' in document.createElement('a')) {
        // 非IE下载
        const elink = document.createElement('a')
        elink.download = this.file.name
        elink.style.display = 'none'
        elink.href = URL.createObjectURL(blob)
        document.body.appendChild(elink)
        elink.click()
        URL.revokeObjectURL(elink.href)
        document.body.removeChild(elink)
      } else {
        // IE10+下载
        navigator.msSaveBlob(blob, this.file.name)
      }
      this.file = null
    }
  }).catch(err => {
    console.log(err)
  })
}

3、后端

@PostMapping("wikipediaImportData")
@ApiOperation("百科excel导入")
JsonResponse<Map<String, Object>> wikipediaExportData(@RequestParam("file") MultipartFile file, HttpServletResponse response){
JsonResponse<Map<String, Object>> jonResponse = JsonResponse.ok();
String fileName = file.getOriginalFilename();
// 校验格式
if (!(fileName != null && (fileName.endsWith(".xlsx") || fileName.endsWith(".xls")))) {
    jonResponse.setCode(RequestStatus.HEAD_FAILED.code);
    jonResponse.setMessage(RequestStatus.HEAD_FAILED.message);
    jonResponse.setSuccess(false);
}
/ 这里得设置返回请求信息
response.setContentType("application/json;charset=UTF-8");
response.setCharacterEncoding("UTF-8");
ExcelReader reader = ExcelFactory.readBuilder()
        .head(WikipediaExcelDTO.class)
        .build();

try {
    AnalyzedResult<WikipediaExcelDTO> result = reader.read(file.getInputStream());

    switch (result.getRStatus()) {
        case SUCCESS:
            List<WikipediaExcelDTO> dataList = result.getDataList();
            List<BaseResourceDTO> baseResourceDTOList = dataList.stream().map(data -> {
                BaseResourceDTO resourceDTO = new BaseResourceDTO();
                BeanUtils.copyProperties(data, resourceDTO);
                return resourceDTO;
            }).collect(Collectors.toList());
            indexService.syncResource(baseResourceDTOList);
            jonResponse.setCode(RequestStatus.OK.code);
            jonResponse.setMessage(RequestStatus.OK.message);
            jonResponse.setSuccess(true);
            break;
        case DATA_FAILED:
            // 数据校验出错时候直接返回错误文件流
            response.setContentType("application/vnd.ms-excel");
            response.setCharacterEncoding("UTF-8");

            try {
                response.setHeader("Content-disposition", "attachment;filename=" + URLEncoder.encode(fileName, "UTF-8") + ".xlsx");
            } catch (UnsupportedEncodingException var3) {
                response.setHeader("Content-disposition", "attachment;filename=" + fileName + ".xlsx");
            }
            // ExcelUtil.writeExcelResponseHeader(response, fileName);
            ExcelFactory.errorExportBuilder()
                    .cellList(result.getCellList())
                    .head(WikipediaExcelDTO.class)
                    .build()
                    .export(response.getOutputStream());
            jonResponse.setCode(RequestStatus.DATA_FAILED.code);
            jonResponse.setMessage(RequestStatus.DATA_FAILED.message);
            jonResponse.setSuccess(false);
            break;
        case HEAD_FAILED:
            jonResponse.setCode(RequestStatus.HEAD_FAILED.code);
            jonResponse.setMessage(RequestStatus.HEAD_FAILED.message);
            jonResponse.setSuccess(false);
            break;
        case ERROR:
            jonResponse.setCode(RequestStatus.ERROR.code);
            jonResponse.setMessage(RequestStatus.ERROR.message);
            jonResponse.setSuccess(false);
            break;
        default:
            jonResponse.setCode(result.getRStatus().getCode());
            jonResponse.setMessage(result.getRStatus().getMessage());
            jonResponse.setSuccess(false);
            break;
    }
} catch (Exception e) {
    log.error("百科导入文件错误");
    jonResponse.setCode(RequestStatus.ERROR.code);
    jonResponse.setMessage(RequestStatus.ERROR.message);
    jonResponse.setSuccess(false);
}
return jonResponse;
}

 返回失败的Json

下载文件:

 

 

  • 10
    点赞
  • 41
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值