大致过程是:

客户端(浏览器)发起页面请求,主机对地址中的域名进行解析,找到对应的 IP 地址,请求发送到服务端,服务器根据请求内容发送响应给客户端,客户端收到响应,将内容渲染成网页。

域名解析

名词解释

(1) 域名:网络是基于TCP/IP协议进行通信和连接的,每一台主机都有唯一且固定的IP地址,从而区分因特网上数量庞大的主机。IP地址是数字型的,数字较多不方便记忆,于是人们又发明了域名,采用字符型结构,域名和IP地址存在一一对应的关系。域名一般由两个或两个以上的词构成,中间用“.”进行分隔,其结构是:四级域名.三级域名.二级域名.一级域名。

(2) DNS:即域名系统,互联网的一项服务。它作为将域名和IP地址相互映射的一个分布式数据库,能够使人更方便地访问互联网。DNS使用TCP和UDP端口53。

DNS 服务器的分层结构

DNS 服务器采用分布式、分层的方式部署在世界各地。按照层级从高到低,DNS 服务器分为:根域名服务器(Root DNS Servers)、顶级域名服务器(TLD DNS Servers)、权威域名服务器(Authoritative DNS Servers),层级关系如下图:

  • 根域名服务器:世界上有 13 个 根域名服务器,准确来说是 13 组服务器群组,服务器组中的每一个根域名服务器都有所有顶级域名服务器(com, org, gov …)的 IP 地址。
  • 顶级域名服务器:为顶级域名如 com、org、net 等提供域名解析服务,每一个顶级域名都有相应的 顶级域名服务器,存放其所有子域名的 IP 地址。
  • 权威域名服务器:各种组织机构,如企业、学校、政府组织等都需为其提供网络服务的主机取一个合适的域名,如 百度公司的 baidu.com,而主机的 IP 地址和域名的对应关系就保存至其权威域名服务器中。一般大公司和学校都会部署自己的权威域名服务器

(3) 域名解析:即域名到IP地址的转换过程。域名的解析工作由DNS服务器完成。DNS查询有两种方式:递归迭代。DNS客户端设置使用的DNS服务器一般都是递归服务器,它负责全权处理客户端的DNS查询请求,直到返回最终结果。而DNS服务器之间一般采用迭代查询方式。

递归查询:本机向本地域名服务器发出一次查询请求,就静待最终的结果。如果本地域名服务器无法解析,自己会以DNS客户机的身份向其它域名服务器查询,直到得到最终的IP地址告诉本机。

迭代查询:本地域名服务器向根域名服务器查询,根域名服务器告诉它下一步到哪里去查询,然后它再去查,每次它都是以客户机的身份去各个服务器查询。

流程介绍

(1) 浏览器输入域名之后,首先会检查浏览器缓存中是否缓存过该域名对应的IP地址

用户通过浏览器浏览过某网站之后,浏览器就会自动缓存该网站域名对应的地址,当用户再次访问的时候,浏览器就会从缓存中查找该域名对应的IP地址,因为缓存不仅是有大小限制,而且还有时间限制(域名被缓存的时间通过属性来设置),所以存在域名对应的找不到的情况。当浏览器从缓存中找到了该网站域名对应的地址,那么整个解析过程结束,如果没有找到,将进行下一步骤。对于的缓存时间问题,不宜设置太长的缓存时间,时间太长,如果域名对应的发生变化,那么用户将在一段时间内无法正常访问到网站,如果太短,那么又造成频繁解析域名。

(2) 如果在浏览器缓存中没有找到IP,那么将继续查找本机系统是否缓存过IP

如果第一个步骤没有完成对域名的解析过程,那么浏览器会去系统缓存中查找系统是否缓存过这个域名对应的地址。其实操作系统也有一个域名解析的过程,通过hosts文件设置,用户可以将任何域名解析到任何能够访问的IP地址。正是因为有这种本地DNS解析的规程,所以有黑客就可能通过修改用户的域名来把特定的域名解析到他指定的IP地址上,导致这些域名被劫持。

(3) 向本地域名解析服务系统发起域名解析的请求

