Nginx
轻量级、高性能HTTP服务器
高性能的reverse proxy反向代理服务器
代理http、mail
高性能、稳定性、丰富的特性,配置简单
单进程:阻塞
多进程:每个进程响应一个请求
进程量大,进程切换次数过多
每个进程的地址空间是独立的,很多空间是重复的数据,所以内存使用效率较低
线程:thread
Light Weight Process, LWP 轻量级进程
每个线程响应一个请求
线程切换:线程切换较之进程切换属于轻量级切换
同一个进程的线程可以共享进程的诸多资源,比如打开的文件、传输的信号等
对内存的需求较之进程略有下降
快速切换时会带来线程抖动
多进程多线程
多线程:
一个线程响应多个请求
AIO:异步IO,不会因为IO没有完成,阻塞线程
多路IO,IO复用
IO DEVICE-------KERNEL BUFFER---------PROCESS
用户请求--->进程响应--->进程请求内核缓存中的数据---->内核向IO设备发出数据请求--->io设备将数据填满内核的BUFFER--->内核BUFFER将数据复制进程内存--->响应用户请求
根据IO等待模式不同,IO等待分为5种模式:
blocking IO:阻塞IO
同步阻塞IO:通过read/write完成交互
进程等待IO设备向内核BUFFER填充数据,内核BUFFER将数据复制到进程地址空间,此过程进程处于阻塞状态
nonblocking IO:非阻塞IO
同步非阻塞IO:通过read/write完成交互
IO设备向内核BUFFER填充数据时,进程处于不停地询问状态,内核BUFFER向进程地址空间复制数据时,进程处于阻塞状态
IO multiplexing:IO复用,一个进程请求多个IO
异步阻塞IO
IO设备向内核BUFFER中填充数据,进程阻塞;数据填充完毕,再次向内核BUFFER发送请求,等待内核BUFFTER将数据复制到进程地址空间,进程阻塞
signal driven IO:信号驱动IO
IO设备将数据复制到内核BUFFER后,通过信号告知进程数据复制完成;进程再次向内核BUFFER发送请求,等待内核BUFFER将数据复制到进程地址空间,进程阻塞
水平触发:多次通知进程数据准备完成
边缘触发:只通知一次进程数据准备完成
epoll(linux) /dev/poll(sloaris) kquequ(freebsd)
asynchronous IO:异步IO
异步非阻塞IO
发起请求,IO设备向内核BUFFER填充数据,内核BUFFER将数据复制到进程地址空间,完成后,通过信号通知进程
mmap---内存映射机制
将IO设备中的数据映射到内核BUFFER中,不需要复制数据,只是在内核BUFFER中与IO设备中的数据建立映射关系
Nginx特性:
支持AIO,event-driven IO ,mmap
一个线程响应多个请求
httpd:
MPM
prefork:一个进程响应一个请求,1024
worker:一个线程响应一个请求,多进程,一个进程生成多个线程
event: 基于事件驱动实现
Nginx:
web服务器
反向代理
web
模块化
重新加载配置及在线升级时,不需要中断正在处理的请求(nginx热部署)
带缓存的日志写操作
重写(rewrite)模块
支持验证HTTP referer,实现反倒链机制
支持sendfile,将数据在内核中直接封装响应客户端,不需要将数据复制到进程地址空间
10000个非活跃的HTTP KEEPALIVE连接仅占用2.5M内存
varnish,squid
nginx:cache(disk)
httpd:cache(disk,memory)
Nginx启动时会启动一个主进程master及多个子进程worker;配置缓存时还会启动cache load和cache manager进程。所有进程以"共享内存"机制完成进程间通信;master进程以特权用户运行,其他进程以非特权用户运行
master主进程主要完成如下工作:
1、读取并验证配置文件
2、创建、绑定、及关闭套接字
3、启动、终止及维护worker进程的个数
4、无须中止服务而重新配置工作特性
5、控制非中断式程序升级,启用新的二进制程序并在需要时回滚至老版本
6、重新打开日志文件
7、编译嵌入式perl脚本
worker进程主要完成如下工作:
1、接收、传入并处理客户端的连接
2、提供反向代理及过滤功能
3、nginx任何能完成的其它任务
cache load进程主要完成的工作:
1、检查缓存存储中的缓存对象
2、使用缓存元数据建立内存数据库
cache manager进程的主要工作:
1、缓存的失效及过期检验
Nginx配置是分段的:
main,http,server,upstream(反向代理),location(类似于documentroot),mail
Nginx安装
# useradd nginx
# yum install -y pcre-devel openssl-devel
# tar zxf nginx-1.4.7.tar.gz
# cd nginx-1.4.7
# ./configure \
--prefix=/usr/local/nginx \
--sbin-path=/usr/sbin/nginx \
--conf-path=/etc/nginx/nginx.conf \
--error-log-path=/var/log/nginx/error.log \
--http-log-path=/var/log/nginx/access.log \
--pid-path=/var/run/nginx/nginx.pid \
--lock-path=/var/lock/nginx.lock \
--user=nginx \
--group=nginx \
--with-http_ssl_module \
--with-http_flv_module \
--with-http_stub_status_module \
--with-http_gzip_static_module \
--http-client-body-temp-path=/var/tmp/nginx/client \
--http-proxy-temp-path=/var/tmp/nginx/proxy \
--http-fastcgi-temp-path=/var/tmp/nginx/fcgi \
--http-uwsgi-temp-path=/var/tmp/nginx/uwsgi \
--http-scgi-temp-path=/var/tmp/nginx/scgi \
--with-pcre \
--with-file-aio \
--with-http_ssl_module \
--with-http_secure_link_module \
--with-http_perl_module \
# make && make install
nginx服务启动脚本:
#!/bin/bash
#
# chkconfig: 2345 86 14
# Descirption: Nginx Script File
prog="/usr/local/nginx/sbin/nginx"
pfile="/var/run/nginx/nginx.pid"
if [ $# -ne 1 ];then
echo "Usage:`basename $0` { start | stop | restart | reload | configtest }"
exit 9
fi
case $1 in
start)
$prog
if [ $? -eq 0 ];then
echo "Starting nginx service ..... [ok]"
# create lock file
touch /var/lock/subsys/nginx
fi
;;
stop)
kill `cat $pfile`
if [ $? -eq 0 ];then
echo "Stopping nginx.... [ok]"
fi
;;
restart)
kill `cat $pfile`
echo "Stopping nginx...."
$prog
if [ $? -eq 0 ];then
echo "Starting nginx service ..... [ok]"
# create lock file
touch /var/lock/subsys/nginx
fi
;;
reload)
kill -s HUP `cat $pfile`
;;
configtest)
$prog -t &> /dev/null
if [ $? -eq 0 ];then
echo "Syntax is ok!!!"
else
$prog -t
fi
;;
*)
echo "Usage:`basename $0` { start | stop | restart | reload | configtest }"
;;
esac
mime:多用途互联网邮件扩展
用于识别非文本文档
Nginx配置---/etc/nginx/nginx.conf
启动worker进程的数量;如果是CPU密集型,如SSL及压缩应用,worker数量与CPU个数一致;如果是IO密集型,如响应大量给客户端 ,worker进程个数为CPU个数的1.5或者2倍
worker_processes 1;
每个worker进程支持的连接数
events {
worker_connections 1024;
}
启用sendfile机制
sendfile on;
启用长连接并设置超时时间
keepalive_timeout 65;
是否对发送给客户端的内容进行压缩
#gzip on;
每个server定义一个虚拟主机 server { }
location / {
root html;
index index.html index.htm;
}
location /URI路径 {
root "/web/htdocs" 定义URI路径所对应的网页文件存放的路径
}
URI路径
http://www.bj.com/URI路径
如果错误代码为500,502,503,504,则返回URI路径下50x.html页面内容
error_page 500 502 503 504 /50x.html;
location [ = | ~ | ~* | ^~ ] URI路径 {...}
location URI路径 {}:
对当前路径及子路径下的所有资源都生效
location = URI路径 {}:
精确匹配指定路径,不包括子路径,因此只对当前资源生效
location ~ URI路径 {}:区分大小写
locaiton ~* URI路径 {}:不区分大小写
模式匹配URI路径,此处的URI可使用正则表达式
location ^~ URI路径 {}
不使用正则表达式
匹配优先级:
=匹配优先级最高
^~匹配优先级次之
~ ~*
示例1:客户端通过http://10.1.1.1访问/web/htdocs下的网页
location / {
root /web/htdocs;
index index.html index.htm;
}
示例2:客户端通过http://10.1.1.1/bbs,访问/web/bbs下的网页
location /bbs {
root /web;
index index.html index.htm;
}
基于客户端IP地址进行访问控制
location / {
....
allow 10.1.1.100;
deny 10.1.1.0/24;
}
默认规则是允许访问。如果想要明确禁止某个客户端访问可直接写deny 10.1.1.1;
如果想要明确只允许某个客户端访问,要这样写
allow 10.1.1.100
deny all
基于用户名/密码认证访问
location / {
auth_basic "please input user:";
auth_basic_user_file /etc/nginx/.user;
}
使用htpasswd命令创建用户名、密码
配置显示nginx连接数
location /status {
stub_status on;
access_log off;
allow 10.1.1.100;
deny all;
}
http://10.1.1.1/status访问结果 :
Active connections: 4 打开的所有连接数
server accepts handled requests
10 10 36 已经接受的连接数 已经处理的连接数 已经处理的请求数
Reading: 0 Writing: 1 Waiting: 3
Reading:nginx正在读取其报文首部的连接数
Writing:nginx正在读取其报文主体的连接数、或者正在处理请求的请求个数以及正在响应客户端的连接个数
Waiting:长连接中保持活动连接的连接个数(Reading+Writing)
配置基于SSL的HTTP
# HTTPS server
#
server {
listen 443;
server_name localhost;
ssl on;
ssl_certificate cert.pem;
ssl_certificate_key cert.key;
ssl_session_timeout 5m;
ssl_protocols SSLv2 SSLv3 TLSv1;
ssl_ciphers HIGH:!aNULL:!MD5;
ssl_prefer_server_ciphers on;
location / {
root html;
index index.html index.htm;
}
}
生成自签证书:
# cd /etc/pki/CA
生成证书服务器私钥
# (umask 077; openssl genrsa 2048 > private/cakey.pem)
Generating RSA private key, 2048 bit long modulus
.........................+++
..............+++
e is 65537 (0x10001)
生成自签证书
# openssl req -new -x509 -key private/cakey.pem -out cacert.pem
# touch index.txt
# echo 01>serial
生成WEB服务器的密钥
# mkdir /etc/nginx/ssl
# cd /etc/nginx/ssl
# (umask 077;openssl genrsa 1024 > nginx.key)
Generating RSA private key, 1024 bit long modulus
..............................++++++
.............++++++
e is 65537 (0x10001)
创建证书申请
# (umask 077;openssl genrsa 1024 > nginx.key)
# openssl req -new -key /etc/nginx/nginx.key -out /etc/nginx/nginx.csr
签署证书
# openssl ca -in nginx.csr -out nginx.crt -days 3650
配置基于域名的虚拟主机
server {
listen 80;
server_name www.a.com;
location / {
root /web/a;
index index.html;
access_log /var/log/nginx/bj/access_log main;
error_log /var/log/nginx/bj/error_log;
}
}
LEMP/LNMP:
PHP+MySQL
仅支持以FastCGI方式工作的PHP
安装MySQL-5.6通用二进制软件
# useradd mysql
# mkdir /mydata/data
# chown -R /mydata/data
# tar zxf mysql-5.6.28-linux-glibc2.5-i686.tar.gz -C /usr/local/
# cd /usr/local/
# ln -s mysql-5.6.28-linux-glibc2.5-i686/ mysql
# cd /usr/local/mysql
# chown -R root.mysql ./*
# cp support-files/mysql.server /etc/rc.d/init.d/mysqld
# chmod +x /etc/rc.d/init.d/mysqld
# chkconfig --add mysqld
# scripts/mysql_install_db --user=mysql --datadir=/mydata/data/
# vim my.cnf
datadir=/mydata/data
socket=/tmp/mysql.sock
innodb_file_per_table=1
# /etc/init.d/mysqld start
# netstat -tnlp | grep mysqld
tcp 0 0 :::3306 :::* LISTEN 9816/mysqld
# vim /etc/profile
export PATH=$PATH:/usr/local/mysql/bin
# source /etc/profile
导出mysql库文件
# vim /etc/ld.so.conf.d/mysql.conf
/usr/local/mysql/lib
# ldconfig -v
导出mysql头文件
# ln -s /usr/local/mysql/include/ /usr/include/mysql
安装php-5.3.6
# yum localinstall -y --nogpgcheck libmcrypt-2.5.7-1.2.el6.rf.i686.rpm libmcrypt-devel-2.5.7-1.2.el6.rf.i686.rpm mhash-0.9.9-1.el6.rf.i686.rpm mhash-devel-0.9.9-1.el6.rf.i686.rpm mcrypt-2.6.8-10.el6.i686.rpm
# tar zxf php-5.3.6.tar.gz
# cd php-5.3.6
# ./configure --prefix=/usr/local/php --with-mysql=/usr/local/mysql --with-openssl --with-mysqli=/usr/local/mysql/bin/mysql_config --enable-mbstring --with-freetype-dir --with-jpeg-dir --with-png-dir --with-zlib --with-libxml-dir=/usr --enable-xml --enable-sockets --enable-fpm --with-mcrypt --with-config-file-path=/etc --with-config-file-scan-dir=/etc/php.d --with-bz2
# make && make install
复制php配置文件
# cp php.ini-production /etc/php.ini
复制php-fpm配置文件
# cp /usr/local/php/etc/php-fpm.conf.default /usr/local/php/etc/php-fpm.conf
复制php-fpm启动脚本
# cp sapi/fpm/init.d.php-fpm /etc/rc.d/init.d/php-fpm
# chmod +x /etc/rc.d/init.d/php-fpm
# chkconfig --add php-fpm
# chkconfig --list php-fpm
php-fpm 0:关闭 1:关闭 2:启用 3:启用 4:启用 5:启用 6:关闭
编辑/usr/local/php/etc/php-fpm.conf配置文件
# vim /usr/local/php/etc/php-fpm.conf
pm.max_children = 150
pm.start_servers = 8
pm.min_spare_servers = 8
pm.max_spare_servers = 10
pid=pid=/usr/local/php/var/run/php-fpm.pid
user=nginx
group=nginx
# /etc/init.d/php-fpm start
Starting php-fpm done
# netstat -tnlp | grep php-fpm
tcp 0 0 127.0.0.1:9000 0.0.0.0:* LISTEN 15457/php-fpm
整合nginx和php
编辑nginx配置文件,去掉如下配置的注释:
# vim /etc/nginx/nginx.conf
location ~ \.php$ {
root /web/htdocs;
fastcgi_pass 127.0.0.1:9000;
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME /scripts$fastcgi_script_name;
include fastcgi_params;
}
编辑/etc/nginx/fastcgi_params文件,并将内容修改为如下内容,配置fastcgi参数:
fastcgi_param GATEWAY_INTERFACE CGI/1.1;
fastcgi_param SERVER_SOFTWARE nginx;
fastcgi_param QUERY_STRING $query_string;
fastcgi_param REQUEST_METHOD $request_method;
fastcgi_param CONTENT_TYPE $content_type;
fastcgi_param CONTENT_LENGTH $content_length;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param SCRIPT_NAME $fastcgi_script_name;
fastcgi_param REQUEST_URI $request_uri;
fastcgi_param DOCUMENT_URI $document_uri;
fastcgi_param DOCUMENT_ROOT $document_root;
fastcgi_param SERVER_PROTOCOL $server_protocol;
fastcgi_param REMOTE_ADDR $remote_addr;
fastcgi_param REMOTE_PORT $remote_port;
fastcgi_param SERVER_ADDR $server_addr;
fastcgi_param SERVER_PORT $server_port;
fastcgi_param SERVER_NAME $server_name;
编辑nginx配置文件,指定php首页
# vim /etc/nginx/nginx.conf
location / {
root /web/htdocs;
index index.php index.html index.htm;
}
# /etc/init.d/nginx restart
在/web/htdocs目录下创建php页面,测试访问
# vim /web/htdocs/index.php
<?php
phpinfo();
?>
xcache:在同一个PHP服务器,为多个进程缓存同一个opcode
安装xcache-2.0.0,加速php解析
# yum install -y m4 autoconf
# tar zxf xcache-2.0.0.tar.gz
# cd xcache-2.0.0
生成configure配置程序
# /usr/local/php/bin/phpize
Configuring for:
PHP Api Version: 20090626
Zend Module Api No: 20090626
Zend Extension Api No: 220090626
# ./configure --enable-xcache --with-php-config=/usr/local/php/bin/php-config
# make && make install
安装完毕后,有如下提示:
Installing shared extensions: /usr/local/php/lib/php/extensions/no-debug-non-zts-20090626/
编辑php.ini,整合php与xcache
将xcache提供的样例配置导入php.ini
# mkdir /etc/php.d
# cp xcache.ini /etc/php.d/
编辑/etc/php.d/xcache.ini,找到zend_extension开头的行,修改为如下内容:
zend_extension = /usr/local/php/lib/php/extensions/no-debug-non-zts-20090626/xcache.so
重新启动php-fpm
/etc/init.d/php-fpm restart
通过浏览器再次浏览php页面,在页面中可以找到关于xcache特性说明,表明成功
XCache
XCache Support enabled
Version 2.0.0
Modules Built cacher
Readonly Protection N/A
Cache Init Time 2015-12-24 14:04:43
Cache Instance Id 19574
Opcode Cache enabled, 62,914,560 bytes, 1 split(s), with 8192 slots each
Variable Cache enabled, 4,194,304 bytes, 1 split(s), with 8192 slots each
Shared Memory Schemes mmap
memcached:缓存服务器
缓存可序列化的数据(string,object)
以key:value方式缓存数据
不可实现持久存储
如缓存php session,及后台数据库的数据
redis:缓存服务器
以列表方式缓存数据,以数据表的方式
可以使用持久存储
NoSQL
如缓存计数器
location ~* \.php$ {
fastcgi_pass 127.0.0.1:9000;
}
Nginx反向代理
server {
listen 80;
server_name www.bj.com;
location / {
后端服务器;
}
}
后端服务器:
proxy_pass
示例:用户访问www.bj.com/forum时,将以后台服务器10.1.1.2的bbs目录中的页面返回客户端
location /forum {
proxy_pass http://10.1.1.2/bbs;
}
特殊情况:
如果在定义location时,加入了~ ~* ^~这样的模式匹配字符,proxy_pass在写时,只能写到服务器地址
location ~* /forum {
proxy_pass http://10.1.1.2;
}
当用户访问www.bj.com/forum时,将代理到http://10.1.1.2/forum
nginx反向代理示例配置:
10.1.1.1安装nginx作为前端服务器
10.1.1.2安装httpd作为后端服务器
客户端访问http://10.1.1.1/forum时,代理到后端服务器的http://10.1.1.2/bbs
location /forum {
proxy_pass http://10.1.1.2/bbs;
}
使用模式匹配的方式定义location,当客户端访问http://10.1.1.1/forum时,代理到后端服务器http://10.1.1.2/forum上
location ~* ^/forum {
proxy_pass http://10.1.1.2;
}
后端服务器上也要有对应的forum目录
此时,对于后端服务器来说,access_log中记录的日志,客户端IP是nginx的IP
10.1.1.1 - - [24/Dec/2015:16:35:36 +0800] "GET /forum/ HTTP/1.0" 200 35 "-" "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/42.0.2311.135 BIDUBrowser/8.1 Safari/537.36"
配置proxy_set_header,实现后端服务器记录真实的客户端IP
编辑/etc/nginx/nginx.conf
# vim /etc/nginx/nginx.conf
location ~* ^/forum {
proxy_pass http://10.1.1.2;
proxy_set_header X-Real-IP $remote_addr;
}
proxy_set_header X-Real-IP $remote_addr;
代理在httpd请求报文中加入X-Real-IP段的内容,该内容是变量$remote_addr的值,即真实客户端的IP
编辑后端服务器配置文件/etc/httpd/conf/httpd.conf,修改combined日志格式,将客户端地址%h换成%{X-Real-IP}i,表示记录HTTP请求报文中X-Real-IP的内容
LogFormat "%{X-Real-IP}i %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\"" combined
刷新浏览器,再次查看后端服务器access_log,日志中记录的是真实客户端的IP地址10.1.1.100
10.1.1.100 - - [24/Dec/2015:16:38:54 +0800] "GET /forum/ HTTP/1.0" 200 35 "-" "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/42.0.2311.135 BIDUBrowser/8.1 Safari/537.36"
Nginx负载均衡
Nginx负载均衡算法:
round-robin,默认算法
ip_hash:根据请求报文中的源IP地址,将相同客户端的请求转发到同一个服务器上
least_conn
nginx负载均衡配置:
定义upstream段,指定后端服务器IP;upstream段要写在server段外面
upstream webserver {
server 10.1.1.2 weight=1 max_fails=2 fail_timeout=2;
server 10.1.1.3 weight=1 max_fails=2 fail_timeout=2;
server 127.0.0.1:8080 backup;
}
server {
....
location / {
proxy_pass http://webserver/;
proxy_set_header X-Real-IP $remote_addr;
}
}
定义虚拟主机,提供错误页面
server {
listen 8080;
server_name localhost;
location / {
root /web/sorry;
index index.html;
}
}
在/web/sorry目录下提供index.html错误页面
经过以上配置后,当客户端访问http://10.1.1.1时,由后端两台服务器10.1.1.2和10.1.1.3负载均衡方式提供页面;当两台后端服务器均down后,跳转到本地8080端口所对应的页面
Nginx缓存
cache: 共享内存: 存储键和缓存对象元数据
磁盘空间:存储数据
定义缓存空间
proxy_cache_path: 不能定义在server{}中
proxy_cache_path /nginx/cache/first levels=1:2:3 keys_zone=first:20m max-size=1G
levels=
定义缓存目录子目录的级别,及每个子目录的名称字符个数; 最多只能有3级子目录
levels=1:2:3,3级子目录,第1级目录字符个数为1,第2级目录字符个数为2,第3级目录字符个数为3
keys_zone=name:size
定义存储键的区域
max-size=1G
指定/nginx/cache/first中的1G空间用于存储缓存数据
Nginx缓存配置:
定义缓存存放路径为/web/cache/first, 最多使用1G空间; 并定义键值区域名称为first,大小为20m
proxy_cache_path /web/cache/first levels=1:2 keys_zone=first:20m max-size 1g;
在location中开启缓存功能,指定使用键值名称为first的缓存
在httpd响应报文中添加额外项X-cache,用于查看缓存是否命中
add_header X-cache "$upstream_cache_status by $server_addr";
$upstream_cache_status: 用于记录缓存是否命中的状态
location / {
proxy_pass http://webserver/;
proxy_set_header X-Real-IP $remote_addr;
proxy_cache first;
proxy_cache_valid 200 1m;
}
proxy_cache_valid 200 1m;
表示为状态码为200的数据缓存1分钟
查看缓存是否命中,在浏览器中按F12打开开发者模式,查看HTTP响应报文,可以看到X-cache:HIT by 10.1.1.1信息,表示缓存命中
常用的3种缓存:
open_log_cache:日志缓存,将日志先保存到内存,再同步到磁盘,降低磁盘IO
open_file_cache:加快响应速度
fastcgi_cache
rewrite:URL地址重写
if (condition) {
...
...
}
建议放在locaiton{ }中使用
测试:
双目测试
~,!~
=,!=
~*,!~*
if($request_method ="POST"){
}
if ($request_uri ~* "/forum") {
}
单目测试
rewrite支持正则表达式
rewrite格式:
rewrite regex replacement [flag]
flag:
last:本次重写完成后,重启下一轮检查;大多数情况下使用
break:本次重写完成后,直接执行后续操作; 不再进行下一轮检查;在非根location下用break
客户端访问http://10.1.1.1/bbs时,重定向到http://10.1.1.2/forum上
location / {
root html;
index index.html index.htm;
rewrite ^/bbs/(.*)$ http://10.1.1.2/forum/$1;
}
客户端访问http://10.1.1.1/bbs时,重写向到本地网页根目录下的forum目录
location / {
root html;
index index.html index.htm;
rewrite ^/bbs/(.*)$ /forum/$1;
}
WebDAV(Web-based Distributed Authoring and Versioning)
一种基于HTTP 1.1协议的通信协议,它扩展了HTTP 1.1,在GET,POST,HEAD等几个HTTP标准方法以外添加了一些新的方法,使应用程序可直接对Web Server直接读写,并支持写文件锁定(Locking)及解锁(Unlock),还可以支持文件的版本控制。
rpm httpd默认支持DAV功能
通过此协议可以支持在Web Server上传文件
Nginx读写分离
前端:Nginx服务器 10.1.1.1
后端:Apache服务器 10.1.1.2 10.1.1.3(可在此服务器上传文件)
确保10.1.1.3服务器开启DAV功能
确保Apache配置文件加载了DAV相关模块
# vim /etc/httpd/conf/httpd.conf
LoadModule dav_module modules/mod_dav.so
LoadModule dav_fs_module modules/mod_dav_fs.so
在相应网页根目录授权段中开启DAV
<Directoy "/var/www/html">
....
dav on
</Directory>
确保运行httpd进程的apache用户对网页根目录拥有写入权限
# setfacl -m u:apache:rwx /var/www/html/
测试在客户端可以向10.1.1.3服务器上传文件
# curl -T /etc/issue http://10.1.1.3
前端Nginx服务器配置读写分离,读操作代理到10.1.1.2上,写操作代理到10.1.1.3上;
# vim /etc/nginx/nginx.conf
location / {
proxy_pass http://10.1.1.2;
if ($request_method = "PUT") {
proxy_pass http://10.1.1.3;
}
}
测试nginx读写分离操作是否成功
读取网页内容时,代理后10.1.1.2服务器上
# curl http://10.1.1.1
<h1>Apache Page of 10.1.1.2</h1>
上传文件时,代理到后端10.1.1.3服务器上
# curl -T /etc/fstab http://10.1.1.1
<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN">
<html><head>
<title>201 Created</title>
</head><body>
<h1>Created</h1>
<p>Resource /fstab has been created.</p>
<hr />
<address>Apache/2.2.15 (Red Hat) Server at 10.1.1.3 Port 80</address>
</body></html>
后端两台服务器通过rsync+inotify进行数据同步,保证上传的数据可以同步到后端所有服务器上