搭建FastDFS集群-二

背景

上一篇 搭建FastDFS集群-一 描述了如何从源码构建FastDFS服务, 并通过脚本进行文件的 上传/下载/删除; 本文将详细描述如何安装nginx扩展模块,并使用http协议下载文件; 同时使用Java Client方式执行文件的 上传/下载/删除/获取文件详情等.

FastDFS 架构

安装 fastdfs-nginx-module

全新安装nginx或在已安装的nginx上添加模块请看文章 源码安装nginx ,笔者已安装nginx, 就按照添加模块方式进行安装.

查看当前已安装模块

1
2
3
4
[root@Node nginx-1.12.1]# nginx -V
nginx version: nginx/1.12.1
built by gcc 4.4.7 20120313 (Red Hat 4.4.7-18) (GCC)
configure arguments: --prefix=/root/devTools/nginx-1.12.1 --with-pcre=/root/workspaces/local/pcre-8.41 --with-zlib=/root/workspaces/local/zlib-1.2.8
1
2
3
4
5
cd ~/workspaces/github
git clone git@github:happyfish100/fastdfs-nginx-module.git
cd /workspaces/local/nginx-1.12.1
./configure --prefix=/root/devTools/nginx-1.12.1 --with-pcre=/root/workspaces/local/pcre-8.41 --with-zlib=/root/workspaces/local/zlib-1.2.8 --add-module=/root/workspaces/github/fastdfs-nginx-module/src/
make

注: 切记不要执行make install指令, 否则将覆盖之前的配置文件

接下来切换到nginx安装目录, 备份可执行的二进制文件, 然后复制源码下./objs目录下的对应文件到安装目录即可, 如下:

1
2
3
cd /root/devTools/nginx-1.12.1/
mv nginx nginx.bak
cp /root/workspaces/local/nginx-1.12.1/objs/nginx ./

查看

1
2
3
4
[root@Node nginx-1.12.1]# nginx -V
nginx version: nginx/1.12.1
built by gcc 4.4.7 20120313 (Red Hat 4.4.7-18) (GCC)
configure arguments: --prefix=/root/devTools/nginx-1.12.1 --with-pcre=/root/workspaces/local/pcre-8.41 --with-zlib=/root/workspaces/local/zlib-1.2.8 --add-module=/root/workspaces/github/fastdfs-nginx-module/src/

安装完成

配置

配置fastdfs-nginx-module

1
2
cd ~/workspaces/github/fastdfs-nginx-module/src
cd ~/workspaces/github/fastdfs-nginx-module/

按照如下进行配置,

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
# FastDFS tracker_server can ocur more than once, and tracker_server format is
# "host:port", host can be hostname or ip address
# valid only when load_fdfs_parameters_from_tracker is true
tracker_server=192.168.10.201:22122

# if the url / uri including the group name
# set to false when uri like /M00/00/00/xxx
# set to true when uri like ${group_name}/M00/00/00/xxx, such as group1/M00/xxx
# default value is false
url_have_group_name = true

# store_path#, based 0, if store_path0 not exists, it's value is base_path
# the paths must be exist
# must same as storage.conf
store_path0=/home/data/fastdfs/storage

复制其余配置,

1
2
cd ~/workspaces/github/fastdfs/conf
cp anti-steal.jpg http.conf mime.types /etc/fdfs/

配置nginx

1
vim ~/devTools/nginx-1.12.1/conf/nginx.conf

server节点中增加如下location配置,

1
2
3
location /group1/M00/ {
ngx_fastdfs_module;
}

测试nginx

在浏览器中输入 http://192.168.10.201 , 能看到 Welcome to nginx!, 说明nginx工作正常.

部分情况可能会出现403 Forbidden, 可能是如下原因:

  • location映射的文件目录无读取权限
  • 用户不对, 修改nginx.conf首行user nobody;为所属用户, 例如: user root;

测试fastdfs-nginx-module

按照上一篇 搭建FastDFS集群-一 介绍的内容, 上传文件; 可获得fileId(group, visual disk, data directory, file name), 例如:

group1/M00/00/00/wKgKyVnmAaOAMTPXAABDgcE2i8g51.jpeg

拼接上schema, host, port即可构成一个url; 例如:

http://192.168.10.201/group1/M00/00/00/wKgKyVnmAaOAMTPXAABDgcE2i8g51.jpeg

在浏览器中访问该url可获得相关信息

至此, fastdfs-nginx-module扩展模块安装完成; 接下来将介绍如何用java代码操纵fastDFS中的文件.

Java 客户端

导入依赖库:

