HTTP

216 阅读5分钟

浏览器输入URL后HTTP请求返回的完整过程

  1. Redirect;
  2. 缓存; 缓存查询顺序:浏览器缓存 -> 操作系统缓存 -> 路由器缓存
  3. DNS解析:通过DNS服务器解析出服务器IP
  4. TCP三次握手,建立连接
  5. 服务器返回html数据,浏览器解析成DOM树以及CSSOM树,并挂载展示

版本

http 0.9

只有GET方法

http 1.0

  • 增加了http请求方法: POST、PUT、DELETE、HEADER、OPTIONS、TRACE
  • 增加了status code 和header

http 1.1

支持持久连接 pipeline,按顺序返回请求数据 增加host和其他一些命令

http 2

所有的数据都是以二进制传输 同一个连接发送多个请求不再根据顺序返回 头信息压缩以及推送等提高效率的功能 https协议

URI、URL、URN

URI: Uniform Resource Identifier 统一资源标志符 URI: Uniform Resource Locator 统一资源定位符 URN: 永久统一资源定位符:在资源移动之后还能被找到

URI和URL的区别: URI是一种概念,表示资源的唯一标识;URL是URI的一个子集,用定位的方式来表示资源; 所以URL并不仅仅局限于描述http协议的资源位置,也可以描述ftp

请求报文

缓存

CORS跨域限制及预请求验证

预请求验证

默认允许方法
  • GET
  • POST
  • HEAD
默认允许的Content-Type
  • "text/plain"
  • "multipart/form-data"
  • "application/x-www-form-urlencoded"

Cache-Control 客户端缓存

  • public 所有内容都将被缓存(客户端和代理服务器都可缓存)
  • private 内容只缓存到私有缓存中(仅用户端可以缓存,代理服务器不可缓存)
  • no-cache 虽然也走缓存,但是需要经过服务端验证,才能使用缓存
  • max-age=xxx 缓存的内容将在xxx秒后失效,这个选项只在HTTP1.1可用,并如果和Last-Modified一起使用时,优先级较高

no-cache 和 no-store的区别

no-store: 彻底禁用缓存

no-cache: 在浏览器使用缓存前,会往返对比ETag,如果ETag没变,返回304,则使用缓存

Last-Modified: 上次修改时间

Etag: 数据签名,对资源的内容进行hash计算

cookie 和session

Cookie属性

默认过期时间: 浏览器关闭时

js获取cookie
document.getCookie()
服务端可以禁止js访问cookie: HttpOnly
response.writeHead(200, {
  'Set-Cookie': ['abc=4656';HttpOnly]
})
Host相同时,共享cookie; host-admin可以直接修改host
const host = request.headers.host
if(request.url === '/') {
  const html = fs.readFileSync('test.html''utf8')
  // 这样无法实现二级域名共享cookie
  if(host === 'a.test.com') {
    response.writeHead(200, {
      'Set-Cookie': ['abc=4656;HttpOnly;domain=test.com']
    })
  }
  // 这样来实现二级域名共享cookie
  if(host === 'test.com') {
    response.writeHead(200, {
      'Set-Cookie': ['abc=4656;HttpOnly;domain=test.com']
    })
  }
}
Connection: keep-alive/close

保持长连接

数据协商

Accept

Accept-Encoding
Accept-Language
User-Agent

Content

Content-Type
Content-Encoding
Content-Language

Status Code

30x

301 永久重定向

除非手动清除缓存,否则浏览器永远直接调用重定向的内容

302 服务器指定重定向

每次都会请求服务器,由服务器指定重定向地址

50x

503 服务器无响应

由于临时的服务器维护或者过载,服务器当前无法处理请求

504 网关超时

由作为代理或网关的服务器使用,表示不能及时地从远程服务器获得应答

CSP - Content-Security-Policy

限制资源获取

response.writeHead(200, {
  'Content-Security-Policy': 'default-src http: https: \'self\' ' // 本站外链脚本
})

报告资源获取越权

网络安全

CSRF - Cross-site request forgery(跨站请求伪造)

从另一个站点(网页)伪造请求对另一个网站发起攻击。简单来说:伪装可信用户的请求来攻击信任该用户的网站。

要完成一个CSRF攻击,必须具备以下几个条件
  1. 受害者已经登录到了目标网站(你的网站)并且没有退出。
  2. 受害者有意或者无意的访问了攻击者发布的页面或者链接地址。

防御

  1. 验证码:强制需要客户进行交互才能操作,跟CSRF在客户不知情的情况下完成攻击的方式相悖
  2. Referer Check:Referer Check最常见的应用就是防止图片盗链,通过查看请求的来源判断请求是否合理,比如通过攻击者的网站嵌入访问博客的地址,那referer就是攻击者网站的地址,这样很大程度能判断出这是一个CSRF攻击,但是这个方法的缺陷是:服务器并不是每次都能取到Referer信息。
  3. 在URL中加入一个token参数。token可以存在用户的cookie中,服务器也存有该客户对应的token值。因为CSRF攻击只是利用登录cookie,并无法获取cookie的具体值(除非用户还被XSS攻击了,导致cookie泄露,那就无济于事了)。
  4. SameSite Cookie,防止 CSRF 攻击

XSS - 跨站脚本攻击

用某种方法让用户的Client端执行指定的一段Javascript脚本,来完成攻击

存储型XSS
存储型XSS

将XSS代码发送到服务器(不管是数据库、内存还是文件系统等。),然后在下次请求页面的时候就不用带上XSS代码了

比如:提交表单时,持久化到数据库

反射型XSS

是指发生请求时,XSS代码出现在请求URL中,作为参数提交到服务器,服务器解析并响应。响应结果中包含XSS代码,最后浏览器解析并执行。

DOM-XSS

DOM XSS代码不需要服务器端的解析响应的直接参与,而是通过浏览器端的DOM解析。这完全是客户端的事情。

防御

  1. Http-Only禁止Cookie被客户端Javascript获取。
  2. 客户端对用户的输入进行转译
  3. 客户端对服务端返回的数据进行转译
  4. 服务端对客户端请求的数据进行转译再保存到数据库或者缓存,因为攻击的人可以直接调接口不通过前端输入。