FastDfs分布式文件系统的搭建及使用

FastDfs分布式文件系统的搭建及使用
本文章是参照江南一点雨发表的博客教程搭建的
https://blog.csdn.net/u012702547/article/details/104589468
在cento7下搭建

1、简介

FastDFS 由淘宝的余庆大佬在 2008 年开源的一款轻量级分布式文件管理系统,FastDFS 用 C 语言实现,支持 Linux、FreeBSD、MacOS 等类 UNIX 系统。FastDFS 类似 google FS,属于应用级文件系统,不是通用的文件系统,只能通过专有 API 访问,目前提供了 C 和 Java SDK ,以及 PHP 扩展 SDK。

这款开源软件从发布至今,历经数十年,这款开源软件的生命力依然旺盛,在业界依然备受推崇,当然这也得益于作者一直在不断完善该软件。

FastDFS 专为互联网应用量身定做,解决大容量文件存储问题,追求高性能和高扩展性,它可以看做是基于文件的 key/value 存储系统,key 为文件 ID,value 为文件内容,因此称作分布式文件存储服务更为合适。

2、架构
  • 文件存储
  • 文件同步
  • 文件上传
  • 文件下载

FastDFS 架构包括 Tracker 和 Storage 两部分,看名字大概就能知道,Tracker 用来追踪文件,相当于是文件的一个索引,而 Storage 则用来保存文件。

我们上传文件的文件最终保存在 Storage 上,文件的元数据信息保存在 Tracker 上,通过 Tracker 可以实现对 Storage 的负载均衡。

Storage 一般会搭建成集群,一个 Storage Cluster 可以由多个组构成,不同的组之间不进行通信,一个组又相当于一个小的集群,组由多个 Storage Server 组成,组内的 Storage Server 会通过连接进行文件同步来保证高可用。

3、安装
Tracker 安装

​ 1、需要gcc环境

yum install gcc-c++

​ 2、安装依赖库

yum -y install libevent

另一个库是 libfastcommon,这是 FastDFS 官方提供的,它包含了 FastDFS 运行所需要的一些基础库。

libfastcommon 下载地址:https://github.com/happyfish100/libfastcommon/archive/V1.0.43.tar.gz

将下载好的 libfastcommon 拷贝至 /usr/local/ 目录下,然后依次执行如下命令:

cd /usr/local
tar -zxvf V1.0.43.tar.gz
cd libfastcommon-1.0.43/
./make.sh
./make.sh install

​ 3、安装

由于 Tracker 和 Storage 是相同的安装包,所以下载一次

安装文件可以从 FastDFS 的 GitHub 仓库上下载,下载地址:https://github.com/happyfish100/fastdfs/archive/V6.06.tar.gz

下载成功后,将下载文件拷贝到 /usr/local 目录下,然后依次执行如下命令安装:

cd /usr/local
tar -zxvf V6.06.tar.gz
cd fastdfs-6.06/
./make.sh
./make.sh install

安装成功后,执行如下命令,将安装目录内 conf 目录下的配置文件拷贝到 /etc/fdfs 目录下:

