赞
踩
目录
带着问题学java系列博文之java基础篇。从问题出发,学习java知识。
FastDFS是一个开源的分布式文件系统,功能包括:文件存储、文件同步、文件访问(文件上传、文件下载)等,解决了大容量存储和负载均衡的问题。特别适合以文件为载体的在线服务,如相册网站、视频网站等等。FastDFS服务端有两个角色:跟踪器(tracker)和存储节点(storage)。跟踪器主要做调度工作,在访问上起负载均衡的作用。
FastDFS系统结构图:
FastDFS文件上传交互图:
1. client询问tracker上传到的storage,不需要附加参数;
2. tracker返回一台可用的storage;
3. client直接和storage通讯完成文件上传。
FastDFS文件下载交互图:
1. client询问tracker下载文件的storage,参数为文件标识(卷名和文件名);
2. tracker返回一台可用的storage;
3. client直接和storage通讯完成文件下载。
linux上安装fastdfs:
首先安装fastdfs依赖的两个组件GCC和libfastcommon
一.安装GCC
yum install make cmake gcc gcc-c++
二.安装libfastcommon
1.下载安装包 link:https://github.com/happyfish100/libfastcommon/releases
2.上传服务器 rz -y 选择压缩包
3.解压缩 tar -zxvf libfastcommon-1.0.42.tar.gz
4.进入解压文件夹 cd libfastcommon-1.0.42
5.编译 ./make.sh
6.安装 ./make.sh install
libfastcommon 默认安装到了 /usr/lib64/libfastcommon.so /usr/lib64/libfdfsclient.so
因为 FastDFS 主程序设置的 lib 目录是/usr/local/lib,所以需要创建软链接:
ln -s /usr/lib64/libfastcommon.so /usr/lib/libfastcommon.so
ln -s /usr/lib64/libfastcommon.so /usr/lib/libfastcommon.so
ln -s /usr/lib64/libfdfsclient.so /usr/local/lib/libfdfsclient.so
ln -s /usr/lib64/libfdfsclient.so /usr/lib/libfdfsclient.so
三.安装FastDFS
1.下载安装包 link:https://github.com/happyfish100/fastdfs/releases
2.上传服务器 rz -y 选择压缩包
3.解压缩 tar -zxvf fastdfs-6.04.tar.gz
4.进入解压文件夹 cd fastdfs-6.04
5.编译 ./make.sh
6.安装 ./make.sh install
安装完成之后,fastdfs的默认配置文件在 /etc/fdfs/下:
client.conf.sample storage.conf.sample
storage_ids.conf.sample tracker.conf.sample
这四个是样板,以后的配置就是复制样板修改。
默认的启动文件在 /etc/init.d/下:
fdfs_storage :storage存储节点服务启动文件 启动storage命令 ./fdfs_storage start
fdfs_tracker :tracker跟踪服务器启动文件 启动tracker命令 ./fdfs_tracker start
修改启动文件,因为fdfs服务脚本设置的bin目录是/usr/local/bin,但是实际安装之后文件都在/usr/bin,因此需要修改两个启动文件,把其中/usr/local/bin的全换成/usr/bin。
方式一:
sed -i ‘s#/usr/local/bin/#/usr/bin/#g’ /etc/init.d/fdfs_storaged
sed -i ‘s#/usr/local/bin/#/usr/bin/#g’ /etc/init.d/fdfs_trackerd
方式二:
vi /etc/init.d/fdfs_storaged 修改其中的路径;
vi /etc/init.d/fdfs_tracker 修改其中的路径
7.配置
i.先创建文件夹用来存放fdfs的日志和数据存储
mkdir -p /data/fdfs/tracker
mkdir -p /data/fdfs/storage
ii.配置tracker
cd /etc/fdfs/
cp tracker.conf.sample tracker.conf (复制模板,去掉sample,tracker会自动启用)
vi tracker.conf
修改的内容如下: disabled=false #启用配置文件 port=22122 #tracker的端口号,一般采用 22122 这个默认端口 base_path=/data/fdfs/tracker #tracker的数据文件和日志目录
保存退出后,测试启动tracker
cd /etc/init.d/ => ./fdfs_trackerd start
Starting FastDFS tracker server:(显示信息表示启动成功,可以在配置的存储目录下看到自动创建了data和base两个文件夹,服务所在端口是22122)
设置开机启动:
vi /etc/rc.d/rc.local
添加如下内容:
## FastDFS Tracker /etc/init.d/fdfs_trackerd start
iii.配置storage存储
cd /etc/fdfs
cp storage.conf.sample storage.conf
vi storage.conf
修改的内容如下:
disabled=false #启用配置文件 group_name=group1 #组名(第一组为 group1,第二组为 group2) port=23000 #storage的端口号,同一个组的 storage 端口号必须相同 base_path=/data/fdfs/storage #设置storage 的日志目录 store_path0=/data/fdfs/storage #存储路径 store_path_count=1 #存储路径个数,需要和 store_path个数匹配 tracker_server=192.168.218.130:22122 #tracker 服务器的 IP 地址和端口 #tracker_server=192.168.1.132:22122 #多个 tracker 直接添加多条配置 http.server_port=8888 #设置 http server 端口号
保存退出之后,测试启动storage
cd /etc/init.d => ./fdfs_storaged start
Starting FastDFS storage server:(显示信息表示启动成功,可以在配置的存储目录下看到自动创建了data和logs两个文件夹,服务所在端口是23000)
设置 FastDFS 存储器开机启动: vi /etc/rc.d/rc.local 添加:
- ## FastDFS Storage
-
- /etc/init.d/fdfs_storaged start
至此fastdfs安装配置完成,可以编写程序测试文件上传下载。完成第三步之后,使用代码操作fdfs,可以实现文件上传下载,不过此时文件上传成功之后返回的url,通过浏览器http方式是无法访问的。这是由于V4.05 以后的版本就把内置HTTP服务去掉了,搭建好fastdfs 系统后 还需要搭建web容器功能。
四.安装nginx web插件
安装配置fastdfs-nginx-module:
1.下载 link:https://github.com/happyfish100/fastdfs-nginx-module/
2.上传 rz -y 选择压缩包
3.解压缩 tar -zxvf fastdfs-nginx-module-1.22.tar.gz
4.修改配置 vi fastdfs-nginx-module-1.22/src/config 把文件中的/usr/local 都改为 /usr
5.复制配置文件到fdfs的配置文件夹下 cp fastdfs-nginx-module-1.22/src/mod_fastdfs.conf /etc/fdfs
6.修改配置 vi /etc/fdfs/mod_fastdfs.conf 修改内容如下:
connect_timeout=10 #连接超时时间 network_timeout=30 #发送接收数据超时时间 base_path=/tmp #日志文件位置 load_fdfs_parameters_from_tracker=true #是否从tracker读取信息 storage_server_port=23000 #本机storage的端口 group_name=group1 #group组名 # url链接中是否包含组名(这个url是fastdfs返回的,目前还不清楚如何配置不返回组名,所以这里的配置 # 要根据url来配置,否则nginx转发无法访问),类似/M00/00/00/xxxx 和 group1/M00/00/00/xxxx;如果# 选择true,即包含组名,则需要修改nginx的映射路径: # location /M00 改为 location /group1/M00 # 这里考虑到有可能有多组,所以可以灵活配置: # location ~*/M00 或者是 location /group[0-9]/M00 匹配所有group) url_have_group_name = true #(注意这里必须和url中一致,如果返回的url中有组名,则这里必须配置成true) tracker_server=192.168.218.130:22122 #tracker服务器ip和端口 store_path_count=1 #存储路径数量,必须和 storage.conf文件一致 store_path0=/data/fdfs/storage #存储路径,必须和 storage.conf文件一致 #(当文件在本地不存在时怎样回应: # proxy 代理,从其它存储服务器获取内容,然后发送给客户 # redirect 重定向原始存储服务器的http头) response_mode=proxy group_count = 0 #设置组的数量,0表示只有一个组,如果有多个组,则配合【group1】组合配置
7.复制fdfs安装包中的配置文件到fdfs的配置文件夹下(/root/fastdfs-6.04/conf)
cp /root/fastdfs-6.04/conf/http.conf /etc/fdfs
cp /root/fastdfs-6.04/conf/mime.types /etc/fdfs
安装配置nginx(nginx安装配置详见 Java EE--组件篇 Nginx)
创建软链接: ln -s /data/fdfs/storage/data/ /data/fdfs/storage/data/M00
配置nginx代理
vi /usr/local/nginx/conf/nginx.conf
添加内容:
# 这种配置是利用nginx的web容器功能,进行静态资源代理 # 有个致命问题是,如果有多个storage节点,并且其他的storage节点是部署在别的服务器上,则这种代理 # 方式将无法确保所有的资源都可以支持访问 server{ listen 8888; server_name 192.168.218.130; location ~/group[0~9]/M[0~9][0~9]{ root /data/fdfs/storage/data; ngx_fastdfs_module; } 注意:如果上面的mod_fastdfs.conf文件中配置了 url_have_group_name = true 即url中包含组名, 则映射路径应该配置成: location /group1/M00 (组名是啥就添加啥,很明显,这个并不好,因为具体有多少group就得配置多少,所以不推荐使用) 或者配置成: location ~*/M00 或者 location /group[0-9]/M00
至此fdfs的全部配置完成,与nginx的整合也搞定,上传成功之后fdfs返回的url:
192.168.218.130:8888/M00/00/00/wKjagl3zR6uAVOedAAHOvkPMWig767.png
可以直接在浏览器中打开。
1.引入依赖
- <dependency>
- <groupId>com.github.tobato</groupId>
- <artifactId>fastdfs-client</artifactId>
- <version>RELEASE</version>
- </dependency>
2.增加配置(application.yml):
- fdfs:
- so-timeout: 1501 #socket读取超时时长
- connect-timeout: 601 #连接tracker服务器超时时长
- pool:
- max-total: 200 #连接池最大数量
- max-total-per-key: 50 #每个tracker地址的最大连接数
- max-wait-millis: 5000 #连接耗尽时等待获取连接的最大毫秒数
- thumb-image:
- height: 150 #缩略图的高
- width: 150 #缩略图的宽
- web-server-url: 192.168.218.129:80/ #storage的webserver地址,nginx代理的ip+port
- tracker-list:
- - 192.168.218.129:22122 #tracker服务器地址
- group-name: group1 #个人配置的组名
3.引入起步配置:
- @SpringBootApplication
- // 因为springboot没有封装fastdfs(从引入的依赖可以看出,不是标准的spring-boot-starter),所以需
- // 要手动引入起步依赖
- @Import(FdfsClientConfig.class)
- public class SpringBootFdfsApplication {
- public static void main(String[] args) {
- SpringApplication.run(SpringBootFdfsApplication.class,args);
- }
- }
4.封装fastdfsClient工具类(可选):
- @Component
- public class FastDFSClient {
- private static final Logger LOGGER = LoggerFactory.getLogger(FastDFSClient.class);
-
-
- @Autowired
- private FdfsWebServer fdfsWebServer;
-
- @Autowired
- private FastFileStorageClient fastFileStorageClient;
-
- @Autowired
- private AppendFileStorageClient appendFileStorageClient;
-
- /**
- * 上传文件MultipartFile类型
- * @param file 文件对象
- * @return 文件访问地址
- * @throws IOException
- */
- public String uploadFile(MultipartFile file) throws IOException {
- InputStream inputStream = file.getInputStream();
- //通过file.getOriginalFilename()获取文件名称,再通过FilenameUtils.getExtension()获取文件类型名
- StorePath storePath = fastFileStorageClient.uploadFile(inputStream, file.getSize(),
- FilenameUtils.getExtension(file.getOriginalFilename()), null);
- inputStream.close();
- return getResAccessUrl(storePath);
- }
-
- /**
- * 上传文件File类型
- * @param file 文件对象
- * @return 文件访问地址
- * @throws IOException
- */
- public String uploadFile(File file) throws IOException {
- InputStream inputStream = new FileInputStream(file);
- StorePath storePath = fastFileStorageClient.uploadFile(inputStream, FileUtils.sizeOf(file),
- FilenameUtils.getExtension(file.getName()), null);
- inputStream.close();
- return getResAccessUrl(storePath);
- }
-
- /**
- * 封装文件完整URL地址
- * @param storePath
- * @return
- */
- private String getResAccessUrl(StorePath storePath) {
- String fileUrl = fdfsWebServer.getWebServerUrl() + storePath.getFullPath();
- return fileUrl;
- }
-
-
- /**
- * 上传头像,并生成缩略图(MultipartFile类型)
- * @param file 文件对象
- * @return 文件访问地址
- * @throws IOException
- */
- public String uploadFace(MultipartFile file) throws IOException {
- InputStream inputStream = file.getInputStream();
- StorePath storePath = fastFileStorageClient.uploadImageAndCrtThumbImage(inputStream, file.getSize(),
- FilenameUtils.getExtension(file.getOriginalFilename()), null);
- inputStream.close();
- return getResAccessUrl(storePath);
- }
-
-
- /**
- * 上传头像,并生成缩略图(File类型)
- * @param file 文件对象
- * @return 文件访问地址
- * @throws IOException
- */
- public String uploadFace(File file) throws IOException {
- InputStream inputStream = new FileInputStream(file);
- StorePath storePath = fastFileStorageClient.uploadImageAndCrtThumbImage(inputStream, FileUtils.sizeOf(file),
- FilenameUtils.getExtension(file.getName()), null);
- inputStream.close();
- return getResAccessUrl(storePath);
- }
-
- /**
- * 根据返回的图片地址获取缩略图地址
- * @param url 图片地址
- * @return 缩略图地址(生成规则与配置有关,150x150)
- */
- public String getThumbImageUrl(String url){
- int index = url.lastIndexOf(".");
- String fileName = url.substring(0,index)+"_150x150.";
- String ext = url.substring(index+1);
- return fileName+ext;
- }
-
-
- /**
- * 上传可追加内容文件
- * @param file 文件对象
- * @param groupName 组名
- * @return 文件访问地址
- * @throws IOException
- */
- public String uploadAppenderFile(MultipartFile file,String groupName) throws IOException {
- InputStream inputStream = file.getInputStream();
- StorePath storePath = appendFileStorageClient.uploadAppenderFile(groupName, inputStream,
- file.getSize(), FilenameUtils.getExtension(file.getOriginalFilename()));
- inputStream.close();
- return getResAccessUrl(storePath);
- }
-
- /**
- * 上传可追加内容,指定文件类型
- * @param data 上传内容
- * @param groupName 组名
- * @param ext 文件类型
- * @return 文件访问地址
- * @throws IOException
- */
- public String uploadAppenderFile(byte[] data,String groupName,String ext) throws IOException {
- InputStream inputStream = new ByteArrayInputStream(data);
- StorePath storePath = appendFileStorageClient.uploadAppenderFile(groupName, inputStream,data.length, ext);
- inputStream.close();
- return getResAccessUrl(storePath);
- }
-
- /**
- * 追加上传
- * @param file 文件对象
- * @param url 可追加文件访问地址
- * @throws IOException
- */
- public void appendFile(MultipartFile file,String url) throws IOException {
- InputStream inputStream = file.getInputStream();
- StorePath storePath = StorePath.parseFromUrl(url);
- appendFileStorageClient.appendFile(storePath.getGroup(),storePath.getPath(),inputStream,
- file.getSize());
- inputStream.close();
- }
-
- /**
- * 追加上传
- * @param data 追加内容
- * @param url 可追加文件访问地址
- * @throws IOException
- */
- public void appendFile(byte[] data,String url) throws IOException {
- InputStream inputStream = new ByteArrayInputStream(data);
- StorePath storePath = StorePath.parseFromUrl(url);
- appendFileStorageClient.appendFile(storePath.getGroup(),storePath.getPath(),inputStream,data.length);
- inputStream.close();
- }
-
- /**
- * 删除文件
- * @param fileUrl
- * @return
- */
- public boolean deleFile(String fileUrl) {
- if (StringUtils.isEmpty(fileUrl)) {
- return false;
- }
- try {
- StorePath storePath = StorePath.parseFromUrl(fileUrl);
- fastFileStorageClient.deleteFile(storePath.getGroup(), storePath.getPath());
- } catch (FdfsUnsupportStorePathException e) {
- LOGGER.error("删除文件异常!", e);
- return false;
- }
- return true;
- }
-
- /**
- * 下载文件
- * @param fileUrl
- * @return
- */
- public byte[] downloadFile(String fileUrl) {
- StorePath storePath = StorePath.parseFromUrl(fileUrl);
- byte[] bytes = fastFileStorageClient.downloadFile(storePath.getGroup(), storePath.getPath(),
- new DownloadByteArray());
- return bytes;
- }
- }
参考文档:https://www.oschina.net/p/fastdfs?hmsr=aladdin1e1
以上系个人理解,如果存在错误,欢迎大家指正。原创不易,转载请注明出处!
赞
踩
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。