0%

Amazon EFS提供外部访问数据卷(一)

数据是最重要的电子资产,但是在持有及维护的过程,需要消耗不少的成本。于是,不得不去探索廉价又安全的数据存储方案。

背景

在云时代,不论是G家,还是AWS等这些大厂,都提供了非常可靠好用的服务。但是,整套使用下来,即便是按量计费,也是一个比较大的花销。

而非大厂的服务提供商,往往能给出价格实惠的虚拟主机,独立主机。但便宜的机器多多少少会有不稳定的问题,而且数据安全上,往往我们无法去信任小商家。

因此,我们是否能使用大厂的存储服务,使用其他商家的主机呢?

经过初步的检索,大致得出这样一套方案去尝试。

数据存储:Amazon EFS。提供可伸缩的数据存储。

接入EFS的代理机:Lightsail 。使用Lightsail而不选 EC2,也是基于成本考虑。EC2更优,5刀/月。

主力机器:独服 4C 32G。25刀/月。

需要数据卷持久化的数据都存储在EFS中,这样基本机器损坏,被搬走等各种原因,数据在AWS上还是可靠的。

安装 amazon-efs-utils

非 Amazon Linux,需要安装 amazon-efs-utils,才能使用efs。

1
2
3
4
5
6
yum -y install git
git clone https://github.com/aws/efs-utils
yum -y install make rpm-build
cd efs-utils
make rpm
yum -y install ./build/amazon-efs-utils*rpm

创建 EFS

image-20201229235242942

通过管理面板创建EFS

image-20201229235334335

在Network面板中,能看到EFS的IP address,创建完成。

配置 VPC,建立对等链接

因为使用的不是EC2,而是Lightsail。默认情况下是无法直接连接Amazon的服务的。需要建立对等连接。

在Lightsail的面板里面,操作建立对等连接。

image-20201229235638796

勾选 “启用 VPC 对等” 即可

在 VPC 面板中,查看对等连接是否建立成功。

image-20201229235829671

配置 EFS 入站规则

image-20201230000452803

新增一个安全组,单独给EFS访问使用。

出站规则默认全放行。

入站规则,因为Lightsail的内网IP与EC2的不同,需要单独放行。添加 172.26.0.0/16 所有流量放行。

到此所有准备工作完成,可以挂载数据卷了。

Lightsail 挂载数据卷

1
2
3
mkdir -p /mnt/efs
mount -t nfs4 -o nfsvers=4.1,rsize=1048576,wsize=1048576,hard,timeo=600,retrans=2,noresvport 172.31.22.169:/ /mnt/efs
# 如果没有返回错误,通过mount查看挂载情况,成功。

image-20201230000918942

配置 Nginx 代理 NFS TCP端口

1
2
3
4
5
6
7
8
9
10
stream {
upstream backend {
server 172.31.22.169:2049;
}
server {
listen 2049;
# 有需要的话,这里也可以做安全策略
proxy_pass backend;
}
}

在Lightsail的防火墙规则,放开2049端口。仅放开目标机器的ip。

image-20201230003254277

外部系统挂载数据卷

因为我的外部系统是Debian 10,也是需要安装 amazon-efs-utils。

1
2
3
4
5
apt-get -y install git binutils
git clone https://github.com/aws/efs-utils
cd efs-utils
./build-deb.sh
apt-get -y install ./build/amazon-efs-utils*deb

然后执行mount进行挂载, 只是将IP改成Lightsail的公网IP

1
mount -t nfs4 -o nfsvers=4.1,rsize=1048576,wsize=1048576,hard,timeo=600,retrans=2,noresvport $PUBLICIP:/ /mnt/efs

设置开机启动自动挂载

1
2
3
4
5
6
7
8
9
10
11
12
13
# 创建目录
mkdir -p /aws-efs

# Edit /etc/fstab 追加
$PUBLICIP:/ /aws-efs nfs defaults,_netdev 0 0