cd conf/
cp ./* /etc/fdfs/

​ 4、配置

接下来进入 /etc/fdfs/ 目录下进行配置:

打开 tracker.conf 文件:

vim /etc/fdfs/tracker.conf

port默认为22122

修改元数据存储目录

base_path = /homo/tom/fastdfs    //元数据存储目录要真实存在

​ 5、启动

/usr/bin/fdfs_trackerd /etc/fdfs/tracker.conf start
Storage安装

1、安装命令和tacker一样,直接修改配置文件就行了

vim /etc/fdfs/storage.conf

base_path、storage_path0 配置的路径和tracker 配置的路径一致

tracker_server的ip地址为tracker的ip地址端口默认

2、启动

/usr/bin/fdfs_storaged /etc/fdfs/storage.conf start
Nginx安装

1、安装依赖

yum -y install pcre-devel
yum -y install openssl openssl-devel

2、解压安装包并进入解压之后的安装包根目录、编译安装

./configure
make
make install

3、装好之后,默认安装位置在 :

/usr/local/nginx/sbin/nginx

4、启动

进入sbin目录下

./nginx

5、如果修改了配置,如下命令重新加载配置文件

./nginx -s reload
安装fastdfs-nginx-module

首先下载 fastdfs-nginx-module,下载地址:https://github.com/happyfish100/fastdfs-nginx-module/archive/V1.22.tar.gz

1、解压安装

2、复制及修改配置文件

然后将 /usr/local/fastdfs-nginx-module-1.22/src/mod_fastdfs.conf 文件拷贝到 /etc/fdfs/ 目录下,并修改该文件的内容:

vi /etc/fdfs/mod_fastdfs.conf

修改tracker_server的路径为tracker的ip地址

修改url_have_group_name = true

修改storage_path0 为tracker配置文件下一样路径的地址

3、接下来,回到第一步下载的 nginx 安装文件的解压目录中,执行如下命令,重新配置编译安装:

./configure --add-module=/usr/local/fastdfs-nginx-module-1.22/src
make
make install

4、修改nginx的配置文件

vi /usr/local/nginx/conf/nginx.conf

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-GY6X0YiV-1615343119636)(C:\Users\tom\AppData\Roaming\Typora\typora-user-images\image-20210115162329136.png)]

5、配置完成后,启动 nginx,看到如下日志,表示 nginx 启动成功:

./nginx -s stop
./nginx


ngx_http_fastdfs_set pid=9908

疑问:fastdfs-nginx-module 有啥用

看了整个安装过程之后,很多小伙伴有疑问,到头来还是 nginx 本身直接找到了图片文件目录,fastdfs-nginx-module 到底有啥用?

前面我们说过,Storage 由很多组构成,每个组又是一个小的集群,在每一个组里边,数据会进行同步,但是如果数据还没同步,这个时候就有请求发来了,该怎么办?此时fastdfs-nginx-module 会帮助我们直接从源 Storage 上获取文件。

安装成功了。

4、springboot整合Fastdfs

1、添加依赖

<dependency>
    <groupId>org.csource</groupId>
    <artifactId>fastdfs-client-java</artifactId>
    <version>1.27-SNAPSHOT</version>
</dependency>

2、添加配置文件

在resource目录下添加配置文件fast_client.conf

connect_timeout = 60
network_timeout = 60
charset = UTF-8
http.tracker_http_port = 80
tracker_server = 192.168.6.128:22122

3、写FastDfs文件类

public class FastDFSFile{
    private String name;
    private byte[] content;
    private String ext;
    private String md5;
    private String author;
    //省略get、set方法及构造
}
    

4、创建FastDFS客户端

public class FastDFSClient {
   private static org.slf4j.Logger logger = LoggerFactory.getLogger(FastDFSClient.class);



   //寻找fastdfs配置文件
   static {
      try {
         //获取文件的绝对路径
         String filePath = new ClassPathResource("fdfs_client.conf").getFile().getAbsolutePath();
         ClientGlobal.init(filePath);
      } catch (Exception e) {
         logger.error("FastDFS Client Init Fail!",e);
      }
   }

   public static String[] upload(FastDFSFile file) {
      logger.info("File Name: " + file.getName() + "File Length:" + file.getContent().length);

      NameValuePair[] meta_list = new NameValuePair[1];
      meta_list[0] = new NameValuePair("author", file.getAuthor());

      long startTime = System.currentTimeMillis();
      String[] uploadResults = null;
      StorageClient storageClient=null;
      try {
         storageClient = getTrackerClient();
         uploadResults = storageClient.upload_file(file.getContent(), file.getExt(), meta_list);
      } catch (IOException e) {
         logger.error("IO Exception when uploadind the file:" + file.getName(), e);
      } catch (Exception e) {
         logger.error("Non IO Exception when uploadind the file:" + file.getName(), e);
      }
      logger.info("upload_file time used:" + (System.currentTimeMillis() - startTime) + " ms");

      if (uploadResults == null && storageClient!=null) {
         logger.error("upload file fail, error code:" + storageClient.getErrorCode());
      }
      String groupName = uploadResults[0];
      String remoteFileName = uploadResults[1];

      logger.info("upload file successfully!!!" + "group_name:" + groupName + ", remoteFileName:" + " " + remoteFileName);
      return uploadResults;
   }

   public static FileInfo getFile(String groupName, String remoteFileName) {
      try {
         StorageClient storageClient = getTrackerClient();
         return storageClient.get_file_info(groupName, remoteFileName);
      } catch (IOException e) {
         logger.error("IO Exception: Get File from Fast DFS failed", e);
      } catch (Exception e) {
         logger.error("Non IO Exception: Get File from Fast DFS failed", e);
      }
      return null;
   }

   public static InputStream downFile(String groupName, String remoteFileName) {
      try {
         StorageClient storageClient = getTrackerClient();
         byte[] fileByte = storageClient.download_file(groupName, remoteFileName);
         InputStream ins = new ByteArrayInputStream(fileByte);
         return ins;
      } catch (IOException e) {
         logger.error("IO Exception: Get File from Fast DFS failed", e);
      } catch (Exception e) {
         logger.error("Non IO Exception: Get File from Fast DFS failed", e);
      }
      return null;
   }

   public static void deleteFile(String groupName, String remoteFileName)
         throws Exception {
      StorageClient storageClient = getTrackerClient();
      int i = storageClient.delete_file(groupName, remoteFileName);
      logger.info("delete file successfully!!!" + i);
   }

   public static StorageServer[] getStoreStorages(String groupName)
         throws IOException {
      TrackerClient trackerClient = new TrackerClient();
      TrackerServer trackerServer = trackerClient.getConnection();
      return trackerClient.getStoreStorages(trackerServer, groupName);
   }

   public static ServerInfo[] getFetchStorages(String groupName,
                                    String remoteFileName) throws IOException {
      TrackerClient trackerClient = new TrackerClient();
      TrackerServer trackerServer = trackerClient.getConnection();
      return trackerClient.getFetchStorages(trackerServer, groupName, remoteFileName);
   }

   public static String getTrackerUrl() throws IOException {
      return "http://"+getTrackerServer().getInetSocketAddress().getHostString()+":"+ClientGlobal.getG_tracker_http_port()+"/";
   }

   private static StorageClient getTrackerClient() throws IOException {
      TrackerServer trackerServer = getTrackerServer();
      StorageClient storageClient = new StorageClient(trackerServer, null);
      return  storageClient;
   }

   private static TrackerServer getTrackerServer() throws IOException {
      TrackerClient trackerClient = new TrackerClient();
      TrackerServer trackerServer = trackerClient.getConnection();
      return  trackerServer;
   }
}

5、文件上传

/****
 * 上传文件
 *
 *
 * @param file
 * @return
 */