以上两步的解析是在本机上完成的,如果本机无法解析域名,那么系统只能请求本地域名解析服务系统进行解析,本地域名系统一般都是本地区的域名服务器,比如你连接的校园网,那么域名解析系统就在你的校园机房里,如果你连接的是电信、移动或者联通的网络,那么本地域名解析服务器就在本地区,由各自的运营商来提供服务。对于本地域名解析服务器,一般都缓存了地区内部域名解析请求的结果,如果缓存命中则返回相应的结果,当然缓存时间也受域名失效时间控制。大约80%的域名解析到这里就结束了,所以本地域名解析系统主要承担了域名的解析工作。

(4) 向根域名解析服务器发起域名解析请求

如果本地域名解析系统的缓存中没有所需要查找到域名,则将会向根域名服务器发起解析请求。

(5) 根域名服务器返回给本地域名服务器一个所查询的主域名服务器(gTLD Server)地址

根域名是不负责解析域名的,它只负责管理所有的顶级域名。比如:你要解析的网址是:www.xxx.com,根域名服务器是不知道这个域名的IP地址的,但是它知道这个IP在它管理的.com域名下,根域名服务器会向请求方发送.com域名服务器的地址,引导请求方继续查询。

(6) 本地域名服务器LDNS再向上一步返回的gTLD服务器发送请求

因为域名服务器之间会有大量的数据需要处理,所以DNS服务器之间一般采用迭代查询方式。本地域名解析服务器向gTLD服务器发起请求。

(7) gTLD服务器接收请求并返回Name Server服务器

指定的域名由指定的Name Server服务器进行解析。

(8) Name Server服务器返回IP地址给本地服务器

服务器查找域名对应的地址,将地址连同值返回给本地域名服务器。

(9) 本地域名服务器缓存解析结果

本地域名服务器缓存解析后的结果,缓存时间由TTL值控制。

(10) 返回解析结果给用户

解析结果将直接返回给用户,用户系统将缓存该地址,用户根据TTL值缓存在本地系统缓存中,域名解析过程结束。

域名解析记录

  • A(Address)记录:用来指定主机名(或域名)对应的IP地址记录。
  • CNAME(别名)记录:即别名记录·,这种记录允许将多个域名映射到另外一个域名。
  • MX 记录: 邮件交换记录。它指向⼀个邮件服务器,⽤于电⼦邮件系统发邮件时根据收信⼈的地址后缀来定位邮件服务器。如:用户所用的邮件是以域名mydomain.com为结尾的,则需要在管理界面中添加该域名的MX记录来处理所有以@mydomain.com结尾的邮件。
  • NS(Name Server)记录:解析服务器记录。⽤来表明由哪台服务器对该域名进⾏解析。这⾥的NS
    记录只对⼦域名⽣效。例如用户希望由12.34.56.78这台服务器解析news.mydomain.com,则需要设置news.mydomain.com的NS记录。   
  • TXT记录:⼀般指为某个主机名或域名设置的说明

DNS安全问题

  • DNS域名劫持,攻击者通过对域名解析服务器的攻击或伪造,把目标网站的域名解析到错误(黑客准备)的页面,从而达到攻击者的某种目的。

    防范措施:进行IP地址和MAC地址的绑定;使用域名系统的安全协议;对DNS数据包进行监测;使用IP进行访问等。

  • DNS 缓存投毒,通过利用网民ISP端的DNS缓存服务器的漏洞进行攻击或控制,从而改变该ISP内的用户访问域名的响应结果;或者通过利用用户权威域名服务器上的漏洞,如当用户权威域名服务器同时可以被当作缓存服务器使用,黑客可以实现缓存投毒,将错误的域名纪录存入缓存中,从而使所有使用该缓存服务器的用户得到错误的DNS解析结果。

  • DNS拒绝服务攻击,利用DNS软件版本漏洞攻击;利用僵尸网络中大量的被控主机,伪装成被攻击主机,在特定时间点上,连续向多个允许递归查询的DNS服务器发送大量的DNS查询请求,迫使其提供应答服务,经DNS服务器放大后的大量应答数据发送到被攻击主机,形成攻击流量,导致其无法提供正常服务甚至瘫痪。

