HTTP性能优化篇上
服务器:
- 合理利用系统资源,提高服务器的吞吐量和并发数,降低响应时间。
客户端: 一次 HTTP ‘请求-响应’的过程延迟的时间是非常惊人的,差不多占了99%。客户端 HTTP 性能优化的关键就是:降低延迟
小结
- 性能优化是一个复杂的概念,在 HTTP 里可以分解为服务器性能优化、客户端性能优化和传输链路优化
- 服务器有三个主要的性能指标:
吞吐量
、并发数
和响应时间
,此外还需要考虑资源利用率
; - 客户端的基本性能指标是延迟,影响因素有地理距离、带宽、DNS 查询、TCP 握手等;
- 从服务器到客户端的传输链路可以分为三个部分,我们能够优化的是前两个部分,也就是“第一公里”和“中间一公里”;
- 有很多工具可以测量这些指标,服务器端有 ab、top、sar 等,客户端可以使用测试网站,浏览器的开发者工具
你有 HTTP 性能优化的经验吗?常用的有哪些方法?
本人生产环境中会用到的:tcp fast open,DNS,HTTP缓存,DNS-prefetch你是怎么理解客户端的“延迟”的?应该怎样降低延迟?
就是客户端与服务器一次请求响应的往反时间,降低延迟的话用DNS缓存,TCP连接复用,使用CDN,应该可以降低延迟
HTTP 性能优化篇下
在整个HTTP系统里有三个可优化的环节
- 服务器
- 客户端:无法控制
- 传输链路
硬件优化: 更强的CPU、更快的网卡、更大的带宽、更多的服务器
软件优化
开源:开发网站服务器自身的潜力,在现有条件不变的情况下尽量挖掘出更多的服务能力。
- 选择高性能的Web服务器,选择Nginx,利用Nginx 强大的反向代理能力实现
动静分离
, 动态页面交给 Tomcat、Django、Rails,图片、样式表等静态资源交给 Nginx - HTTP/1.1 升级到 HTTP/2
- TSL/1.2 升级到 TSL/1.3
- 选择高性能的Web服务器,选择Nginx,利用Nginx 强大的反向代理能力实现
节流:减少客户端和服务器之间收发的数据流,在有限的带宽里传输更多的内容
HTTP 协议内置的“数据压缩”编码 gzip br
HTML/CSS/JavaScript 属于纯文本,就可以采用特殊的“压缩”,去掉源码里多余的空格、换行、注释等元素
图片在 HTTP 传输里占有非常高的比例,虽然它本身已经被压缩过了,不能被 gzip、br 处理,但仍然有优化的空间。比如说,去除图片里的拍摄时间、地点、机型等元数据,适当降低分辨率,缩小尺寸。图片的格式也很关键,尽量选择高压缩率的格式,有损格式应该用
JPEG
,无损格式应该用Webp
格式对于小文本或者小图片,还有一种叫做
资源合并
(Concatenation)的优化方式,就是把许多小资源合并成一个大资源,用一个请求全下载到客户端,然后客户端再用JavaScript、CSS
切分后使用,好处是节省了请求次数,但缺点是处理比较麻烦DNS 解析域名会耗费不少的时间,如果网站拥有多个域名,那么域名解析获取 IP 地址就是一个不小的成本,所以应当适当“收缩”域名,限制在两三个左右,减少解析完整域名所需的时间,让客户端尽快从系统缓存里获取解析结果。
重定向引发的客户端延迟也很高,它不仅增加了一次请求往返,还有可能导致新域名的 DNS 解析,是 HTTP 前端性能优化的“大忌”。除非必要,应当尽量不使用重定向,或者使用 Web 服务器的“内部重定向”。
缓存,CDN,“没有请求的请求,才是最快的请求。”
HTTP/2
HTTP性能优化还有一个选择,就是把协议由HTTP/1升级到 HTTP/2
HTTP/2很多优点,它消除了应用层的队头阻塞,拥有
头部压缩
、二进制帧
、多路复用
、流量控制
、服务器推
送等许多特性有些在HTTP/1 里的优化手段到了 HTTP/2里会有反效果
- 对于 HTTP/2 来说,一个域名使用一个 TCP 连接才能够获得最佳性能,如果开多个域名,就会浪费带宽和服务器资源,也会降低 HTTP/2 的效率,所以“域名收缩”在 HTTP/2 里是必须要做的。“
- 资源合并”在 HTTP/1 里减少了多次请求的成本,但在 HTTP/2 里因为有头部压缩和多路复用,传输小文件的成本很低,所以合并就失去了意义。
- 而且“资源合并”还有一个缺点,就是降低了缓存的可用性,只要一个小文件更新,整个缓存就完全失效,必须重新下载。所以在现在的大带宽和 CDN 应用场景下,应当尽量少用资源合并(JavaScript、CSS 图片合并,数据内嵌),让资源的粒度尽可能地小,才能更好地发挥缓存的作用
精灵图(Spriting)、资源内联(inlining)、域名分片(Sharding)这些手段为什么会对 HTTP/2 的性能 优化造成反效果呢?
HTTP2 有多路复用,因为HTTP/2中使用小颗粒化的资源,优化了缓存,而使用精灵图就相当于传输大文件,但是大文件会延迟客户端的处理执行,并且缓存失效的开销很昂贵,很少数量的数据更新就会使整个精灵图失效,需要重新下载(http1中使用精灵图是为了减少请求)
HTTP1
中使用内联资源也是为了减少请求,内联资源没有办法独立缓存,破坏了HTTP/2的多路复用和优先级策略域名分片在
HTTP1
中是为了突破浏览器每个域名下同时连接数,但是这在HTTP/2中使用多路复用解决了这个问题,如果使用域名分片反而会限制HTTP2的自由发挥