OSI与TCP/IP网络模型
物理层与数据链路层也被称为 网络访问层
基础知识
IP地址
设备在某一个网络中的地址,目前最常见的格式: [0-255].[0-255].[0-255].[0-255] 即为四个 0-255 的数字组成。
作用就是标识一个网络设备(计算机、手机、电视)在某一个具体的网络当中的地址。
单个网络情况下
在单个局域网下,结构非常简单,就是我们所连接的网络设备(网关)给我们分配了一个地址,在这个范围之内我们都可以通过这个地址找到我们的这个设备。
如果设备没有连接任何网络情况下,我们会有一个本地回环地址 127.0.0.1
多个网络情况下
可以理解为:
小明这个同学同时报名了两个课程,在 A 班级小明是班长,所有 A 班级的同学都管他叫班长(叫班长就能找到他)。而在 B 班级小明是课代表,所有 B 班的同学都管他叫课代表(叫课代表就能找到他)。
同样的一个人在不同的环境有不同的身份,这些身份只有特定的环境才生效。
域名
由于 IP 地址都是没有规律的一些数字组成的,很难被人记住,不利于广泛传播,所以就有人想出来要给 IP 起名字(别名)。
DNS寻址
通过宽带运营商提供的服务器解析一个域名背后对应的 IP,这个过程叫做 DNS 寻址,帮你完成 DNS 寻址过程的服务器叫做 DNS 服务器。
host文件
操作系统在发起对 DNS 服务器的查询请求之前,会优先检查本机的 hosts 文件。如果这个文件中包含了对当前需要解析的域名的配置,则不再发起对 DNS 服务器的请求,直接使用 hosts 文件中的配置。
本机的 hosts 文件配置只能到影响本机的 DNS 寻址
端口
计算机本身是一个封闭的环境,就像是一个大楼,如果需要有数据通信往来,必须有门,这个门在术语中就叫端口,每一个端口都有一个编号,每台计算机只有 65536 个端口(0-65535)。
一般我们把“占门”的过程叫做监听
http 默认的端口 80,https 默认的端口是 443
URL
URL(Uniform Resource Locator),统一资源定位符,通俗点来说就是表示网络当中某一个网页的完整访问地址
请求响应流程
三次握手
为了数据传输的可靠性
四次挥手
防止数据丢失
HTTP
http发展史
1. http0.9
- 只有一个命令GET,没有header等描述数据的信息, 服务器发送完毕,就关闭tcp协议。
2. htto1.0:
-
增加了请求命令(GET, POST 和 HEAD)
-
status code
-
header
-
多字符集支持
-
权限
-
缓存
-
内容编码
-
多部分发送 缺点:
-
HTTP/1.0 版的主要缺点是,每个TCP连接只能发送一个请求。发送数据完步,连接就关闭,如果还要请求其他资源,就必须再新建一个连接。
-
TCP连接的新建成本很高,因为需要客户端和服务器三次握手,并且开始时发送速率较慢。所以HTTP 1.0版本的性能比较差。随着网页加载的外部资源越来越多,这个问题就想发突出了。
-
为了解决这个问题,有些浏览器在请求时,用了一个非标准的Connection宇段。connection:lkeep-alive这个宇段要求服务器不要关闭TCP连接,以便其他请求复用。服务器同样回应这个字段。一个可以复用的TCP连接就建立了,直到客户端或服务器主动关闭连接。但是,这不是标准字段,不同实现的行为可能不一致,因此不是根本的解决办法。
3. http1.1
-
增加了请求命令 (OPTIONS. PUT、PATCH、DELETE、TRACE、 CONNECT)
-
持久连接
-
增加host 缺点:
-
虽然1.1版允许复用TCP连接,但是同-个TCP连接里面,所有的数据通信是按次序进行的。服务器只有处理完一个回应,才会进行下一个回应。要是前面的回应特别慢,后面就会有许多请求排队等者。这称为队头堵塞 为了避免这个问题,只有两种方法:
- 减少请求数
- 同时多开持久连接 这导致了很多的网页优化技巧,比如合并脚本和样式表、将图片嵌入CSS代码、域名分片 (domainsharding) 等等。如果HTTP协议设计得更好一些,这些额外的工作是可以避免的
spdy协议:谷歌自行研发,主要解决gttp1.1效率不高的问题,被当做http2的基础,主要特性都被http2继承
4. https
- 客户端请求服务器获取证书公钥
- 客户端(S4 / LS)解析证书(无效会弹出警告)
- 生成随机值
- 用公钥加密 随机值生成密钥
- 客户端将秘钥 发送给服务器
- 服务端用私钥解密秘钥得到随机值
- 将信息和随机值混合在—起进行对称加密
- 将加密的内容发送给客户端
- 客户端用秘钥解密信息
5. http2(待学习)
- 二进制传输
- 信道复用
- 分帧传输
- server push
http协议
定义
HTTP(HyperText Transfer Protocol,超文本传输协议)最早就是计算机与计算机之间沟通的一种标准协议(现在也称为端到端的协议),这种协议限制了通讯内容的格式以及各项内容的含义。
Version:0.9 StartHTML:0000000105 EndHTML:0000001564 StartFragment:0000000141 EndFragment:0000001524
约定内容
- 请求 / 响应报文格式
- 请求方法 —— GET / POST
- 响应状态 —— 200 / 404 / 302 / 304
- 预设的请求 / 响应头
约定形式
- 客户端通过随机端口与服务端某个固定端口(一般为80)建立连接 三次握手
- 客户端通过这个连接发送请求到服务端(这里的请求是名词)
- 服务端监听端口得到的客户端发送过来的请求
- 服务端通过连接响应给客户端状态和内容
请求报文
图示
请求头:
| 键 | 值 |
|---|---|
| Host | 请求的主机 |
| Cache-Control | 控制缓存(例如:max-age=60 缓存 60 秒 ) |
| Accept | 客户端想要接收的文档类型,逗号分隔 |
| User-Agent | 标识什么客户端帮你发送的这次请求 |
| Referer | 这次请求的来源 |
| Accept-Encoding | 可以接受的压缩编码 |
| Cookie | 客户端本地的小票信息 |
响应报文
图示
状态行
HTTP/1.1 200 OK
HTTP 协议版本 + 空格 + 状态码 + 空格 + 状态描述
响应头
| 键 | 值 |
|---|---|
| Date | 响应时间 |
| Server | 服务器信息 |
| Content-Type | 响应体的内容类型 |
| Content-Length | 响应的内容大小 |
| Set-Cookie | 让客户端设置一个小票 |
响应体
这次请求服务端想要返回给客户端的数据正文,一般返回的都是 HTML,也可以返回 JavaScript 或者 CSS(需要修改响应头中的响应类型)。
http缓存
请求方式
下面的表格比较了两种 HTTP 方法:GET 和 POST。
| GET | POST | |
|---|---|---|
| 后退按钮/刷新 | 无害 | 数据会被重新提交(浏览器应该告知用户数据会被重新提交)。 |
| 书签 | 可收藏为书签 | 不可收藏为书签 |
| 缓存 | 能被缓存 | 不能缓存 |
| 编码类型 | application/x-www-form-urlencoded | application/x-www-form-urlencoded 或 multipart/form-data。为二进制数据使用多重编码。 |
| 历史 | 参数保留在浏览器历史中。 | 参数不会保存在浏览器历史中。 |
| 对数据长度的限制 | 是的。当发送数据时,GET 方法向 URL 添加数据;URL 的长度是受限制的(URL 的最大长度是 2048 个字符)。 | 无限制。 |
| 对数据类型的限制 | 只允许 ASCII 字符。 | 没有限制。也允许二进制数据。 |
| 安全性 | 与 POST 相比,GET 的安全性较差,因为所发送的数据是 URL 的一部分。在发送密码或其他敏感信息时绝不要使用 GET ! | POST 比 GET 更安全,因为参数不会被保存在浏览器历史或 web 服务器日志中。 |
| 可见性 | 数据在 URL 中对所有人都是可见的。 | 数据不会显示在 URL 中。 |
状态码
状态代码由三位数字组成,第一个数字定义了响应的类别,且有五种可能取值。
- 1xx:指示信息 —— 表示请求已接收,继续处理。
- 2xx:成功 —— 表示请求已被成功接收、理解、接受。
- 3xx:重定向 —— 要完成请求必须进行更进一步的操作。
- 4xx:客户端错误 —— 请求有语法错误或请求无法实现。
- 5xx:服务器端错误 —— 服务器未能实现合法的请求。
常见状态代码、状态描述的说明如下。
- 200 OK:客户端请求成功。
- 301 永久重定向,302临时重定向
- 400 Bad Request:客户端请求有语法错误,不能被服务器所理解。
- 401 Unauthorized:请求未经授权,这个状态代码必须和 WWW-Authenticate 报头域一起使用。
- 403 Forbidden:服务器收到请求,但是拒绝提供服务。
- 404 Not Found:请求资源不存在,举个例子:输入了错误的URL。
- 500 Internal Server Error:服务器发生不可预期的错误。
- 503 Server Unavailable:服务器当前不能处理客户端的请求,一段时间后可能恢复正常。
http会话
cookie
HTTP 很重要的一个特点就是无状态(每一次见面都是“初次见面”),如果单纯的希望通过我们的服务端程序去记住每一个访问者是不可能的,所以必须借助一些手段或者说技巧让服务端记住客户端,这种手段就是 Cookie。
Cookie 就像是在超级市场买东西拿到的小票,由超市(Server)发给消费者(Browser),超市方面不用记住每一个消费者的脸,但是他们认识消费者手里的小票(Cookie),可以通过小票知道消费者之前的一些消费信息(在服务端产生的数据)。
//操作cookie
document.cookie = 'name=value; expires=Tue, 10 Oct 2017 16:14:47 GMT; path=/; domain=zce.me'
// 获取全部 cookie
console.log(document.cookie)
// => 'key1=value1; key2=value2'
// 得到的结果是字符串,需要自己通过字符串操作解析
session
由于 Cookie 是服务端下发给客户端由客户端本地保存的。换而言之客户端可以在本地对其随意操作,包括删除和修改。如果客户端随意伪造一个 Cookie 的话,对于服务端是无法辨别的,就会造成服务端被蒙蔽,构成安全隐患。
Session 区别于 Cookie 一个很大的地方就是:Session 数据存在了服务端,而 Cookie 存在了客户端本地,存在服务端最大的优势就是,不是用户想怎么改就怎么改了。
Session 这种机制会更加适合于存放一些属于用户而又不能让用户修改的数据,因为客户端不再保存具体的数据,只是保存一把“钥匙”,伪造一把可以用的钥匙,可能性是极低的,所以不需要在意。
AJAX(遵循http)
简介
我们可以通过以下几种方式让浏览器发出对服务端的请求,获得服务端的数据:
- 地址栏输入地址,回车,刷新
- 特定元素的 href 或 src 属性
- 表单提交
- AJAX 就是浏览器提供的一套 API,可以通过 JavaScript 调用,从而实现通过代码控制请求与响应。实现网络编程。 代码
代码
// 1. 创建一个 XMLHttpRequest 类型的对象 —— 相当于打开了一个浏览器
var xhr = new XMLHttpRequest()
// 2. 打开与一个网址之间的连接 —— 相当于在地址栏输入访问地址
// 设置请求报文的请求行
// 默认第三个参数为 true 意味着采用异步方式执行
//xhr.open('GET', './time.php', true)
xhr.open('GET', './time.php')
// 3. 通过连接发送一次请求 —— 相当于回车或者点击访问发送请求
// 设置请求体
xhr.send(null)
// 设置请求头
xhr.setRequestHeader('Accept', 'text/plain')
// 4. 指定 xhr 状态变化事件处理函数 —— 相当于处理网页呈现后的操作
xhr.onreadystatechange = function () {
if (this.readyState === 4) {
// 获取响应状态码
console.log(this.status)
// 获取响应状态描述
console.log(this.statusText)
// 获取响应头信息
console.log(this.getResponseHeader('Content‐Type')) // 指定响应头
console.log(this.getAllResponseHeader()) // 全部响应头
// 获取响应体
console.log(this.responseText) // 文本形式
}
}
readyState状态含义
| readyState | 状态描述 | 说明 |
|---|---|---|
| 0 | UNSENT | 代理(XHR)被创建,但尚未调用 open() 方法。 |
| 1 | OPENED | open() 方法已经被调用,建立了连接。 |
| 2 | HEADERS_RECEIVED | send() 方法已经被调用,并且已经可以获取状态行和响应头。 |
| 3 | LOADING | 响应体下载中, responseText 属性可能已经包含部分数据。 |
| 4 | DONE | 响应体下载完成,可以直接使用 responseText 。 |
跨域
简介
同源策略是浏览器的一种安全策略,所谓同源是指域名,协议,端口完全相同,只有同源的地址才可以相互通过AJAX 的方式请求。
同源或者不同源说的是两个地址之间的关系,不同源地址之间请求我们称之为跨域请求
例如:www.example.com:8080/detail.html 的域名协议为http,域名为www.example.com , 端口为8080.
解决方案
- JSONP
//服务端返回一段js函数
http.createServer(function(req, res){
var params = urllib.parse(req.url, true);
console.log(params);
if (params.query && params.query.callback) {
//console.log(params.query.callback);
var str = params.query.callback + '(' + JSON.stringify(data) + ')';//jsonp
res.end(str);
} else {
res.end(JSON.stringify(data));//普通的json
}
}).listen(port, function(){
console.log('server is listening on port ' + port);
})
//前端代码,先定义一个处理函数,下面的请求返回的事这个函数的调用
<script type="text/javascript">
function callbackFunction(result) {
//处理数据
}
</script> <script type="text/javascript"
src="xxxxxx?jsoncallback=callbackFunction"></script>
- CORS Cross Origin Resource Share,跨域资源共享
// 允许远端访问
header('Access‐Control‐Allow‐Origin: *');
- 反向代理