HTTP协议

HTTP (超文本传输协议) 是应用层协议,使用 TCP 协议进行数据传输,端口80,用于实现 Web 客户端 和 Web 服务器之间的通信。HTTP 协议规定了客户端和服务端之间通信的报文格式以及数据交换的流程。

HTTP是一种无状态协议,与WEB浏览器之间不会建立永久连接;当服务器返回响应后,就会关闭与服务器之间的连接,只有在重新发起请求的时候才会重新建立连接。

URL

URL(Uniform Resource Locator),即统一资源定位符,是专为标识Internet网上资源位置而设置的一种编址方式,我们平时所说的网页地址指的即是URL。互联网上的每个文件都有一个唯一的URL,它包含的信息指出文件的位置以及浏览器应该怎么处理它。

1
协议://用户名:密码@子域名.域名.顶级域名(服务器IP):端口号/目录/文件名.文件后缀?参数=值

可以使用curl命令发送HTTP请求:

1
2
3
4
#回显HTTP响应数据
curl http://www.baidu.com
#回显HTTP响应头部数据
curl http://www.baidu.com -I

HTTP协议的结构

① 请求报文的组成:

请求行 + 信息头 + 请求头 + 实体头 + 报文主体

请求行的格式如下:

Method [分隔符] Request - URL [分隔符] HTTP-Version CRLF

解释说明:

(1)Method 表示HTTP请求方法,通常有:

方法 描述
HEAD HEAD方法跟GET方法相同,只不过服务器响应时不会返回消息体
PUT 把消息本体中的消息发送到一个URL,跟POST类似
TRACE 是用来调用一个远程的请求信息应用程序层的循环后退
CONNECT HTTP/1.1协议中预留给能够将连接改为管道方式的代理服务器。
DELETE 请求服务器删除Request-URI所标识的资源
GET 由客户端请求服务端获取Request-URI所标识的资源的方法
POST 由客户端向服务端提交Request-URI所标识的资源后附加新的数据
OPTIONS 请求获得由Request-URI标识的资源在请求/响应的通信过程中可以使用的功能选项

(2)[分隔符]为空格

(3)Request - URL: 遵循URL格式,此字段为星号(*)时,说明请求并不用于某个特定的资源地址,而是用于服务本身。

(4)HTTP-Version:表示支持的HTTP版本,如HTTP/1.1

(5)CRLF:表示换行回车符

HTTP的头包括通用的信息头、请求头、响应头、实体头4部分,每个头域由一个域名、冒号和值域3部分组成。域名是大小写无关的;域值前可以添加任何数量的空格,每个HTTP请求可以包含多个HTTP头域。

HTTP报文主体则包含了HTTP请求的内容,对于get方法,报文主体为空,对于post方法,报文主体则包含需要发送给服务器的数据。

② 响应报文的组成:

状态行 + 信息头 + 响应头 + 实体头 + 报文主体

解释说明:

状态行由状态码和原因分析两部分组成,其中,状态码由3位数字组成,表示请求是否被理解或被满足,用来支持自动操作;原因分析是对原文的状态码作简单的描述,用于供用户使用。

③HTTP状态码

分类 分类描述
1** 信息,服务器收到请求,需要请求者继续执行操作
2** 成功,操作被成功接收并处理
3** 重定向,需要进一步的操作以完成请求
4** 客户端错误,请求包含语法错误或无法完成请求
5** 服务器错误,服务器在处理请求的过程中发生了错误

实例说明

无论是请求报文还是响应报文,虽然分别由以上五个部分组成,但是在一定情况下有些并不是必须要的,但是对于:General-header(通用头部)、请求头(客户端->服务器[Request Header])、响应头(服务端->客户端[Response Header]) 这三部分是必须要有的。于是拿一个实例来对这三部分的内容进行说明记录:

(1)General-header(通用头部)

