图片上传流程步骤
- 前端传送图片(base64)到服务器
- 服务器将base64转换为byte []
- 服务器根据存储路径生成文件,然后以流的方式写入byte[]
- 前端请求图片
- 服务器根据路径读取文件,以流的方式返回
前端上传图片
<input
type="file"
class="img-upload"
@change="uploadChange"
accept="image/*"
/>
uploadChange(el) {
let that = this;
if (
el &&
el.target &&
el.target.files &&
el.target.files.length > 0
) {
const files = el.target.files[0];
const reader = new FileReader();
reader.readAsDataURL(files);
reader.onload = function () {
that.base64src = this.result; // 图片的base64编码
...// 发送http请求
};
}
}
服务器保存图片
// application-dev.yml
var:
uploadFileSavePath: D:\company\static
// 文件名:FileUtil
/**
* yml中的变量,图片存储地址
*/
@Value("${var.uploadFileSavePath}")
public String filePath;
public Boolean saveFile(String fileName, String base64src) {
String base64 = base64src.split(",")[1];//通过base64来转化图片,去掉图片头(data:image/jpg;base64,)
BASE64Decoder decoder = new BASE64Decoder();
byte[] bytes = null;
try {
bytes = decoder.decodeBuffer(base64); // base64 -> byte[]
}catch (IOException e) {
return false;
}
if(bytes != null) {
Boolean tag = writeFile(filePath,fileName,bytes);
if(!tag) {
return false;
}
}
return true;
}
// 文件名:FileUtil
private Boolean writeFile(String filePath, String fileName, byte[] bytes) {
Boolean flag = false;
new File(filePath).mkdirs(); // 先创建父目录
File file = new File(filePath , fileName);
try {
FileOutputStream out = new FileOutputStream(file);
out.write(bytes, 0, bytes.length);
out.flush();
out.close();
flag = true;
} catch (Exception e) {
System.out.println(e);
}
return flag;
}
BUG: 文件拒绝访问
创建文件时,必须先创建父目录,再用双参方式初始化file
对象,不要使用下面的方式
File file1 = new File(filePath + File.separator + fileName);
file1.mkdirs();
服务器返回图片请求
@Autowired
private FileUtil fileUtil;
@GetMapping(value = "/images/{name}",produces = MediaType.IMAGE_JPEG_VALUE)
@ResponseBody
public BufferedImage getImage(@PathVariable(name = "name") String fileName) throws IOException {
File file = new File(fileUtil.filePath,fileName);
ImageIcon src = new ImageIcon(file.getAbsolutePath());
// 去除红色png背景
BufferedImage bufferedImage = new BufferedImage(src.getIconWidth(),
src.getIconHeight(), BufferedImage.TYPE_INT_RGB);
Graphics g = bufferedImage.createGraphics();
g.setColor(Color.white);
g.fillRect(0, 0, src.getIconWidth(), src.getIconHeight());
g.drawImage(src.getImage(), 0, 0, null);
g.dispose();
ImageIO.write(bufferedImage, "jpg", file);
return bufferedImage;
}
BUG: preset Content-Type ‘null’
加一个图片转换器,即可解决
@Configuration
public class WebMvcConfig implements WebMvcConfigurer {
@Override
public void extendMessageConverters(List<HttpMessageConverter<?>> converters) {
converters.add(new BufferedImageHttpMessageConverter());
}
}
BUG: 图片背景红色
解决方法代码中已写