日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

FastDFS教程

發布時間:2024/9/18 编程问答 27 豆豆
生活随笔 收集整理的這篇文章主要介紹了 FastDFS教程 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

FastDFS簡介

FastDFS為互聯網量身定制,充分考慮了冗余備份、負載均衡、線性擴容等機制,并注重高可用、高性能等指標,使用FastDFS很容易搭建一套高性能的文件服務器集群提供文件上傳、下載等服務。

FastDFS服務端有兩個角色:跟蹤器(tracker)和存儲節點(storage)。

跟蹤器主要負責調度工作,在訪問上起負載均衡的作用。

存儲節點存儲文件,完成文件管理的所有功能,同時FastDFS同時對文件的metaData(文件屬性列表)進行管理。所謂文件的metaData就是文件的相關屬性,以鍵值對(key value pair)方式表示,如:width=1024,其中的key為width,value為1024。文件meta data是文件屬性列表,可以包含多個鍵值對。

tracker和storage都可以由一臺或多臺服務器構成。tracker和storage中的服務器均可以隨時增加或下線而不影響線上服務。其中tracker中的所有服務器都是對等的,可以根據服務器的壓力情況隨時增加或減少。

為了支持大容量,storage采用了分卷(或分組)的組織方式。存儲系統由一個或多個卷組成,卷與卷之間的文件是相互獨立的,所有卷的文件容量累加就是整個存儲系統中的文件容量。一個卷可以由一臺或多臺存儲服務器組成,一個卷下的存儲服務器中的文件都是相同的,卷中的多臺存儲服務器起到了冗余備份和負載均衡的作用。

在卷中增加服務器時,同步已有的文件由系統自動完成,同步完成后,系統自動將新增服務器切換到線上提供服務。

當存儲空間不足或即將耗盡時,可以動態添加卷。只需要增加一臺或多臺服務器,并將他們配置為一個新的組,這樣就擴大了存儲的容量。

FastDFS中的文件標識分為兩個部分:組名和文件名。二者缺一不可。

FastDFS原理

存儲節點采用了分組(group)的方式。存儲系統由一個或多個group組成,group與group之間的文件是相互獨立的,所有group的文件容量累加就是整個存儲系統中的文件容量。

一個group可以由一臺或多臺存儲服務器組成,一個group下的存儲服務器中的文件都是相同的,group中的多臺存儲服務器起到了冗余備份和負載均衡的作用(一個組的存儲容量為該組內存儲服務器容量最小的那個,不同組的Storage server之間不會相互通信,同組內的Storage server之間會相互連接進行文件同步)。

工作流程

文件上傳

Client會先想Tracker詢問存儲地址,Tracker查詢到存儲地址后返回給Client,Client拿著地址直接和對應的Storage通信,將文件上傳到storage。

文件下載

同樣,Client會向Tracker詢問地址,并帶上要查詢的文件名和組名,tracker查詢后會將地址返回給Client,client拿到地址和指定Storage通訊并下載文件。