1
2
3
4
5
Request URL: http://115.148.141.110:8980/v1/purchase/list     # 请求的URL地址(包含请求类型、请求域名、请求端口、请求地址)
Request Method: POST                    # 请求方式
Status Code: 200 OK # 响应的状态码、结果
Remote Address: 127.0.0.1:8899 # 请求的远程地址
Referrer Policy: no-referrer-when-downgrade # referrer策略(五种方法)

(2)请求头(客户端->服务器[Request Header])

1
2
3
4
5
6
7
8
9
10
11
12
POST /v1/purchase/list HTTP/1.1       # 请求方式、请求地址、请求所使用的协议和版本
Host: 115.157.151.673:8180 # 目标主机地址和端口号
Connection: keep-alive # 维护客户端和服务端的连接关系
Content-Length: 68 # 描述HTTP消息实体的传输长度
Accept: application/json, text/javascript, */*; q=0.01 #发送端(客户端)希望接受的数据类型、q 是权重系数,范围 0 =< q <= 1,q 值越大,请求越倾向于获得其“;”之前的类型表示的内容
Origin: http://apptest.zhidianlife.com:8007          # 浏览器在referrer字段中只显示源网站的源地址(即协议、域名、端口),而不包括完整的路径
Authorization: c81e7286507f4aa4b6179f4c381b4c64       # 请求所需的认证信息
User-Agent: Mozilla/5.0 (Windows NT 6.3; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/75.0.3770.100 Safari/537.36 # 携带当前的用户代理信息,一般包含浏览器、浏览器内核和操作系统的版本型号信息。
Content-Type: application/json            # 请求实体,文档类型
Referer: http://apptest.zhidianlife.com:8007/procurement/order?_t=756512&_winid=w9290 # 常用于同源限制策略,表示请求发起来源的URI,也就是当前页面资源的父页面。通过追踪Referer可得出资源页面之间复杂的跳转链。
Accept-Encoding: gzip, deflate # 客户端接收编码类型,一些网络压缩格式: gzip, deflate
Accept-Language: zh-CN,zh;q=0.9 # 客户端接收的语言类型 、中文

(3)响应头(服务端->客户端[Response Header])

1
2
3
4
5
6
7
8
HTTP/1.1 200 OK             		# 请求协议以及本版、请求状态码
Date: Tue, 02 Jul 2019 14:07:31 GMT # 服务端响应客户端的内容过期时间
Content-Type: application/json; charset=utf-8 # 服务端发送的类型及采用的编码方式
Server: Kestrel        # WEB 服务器 服务端的Web服务端名
Vary: Origin # WEB服务器用该头部的内容告诉 Cache 服务器,在什么条件下才能用本响应所返回的对象响应后续的请求
Access-Control-Allow-Credentials: true  # 允许运行客户端携带证书式访问
Access-Control-Allow-Origin: http://apptest.zhidianlife.com:8007
Content-Length: 33310         # 允许指定的域名、地址访问

HTTP安全问题

  • Http的通信是明文的,存在被窃听的风险
  • 无法确认通信双方身份,有可能会被人伪造
  • 无法验证报文的完整性,无法验证是否被篡改过

web中间件

中间件(Middleware)是提供系统软件和应用软件之间连接的软件,以便于软件各部件之间的沟通。中间件处在操作系统和更高一级应用程序之间。它充当的功能是:将应用程序运行环境与操作系统隔离,从而实现应用程序开发者不必为更多系统问题忧虑,而直接关注该应用程序在解决问题上的能力 。容器就是中间件的一种。

也就是说,关于中间件,我们可以理解为:是一类能够为一种或多种应用程序合作互通、资源共享,同时还能够为该应用程序提供相关的服务的软件。(注意:中间件是一类软件的总称,不是单独的一个软件)

我们经常管web中间件叫做web服务器或者web容器

web服务器、Web中间件和Web容器的区别

正常情况下一次web的访问顺序是:web浏览器—服务器(硬件)—web容器—web应用服务器—数据库服务器。

Tomcat

Tomcat 是Apache 软件基金会(Apache Software Foundation)的Jakarta 项目中的一个核心项目,由Apache、Sun 和其他一些公司及个人共同开发而成。因为Tomcat 技术先进、性能稳定,而且免费,因而深受Java 爱好者的喜爱并得到了部分软件开发商的认可,成为目前比较流行的Java Web 应用服务器(Servlet 容器)。实际上Tomcat 部分是Apache 服务器的扩展,但它是独立运行的,所以当你运行tomcat 时,它实际上作为一个与Apache 独立的进程单独运行的。Tomcat 服务器是一个免费的开放源代码的Web 应用服务器,属于轻量级应用服务器,在中小型系统和并发访问用户不是很多的场合下被普遍使用,是开发和调试JSP 程序的首选。Tomcat默认使用 8080 号端口

Weblogic

WebLogic 是美国Oracle公司出品的一个application server,确切的说是一个基于JAVAEE架构的中间件,WebLogic是用于开发、集成、部署和管理大型分布式Web应用、网络应用和数据库应用的Java应用服务器。将Java的动态功能和Java Enterprise标准的安全性引入大型网络应用的开发、集成、部署和管理之中。Weblogic默认端口是 7001。

Jboss

Jboss 是一个基于Java EE的开放源代码的应用服务器。 它不但是Servlet容器,而且也是EJB容器,从而受到企业级开发人员的欢迎。JBoss是一个管理EJB的容器和服务器。但JBoss核心服务不包括支持 servlet/JSP 的WEB容器,一般与 Tomcat 或 Jetty 绑定使用。Jboss默认端口号是8080。

Jetty

Jetty 是一个开源的servlet容器,它为基于Java的web容器,例如JSP和servlet提供运行环境。Jetty是使用JAVA编写的,它的API以一组JAR包的形式发布。开发人员可以将Jetty容器实例化成一个对象,可以迅速为一些独立运行(stand-alone)的Java应用提供网络和web连接。

Webshere

WebShere 是 IBM 的软件平台。它包含了编写、运行和监视全天候的工业强度的随需应变 Web 应用程序和跨平台、跨产品解决方案所需要的整个中间件基础设施,如服务器、服务和工具。WebSphere 提供了可靠、灵活和健壮的软件。WebSphere 是一个模块化的平台,基于业界支持的开放标准。可以通过受信任和持久的接口,将现有资产插入 WebSphere,可以继续扩展环境。WebSphere 可以在许多平台上运行。Webshere默认端口号是 9080。

Glasshfish

GlassFish 是一款强健的商业兼容应用服务器,达到产品级质量,可免费用于开发、部署和重新分发。开发者可以免费获得源代码,还可以对代码进行更改。

WAF和CDN

  • WAF

WAF(Web Application Firewall)称为web应用防火墙,是通过执行一系列针对HTTP,HTTPS的安全策略,来专门对web应用提供保护的一款产品,对来自Web应用程序客户端的各类请求进行内容检测和验证,确保其安全性与合法性,对非法的请求予以实时阻断,为Web应用提供防护。通俗的说,WAF类似于地铁站的安检,对于HTTP请求进行快速安全检查,通过解析HTTP数据,在不同的字段分别在特征、规则等维度进行判断,判断的结果作为是否拦截的依据从而决定是否放行。

WAF 可以用来屏蔽常见的网站漏洞攻击,如SQL注入,XML注入、XSS等。一般针对的是应用层而非网络层的入侵,从技术角度应该称之为Web IPS。其防护重点是SQL注入。

  • CDN

CDN的全称是Content Delivery Network,即内容分发网络。CDN是构建在现有网络基础之上的智能虚拟网络,依靠部署在各地的边缘服务器,通过中心平台的负载均衡、内容分发、调度等功能模块,使用户就近获取所需内容,降低网络拥塞,提高用户访问响应速度和命中率。

CDN将用户经常访问的静态数据资源直接缓存到节点服务器上,当用户再次请求时,会直接分发到在离用户近的节点服务器上响应给用户,当用户有实际数据交互时才会从远程Web服务器上响应,这样可以大大提高网站的响应速度及用户体验。