一、FastDFS简介
FastDFS是一个开源的轻量级分布式文件系统,它对文件进行管理,功能包括:文件存储、文件同步、文件访问(文件上传、文件下载)等,解决了大容量存储和负载均衡的问题。特别适合以文件为载体的在线服务,如相册网站、视频网站等等。
FastDFS为互联网量身定制,充分考虑了冗余备份、负载均衡、线性扩容等机制,并注重高可用、高性能等指标,使用FastDFS很容易搭建一套高性能的文件服务器集群提供文件上传、下载等服务。
两个核心概念:Tracker(跟踪器) Storage(存储节点)
Tracker Server作用是负载均衡和调度,可称为追踪服务器或调度服务器。
Storage Server作用是文件存储,客户端上传的文件最终存储在Storage服务器,Storage使用操作系统的文件系来管理文件,因此被称为存储服务器。
二、Java代码实现
- pom.xml文件中添加
<dependency>
<groupId>com.github.tobato</groupId>
<artifactId>fastdfs-client</artifactId>
<exclusions>
<exclusion>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
</exclusion>
</exclusions>
<version>1.26.7</version>
</dependency>
- yml文件中添加
fdfs:
so-timeout: 6000
connect-timeout: 6000
thumb-image:
width: 150
height: 150
tracker-list:
- 192.168.13.222:22122
- 创建上传下载工具类 FastdfsUtil(FastFileStorageClient )
package com.xbb.cloud.utils;
import com.github.tobato.fastdfs.domain.fdfs.StorePath;
import com.github.tobato.fastdfs.domain.proto.storage.DownloadByteArray;
import com.github.tobato.fastdfs.service.FastFileStorageClient;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
@Slf4j
@Component
public class FastdfsUtil {
@Autowired
private FastFileStorageClient storageClient;
/**
* 上传文件
* @param file
* @return
* @throws FileNotFoundException
*/
public String uploadFile(File file) throws FileNotFoundException {
StorePath storePath = this.storageClient.uploadFile(new FileInputStream(file), file.length(), "jpg", null);
System.out.println(storePath.getFullPath());//带分组的路径
System.out.println(storePath.getPath());//不带分组的路径
return "/"+storePath.getFullPath();
}
/**
* 单文件下载
* @param
*/
public byte[] downloadFile(String fileUrl) {
byte[] b = null;
try {
int index1 = StringUtils.ordinalIndexOf(fileUrl,"/",1);
int index2 = StringUtils.ordinalIndexOf(fileUrl,"/",2);
String group = fileUrl.substring(index1+1,index2);
String filepath = fileUrl.substring(fileUrl.lastIndexOf(group + "/")+7);
DownloadByteArray callback = new DownloadByteArray();
b = storageClient.downloadFile(group, filepath,callback);
}
catch (Exception e) {
e.printStackTrace();
}
return b;
}
}
- 控制层实现
/**
* 上传文件
*
* @param file 文件
* @return 文件路径
*/
@PostMapping(value = "upload")
public String uploadFile(MultipartFile file) {
String filePath = null;
try {
filePath = fastdfsUtil.uploadFile(transferToFile(file));
} catch (IOException e) {
log.error("上传文件异常:{}", e);
return "上传文件失败";
}
System.out.println(filePath);
return filePath;
}
//将multipartFile转换成File
private File transferToFile(MultipartFile multipartFile) {
// 选择用缓冲区来实现这个转换即使用java 创建的临时文件 使用 MultipartFile.transferto()方法 。
File file = null;
try {
String originalFilename = multipartFile.getOriginalFilename();
String[] filename = originalFilename.split("\\.");
file=File.createTempFile(filename[0], filename[1]);
multipartFile.transferTo(file);
file.deleteOnExit();
} catch (IOException e) {
e.printStackTrace();
}
return file;
}
/**
* 下载文件
*
* @param id 文件
* @return 文件路径
*/
@ApiOperation(value = "下载文件")
@GetMapping(value = "download")
public byte[] download(Integer id) {
TNews byId = service.getById(id);
String path = byId.getPath();
byte[] bytes = fastdfsUtil.downloadFile(path);
return bytes;
}
- 获取上传的路径在浏览器直接访问即可