# 可以用 mount 指令检测下是否写对
mount -fav
# mount -fav
/ : ignored
mount.nfs: timeout set for Tue Dec 29 17:36:13 2020
mount.nfs: trying text-based options 'vers=4.2,addr=$PUBLICIP,clientaddr=$PUBLICIP'
/aws-efs : successfully mounted

性能测试

通过dd指令读写2G数据进行对比

1
2
3
4
5
# write
time dd if=/dev/zero of=/mnt/efs/2g-dd-data bs=1M count=2048 conv=fsync

# read
time dd if=/mnt/efs/2g-dd-data of=/dev/null bs=1M count=2048 conv=fsync
  1. Lightsail 本地 IO

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    # time dd if=/dev/zero of=/root/2g-dd-data bs=1M count=2048 conv=fsync
    2048+0 records in
    2048+0 records out
    2147483648 bytes (2.1 GB) copied, 33.3782 s, 64.3 MB/s

    real 0m33.386s
    user 0m0.011s
    sys 0m1.049s

    # time dd if=/mnt/efs/2g-dd-data of=/dev/null bs=1M count=2048 conv=fsync
    2048+0 records in
    2048+0 records out
    2147483648 bytes (2.1 GB) copied, 32.5695 s, 65.9 MB/s

    real 0m32.578s
    user 0m0.000s
    sys 0m0.944s
  2. 本机EFS IO

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    # time dd if=/dev/zero of=/mnt/efs/2g-dd-data bs=1M count=2048 conv=fsync
    2048+0 records in
    2048+0 records out
    2147483648 bytes (2.1 GB) copied, 19.2469 s, 112 MB/s

    real 0m19.254s
    user 0m0.000s
    sys 0m1.078s

    # time dd if=/mnt/efs/2g-dd-data of=/dev/null bs=1M count=2048 conv=fsync
    2048+0 records in
    2048+0 records out
    2147483648 bytes (2.1 GB) copied, 19.3482 s, 111 MB/s

    real 0m19.352s
    user 0m0.005s
    sys 0m0.760s
  3. 远程主机 EFS IO

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    # time dd if=/dev/zero of=/mnt/efs/2g-dd-data bs=1M count=2048 conv=fsync
    2048+0 records in
    2048+0 records out
    2147483648 bytes (2.1 GB, 2.0 GiB) copied, 67.4047 s, 31.9 MB/s

    real 1m10.265s
    user 0m0.005s
    sys 0m1.225s

    # time dd if=/mnt/efs/2g-dd-data of=/dev/null bs=1M count=2048 conv=fsync
    2048+0 records in
    2048+0 records out
    2147483648 bytes (2.1 GB, 2.0 GiB) copied, 0.266611 s, 8.1 GB/s

    real 0m0.274s
    user 0m0.000s
    sys 0m0.266s

结语

整个流程下来,可以预期的是,在外网访问EFS是可行的。

然后从测试数据来看,即便在一个Lightsail性能非常差的机器上面,网络IO也会比本地IO性能优越很多。

但是在远程机器IO的读写测试就变得不准确了,而且写入速度来说,确实会有非常大的损失。这里的性能损失有多方面的原因。

即便我的另一个机房的主机,与AWS Lightsail的主机ping值是低于10ms的网络情况下。网络的读写也不高。这里nginx的反向代理参数没配置对,机器的性能等等也是原因。

从测试结果来看,即便选用低配的 EC2,这里的性能也会有可观的增长。那为什么选用LIghtsail,那还是为了省钱。。。

其实原本这套方案是想接入G家的GCP的Cloud Filestore的。但是G家的数据卷,最低配1T存储定量,不是按可用来算。月费用惊人。。。

最后, 测试数据文件赶紧删掉。占用是要花钱的 XD

image-20201230011852390


下期预告:Amazon-EFS提供外部访问数据卷(二)—— 配置传输过程数据加密