You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在HTML中展示MediaType返回的图片响应?

问题原因及解决方案

问题根源

你后端代码里设置了Content-Disposition: attachment响应头,这个头会告诉浏览器将返回的资源视为下载文件,而非可内嵌展示的图片资源,这就是HTML中img标签无法正常显示的核心原因。

后端代码调整

方案1:仅用于图片展示场景

修改后端的header配置,移除setContentDispositionFormData这一行,让浏览器识别返回内容为图片资源:

@GetMapping(value = "/{id}/download")
public ResponseEntity<Resource> download(@PathVariable UUID id, @RequestParam String key) {
  try {
    final Path file = Paths.get(String.format("%s/%s", "app/resource", key));
    final Resource resource = new UrlResource(file.toUri());

    if (resource.exists() && resource.isReadable()) { // 建议改成&&,避免存在但不可读的无效情况
      final HttpHeaders httpHeaders = new HttpHeaders();
      httpHeaders.setContentType(MediaType.IMAGE_JPEG);
      // 移除下载头设置:httpHeaders.setContentDispositionFormData("attachment", resource.getFilename());

      return ResponseEntity.ok()
          .headers(httpHeaders)
          .body(resource);
    } else {
      // 处理文件不存在/不可读的错误
      return ResponseEntity.notFound().build();
    }
  } catch (MalformedURLException e) {
    // 处理URL格式错误
    return ResponseEntity.badRequest().build();
  }
}

方案2:同时支持下载和展示(更灵活)

新增一个请求参数控制是否触发下载,让同一个接口兼顾图片展示和文件下载场景:

@GetMapping(value = "/{id}/download")
public ResponseEntity<Resource> download(@PathVariable UUID id, 
                                         @RequestParam String key,
                                         @RequestParam(required = false) Boolean download) {
  try {
    final Path file = Paths.get(String.format("%s/%s", "app/resource", key));
    final Resource resource = new UrlResource(file.toUri());

    if (resource.exists() && resource.isReadable()) {
      final HttpHeaders httpHeaders = new HttpHeaders();
      httpHeaders.setContentType(MediaType.IMAGE_JPEG);
      
      if (Boolean.TRUE.equals(download)) {
        // 仅当需要下载时才设置attachment头
        httpHeaders.setContentDispositionFormData("attachment", resource.getFilename());
      }

      return ResponseEntity.ok()
          .headers(httpHeaders)
          .body(resource);
    } else {
      return ResponseEntity.notFound().build();
    }
  } catch (MalformedURLException e) {
    return ResponseEntity.badRequest().build();
  }
}

前端正确展示方式

方式1:直接使用接口URL作为img的src(最简单)

无需发起异步请求,直接将接口地址赋值给img标签的src,浏览器会自动请求并渲染图片:

<img :src="`/${id}/download?key=test.jpeg`" />

如果需要支持下载,给下载按钮绑定带download=true参数的接口地址即可:

<a :href="`/${id}/download?key=test.jpeg&download=true`" download>下载图片</a>

方式2:异步请求后展示(适合需前置处理的场景)

如果必须通过异步请求获取图片,需指定响应类型为blob,避免二进制数据损坏,再转换成Object URL赋值给src:

// 请求时设置responseType为blob
const { data } = await download(id, "test.jpeg", { responseType: 'blob' });
this.imageContent = URL.createObjectURL(data);

// 组件销毁时释放资源,避免内存泄漏
onUnmounted(() => {
  URL.revokeObjectURL(this.imageContent);
});

对应img标签:

<img :src="imageContent" />

为什么之前的Base64方式失效?

因为你未指定响应类型,axios默认会把二进制响应转换成字符串,导致原始二进制数据丢失,即使转成Base64也无法还原成正确图片。若要用Base64方式,需将响应类型设为arraybuffer:

const { data } = await download(id, "test.jpeg", { responseType: 'arraybuffer' });
this.imageContent = "data:image/jpeg;base64," + btoa(String.fromCharCode(...new Uint8Array(data)));

内容的提问来源于stack exchange,提问作者Eniss

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.24 23:17:28