使用docker安裝FastDFS

  • 拉取鏡像:docker pull season/fastdfs
  • 創建tracker容器:docker run -it -d --name tracker -v /home/iie4bu/docker/fastDFS/tracker:/fastdfs/tracker/data --net=host season/fastdfs tracker 默認端口是22122
  • 創建storage容器:docker run -itd --name storage -v /home/iie4bu/docker/fastDFS/storage:/fastdfs/storage/data -v /home/iie4bu/docker/fastDFS/store_path:/fastdfs/store_path --net=host -e TRACKER_SERVER:192.168.171.25(本機IP):22122 -e GROUP_NAME=group1 season/fastdfs storage
  • 此時兩個服務都以啟動,進行服務的配置。
    進入storage容器,到storage的配置文件中配置http訪問的端口,配置文件在fdfs_conf目錄下的storage.conf。將文件拷貝出來進行修改:docker cp storage:/fdfs_conf/storage.conf ~/,修改storage.conf文件中的tracker_server=你自己的宿主機ip:22122
    將修改后的配置文件拷貝到storage的配置目錄下:docker cp ~/storage.conf storage:/fdfs_conf/
    重啟storage容器:docker container restart storage
  • 查看tracker容器和storage容器的關聯
  • [root@localhost ~]# docker exec -it storage bash root@localhost:/# cd fdfs_conf root@localhost:/fdfs_conf# fdfs_monitor storage.conf

    在docker模擬客戶端上傳文件到storage容器

    開啟一個客戶端:docker run -tid --name fdfs_sh --net=host season/fastdfs sh
    將之前的storage.conf文件拷貝到容器fdfs_sh:/fdfs_conf/目錄下:docker cp ~/storage.conf fdfs_sh:/fdfs_conf/
    創建一個txt文件:

    [root@localhost 00]# docker exec -it fdfs_sh bash root@localhost:/# echo hello>a.txt

    進入fdfs_conf目錄,并將文件上傳到storage容器:

    root@localhost:/# cd fdfs_conf root@localhost:/fdfs_conf# fdfs_upload_file storage.conf /a.txt

    返回路徑:

    然后去我們對應的宿主機掛載文件夾下查看:

    FastDFS配合使用Nginx

    使用delron/fastdfs鏡像,這個鏡像中自帶Nginx服務。

  • 首先拉取鏡像:docker pull delron/fastdfs
  • 開啟tracker 服務:docker run -it -d --network=host --name tracker -v ~/docker/fastdfs/tracker/:/var/fdfs delron/fastdfs tracker。將fastDFS tracker運行目錄映射到本機的~/docker/fastdfs/tracker/目錄中。
  • 開啟storage服務:docker run -it -d --network=host --name storage -e TRACKER_SERVER=192.168.1.5(本機IP):22122 -v ~/docker/fastdfs/storage/:/var/fdfs delron/fastdfs storage
    查看docker服務:

    正常啟動了兩個服務。
    • 端口8888是默認的nginx代理端口
    • 端口23000是storage服務端口
    • 端口22122是tracker服務端口

    配置Storage

    進入storage容器,到storage的配置文件中配置http訪問的端口,配置文件在/etc/fdfs目錄下的storage.conf。


    默認的端口是8888,可以不修改

    配置Nginx

    在/usr/local/nginx目錄下,修改nginx.conf文件

    默認配置如下:(這里可以不用修改)

    開啟一個客戶端容器

    docker run -it -d --network=host --name fdfs_sh -e TRACKER_SERVER=192.168.1.5:22122 delron/fastdfs sh

    然后上傳一個文件到fdfs_sh容器中:docker cp timg.jpg fdfs_sh:/
    然后進入fdfs_sh容器:docker exec -it fdfs_sh bash
    上傳文件:fdfs_upload_file /etc/fdfs/client.conf timg.jpg
    返回信息如下:

    [root@manager /]# fdfs_upload_file /etc/fdfs/client.conf timg.jpg group1/M00/00/00/wKirGV6yybOAdf9TAABjtCKBG50922.jpg

    在瀏覽器中輸入:ip:8088/group1/M00/00/00/wKirGV6yybOAdf9TAABjtCKBG50922.jpg就可以看到這張圖片了。

    Springboot代碼實現上傳與下載

    添加依賴包pom.xml內容如下:

    <dependencyManagement><dependencies><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-dependencies</artifactId><version>2.1.4.RELEASE</version><scope>import</scope><type>pom</type></dependency></dependencies></dependencyManagement><dependencies><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId></dependency><dependency><groupId>com.github.tobato</groupId><artifactId>fastdfs-client</artifactId><version>1.27.2</version></dependency><dependency><groupId>com.alibaba</groupId><artifactId>fastjson</artifactId><version>1.2.68</version></dependency></dependencies>

    配置文件application.yaml內容如下:

    fdfs:soTimeout: 1500 #socket連接超時時長connectTimeout: 600 #連接tracker服務器超時時長reqHost: manager #nginx訪問地址reqPort: 8888 #nginx訪問端口thumbImage: #縮略圖生成參數,可選width: 150height: 150trackerList: #TrackerList參數,支持多個,我這里只有一個,如果有多個在下方加- x.x.x.x:port- manager:22122spring:servlet:multipart:max-request-size: 500MBmax-file-size: 500MB server:port: 8080

    添加配置文件FdfsConfiguration.java:

    package cn.ac.iie.config;import com.github.tobato.fastdfs.FdfsClientConfig; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.EnableMBeanExport; import org.springframework.context.annotation.Import; import org.springframework.jmx.support.RegistrationPolicy;@Configuration @Import(FdfsClientConfig.class) // 導入FastDFS-Client組件 @EnableMBeanExport(registration = RegistrationPolicy.IGNORE_EXISTING) // 解決jmx重復注冊bean的問題 public class FdfsConfiguration { }

    工具類FastDFSClientUtil.java:

    package cn.ac.iie.utils;import com.github.tobato.fastdfs.domain.fdfs.StorePath; import com.github.tobato.fastdfs.domain.fdfs.ThumbImageConfig; import com.github.tobato.fastdfs.domain.proto.storage.DownloadCallback; import com.github.tobato.fastdfs.service.FastFileStorageClient; import org.apache.commons.io.FilenameUtils; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Value; import org.springframework.stereotype.Component; import org.springframework.web.multipart.MultipartFile;import java.io.IOException; import java.io.InputStream;@Component public class FastDFSClientUtil {@Value("${fdfs.reqHost}")private String reqHost;@Value("${fdfs.reqPort}")private String reqPort;@Autowiredprivate FastFileStorageClient storageClient;@Autowiredprivate ThumbImageConfig thumbImageConfig; //創建縮略圖 , 縮略圖訪問有問題,暫未解決public String uploadFile(MultipartFile file) throws IOException {StorePath storePath = storageClient.uploadFile(file.getInputStream(),file.getSize(), FilenameUtils.getExtension(file.getOriginalFilename()),null);String path = thumbImageConfig.getThumbImagePath(storePath.getPath()) ;System.out.println("thumbImage :" + path); // 縮略圖訪問有問題,暫未解決System.out.println(storePath);return getResAccessUrl(storePath);}public void delFile(String filePath) {storageClient.deleteFile(filePath);}public InputStream download(String groupName, String path ) {InputStream ins = storageClient.downloadFile(groupName, path, new DownloadCallback<InputStream>(){public InputStream recv(InputStream ins) throws IOException {// 將此ins返回給上面的insreturn ins;}}) ;return ins ;}/*** 封裝文件完整URL地址* @param storePath* @return*/private String getResAccessUrl(StorePath storePath) {System.out.println(storePath.getFullPath());String fileUrl = "http://" + reqHost + ":" + reqPort + "/" + storePath.getFullPath();return fileUrl;}}

    controller:

    package cn.ac.iie.controller;import cn.ac.iie.utils.FastDFSClientUtil; import com.alibaba.fastjson.JSONObject; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.PostMapping; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestParam; import org.springframework.web.bind.annotation.RestController; import org.springframework.web.multipart.MultipartFile;import org.apache.commons.io.IOUtils; import javax.servlet.ServletOutputStream; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import java.io.IOException; import java.io.InputStream;@RestController public class UploadController {@Autowiredprivate FastDFSClientUtil dfsClient;@PostMapping("/upload")public JSONObject fdfsUpload(@RequestParam("file") MultipartFile file, HttpServletRequest request) {JSONObject jsonObject = new JSONObject();try {String fileUrl = dfsClient.uploadFile(file);jsonObject.put("url", fileUrl);} catch (IOException e) {e.printStackTrace();}return jsonObject;}/** http://localhost:8080/download?filePath=group1/M00/00/00/wKgIZVzZEF2ATP08ABC9j8AnNSs744.jpg*/@RequestMapping("/download")public void download(String filePath , HttpServletRequest request , HttpServletResponse response) throws IOException {// group1/M00/00/00/wKgIZVzZEF2ATP08ABC9j8AnNSs744.jpgString[] paths = filePath.split("/");String groupName = null;for (String item : paths) {if (item.indexOf("group") != -1) {groupName = item;break ;}}String path = filePath.substring(filePath.indexOf(groupName) + groupName.length() + 1, filePath.length());InputStream input = dfsClient.download(groupName, path);//根據文件名獲取 MIME 類型String fileName = paths[paths.length-1] ;System.out.println("fileName :" + fileName); // wKgIZVzZEF2ATP08ABC9j8AnNSs744.jpgString contentType = request.getServletContext().getMimeType(fileName);String contentDisposition = "attachment;filename=" + fileName;// 設置頭response.setHeader("Content-Type",contentType);response.setHeader("Content-Disposition",contentDisposition);// 獲取綁定了客戶端的流ServletOutputStream output = response.getOutputStream();// 把輸入流中的數據寫入到輸出流中IOUtils.copy(input,output);input.close();}@RequestMapping("/deleteFile")public String delFile(String filePath , HttpServletRequest request ,HttpServletResponse response) {try {dfsClient.delFile(filePath);} catch(Exception e) {// 文件不存在報異常 : com.github.tobato.fastdfs.exception.FdfsServerException: 錯誤碼:2,錯誤信息:找不到節點或文件// e.printStackTrace();}request.setAttribute("msg", "成功刪除,'" + filePath);return "index";}}

    總結

    以上是生活随笔為你收集整理的FastDFS教程的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。