文章目录
CDN简介
CDN的全称是Content Delivery Network,即内容分发网络。
- 基本思路:尽可能避开互联网上有可能影响数据传输速度和稳定性的瓶颈和环节,使内容传输得更快、更稳定。通过在网络各处放置节点服务器所构成的在现有的互联网基础之上的一层智能虚拟网络,CDN系统能够实时地根据网络流量和各节点的连接、负载状况以及到用户的距离和响应时间等综合信息将用户的请求重新导向离用户最近的服务节点上。
- 目的:使用户可就近取得所需内容,解决 Internet网络拥挤的状况,提高用户访问网站的响应速度。
- 使用CDN的好处:
- 不用担心自己网站访客,在任何时间,任何地点,任何网络运营商,都能快速打开网站。
- 各种服务器虚拟主机带宽等采购成本,包括后期运维成本都会大大减少。
- 给网站直接带来的好处就是:流量,咨询量,客户量,成单量,都会得到大幅度提升。
CDN原理
CDN的基本原理为反向代理,反向代理(Reverse Proxy)方式是指以代理服务器来接受internet上的连接请求,然后将请求转发给内部网络上的服务器,并将从服务器上得到的结果返回给internet上请求连接的客户端,此时代理服务器对外就表现为一个节点服务器。通过部署更多的反向代理服务器,来达到实现多节点CDN的效果。
- 传统的未加缓存服务的访问过程:
用户提交域名→浏览器对域名进行解析→得到目的主机的IP地址→根据IP地址访问发出请求→得到请求数据并回复
由上可见,用户访问未使用CDN缓存网站的过程为:
1)、用户向浏览器提供要访问的域名;
2)、浏览器调用域名解析函数库对域名进行解析,以得到此域名对应的IP地址;
3)、浏览器使用所得到的IP地址,向域名的服务主机发出数据访问请求;
4)、浏览器根据域名主机返回的数据显示网页的内容。
CDN网络是在用户和服务器之间增加Cache层,如何将用户的请求引导到Cache上获得源服务器的数据,主要是通过接管DNS实现,下面让我们看看访问使用CDN缓存后的网站的过程:
- 使用了CDN缓存后的网站的访问过程:
1)、用户向浏览器提供要访问的域名;
2)、浏览器调用域名解析库对域名进行解析,由于CDN对域名解析过程进行了调整,所以解析函数库一般得到的是该域名对应的CNAME记录,为了得到实际IP地址,浏览器需要再次对获得的CNAME域名进行解析以得到实际的IP地址;在此过程中,使用的全局负载均衡DNS解析,如根据地理位置信息解析对应的IP地址,使得用户能就近访问。
3)、此次解析得到CDN缓存服务器的IP地址,浏览器在得到实际的IP地址以后,向缓存服务器发出访问请求;
4)、缓存服务器根据浏览器提供的要访问的域名,通过Cache内部专用DNS解析得到此域名的实际IP地址,再由缓存服务器向此实际IP地址提交访问请求;
5)、缓存服务器从实际IP地址得得到内容以后,一方面在本地进行保存,以备以后使用,另一方面把获取的数据返回给客户端,完成数据服务过程;
6)、客户端得到由缓存服务器返回的数据以后显示出来并完成整个浏览的数据请求过程。
主流CDN加速软件Varnish
suqid
或者varnish
均可以当wed服务器或者代理服务器,实现CDN加速。我们今天主要讲Varnish的安装和使用。
实验示例:
我们本实验将使用一台虚拟机node1作为CDN服务器,两台虚拟机node2、node3作为Apache的web服务,使用node1作为我们的CDN服务器实现反向代理和缓存,当然,使用的软件是Varnish。那么首先,我们将安装多个虚拟机作为实验平台。
装多个7.5版本的虚拟机的封装
详情请参照这篇博客:7.5虚拟机封装
为了实验环境一致,我们首先需要安装一个虚拟机作为母盘,使用次母盘镜像利用qemu快照出多个虚拟机快照进行实验。
qemu-img create -f qcow2 -b rhel7.5.qcow2 node1
qemu-img create -f qcow2 -b rhel7.5.qcow2 node2
qemu-img create -f qcow2 -b rhel7.5.qcow2 node3
会发现已经创建成功,接下来我们就以这三个快照为虚拟机开始实验:
[root@foundation40 images]# du -sh node*
196K node1
196K node2
196K node3
因为刚刚三个快照都是基于一个镜像做成的,所以需要进去修改各自的IP和主机名,方便区分。
到这里我们就成功安装了三台虚拟机:
安装varnish服务
我们将server1作为我们的CDN服务器,安装相关的软件。
- 我们需要从varnish官网上下载这三个rpm包:
jemalloc-3.6.0-1.el7.x86_64.rpm
varnish-libs-4.0.5-1.el7.x86_64.rpm
varnish-4.0.5-1.el7.x86_64.rpm
- 然后使用
yum install *
安装,因为我们当前目录只有这三个包。 - 使用
rpm -qc varnish
查看软件的配置文件。
[root@server1 ~]# rpm -qc varnish
/etc/logrotate.d/varnish #
/etc/varnish/default.vcl # 服务的主配置文件,使用vcl语法去设置cdn的模式
/etc/varnish/varnish.params # 服务的环境变量配置文件
- 我们通过查看varnish启动服务的脚本内容,看相关的varnish服务配置要求。
vim /usr/lib/systemd/system/varnish.service
我们可以看到,这里对服务的要求文件描述符数量和内存锁定的要求。我们此时查看server1上默认提供的文件描述符和内存锁定。
[root@server1 ~]# ulimit -l
64
[root@server1 ~]# ulimit -n
1024
所以,需要修改默认配置以适应varnish服务的要求。
vim /etc/security/limits.conf # 一些系统上限的配置文件
在配置文件中底部写入:
varnish - nofile 131072
varnish - memlock 82000
作用域 类型(默认为-) 修改上限的item 修改后的数值
修改完成后,重启varnish服务。
- 此时,我们查看服务端口:
netstat -tnlp
[root@server1 ~]# netstat -tnlp
Active Internet connections (only servers)
Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name
tcp 0 0 0.0.0.0:6081 0.0.0.0:* LISTEN 1492/varnishd
tcp 0 0 127.0.0.1:6082 0.0.0.0:* LISTEN 1491/varnishd
tcp 0 0 0.0.0.0:22 0.0.0.0:* LISTEN 864/sshd
tcp 0 0 127.0.0.1:25 0.0.0.0:* LISTEN 1103/master
tcp6 0 0 :::6081 :::* LISTEN 1492/varnishd
tcp6 0 0 :::22 :::* LISTEN 864/sshd
tcp6 0 0 ::1:25 :::* LISTEN 1103/master
可以看到此时其端口为6081,因为我们做的是http网站的CDN反向代理和缓存,所以,需要将默认的varnish的端口改为80。
vim /etc/varnish/varnish.params
重启服务,再次查看端口,成功。
[root@server1 ~]# netstat -lntp
Active Internet connections (only servers)
Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name
tcp 0 0 127.0.0.1:6082 0.0.0.0:* LISTEN 12210/varnishd
tcp 0 0 0.0.0.0:80 0.0.0.0:* LISTEN 12211/varnishd
tcp 0 0 0.0.0.0:22 0.0.0.0:* LISTEN 864/sshd
tcp 0 0 127.0.0.1:25 0.0.0.0:* LISTEN 1103/master
tcp6 0 0 :::80 :::* LISTEN 12211/varnishd
tcp6 0 0 :::22 :::* LISTEN 864/sshd
tcp6 0 0 ::1:25 :::* LISTEN 1103/master
我们可以使用ps aux
查看varnish的进程号:
root 12210 0.0 8.6 122844 87856 ? SLs 11:37 0:00 /usr/sbin/varnishd -P /var
varnish 12211 0.1 9.1 270548 93060 ? Sl 11:37 0:00 /usr/sbin/varnishd -P /var
通过cat /proc/12210/status
和cat /proc/12211/status
可以查看其进程的相关信息:
[root@server1 ~]# cat /proc/12210/status
Name: varnishd
Umask: 0022
State: S (sleeping)
Tgid: 12210
Ngid: 0
Pid: 12210
PPid: 1
TracerPid: 0
Uid: 0 0 0 0
Gid: 0 0 0 0
FDSize: 64
Groups:
VmPeak: 122844 kB
VmSize: 122844 kB
VmLck: 82944 kB
VmPin: 0 kB
VmHWM: 87856 kB
VmRSS: 87856 kB
RssAnon: 4392 kB
RssFile: 83464 kB
RssShmem: 0 kB
VmData: 8316 kB
VmStk: 132 kB
VmExe: 612 kB
VmLib: 4092 kB
VmPTE: 248 kB
VmSwap: 0 kB
Threads: 1
SigQ: 0/3871
SigPnd: 0000000000000000
ShdPnd: 0000000000000000
SigBlk: 0000000000000000
SigIgn: 0000000000001001
SigCgt: 0000000180004002
CapInh: 0000000000000000
CapPrm: 0000001fffffffff
CapEff: 0000001fffffffff
CapBnd: 0000001fffffffff
CapAmb: 0000000000000000
Seccomp: 0
Cpus_allowed: 1
Cpus_allowed_list: 0
Mems_allowed: 00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000001
Mems_allowed_list: 0
voluntary_ctxt_switches: 303
nonvoluntary_ctxt_switches: 5
[root@server1 ~]# cat /proc/12211/status
Name: varnishd
Umask: 0022
State: S (sleeping)
Tgid: 12211
Ngid: 0
Pid: 12211
PPid: 12210
TracerPid: 0
Uid: 998 998 998 998
Gid: 996 996 996 996
FDSize: 64
Groups: 996
VmPeak: 274640 kB
VmSize: 270548 kB
VmLck: 0 kB
VmPin: 0 kB
VmHWM: 93060 kB
VmRSS: 93060 kB
RssAnon: 10144 kB
RssFile: 82916 kB
RssShmem: 0 kB
VmData: 153948 kB
VmStk: 132 kB
VmExe: 612 kB
VmLib: 4112 kB
VmPTE: 344 kB
VmSwap: 0 kB
Threads: 217
SigQ: 0/3871
SigPnd: 0000000000000000
ShdPnd: 0000000000000000
SigBlk: 0000000000000000
SigIgn: 0000000000001001
SigCgt: 0000000180000000
CapInh: 0000000000000000
CapPrm: 0000000000000000
CapEff: 0000000000000000
CapBnd: 0000001fffffffff
CapAmb: 0000000000000000
Seccomp: 0
Cpus_allowed: 1
Cpus_allowed_list: 0
Mems_allowed: 00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000000,00000001
Mems_allowed_list: 0
voluntary_ctxt_switches: 87
nonvoluntary_ctxt_switches: 5
至此,我们的varnish服务已经基本配置完成。
varnish实现HTTP缓存
- 我们在server2上搭建一个web服务器。
yum install httpd -y
systemctl start httpd
vim /var/www/html/index.html
写入:server2 作为发布页面
curl localhost # 测试页面是否发布
- 此时,我们回到server1(也就是我们的CDN服务器)
修改varnish的匹配文件vim /etc/varnish/default.vcl
,将其中的backend default的ip和端口改为server2的。
完成后,重启varnish服务。 - 我们回到我们真实的物理机上进行测试:
[root@foundation40 varnish]# curl 172.25.40.1
server2
可以发现,此时server1已经反向代理了web服务器server2的发布页面。
- 接下来,我们继续修改server1的varnish的配置文件,实现页面缓存功能。(实质上是可以查看到缓存命中的情况)
我们打开vim /etc/varnish/default.vcl
,在函数sub vcl_deliver
中写入如下内容:可以看到就是关于缓存命中的显示的。
if (obj.hits > 0) {
set resp.http.X-Cache = "HIT from westos cache";
}
else {
set resp.http.X-Cache = "MISS from westos cache";
}
return (deliver);
重启varnish服务。
我们可以发现,当我们使用curl -I 除此访问页面时,会题时没有缓存MISS from westos cache
,之后都会题时缓存命中HIT from westos cache
初次访问:
[root@foundation40 varnish]# curl -I 172.25.40.1
HTTP/1.1 200 OK
Date: Fri, 19 Jul 2019 05:19:08 GMT
Server: Apache/2.4.6 (Red Hat Enterprise Linux)
Last-Modified: Fri, 19 Jul 2019 04:50:52 GMT
ETag: "8-58e017894f220"
Content-Length: 8
Content-Type: text/html; charset=UTF-8
X-Varnish: 32775
Age: 0
Via: 1.1 varnish-v4
X-Cache: MISS from westos cache
Connection: keep-alive
[root@foundation40 varnish]# curl -I 172.25.40.1
HTTP/1.1 200 OK
Date: Fri, 19 Jul 2019 05:19:08 GMT
Server: Apache/2.4.6 (Red Hat Enterprise Linux)
Last-Modified: Fri, 19 Jul 2019 04:50:52 GMT
ETag: "8-58e017894f220"
Content-Length: 8
Content-Type: text/html; charset=UTF-8
X-Varnish: 32775
Age: 0
Via: 1.1 varnish-v4
X-Cache: MISS from westos cache
Connection: keep-alive
再次访问:
[root@foundation40 varnish]# curl -I 172.25.40.1
HTTP/1.1 200 OK
Date: Fri, 19 Jul 2019 05:19:08 GMT
Server: Apache/2.4.6 (Red Hat Enterprise Linux)
Last-Modified: Fri, 19 Jul 2019 04:50:52 GMT
ETag: "8-58e017894f220"
Content-Length: 8
Content-Type: text/html; charset=UTF-8
X-Varnish: 11 32776
Age: 2
Via: 1.1 varnish-v4
X-Cache: HIT from westos cache
Connection: keep-alive
手动清理缓存
我们在server1的cdn服务器上可以手动清理缓存:
varnishadm ban req.url "~" / # 清理所有缓存
varnishadm ban req.url "~" /index.html #清理指定页面的缓存
当我们再次访问时,就已经没有缓存了。
[root@foundation40 varnish]# curl -I 172.25.40.1
HTTP/1.1 200 OK
Date: Fri, 19 Jul 2019 05:22:46 GMT
Server: Apache/2.4.6 (Red Hat Enterprise Linux)
Last-Modified: Fri, 19 Jul 2019 04:50:52 GMT
ETag: "8-58e017894f220"
Content-Length: 8
Content-Type: text/html; charset=UTF-8
X-Varnish: 32778
Age: 0
Via: 1.1 varnish-v4
X-Cache: MISS from westos cache
Connection: keep-alive
varnish实现轮询访问web服务器
我们在server3中安装httpd,在其发布页面写入:webpage of server3
同样使用curl检测是否成功。
[root@server3 ~]# curl 127.0.0.1
webpage of server3
- 回到server1进行varnish轮询的设置,编辑文件
vim /etc/varnish/default.vcl
- 首先,需要用到调度器directors模块的方法轮询调度,所以要先导入directors模块:
vcl 4.0; # 在这个下面导入
import directors from "/usr/lib64/varnish/vmods/libvmod_directors.so";
- 将修改默认的后端访问的default为web1和web2:
backend web1 {
.host = "172.25.40.2";
.port = "80";
}
backend web2 {
.host = "172.25.40.3";
.port = "80";
}
- 添加初始化函数,new一个轮询的对象,即实例化调度器directors的轮询方法。添加后端服务器分别为web1和web2。
sub vcl_init {
new lb = directors.round_robin()
lb.add_backend(web1);
lb.add_backend(web2);
}
- 在接受函数中,添加如下内容,其逻辑是,访问域名为
www.westos.org
时,其后端实质是进行轮询访问web1和web2。当访问域名为bbs.westos.org
时,其后端实质是访问web2。
sub vcl_recv {
# Happens before we check if we have this in cache already.
#
# Typically you clean up the request here, removing cookies you don't need,
# rewriting the request, etc.
if (req.http.host ~ "^(www.)?westos.org") {
set req.http.host = "www.westos.org";
set req.backend_hint = lb.backend();
return (pass); #为了测试方便,不进行缓存。
}
elsif (req.http.host ~ "^bbs.westos.org") {
set req.backend_hint = web2;
}
else {
return (synth(405));
}
}
重启varnish服务。
- 我们在物理主机上添加本地解析
vim /etc/hosts
,写入:
172.25.40.1 bbs.westos.org www.westos.org
测试:
[root@foundation40 varnish]# curl www.westos.org
server2
[root@foundation40 varnish]# curl www.westos.org
webpage of server3
[root@foundation40 varnish]# curl www.westos.org
server2
[root@foundation40 varnish]# curl www.westos.org
webpage of server3
发现访问域名 www.westos.org
已经开始轮询到后端的web1和web2,而因为域名bbs.westos.org
访问没有设置沦询,只是访问web2。
[root@foundation40 varnish]# curl bbs.westos.org
webpage of server3
[root@foundation40 varnish]# curl bbs.westos.org
webpage of server3
使用web管理界面清理缓存
我们需要安装一些软件支持,varnish官方也有类似界面,不过收费,我们这里用了一个免费的web管理界面。同样,是在server1上。
- 首先,我们需要安装一些软件支持web界面:
yum install httpd unzip php -y
- 当然,我们这里有免费web管理界面的压缩包
bansys
,使用unzip解压缩到本地的apache默认发布目录中。
unzip bansys.zip -d /var/www/html/
- 将所有解压后的bansys目录中的所有文件和目录复制到apache默认发布目录中:
cp -r * ..
- 需要修改
vim config.php
这个文件为:
- 设置cdn推送管理界面的访问权限列表:acl,所以需要修改varnish的配置文件,完成后重启varnish服务。
- 因为我们之前设置过varnish的端口为80,会与开启httpd服务端口冲突,所以我们把server1的httpd端口改为8080:
vim /etc/httpd/conf/httpd.conf
修改端口为:8080
重启httpd服务。
- 此时可以在真机的浏览器中,输入server1的ip和端口8080,进行缓存管理:
- 这里为了可以看到效果,我们需要把刚刚的配置文件进行修改,注释掉return pass,因为它表示默认不缓存。
- 同时,我们在server3上开两台虚拟主机进行不同web资源的提供。
vim /etc/httpd/conf.d/vhost.conf
写入:
<VirtualHost *:80>
DocumentRoot /www
ServerName www.westos.org
</VirtualHost>
<Directory "/www">
Require all granted
</Directory>
<VirtualHost *:80>
DocumentRoot /bbs
ServerName bbs.westos.org
</VirtualHost>
<Directory "/www">
Require all granted
</Directory>
创建对应的发布目录:mkdir /www /bbs
创建对应的发布文件:server3---wwwVhost1
和 server3---bbsVhost2
重启httpd服务。
- 测试:
我们在真实主机进行测试:
[root@foundation40 varnish]# curl www.westos.org
server2
[root@foundation40 varnish]# curl www.westos.org
server2
说明已经命中缓存,我们通过web管理界面清理缓存,输入.*
清除所有缓存:
再次输入,发现已经清理缓存,而且由于我们设置的轮询机制,所以此时访问的是server3的虚拟主机。
[root@foundation40 varnish]# curl -I www.westos.org
HTTP/1.1 200 OK
Date: Fri, 19 Jul 2019 07:42:43 GMT
Server: Apache/2.4.6 (Red Hat Enterprise Linux)
Last-Modified: Fri, 19 Jul 2019 07:01:46 GMT
ETag: "14-58e034cb38db8"
Content-Length: 20
Content-Type: text/html; charset=UTF-8
X-Varnish: 32804
Age: 0
Via: 1.1 varnish-v4
X-Cache: MISS from westos cache
Connection: keep-alive
[root@foundation40 varnish]# curl www.westos.org
server3---wwwVhost1
[root@foundation40 varnish]# curl www.westos.org
server3---wwwVhost1
同时,由于虚拟主机的域名设置,所以当物理机访问域名bbs.westos.com
时,通过本地解析到cdn反向代理服务器server1,由于server1中的varnish配置文件中指定了bbs.westos.com
域名的对应主机为server3,那么到server3时,由于虚拟主机配置文件中,写入,所有域名为bbs.westos.com
的指定访问时,访问的是发布目录为/bbs的下的文件。所以,当我们在物理机访问bbs.westos.com
,得到的是:
[root@foundation40 varnish]# curl bbs.westos.org
server3---bbsVhost2