apache所运行的硬件环境都是对性能影响最大的因素,即使不能对硬件进行升级,也最好给apache一个单独的主机以免受到其他应用的干扰。各个硬件指标中,对性能影响最大的是内存,对于静态内容(图片、javascript文件、css文件等),它决定了apache可以缓存多少内容,它缓存的内容越多,在硬盘上读取内容的机会就越少,大内存可以极大提高静态站点的速度;对动态高负载站点来说,每个请求保存的时间更多一些,apache的mpm模块会为每个请求派生出相应的进程或线程分别处理,而进程或线程的数量与内存的消耗近似成正比,因此增大内存对提高动态站点的负载和运行速度也极为有利
其次是硬盘的速度,静态站点尤为突出,apache不断的在读取文件并发送给相应的请求,硬盘的读写是极其频繁的;动态站点也要不断的加载web程序(php等),一个请求甚至要读取十几个文件才能处理完成,因此尽可能的提高硬盘速度和质量对提高apache的性能是有积极意义的。
最后是cpu和网络,cpu影响的是web程序执行速度,网络影响流量大小。
1、apache的工作模式:Apache HTTP服务器被设计为一个强大的、灵活的能够在多种平台以及不同环境下工作的服务器。这种模块化的设计就叫做\"多进程处理模块\"(Multi-Processing Module,MPM),也叫做工作模式。
Prefork模式(一个非线程型的):
其主要工作方式是:当Apache服务器启动后,mpm_prefork模块会预先创建多个子进程(默认为5个),每个子进程只有一个线程,当接收到客户端的请求后,mpm_prefork模块再将请求转交给子进程处理,并且每个子进程同时只能用于处理单个请求。如果当前的请求数将超过预先创建的子进程数时,mpm_prefork模块就会创建新的子进程来处理额外的请求。Apache总是试图保持一些备用的或者是空闲的子进程用于迎接即将到来的请求。这样客户端的请求就不需要在接收后等候子进程的产生。
由于在mpm_prefork模块中,每个请求对应一个子进程,因此其占用的系统资源相对其他两种模块而言较多。不过mpm_prefork模块的优点在于它的每个子进程都会独立处理对应的单个请求,这样,如果其中一个请求出现问题就不会影响到其他请求。Prefork在效率上要比Worker要高,但是内存使用大得多不擅长处理高并发的场景。
Apache在prefork工作模式下影响性能的重要参数说明
[root@www ~]# vim /usr/local/http-2.4.23/conf/extra/httpd-mpm.conf
# prefork MPM
<IfModule mpm_prefork_module>
StartServers 5 #apache启动时候默认开始的子进程数
MinSpareServers 5 #最小的闲置子进程数
MaxSpareServers 10 #最大的闲置子进程数
MaxRequestWorkers 250 #允许同时的最大接入请求数量
MaxConnectionsPerChild 500 #每个子进程可处理的请求数
</IfModule>
重点参数1:MaxRequestWorkers
设置了允许同时的最大接入请求数量。任何超过MaxRequestWorkers限制的请求将进入等候队列,在apache2.3.1以前的版本MaxRequestWorkers被称为MaxClients,旧的名字仍旧被支持。MaxRequestWorkers是这些指令中最为重要的一个,设定的是 Apache可以同时处理的请求,是对Apache性能影响最大的参数。如果请求总数已达到这个值(可通过ps -ef|grep http|wc -l来确认),那么后面的请求就要排队,直到某个已处理请求完毕。这就是系统资源还剩下很多而HTTP访问却很慢的主要原因。虽然理论上这个值越大,可以处理的请求就越多,建议将初始值设为(以Mb为单位的最大物理内存/2),然后根据负载情况进行动态调整。比如一台4G内存的机器,那么初始值就是4000/2=2000。
重点参数2:MaxConnectionsPerChild
设置的是每个子进程可处理的请求数。每个子进程在处理了\"MaxConnectionsPerChild\"个请求后将自动销毁。0意味着无限,即子进程永不销毁。虽然缺省设为0可以使每个子进程处理更多的请求,但如果设成非零值也有两点重要的好处:1、可防止意外的内存泄漏。2、在服务器负载下降的时侯会自动减少子进程数。因此,可根据服务器的负载来调整这个值。在Apache2.3.9之前称之为MaxRequestsPerChild。
注1:prefork 控制进程在最初建立\"StartServers\"个子进程后,为了满足MinSpareServers设置的需要创建一个进程,等待一秒钟,继续创建两 个,再等待一秒钟,继续创建四个……如此按指数级增加创建的进程数,最多达到每秒32个,直到满足MinSpareServers设置的值为止。这种模式 可以不必在请求到来时再产生新的进程,从而减小了系统开销以增加性能。MaxSpareServers设置了最大的空闲进程数,如果空闲进程数大于这个 值,Apache会自动kill掉一些多余进程。这个值不要设得过大,但如果设的值比MinSpareServers小,Apache会自动把其调整为 MinSpareServers+1。如果站点负载较大,可考虑同时加大MinSpareServers和MaxSpareServers。
注2:ServerLimit和MaxClients(MaxRequestWorkers)有什么区别呢?
是因为在apache1时代,控制最大进程数只有MaxClients这个参数,并且这个参数最大值为256,并且是写死了的,试图设置为超过256是无效的,这是由于apache1时代的服务器硬件限制的。但是apache2时代由于服务器硬件的升级,硬件已经不再是限制,所以使用ServerLimit这个参数来控制最大进程数,ServerLimit值>=MaxClient值才有效。ServerLimit要放在MaxClients之前,值要不小于MaxClients。
查看Apache加载的模块
[root@www ~]#apachectl -t -D DUMP_MODULES
[root@www ~]# apachectl -M
查看Apache的工作模式
[root@www ~]# apachectl -l
Compiled in modules:
core.c
mod_so.c
http_core.c
[root@www ~]# httpd -V
Server version: Apache/2.4.23 (Unix)
Server built: Apr 10 2017 15:06:54
Server's Module Magic Number: 20120211:61
Server loaded: APR 1.5.2, APR-UTIL 1.5.4
Compiled using: APR 1.5.2, APR-UTIL 1.5.4
Architecture: 64-bit
Server MPM: prefork
threaded: no
forked: yes (variable process count)
修改prefork参数
[root@www ~]# vi /usr/local/http-2.4.23/conf/extra/httpd-mpm.conf
启用prefork模式
[root@www ~]# vi /usr/local/http-2.4.23/conf/httpd.conf
#LoadModule mpm_event_module modules/mod_mpm_event.so#给此行开头加上\"#\"
LoadModule mpm_prefork_module modules/mod_mpm_prefork.so#去掉此行的注释\"#\"
Include conf/extra/httpd-mpm.conf#去掉此行的注释\"#\"
重启httpd服务
[root@www ~]# systemctl restart httpd
Worker模式(多线程多进程):
和prefork模式相比,worker使用了多进程和多线程的混合模式,worker模式也同样会先预派生一些子进程,然后每个子进程创建一些线程,同时包括一个监听线程,每个请求过来会被分配到一个线程来服务。线程比起进程会更轻量,因为线程是通过共享父进程的内存空间,因此,内存的占用会减少一些,在高并发的场景下会比prefork有更多可用的线程,表现会更优秀一些;另外,如果一个线程出现了问题也会导致同一进程下的线程出现问题,如果是多个线程出现问题,也只是影响Apache的一部分,而不是全部。由于用到多进程多线程,需要考虑到线程的安全了,在使用keep-alive长连接的时候,某个线程会一直被占用,即使中间没有请求,需要等待到超时才会被释放(该问题在prefork模式下也存在)
总的来说,prefork方式速度要稍高于worker,然而它需要的cpu和memory资源也稍多于woker。
Apache在worker工作模式下影响性能的重要参数说明
[root@www ~]# vim /usr/local/http-2.4.23/conf/extra/httpd-mpm.conf
# worker MPM
<IfModule mpm_worker_module>
StartServers 3 #apache启动时候默认开始的子进程数
MinSpareThreads 75 #最小空闲数量的工作线程
MaxSpareThreads 250 #最大空闲数量的工作线程
ThreadsPerChild 25 #每个子进程产生的线程数量
MaxRequestWorkers 400 #允许同时的最大接入请求数量
MaxConnectionsPerChild 0 #每个子进程可处理的请求数
</IfModule>
注1:Worker 由主控制进程生成\"StartServers\"个子进程,每个子进程中包含固定的ThreadsPerChild线程数,各个线程独立地处理请求。同样, 为了不在请求到来时再生成线程,MinSpareThreads和MaxSpareThreads设置了最少和最多的空闲线程数;
而MaxRequestWorkers 设置了同时连入的clients最大总数。如果现有子进程中的线程总数不能满足负载,控制进程将派生新的子进程MinSpareThreads和 MaxSpareThreads的最大缺省值分别是75和250。这两个参数对Apache的性能影响并不大,可以按照实际情况相应调节 。
注2:ThreadsPerChild是worker MPM中与性能相关最密切的指令。ThreadsPerChild的最大缺省值是64,如果负载较大,64也是不够的。这时要显式使用 ThreadLimit指令,它的最大缺省值是20000。
注3:Worker模式下所能同时处理的请求总数是由子进程总数乘以ThreadsPerChild 值决定的,应该大于等于MaxRequestWorkers。如果负载很大,现有的子进程数不能满足时,控制进程会派生新的子进程。默认最大的子进程总数是16,加大时 也需要显式声明ServerLimit(系统配置的最大进程数量,最大值是20000)。需要注意的是,如果显式声明了ServerLimit,那么它乘以 ThreadsPerChild的值必须大于等于MaxRequestWorkers,而且MaxRequestWorkers必须是ThreadsPerChild的整数倍,否则 Apache将会自动调节到一个相应值。
注4:进程与线程的区别
进程是具有一定独立功能的程序关于某个数据集合上的一次运行活动,进程是系统进行资源分配和调度的一个独立单位;进程和线程都是由操作系统所体会的程序运行的基本单元,系统利用该基本单元实现系统对应用的并发性
进程和线程的区别在于:
简而言之,一个程序至少有一个进程,一个进程至少有一个线程. 线程的划分尺度小于进程,使得多线程程序的并发性高;另外,进程在执行过程中拥有独立的内存单元,而多个线程共享内存,从而极大地提高了程序的运行效率。
线程是一个实体,是CPU调度和分派的基本单位,他是比进程更小的独立运行的基本单位,线程自己基本上不拥有系统资源,只拥有一点在运行中不可少的资源(寄存器,栈,程序计数器),但是它可与同一个进程的其他线程共享进程所拥有的全部资源
线程与进程的区别:
(1)地址空间:进程内的一个执行单元;进程至少有一个线程;它们共享进程的地址空间;而进程有自己独立的地址空间;
(2)资源拥有:进程是资源分配和拥有的单位,同一个进程内的线程共享进程的资源
(3)线程是处理器调度的基本单位,但进程不是.
(4)二者均可并发执行
Event模式:
这是Apache最新的工作模式,是worker模式的变种,它把服务进程从连接中分离出来,一worker模式不同的是在于它解决了keep-alive长连接的时候占用线程资源被浪费的问题,在event工作模式中,会有一些专门的线程用来管理这些keep-alive类型的线程,当有真实请求过来的时候,将请求传递给服务器的线程,执行完毕后,又允许它释放。这增强了在高并发场景下的请求处理。这样,一个线程就能处理几个请求了,实现了异步非阻塞。event MPM在遇到某些不兼容的模块时,会失效,将会回退到worker模式,一个工作线程处理一个请求。官方自带的模块,全部是支持event MPM的。
注意一点,event MPM需要Linux系统(Linux 2.6+)对Epoll的支持,才能启用。
还有,需要补充的是HTTPS的连接(SSL),它的运行模式仍然是类似worker的方式,线程会被一直占用,知道连接关闭。部分比较老的资料里,说event MPM不支持SSL,那个说法是几年前的说法,现在已经支持了。
2、apache配置参数[root@www ~]# vim /usr/local/http-2.4.23/conf/extra/httpd-mpm.conf
# event MPM
<IfModule mpm_worker_module>
StartServers 3 #服务器启动时建立的子进程数量
MinSpareThreads 75 #空闲子进程的最小数量
MaxSpareThreads 250 #空闲子进程的最小数量
ThreadsPerChild 25 #每个子进程产生的线程数量
MaxRequestWorkers 400 #限定服务器同一时间内客户端最大接入的请求数量,默认是150;任何超过了该限制的请求都要进入等待队列,一旦一个个连接被释放,队列中的请求才将得到服务。
MaxRequestsPerChild 0 #每个子进程在其生命周期内允许最大的请求数量,如果请求总数已经达到这个数值,子进程将会结束,如果设置为0,子进程将永远不会结束。将该值设置为非0值,可以防止运行PHP导致的内存泄露</IfModule>
1.httpd-default.conf
配置文件位于:
[root@www ~]# vim /usr/local/http-2.4.23/conf/extra/httpd-default.conf
Timeout 5
推荐5 这个是 apache接受请求或者发出相应的时间超过这个时间断开
KeepAlive On/Off KeepAlive
指的是保持连接活跃,换一句话说,如果将KeepAlive设置为On,那么来自同一客户端的请求就不需要再一次连接,避免每次请求都要新建一个连接而加重服务器的负担。一般情况下,图片较多的网站应该把KeepAlive设为On。
MaxKeepAliveRequests 100
一次连接可以进行的HTTP请求的最大请求次数。将其值设为0将支持在一次连接内进行无限次的传输请求。事实上没有客户程序在一次连接中请求太多的页面,通常达不到这个上限就完成连接了。
KeepAliveTimeout number
如果第二次请求和第一次请求之间超过KeepAliveTimeOut的时间的话,第一次连接就会中断,再新建第二个连接。它的设置一般考虑图片或者JS等文件两次请求间隔,一般设置为3-5秒。
HostnameLookups on|off|double
如果是使用on,那么只有进行一次反查,如果用double,那么进行反查之后还要进行一次正向解析,只有两次的结果互相符合才行,而off就是不进行域名验证。 如果为了安全,建议使用double;为了加快访问速度,建议使用off。域名查找开启这个会增加apache的负担, 减慢访问速度建议关闭
配置完后在httpd.conf文件中通过include选项引用并重启生效
[root@www ~]# vim /usr/local/http-2.4.23/conf/httpd.conf
Include conf/extra/httpd-default.conf#去掉此行的注释\"#\"
[root@www ~]# systemctl restart httpd
2.httpd-mpm.conf
配置文件位于
[root@www ~]# vim /usr/local/http-2.4.23/conf/extra/httpd-mpm.conf
StartServers 10MPM 这个比较关键是影响并发效率的主要因素
设置服务器启动时建立的子进程数量。因为子进程数量动态的取决于负载的轻重,所以一般没有必要调整这个参数。
MinSpareServers 10
设置空闲子进程的最小数量。所谓空闲子进程是指没有正在处理请求的子进程。如果当前空闲子进程数少于MinSpareServers ,那么Apache将以最大每秒一个的速度产生新的子进程。只有在非常繁忙机器上才需要调整这个参数。将此参数设的太大通常是一个坏主意。
MaxSpareThreads 75
设置空闲子进程的最大数量。如果当前有超过MaxSpareServers数量的空闲子进程,那么父进程将杀死多余的子进程。只有在非常繁忙机器上才需要调整这个参数。将此参数设的太大通常是一个坏主意。如果你将该指令的值设置为比MinSpareServers小,Apache将会自动将其修改成\"MinSpareServers+1″。
ServerLimit 2000
服务器允许配置的进程数上限。只有在你需要将MaxClients设置成高于默认值256的时候才需要使用。要将此指令的值保持和MaxClients一样。修改此指令的值必须完全停止服务后再启动才能生效,以restart方式重启动将不会生效。
MaxClients/MaxRequestWorkers 256
用于客户端请求的最大请求数量(最大子进程数),任何超过MaxClients限制的请求都将进入等候队列。默认值是256,如果要提高这个值必须同时提高ServerLimit的值。建议将初始值设为(以Mb为单位的最大物理内存/2),然后根据负载情况进行动态调整。比如一台4G内存的机器,那么初始值就是4000/2=2000。
MaxRequestsPerChild /MaxConnectionsPerChild 0
设置的是每个子进程可处理的请求数。每个子进程在处理了\"MaxRequestsPerChild\"个请求后将自动销毁。0意味着无限,即子进程永不销毁。内存较大的服电脑务器可以设置为0或较大的数字。内存较小的服务器不妨设置成30、50、100。所以一般情况下,如果你发现服务器的内存直线上升,建议修改该参数试试。
配置完后在httpd.conf文件中通过include选项引用并重启生效
3.开启apache的Gzip(deflate)功能[root@www ~]# vim /usr/local/http-2.4.23/conf/httpd.conf
Include conf/extra/httpd-mpm.conf#去掉此行的注释\"#\"
[root@www ~]# systemctl restart httpd
gzip可以极大的加速网站,有时压缩比率高到80%,最少都有40%以上,还是相当不错的。在Apache2之后的版本,模块名不叫gzip,而叫mod_deflate
未使用Gzip
开启使用Gzip
如果要开启deflate的话,一定要打开下面二个模块
[root@www ~]# vim /usr/local/http-2.4.23/conf/httpd.conf
LoadModule 电脑 deflate_module modules/mod_deflate.so
LoadModule headers_module modules/mod_headers.so
[root@www ~]# systemctl restart httpd
mod_deflate模块检查及安装设置压缩比率,取值范围在 1(最低) 到 9(最高)之间,不建议设置太高,虽然有很高的压缩率,但是占用更多的CPU资源
[root@www ~]# apachectl -M | grep deflate
deflate_module (shared)
mod_deflate安装方法:
1、 编译的时候跟上--enable-deflate即可实现安装
2、DSO方式安装
电脑进入apache源码包mod_deflate所在的目录下
[root@www ~]# cd /root/httpd-2.4.23/modules/filters/
以dso的方式编译安装到apache中
[root@www filters]# /usr/local/http-2.4.23/bin/apxs -c -i -a mod_deflate.c
[root@www filters]#/usr/local/http2.2/bin/apxs -c -i -a /root/httpd-2.2.17/modules/metada ta/mod_headers.c
检查mod_deflate是否安装,成功安装这里会显示出该文件
[root@www filters]# ll /usr/local/http-2.4.23/modules/mod_deflate.so -rwxr-xr-x. 1 root root 98144 Apr 10 15:08 /usr/local/http-2.4.23/modules/mod_deflate.so
apxs命令参数说明:
-i 此选项表示需要执行安装操作,以安装一个或多个动态共享对象到服务器的modules目录中。
-a 此选项自动增加一个LoadModule行到httpd.conf文件中,以启用此模块,或者,如果此行已经存在,则启用之。
-c 此选项表示需要执行编译操作。
如果重启的时候出现错误
引用
Cannot load /usr/local/apache/modules/mod_deflate.so into server: /usr/local/apache/modules/mod_deflate.so: undefined symbol: inflateEnd
这里需要注意的是LoadModule deflate_module需要放在LoadModule php5_module之后需要在 LoadModuledeflate_module modules/mod_deflate.so 的前面加载zlib.so
引用
LoadFile /usr/lib/libz.so(x64系统中该库文件位于/usr/lib64目录下,可以软链接到/usr/lib下
LoadModule deflate_module modules/mod_deflate.so
重新启动httpd:
[root@www ~]# /usr/local/http2.4.23/bin/apachectl graceful #优雅启动httpd服务
修改Apache配置文件开启gzip压缩传输:
http.conf修改、增加配置参数
LoadModule deflate_module modules/mod_deflate.so
LoadModule headers_module modules/mod_headers.so
打开httpd.conf后,先将上面两行配置前面的#号去掉,这样apache就会启用这两个模块,其中mod_deflate是压缩模块,就是对要传输到客户端的代码进行gzip压缩;mod_headers模块的作用是告诉浏览器页面使用了gzip压缩,如果不开启mod_headers那么浏览器就会对gzip压缩过的页面进行下载,而无法正常显示。
在httpd.conf中加入以下代码,可以加到任何空白地方,不了解apache的话,如果担心加错地方,就放到http.conf文件的最后一行
注:在添加代码前最好先查一查要添加的代码是否存在
<IfModule mod_deflate.c>
DeflateCompressionLevel 6
SetOutputFilter DEFLATE
#AddOutputFilterByType DEFLATE text/html text/plain text/xml
application/x-javascript application/x-httpd-php
#AddOutputFilterByType DEFLATE image/*
AddOutputFilterByType DEFLATE text/*
AddOutputFilterByType DEFLATE application/ms* application/vnd* application/postscript application/javascript application/x-javascript
AddOutputFilterByType DEFLATE application/x-httpd-php application/x-httpd-fastphp
SetEnvIfNoCase Request_URI .(?:gif|jpe?g|png)$ no-gzip dont-vary
SetEnvIfNoCase Request_URI .(?:exe|t?gz|zip|bz2|sit|rar)$ no-gzip dont-vary
SetEnvIfNoCase Request_URI .(?:pdf|mov|avi|mp3|mp4|rm)$ no-gzip dont-vary </Ifmodule>
DeflateFilterNote Input input_info
DeflateFilterNote Output output_info
DeflateFilterNote Ratio ratio_info
LogFormat '\"%r\" %{output_info}n/%{input_info}n (%{ratio_info}n%%)' deflate
CustomLog logs/deflate_log.log deflate
各参数解释:
DeflateCompressionLevel 6
压缩程度的等级,预设可以采用 6 这个数值,以维持耗用处理器效能与网页压缩质量的平衡。
SetOutputFilter DEFLATE
设置输出过滤器,对输出启用压缩,必须的,就像一个开关一样,告诉apache对传输到浏览器的内容进行压缩
AddOutputFilterByType DEFLATE text/*
设置对文件是文本的内容进行压缩,例如text/html text/css text/plain等.
AddOutputFilterByType DEFLATE application/ms* application/vnd* application/postscriptapplication/javascript application/x-javascript
对javascript文件进行压缩
AddOutputFilterByType DEFLATE application/x-httpd-php application/x-httpd-fastphp
对php类型的文件进行压缩
SetEnvIfNoCase Request_URI .(?:gif|jpe?g|png)$ no-gzip dont-vary
设置不对后缀gif,jpg,jpeg,png的图片文件进行压缩。注:?:表示不会捕获 ( )里内容了
SetEnvIfNoCase Request_URI .(?:exe|t?gz|zip|bz2|sit|rar)$ no-gzip dont-vary
同上,就是设置不对exe,tgz,gz等的文件进行压缩
SetEnvIfNoCase Request_URI .(?:pdf|mov|avi|mp3|mp4|rm)$ no-gzip dont-vary
同上就是设置不对pdf,avi,mp3等的文件进行压缩
###设置日志输出!
DeflateFilterNote Input input_info
声明输入流的byte数量
DeflateFilterNote Output output_info
声明输出流的byte数量
DeflateFilterNote Ratio ratio_info
声明压缩的百分比
LogFormat '\"%r\" %{output_info}n/%{input_info}n (%{ratio_info}n%%)' deflate
声明日志格式
CustomLog logs/deflate_log.log deflate
修改完成后保存退出并重启httpd服务
[root@www ~]# vim /usr/local/http-2.4.23/conf/httpd.conf
[root@www ~]# systemctl restart httpd
使用谷歌浏览器测试访问,如下图显示结果:(提示:在访问测试页之前按F12键)
查看日志:
[root@www htdocs]# cat ../logs/deflate_log.log
\"GET /test.html HTTP/1.1\" 6421/19949 (32%)
\"GET /test1.html HTTP/1.1\" 1360/4266 (31%)
注:图片是不需要启用GZip压缩的,从GZip检测结果来看,压缩后的图片体积竟然大过原体积!这就解释了为什么图片不用启用GZip压缩的原因了!
可以检测了几个门户网站的图片,还有Google、baidu的图片,统统都没有启用图片GZip压缩,只是启用了html、css、js等文件的GZip压缩,这就更加说明了GZip压缩不适用于图片上。另外,除了图片之外,flash的swf文件也是不用启用GZip压缩的。
4.配置mod_expires模块这个非常有用的优化,mod_expires可以减少20-30%左右的重复请求,让重复的用户对指定的页面请求结果都CACHE在本地,根本不向服务器发出请求。但要注意更新快的文件不要这么做。
这个模块控制服务器应答时的Expires头内容和Cache-Control头的max-age指令。有效期(expiration date)可以设置为相对于源文件的最后修改时刻或者客户端的访问时刻。
未启用expire的效果:
[root@www htdocs]# curl -I 192.168.31.83/12.png
HTTP/1.1 200 OK
Date: Tue, 25 Oct 2016 15:52:37 GMT
Server: Apache/2.4.23 (Unix)
Last-Modified: Sun, 23 Oct 2016 15:34:10 GMT
ETag: \"8c9f-53f8a01b18080\"
Accept-Ranges: bytes
Content-Length: 35999
Vary: Accept-Encoding
Content-Type: image/png
启用expire缓存:
mod_expires的安装配置:
启用expires_module
LoadModule expires_module modules/mod_expires.so
然后添加Expires配置规则
<IfModule mod_expires.c>
ExpiresActive On
ExpiresByType text/css \"now plus 1 month\"
ExpiresByType application/x-javascript \"now plus 5 day\"
ExpiresByType image/jpeg \"access plus 1 month\"
ExpiresByType image/gif \"access plus 1 month\"
ExpiresByType image/bmp \"access plus 1 month\"
ExpiresByType image/x-icon \"access plus 1 month\"
ExpiresByType image/png \"access plus 1 minutes\"
ExpiresByType application/x-shockwave-flash \"access plus 1 month\"
ExpiresDefault \"now plus 0 minutes\"
</IfModule>
验证:
[root@www htdocs]# curl -I 192.168.31.83/12.png
HTTP/1.1 200 OK
Date: Tue, 25 Oct 2016 16:00:57 GMT
Server: Apache/2.4.23 (Unix)
Last-Modified: Sun, 23 Oct 2016 15:34:10 GMT
ETag: \"8c9f-53f8a01b18080\"
Accept-Ranges: bytes Content-Length: 35999
Cache-Control: max-age=60
Expires: Tue, 25 Oct 2016 16:01:57 GMT
Vary: Accept-Encoding
Content-Type: image/png
ExpiresDefault 和ExpiresByType 指令同样能够用易懂的语法格式进行定义:
ExpiresDefault \"<base> [plus] {<num><type>}\"
ExpiresByType type/encoding \"<base> [plus] {<num><type>}\"
其中<base>是下列之一:
access
now (等价于'access ')
modification
plus 关键字是可选的。<num>必须是整数,<type>是下列之一:
years
months
weeks
days
hours
minutes
seconds
例如,下列3个指令都表示文档默认的有效期是一个月:
ExpiresDefault \"access plus 1 month\"
ExpiresDefault \"access plus 4 weeks\"
ExpiresDefault \"access plus 30 days\" 有效期可以通过增加\"<num><type>\"子句进一步调整:
ExpiresByType text/html \"access plus 1 month 15 days 2 hours\"
ExpiresByType image/gif \"modification plus 5 hours 3 minutes\" 注意,如果你使用基于最后修改日期的设置,\"Expires:\"头将不会 被添加到
那些并非来自于磁盘文件的内容。这是因为这些内容并不存在\"最后修改时间\"的属性。
# GIF有效期为1个月(秒数)
ExpiresByType image/gif A2592000
ExpiresByType image/jpeg A2592000
ExpiresByType image/png A2592000
ExpiresByType image/x-icon A2592000
ExpiresByType application/x-javascript A604800
ExpiresByType text/plain A604800 # HTML文档的有效期是最后修改时刻后的一星期 ExpiresByType text/html M604800
</IfModule>
\"M\"表示源文件的最后修改时刻,\"A\"表示客户端对源文件的访问时刻。后面的时间则以秒计算。
有关 Apache Expires Module 的介绍,可以参阅其官方文档:
http://httpd.apache.org/docs/2.4/mod/mod_expires.html
5.Apache禁止目录遍历将Options Indexes FollowSymLinks中的Indexes 去掉,就可以禁止 Apache 显示该目录结构。Indexes 的作用就是当该目录下没有 index.html文件时,就显示目录结构。
6.apache 隐藏版本信息[root@www ~]# vim /usr/local/http-2.4.23/conf/httpd.conf
Options Indexes FollowSymLinks ##去掉Indexes
测试默认 apache 的状态信息
[root@www htdocs]# curl -I 192.168.31.83
HTTP/1.1 200 OK
Date: Tue, 25 Oct 2016 16:09:09 GMT
Server: Apache/2.4.23 (Unix)
Last-Modified: Mon, 11 Jun 2007 18:53:14 GMT
ETag: \"2d-432a5e4a73a80\" Accept-Ranges: bytes
Content-Length: 45
Cache-Control: max-age=0
Expires: Tue, 25 Oct 2016 16:09:09 GMT
Content-Type: text/html
1、主配置中启用httpd-default.conf
[root@www ~]# vim /usr/local/http-2.4.23/conf/httpd.conf
Include conf/extra/httpd-default.conf
2、修改httpd-default.conf
vim /usr/local/http-2.4.23/conf/extra/httpd-default.conf
找到
ServerTokens Full
ServerSignature On
改成
ServerTokens Prod
ServerSignature off
重启 apache 测试
测试隐藏版本号后 apache 的状态信息
[root@www htdocs]# curl -I 192.168.31.83
HTTP/1.1 200 OK
Date: Tue, 25 Oct 2016 16:14:32 GMT
Server: Apache Last-Modified: Mon, 11 Jun 2007 18:53:14 GMT
ETag: \"2d-432a5e4a73a80\"
Accept-Ranges: bytes
Content-Length: 45
Cache-Control: max-age=0
Expires: Tue, 25 Oct 2016 16:14:32 GMT
Content-Type: text/html
如果你需要彻底将版本之类的信息进行改头换面,你就需要在编译之前做准备或者进行从新编译了。在重新编译时,修改源码包下include目录下的ap_release.h文件
#define AP_SERVER_BASEVENDOR \"Apache Software Foundation\"#服务的供应商名称
#define AP_SERVER_BASEPROJECT \"Apache HTTP Server\" #服务的项目名称
#define AP_SERVER_BASEPRODUCT \"Apache\" #服务的产品名
#define AP_SERVER_MAJORVERSION_NUMBER 2 #主要版本号
#define AP_SERVER_MINORVERSION_NUMBER 4 #小版本号
#define AP_SERVER_PATCHLEVEL_NUMBER 23 #补丁级别
#define AP_SERVER_DEVBUILD_BOOLEAN 0 #
上述列出的行,已经给出了注释,大家可以修改成自己想要的,然后编译安装之后,对方就彻底不知道你的版本号了。
7.Apache日志切割为什么要分割日志
随着网站的访问越来越大,WebServer产生的日志文件也会越来越大,如果不对日志进行分割,那么只能一次将大的日志(如Apache的日志)整个删除,这样也丢失了很多对网站比较宝贵的信息,因为这些日志可以用来进行访问分析、网络安全监察、网络运行状况监控等,因此管理好这些海量的日志对网站的意义是很大的。
方法1:使用rotatelogs(apache自带的工具)每隔一天记录一个日志
辑Apache的主配置文件,更改内容如下:
[root@www ~]# vim /usr/local/http-2.4.23/conf/httpd.conf
注释掉如下两
# ErrorLog logs/error_log
#CustomLog logs/access_log common
然后添加如下两行
ErrorLog \"|/usr/local/http-2.4.23/bin/rotatelogs -l logs/error_%Y%m%d.log 86400\"
CustomLog \"|/usr/local/http-2.4.23/bin/rotatelogs -l logs/access_%Y%m%d.log 86400\" combined
注:其中86400为轮转的时间单位为秒
验证:查看logs目录下的日志文件
[root@www ~]# ls /usr/local/http-2.4.23/logs/
access_20161026.log access_log deflate_log.log error_20161026.log error_log httpd.pid
由于apache自带的日志轮询工具rotatelogs,据说在进行日志切割时容易丢日志,因此我们通常使用cronolog进行日志轮询。
方法2:使用 cronolog 为每一天建立一个新的日志
安装cronolog程序
下载cronolog
[root@www ~]# tar zxf cronolog-1.6.2.tar.gz
[root@www ~]# cd cronolog-1.6.2/
[root@www cronolog-1.6.2]# ./configure && make && make install
主配置文件中的使用方法
ErrorLog \"|/usr/local/sbin/cronolog logs/error-%Y%m%d.log\"
CustomLog \"|/usr/local/sbin/cronolog logs/access-%Y%m%d.log\" combined
如果Apache中有多个虚拟主机,最好每个虚拟主机中放置一个这样的代码,并将日志文件名改成不同的名字。
扩展:
这个保证了每天一个文件夹文件夹下每个小时产生一个log
CustomLog \"|/usr/local/sbin/cronolog logs/%Y%m%d/access_log.%H\" combined
按天轮询(生产环境常见用法,推荐使用):
CustomLog \"|/usr/local/sbin/cronolog logs/access_www_%Y%m%d.log\" combined
按小时轮询(生产环境较常见用法):
CustomLog \"|/usr/local/sbin/cronolog logs/access_www_ %Y%m%d%H.log\" combined
验证:查看logs目录下的日志文件
[root@www ~]# ls /usr/local/http-2.4.23/logs/
access_20170415.log access_log error_20170415.log error_log httpd.pid
注意:这两个管道日志文件程序还有一点不同之处是使用 cronolog 时如果日志是放在某个不存在的路径则会自动创建目录,而使用 rotatelogs 时不能自动创建,这一点要特别注意
8.配置防盗链有时候,你的网站莫名其妙的访问量变大,不要高兴的太早,有可能是被别人盗链了。
举个例子:比如你搭了个discuz论坛,里面有些热点图片、视频;然后别人将他网站上访问图片的地址重定向到你的discuz上,这样他的服务器就可以空闲出来了;也就是说别人访问他网站的图片视频,消耗的确是你服务器的资源;
解决这个问题的方法是配置下防盗链,让外来的盗不了链;
方法1:
Apache 防盗链的第一种实现方法,可以用rewrite实现。
在web1上创建测试文件
[root@www ~]# mkdir /usr/local/http-2.4.23/htdocs/about
[root@www ~]# ls /usr/local/http-2.4.23/htdocs/ about index.html Koala.jpg
[root@www ~]# ls /usr/local/http-2.4.23/htdocs/about/ nolink.png
在web2测试机上创建指向web1的超链接
[root@web2 ~]# /var/www/html/index.html
<a href=\"http://www.wubolive.com/Kaola.jpg\"test</a>
首先要确认 Apache 的rewrite module可用:
[root@www ~]# vim /usr/local/http-2.4.23
/conf/httpd.conf
LoadModule rewrite_module modules/mod_rewrite.so
[root@www ~]# apachectl graceful
[root@www ~]# apachectl -M | grep rewrite rewrite_module (shared)
然后在找到自己网站对应的配置的地方(如在主配置文件中或虚拟主机中),加入下列代码:
ServerName www.wubolive.com
#防盗链配置
RewriteEngine On
RewriteCond %{HTTP_REFERER} !^$
RewriteCond %{HTTP_REFERER} !wubolive\.com/.*$ [NC]
RewriteCond %{HTTP_REFERER} !www\.wubolive\.com/.*$ [NC]
RewriteRule .*\.(gif|jpg|swf)$ http://www.wubolive.com/about/nolink.png [R,NC,L]
注:相关选项的解释
RewriteEngine On #启用rewrite,要想rewrite起作用,必须要写上
RewriteCond test-string condPattern #写在RewriteRule之前,可以有一或N条,用于测试rewrite的匹配条件,具体怎么写,后面会详细说到。
RewriteRule Pattern Substitution #规则
%{HTTP_REFERER}:服务器变量,HTTPReferer是header的一部分,当浏览器向web服务器发送请求的时候,一般会带上Referer,告诉服务器我是从哪个页面链接过来的,服务器藉此可以获得一些信息用于处理。比如从我主页上链接到一个朋友那里,他的服务器就能够从HTTP Referer中统计出每天有多少用户点击我主页上的链接访问他的网站。
[ NC]指的是不区分大小写,[R]强制重定向 redirect
字母L表示如果能匹配本条规则,那么本条规则是最后一条(Last),忽略之后的规则
防盗链配置的说明:
红色部分: 表示自己的信任站点。对我的站点来说,设置为 http://www.wubolibe.com 和 http://wubolibe.com
绿色部分: 要保护文件的扩展名(以|分开)。以这些为扩展名的文件,必须通过红色标注的网址引用,才可以访问。
蓝色部分: 定义被盗链时替代的图片,让所有盗链 jpg、gif、swf 等文件的网页,显示网页文档根目录下的about/nolink.png 文件。注意:替换显示的图片不要放在设置防盗链的目录中,并且该图片文件体积越小越好。当然你也可以不设置替换图片,而是使用下面的语句即可:RewriteRule .*\.(gif|jpg|png)$ - [F]
注:[F] (强制URL为被禁止的 forbidden),强制当前URL为被禁止的,即,立即反馈一个HTTP响应代码403(被禁止的)。
注:RewriteCond%{HTTP_REFERER}!^$ 这一行意在允许空\"HTTP_REFERER\"的访问,即允许用户在浏览器地址栏中直接输入图片地址时图片文件的显示。
RewriteCond %{HTTP_REFERER} !wubolibe\.com/.*$ [NC]
RewriteCond %{HTTP_REFERER} !www\.wubolibe\.com/.*$ [NC]
设置允许访问的HTTP来源,包括网站自身。
RewriteRule .*\.(gif|jpg|swf)$ http://www.wubolive.com/about/nolink.png [R,NC,L]
注意:测试时要清除济浏览器缓存将不满足referer条件的访问重定向至nolink.png。nolink.png位于允许\"盗链\"的目录about中,要相当注意,不然,警告信息和图片将无法在对方网站上显示。
方法2:通过判断浏览器头信息来阻止某些请求,即利用SetEnvIfNoCase和access。
这个方法可以通过阻止某些机器人或蜘蛛爬虫抓取你的网站来节省你的带宽流量。
语法: SetEnvIfNoCase attribute regex [!]env-variable[=value] [[!]env-variable[=value]] ...
SetEnvIfNoCase 当满足某个条件时,为变量赋值,即根据客户端请求属性设置环境变量。
注:Referer :指明了请求当前资源原始资源的URL,使用referer是可以防盗链
然后在找到自己网站对应的配置的地方(如在主配置文件中或虚拟主机中),加入下列代码:
SetEnvIfNoCase Referer \"^$\" local_ref
SetEnvIfNoCase Referer \"www.wubolibe.com/.*$\" local_ref
SetEnvIfNoCase Referer \"wubolibe.com/.*$\" local_ref
# 2.4版本以下的
方法一:
<filesmatch \"\.(mp3|mp4|zip|rar|jpg|gif)\">
Order Deny,Allow
Allow from env=local_ref
Deny from all </filesmatch> 方法二:
<filesmatch \"\.(mp3|mp4|zip|rar|jpg|gif)\">
Order Allow,Deny
Allow from env=local_ref
</filesmatch>
#2.4版本以上,方法如下:
<filesmatch \"\.(mp3|mp4|zip|rar|jpg|gif)\">
Require all denied
Require env local_ref
</filesmatch>
电脑