@RequestMapping("/upload")
@ResponseBody
public JSONObject singleFileUpload(@RequestParam("file") MultipartFile file) {
    JSONObject jsonObject = new JSONObject();
    if (file.isEmpty()) {
        jsonObject.put("msg","file cannot null");
    }
    try {
        //保存文件
        String path=saveFile(file);
        jsonObject.put("message","You successfully uploaded '" + file.getOriginalFilename() + "'");
        jsonObject.put("path", path);
    } catch (Exception e) {
        logger.error("upload file failed",e);
    }
    return jsonObject;
}

/**
 * @param multipartFile
 * @return
 * @throws IOException
 */
public String saveFile(MultipartFile multipartFile) throws IOException {
    String[] fileAbsolutePath={};
    String fileName=multipartFile.getOriginalFilename();
    String ext = fileName.substring(fileName.lastIndexOf(".") + 1);
    byte[] file_buff = null;
    InputStream inputStream=multipartFile.getInputStream();
    if(inputStream!=null){
        int len1 = inputStream.available();
        file_buff = new byte[len1];
        inputStream.read(file_buff);
    }
    inputStream.close();
    FastDFSFile file = new FastDFSFile(fileName, file_buff, ext);
    try {
        fileAbsolutePath = FastDFSClient.upload(file);  //upload to fastdfs
    } catch (Exception e) {
        logger.error("upload file Exception!",e);
    }
    if (fileAbsolutePath==null) {
        logger.error("upload file failed,please upload again!");
    }
    return FastDFSClient.getTrackerUrl()+fileAbsolutePath[0]+ "/"+fileAbsolutePath[1];
}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值