1
2
3
4
5
<dependency>
<groupId>net.arccode</groupId>
<artifactId>fastdfs-client-java</artifactId>
<version>1.27.0</version>
</dependency>

fdfs_client.conf 配置如下:

1
2
3
4
connect_timeout = 30
network_timeout = 60
charset = UTF-8
tracker_server = 192.168.10.201:22122
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
package com.service_im;

import org.apache.commons.io.IOUtils;
import org.csource.common.NameValuePair;
import org.csource.fastdfs.*;
import org.junit.Before;
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.InputStream;

/**
* fastDFS 功能测试
*
* @author http://arccode.net
* @since 2017-10-19
*/

public class FastDFSTest {

private static final Logger LOG = LoggerFactory.getLogger(FastDFSTest.class);

private static final String FDFS_CLIENT_FILENAME = "fdfs_client.conf";//配置文件名
private static final String BASE_PATH = "/Users/ac/temp/";//本地存储基本路径
private static TrackerClient trackerClient = null;
private static TrackerServer trackerServer = null;
private static StorageServer storageServer = null;
private static StorageClient1 storageClient = null;

String groupName = "group1";
String remotePath = "M00/00/00/wKgKyVnpmxyAP6bdAABDgcE2i8g49.jpeg";

@Before
public void before() throws Exception {
//初始化配置文件
String resourcePath = FastDFSTest.class.getClassLoader().getResource("").getPath();
String fdfsConfigPath = resourcePath + FDFS_CLIENT_FILENAME;
ClientGlobal.init(fdfsConfigPath);

LOG.info("{}", ClientGlobal.configInfo());

//连接FastDFS,创建tracker和storage
trackerClient = new TrackerClient();
trackerServer = trackerClient.getConnection();
storageClient = new StorageClient1(trackerServer, storageServer);

}

@Test
public void uploadFile() throws Exception {

LOG.info("uploadFile start...");

File file = new File("/Users/ac/Pictures/for_test/t1.jpeg");
String extName = "jpeg";

//设置文件信息
NameValuePair[] nameValues = new NameValuePair[1];
nameValues[0] = new NameValuePair("fileName", file.getName());
LOG.info("=================>>>>>>>>>" + file.getName());

//读取本地文件到缓存中
InputStream inputStream = new FileInputStream(file);
long fileSize = file.length();
byte[] buffer = new byte[(int) fileSize];
inputStream.read(buffer);

//上传文件
String fileId = storageClient.upload_file1(buffer, extName, nameValues);
if (fileId != null) {
//成功
LOG.info("=================>>>>>>>>>" + fileId);
}
}

@Test
public void downloadFile() throws Exception {
LOG.info("downloadFile start...");

FileInfo fi = storageClient.get_file_info(groupName, remotePath);
LOG.info(fi.toString());


//下载文件,并将文件放到缓冲区内
byte[] buffer = storageClient.download_file(groupName, remotePath);

//查询文件信息
String fileName = "";
NameValuePair[] nameValues = storageClient.get_metadata(groupName, remotePath);
if (nameValues != null) {
for (NameValuePair nameValue : nameValues) {
LOG.info("{} → {}", nameValue.getName(), nameValue.getValue());
if ("fileName".equals(nameValue.getName())) {
fileName = nameValue.getValue();
}
}

//写入到磁盘中
IOUtils.write(buffer, new FileOutputStream(BASE_PATH + fileName));
} else {
LOG.info("error: 文件不存在...");
}

}

@Test
public void removeFile() throws Exception {

LOG.info("removeFile start...");

int result = storageClient.delete_file(groupName, remotePath);
LOG.info(result == 0 ? "删除成功" : "删除失败:" + result);
}


}

待解决问题

fastdfs-nginx-module 高可用方案配置.

已解决, 解决方案如下:

nginx中server节点中的location的配置修改如下:

1
2
3
location /group1/M00/ {
ngx_fastdfs_module;
}

如果还是没有生效, 可尝试如下方法, 定能解决:

  1. 查看nginx错误日志, 根据提示进行修改
  2. 重新编译nginx; 示例如下
1
2
3
./configure --prefix=/home/devTools/nginx-1.12.2 --with-pcre=/home/installPackage/pcre-8.41 --with-zlib=/home/installPackage/zlib-1.2.8 --add-module=/home/workspaces/github/fastdfs-nginx-module/src

make

之后把objs/nginx复制到nginx的安装目录进行覆盖.

相关内容

FastDFS架构剖析

搭建FastDFS集群-一

搭建FastDFS集群-二

转载

本文出自<<arccode>>, 欢迎转载, 转载请注明出处.