100 Continue:客户端应当继续发送请求。这个临时响应是用来通知客户端它的部分请求已经被服务器接收,且仍未被拒绝。客户端应当继续发送请求的剩余部分,或者若是请求已经完成,忽略这个响应。服务器必须在请求完成后向客户端发送一个最终响应。javascript
400 Bad Request:语义有误,当前请求没法被服务器理解。除非进行修改,不然客户端不该该重复提交这个请求。请求参数有误。html
401 Unauthorized:当前请求须要用户验证。该响应必须包含一个适用于被请求资源的 WWW-Authenticate 信息头用以询问用户信息。客户端能够重复提交一个包含恰当的 Authorization 头信息的请求。若是当前请求已经包含了 Authorization 证书,那么401响应表明着服务器验证已经拒绝了那些证书。若是401响应包含了与前一个响应相同的身份验证询问,且浏览器已经至少尝试了一次验证,那么浏览器应当向用户展现响应中包含的实体信息,由于这个实体信息中可能包含了相关诊断信息。参见RFC 2617。前端
403 Forbidden:服务器已经理解请求,可是拒绝执行它。与401响应不一样的是,身份验证并不能提供任何帮助,并且这个请求也不该该被重复提交。若是这不是一个 HEAD 请求,并且服务器但愿可以讲清楚为什么请求不能被执行,那么就应该在实体内描述拒绝的缘由。固然服务器也能够返回一个404响应,假如它不但愿让客户端得到任何信息。html5
404 Not Found:请求失败,请求所但愿获得的资源未被在服务器上发现。没有信息可以告诉用户这个情况究竟是暂时的仍是永久的。假如服务器知道状况的话,应当使用410状态码来告知旧资源由于某些内部的配置机制问题,已经永久的不可用,并且没有任何能够跳转的地址。404这个状态码被普遍应用于当服务器不想揭示到底为什么请求被拒绝或者没有其余适合的响应可用的状况下。出现这个错误的最有可能的缘由是服务器端没有这个页面。java
405 Method Not Allowed:请求行中指定的请求方法不能被用于请求相应的资源。该响应必须返回一个Allow 头信息用以表示出当前资源可以接受的请求方法的列表。node
鉴于 PUT,DELETE 方法会对服务器上的资源进行写操做,于是绝大部分的网页服务器都不支持或者在默认配置下不容许上述请求方法,对于此类请求均会返回405错误。jquery
406 Not Acceptable:请求的资源的内容特性没法知足请求头中的条件,于是没法生成响应实体。ios
500 Internal Server Error:服务器遇到了一个不曾预料的情况,致使了它没法完成对请求的处理。通常来讲,这个问题都会在服务器端的源代码出现错误时出现。nginx
501 Not Implemented:服务器不支持当前请求所须要的某个功能。当服务器没法识别请求的方法,而且没法支持其对任何资源的请求。es6
502 Bad Gateway:做为网关或者代理工做的服务器尝试执行请求时,从上游服务器接收到无效的响应。
503 Service Unavailable:因为临时的服务器维护或者过载,服务器当前没法处理请求。这个情况是临时的,而且将在一段时间之后恢复。若是可以预计延迟时间,那么响应中能够包含一个 Retry-After 头用以标明这个延迟时间。若是没有给出这个 Retry-After 信息,那么客户端应当以处理500响应的方式处理它。
注意:503状态码的存在并不意味着服务器在过载的时候必须使用它。某些服务器只不过是但愿拒绝客户端的链接。
504 Gateway Timeout:做为网关或者代理工做的服务器尝试执行请求时,未能及时从上游服务器(URI标识出的服务器,例如HTTP、FTP、LDAP)或者辅助服务器(例如DNS)收到响应。
注意:某些代理服务器在DNS查询超时时会返回400或者500错误
505 HTTP Version Not Supported:服务器不支持,或者拒绝支持在请求中使用的 HTTP 版本。这暗示着服务器不能或不肯使用与客户端相同的版本。响应中应当包含一个描述了为什么版本不被支持以及服务器支持哪些协议的实体。
· 200 OK (from cache) ——强制缓存,指的是浏览器没有跟服务器确认,直接用了浏览器缓存。经过设置 expires/cache-control 来实现的。虽然是强缓存,但用户主动触发的刷新行为,仍是会采用缓存协商的策略
,主动触发的刷新行为包括点击刷新按钮、右键刷新、f5刷新、ctrl+f5刷新等。
· 304 Not Modified——协商缓存,比 200 OK (from cache) 慢,指的是浏览器还向服务器确认了下 "If-Not-Modified",才用的缓存。
Last-Modified:在浏览器第一次请求某一个URL时,服务器端的返回状态会是200,资源响应头有一个Last-Modified的属性标记此文件在服务期端最后被修改的时间,另一半也有个Etag。
HTTP中,经过Cache-Control首部和Expires首部为文档指定了过时时间,经过对过时时间的判断,缓存就能够知道文档是否是在保质期内。
Last-Modified(Etag)
(1)Last-Modified : http1.0时期属性, 如今仍在使用。
(2)ETag(Entity Tag) http1.1时期新加属性 。由于如下几个缘由增长此属性:
Last-Modified与ETag同时使用时,浏览器在验证时会同时发送If-Modified-Since和If-None-Match,按照http/1.1规范,若是同时使用If-Modified-Since和If-None-Match则服务端必须两个都验证经过后才能返回304;且nginx就是这样作的。所以实际使用时应该根据实际状况选择。
分布式的Web系统中,当访问落在不一样的物理机上时会返回不一样的ETag,进而致使304失效,降级为200请求,因此常常在使用中会关闭ETag。
Cache-Control(expires)
(1)Pragma : no-cache http1.0时期的属性 为了兼容会使用
(2)expires:0 http1.0时期的属性 ,如今默认浏览器均默认使用HTTP 1.1,因此它的做用基本忽略。expires 的一个缺点就是,返回的到期时间是服务器端的时间,这样存在一个问题,若是客户端的时间与服务器的时间相差很大(好比时钟不一样步,或者跨时区),那么偏差就很大,因此在HTTP 1.1版开始,使用Cache-Control: max-age=秒替代。
(3)Cache-Control http1.1 中加入的新属性,它有如下经常使用参数:
301和302状态码都表示重定向,就是说浏览器在拿到服务器返回的这个状态码后会自动跳转到一个新的URL地址,这个地址能够从响应的Location首部中获取(用户看到的效果就是他输入的地址A瞬间变成了另外一个地址B)
场景一 想换个域名,旧的域名不用啦,这样用户访问旧域名时用301就重定向到新的域名。其实也是告诉搜索引擎收录的域名须要对新的域名进行收录。
场景二 登陆后重定向到指定的页面,这种场景比较常见就是登陆成功跳转到具体的系统页面。
场景三 有时候须要自动刷新页面,好比5秒后回到订单详细页面之类。
场景四 有时系统进行升级或者切换某些功能时,须要临时更换地址。
场景五 像微博之类的使用短域名,用户浏览后须要重定向到真实的地址之类。
从网址A 作一个302 重定向到网址B 时,主机服务器的隐含意思是网址A 随时有可能改主意,从新显示自己的内容或转向其余的地方。大部分的搜索引擎在大部分状况下,当收到302重定向时,通常只要去抓取目标网址就能够了,也就是说网址B。若是搜索引擎在遇到302 转向时,百分之百的都抓取目标网址B 的话,就不用担忧网址URL 劫持了。问题就在于,有的时候搜索引擎,尤为是Google,并不能老是抓取目标网址。
好比说,有的时候A 网址很短,可是它作了一个302重定向到B网址,而B网址是一个很长的乱七八糟的URL网址,甚至还有可能包含一些问号之类的参数。很天然的,A网址更加用户友好,而B网址既难看,又不用户友好。这时Google颇有可能会仍然显示网址A。因为搜索引擎排名算法只是程序而不是人,在遇到302重定向的时候,并不能像人同样的去准确断定哪个网址更适当,这就形成了网址URL劫持的可能性。也就是说,一个不道德的人在他本身的网址A作一个302重定向到你的网址B,出于某种缘由, Google搜索结果所显示的仍然是网址A,可是所用的网页内容倒是你的网址B上的内容,这种状况就叫作网址URL 劫持。你辛辛苦苦所写的内容就这样被别人偷走了。302重定向所形成的网址URL劫持现象,已经存在一段时间了。不过到目前为止,彷佛也没有什么更好的解决方法。
大致意思是会引发搜索引擎的排名,并且302重定向很容易被搜索引擎误认为是利用多个域名指向同一网站,那么你的网站就会被封掉。总之,除非真是临时重定向使用302,其余的状况最好仍是使用301.
cookie 是一个很是具体的东西,指的就是浏览器里面能永久存储的一种数据,仅仅是浏览器实现的一种数据存储功能。
cookie由服务器生成,发送给浏览器,浏览器把cookie以kv形式保存到某个目录下的文本文件内,下一次请求同一网站时会把该cookie发送给服务器。因为cookie是存在客户端上的,因此浏览器加入了一些限制确保cookie不会被恶意使用,同时不会占据太多磁盘空间,因此每一个域的cookie数量是有限的。服务端能够设置httpOnly,使得前端没法操做cookie
session 从字面上讲,就是会话。这个就相似于你和一我的交谈,你怎么知道当前和你交谈的是张三而不是李四呢?对方确定有某种特征(长相等)代表他就是张三。
session 也是相似的道理,服务器要知道当前发请求给本身的是谁。为了作这种区分,服务器就要给每一个客户端分配不一样的“身份标识”,而后客户端每次向服务器发请求的时候,都带上这个“身份标识”,服务器就知道这个请求来自于谁了。至于客户端怎么保存这个“身份标识”,能够有不少种方式,对于浏览器客户端,你们都默认采用 cookie 的方式。
服务器使用session把用户的信息临时保存在了服务器上,用户离开网站后session会被销毁。这种用户信息存储方式相对cookie来讲更安全,但是session有一个缺陷:若是web服务器作了负载均衡,那么下一个操做请求到了另外一台服务器的时候session会丢失。
在Web领域基于Token的身份验证随处可见。在大多数使用Web API的互联网公司中,tokens 是多用户下处理认证的最佳方式。
如下几点特性会让你在程序中使用基于Token的身份验证
1.无状态、可扩展
2.支持移动设备
3.跨程序调用
4.安全
基于服务器验证方式暴露的一些问题
1.Seesion:每次认证用户发起请求时,服务器须要去建立一个记录来存储信息。当愈来愈多的用户发请求时,内存的开销也会不断增长。
2.可扩展性:在服务端的内存中使用Seesion存储登陆信息,伴随而来的是可扩展性问题。
3.CORS(跨域资源共享):当咱们须要让数据跨多台移动设备上使用时,跨域资源的共享会是一个让人头疼的问题。在使用Ajax抓取另外一个域的资源,就能够会出现禁止请求的状况。
4.CSRF(跨站请求伪造):用户在访问银行网站时,他们很容易受到跨站请求伪造的攻击,而且可以被利用其访问其余的网站。
在这些问题中,可扩展行是最突出的。所以咱们有必要去寻求一种更有行之有效的方法。
基于Token的验证原理
基于Token的身份验证是无状态的,咱们不将用户信息存在服务器或Session中。这种概念解决了在服务端存储信息时的许多问题,NoSession意味着你的程序能够根据须要去增减机器,而不用去担忧用户是否登陆。
基于Token的身份验证的过程以下:
1.用户经过用户名和密码发送请求。
2.程序验证。
3.程序返回一个签名的token 给客户端。
4.客户端储存token,而且每次用于每次发送请求。
5.服务端验证token并返回数据。
本部分摘自:http://www.javashuo.com/article/p-pmqrabgg-cs.html
1.使用前端cookie技术来保存本地化数据,如jquery.cookie.js;
2.使用html5提供的localStorage技术来提供解决方案;
html5中的Web Storage包括了两种存储方式:sessionStorage和localStorage。
sessionStorage用于本地存储一个会话(session)中的数据,这些数据只有在同一个会话中的页面才能访问而且当会话结束后数据也随之销毁。所以sessionStorage不是一种持久化的本地存储,仅仅是会话级别的存储。而localStorage用于持久化的本地存储,除非主动删除数据,不然数据是永远不会过时的。若是是要永久保存的,那么就请使用localStorage方法存取值,若是是要浏览关闭会话结束就清除缓存的,固然就得选择sessionStorage方法了;
网络通信大部分是基于TCP/IP的,而TCP/IP是基于IP地址的,因此计算机在网络上进行通信时只能识别如“202.96.134.133”之类的IP地址,而不能认识域名。咱们没法记住10个以上IP地址的网站,因此咱们访问网站时,更多的是在浏览器地址栏中输入域名,就能看到所须要的页面,这是由于有一个叫“DNS服务器”的计算机自动把咱们的域名“翻译”成了相应的IP地址,而后调出IP地址所对应的网页。它所提供的服务是用来将主机名和域名转换为IP地址.
一、在浏览器中输入www . qq .com 域名,操做系统会先检查本身本地的hosts文件是否有这个网址映射关系,若是有,就先调用这个IP地址映射,完成域名解析。
二、若是hosts里没有这个域名的映射,则查找本地DNS解析器缓存,是否有这个网址映射关系,若是有,直接返回,完成域名解析。
三、若是hosts与本地DNS解析器缓存都没有相应的网址映射关系,首先会找TCP/ip参数中设置的首选DNS服务器,在此咱们叫它本地DNS服务器,此服务器收到查询时,若是要查询的域名,包含在本地配置区域资源中,则返回解析结果给客户机,完成域名解析,此解析具备权威性。
四、若是要查询的域名,不禁本地DNS服务器区域解析,但该服务器已缓存了此网址映射关系,则调用这个IP地址映射,完成域名解析,此解析不具备权威性。
五、若是本地DNS服务器本地区域文件与缓存解析都失效,则根据本地DNS服务器的设置(是否设置转发器)进行查询,若是未用转发模式,本地DNS就把请求发至13台根DNS,根DNS服务器收到请求后会判断这个域名(.com)是谁来受权管理,并会返回一个负责该顶级域名服务器的一个IP。本地DNS服务器收到IP信息后,将会联系负责.com域的这台服务器。这台负责.com域的服务器收到请求后,若是本身没法解析,它就会找一个管理.com域的下一级DNS服务器地址(http://qq.com)给本地DNS服务器。当本地DNS服务器收到这个地址后,就会找http://qq.com域服务器,重复上面的动做,进行查询,直至找到www . qq .com主机。
六、若是用的是转发模式,此DNS服务器就会把请求转发至上一级DNS服务器,由上一级服务器进行解析,上一级服务器若是不能解析,或找根DNS或把转请求转至上上级,以此循环。无论是本地DNS服务器用是是转发,仍是根提示,最后都是把结果返回给本地DNS服务器,由此DNS服务器再返回给客户机。
从客户端到本地DNS服务器是属于递归查询,而DNS服务器之间就是的交互查询就是迭代查询。
1) 浏览器缓存
当用户经过浏览器访问某域名时,浏览器首先会在本身的缓存中查找是否有该域名对应的IP地址(若曾经访问过该域名且没有清空缓存便存在);
2) 系统缓存
当浏览器缓存中无域名对应IP则会自动检查用户计算机系统Hosts文件DNS缓存是否有该域名对应IP;
3) 路由器缓存
当浏览器及系统缓存中均无域名对应IP则进入路由器缓存中检查,以上三步均为客服端的DNS缓存;
4) ISP(互联网服务提供商)DNS缓存
当在用户客服端查找不到域名对应IP地址,则将进入ISP DNS缓存中进行查询。好比你用的是电信的网络,则会进入电信的DNS缓存服务器中进行查找;
5) 根域名服务器
当以上均未完成,则进入根服务器进行查询。全球仅有13台根域名服务器,1个主根域名服务器,其他12为辅根域名服务器。根域名收到请求后会查看区域文件记录,若无则将其管辖范围内顶级域名(如.com)服务器IP告诉本地DNS服务器;
6) 顶级域名服务器
顶级域名服务器收到请求后查看区域文件记录,若无则将其管辖范围内主域名服务器的IP地址告诉本地DNS服务器;
7) 主域名服务器
主域名服务器接受到请求后查询本身的缓存,若是没有则进入下一级域名服务器进行查找,并重复该步骤直至找到正确纪录;
8)保存结果至缓存
本地域名服务器把返回的结果保存到缓存,以备下一次使用,同时将该结果反馈给客户端,客户端经过这个IP地址与web服务器创建连接。
CDN的全称是Content Delivery Network,即内容分发网络。CDN是构建在现有网络基础之上的智能虚拟网络,依靠部署在各地的边缘服务器,经过中心平台的负载均衡、内容分发、调度等功能模块,使用户就近获取所需内容,下降网络拥塞,提升用户访问响应速度和命中率。CDN的关键技术主要有内容存储和分发技术。
协议数据单元PDU(Protocol Data Unit)是指对等层次之间传递的数据单位
物理层的 PDU是数据位(bit)
数据链路层的 PDU是数据帧(frame)
网络层的PDU是数据报(packet)
传输层的 PDU是数据段(segment)
其余更高层次的PDU是报文(message)
应用层: (典型设备:应用程序,如FTP,SMTP ,HTTP)
DHCP(Dynamic Host Configuration Protocol)动态主机分配协议,使用 UDP 协议工做,主要有两个用途:给内部网络或网络服务供应商自动分配 IP 地址,给用户或者内部网络管理员做为对全部计算机做中央管理的手段。实现即插即用连网。
DNS (Domain Name System )域名解析<端口号53>
FTP (File Transfer Protocol )文件传输协议<端口号21>减小或消除不一样操做系统下处理文件的不兼容性。
HTTP (Hypertext Transfer Protocol )超文本传输协议 <端口号 80>, 面向事务的应用层协议。
POP3 (Post Office Protocol 3) 即邮局协议的第3 个版本,用于接受邮件。
SMTP (Simple Mail Transfer Protocol )简单邮件传输协议 <端口号25> 用于发送邮件。
SSH (Secure Shell )安全外壳协议
TELNET 远程登陆协议 <端口号23>
传输层: (典型设备: 进程和端口) 数据单元:数据段 (Segment)
TCP (Transmission Control Protocol )传输控制协议提供可靠的面向链接的服务,传输数据前须先创建链接,结束后释放。可靠的全双工信道。可靠、有序、无丢失、不重复。
UDP (User Datagram Protocol )用户数据报协议发送数据前无需创建链接,不使用拥塞控制,不保证可靠交付,最大努力交付。
网络层: (典型设备:路由器,防火墙、多层交换机) 数据单元:数据包(Packet )
IP (IPv4 · IPv6) (Internet Protocol) 网络之间互连的协议
ARP (Address Resolution Protocol) 即地址解析协议,实现经过IP 地址得 知其物理地址。
RARP (Reverse Address Resolution Protocol)反向地址转换协议容许局域 网的物理机器从网关服务器的 ARP 表或者缓存上请求其 IP地址。
ICMP (Internet Control Message Protocol )Internet 控制报文协议。它是TCP/IP 协议族的一个子协议,用于在IP 主机、路由器之间传递控制消息。
ICMPv6 :
IGMP (Internet Group Management Protocol) Internet 组管理协议,是因特 网协议家族中的一个组播协议,用于 IP 主机向任一个直接相邻的路由器报 告他们的组成员状况。
RIP (Router information protocol) 路由信息协议是一种在网关与主机之间交换路由选择信息的标准。
OSPF (Open Shortest Path Firs)开放式最短路径优先,分布式链路状态协议。
BGP(Border Gateway Protocol )边界网关协议,用来链接Internet 上独立系统的路由选择协议.采用路径向量路由选择协议。
数据链路层: (典型设备: 网卡,网桥,交换机) 数据单元:帧 (Frame)
ARQ(Automatic Repeat-reQuest )自动重传请求协议,错误纠正协议之一,包括中止等待ARQ 协议和连续ARQ 协议,错误侦测、正面确认、逾时重传与负面确认继以重传等机制。
中止等待协议:
CSMA/CD(Carrrier Sense Multiple Access with Collision Detection)载波监听多点接入/碰撞检测协议。总线型网络,协议的实质是载波监听和碰撞检测。载波监听即发数据前先检测总线上是否有其余计算机在发送数据,如暂时不发数据,避免碰撞。碰撞检测为计算机边发送数据边检测信道上的信号电压大小。
PPP(Point-to-Ponit Protocol)点对点协议面向字节,由三部分组成:
一个将IP 数据报封装到串行链路的方法
一个用于创建、配置和测试数据链路链接的链路控制协议LCP
一套网络控制协议NCP
HDLC (High-Level Data Link Control )高级数据链路控制同步网上传输数据、面向比特的数据链路层协议。
ATM (Asynchronous Transfer Mode )异步传递方式,创建在电路交换和分组交换的基础上的一种面向链接的快速分组交换技术。 “异步”是指将ATM 信元“异步插入”到同步的 SDH 比特流中。如同步插入则用户在每帧中所占的时隙相对位置固定不变。“同步”是指网络中各链路上的比特流都是受同一很是精确的主时钟的控制。Wi-Fi 、WiMAX 、DTM 、令牌环、以太网、FDDI 、帧中继、 GPRS 、 EVDO 、HSPA 、L2TP 、ISDN
物理层:(典型设备:中继器,集线器) 数据单元:比特 (Bit)
光纤、 同轴电缆、双绞线…
Transmission Control Protocol/Internet Protocol的简写,中译名为传输控制协议/因特网互联协议,又名网络通信协议,是Internet最基本的协议、Internet国际互联网络的基础,由网络层的IP协议和传输层的TCP协议等组成(固然还有其余后来发展起来的网络协议,还包括 ARP,ICMP,IGMP,UDP,以及让域名访问成为可能的DNS,以及电脑/手机能够自动获取IP地址的DHCP。固然还有形形色色的应用层的协议如 HTTP / SMTP / FTP 等。)。TCP/IP 定义了电子设备如何连入因特网,以及数据如何在它们之间传输的标准。协议采用了4层的层级结构,每一层都呼叫它的下一层所提供的协议来完成本身的需求。通俗而言:TCP负责发现传输的问题,一有问题就发出信号,要求从新传输,直到全部数据安全正确地传输到目的地。而IP是给因特网的每一台联网设备规定一个地址。
IP协议(Internet Protocol)是将多个包交换网络链接起来,它在源地址和目的地址之间传送一种称之为数据包的东西,它还提供对数据大小的从新组装功能,以适应不一样网络对包大小的要求。IP协议在OSI参考模型中应用于网络层,以“数据包(Package)”为单位。其中,IP地址的定义是确认惟一端口号和路由选择的关键,IP地址至关于每台电话的电话号码,惟一且是咱们互相联系的关键,所以IP协议也是网络互连的关键。
IP协议特色
TCP(Transmission Control Protocol 传输控制协议)是一种面向链接的、可靠的, 基于IP的传输层协议。TCP在IP报文的协议号是6。TCP是一个超级麻烦的协议,而它又是互联网的基础。
TCP工做在网络OSI的七层模型中的第四层——Transport层(传输层),IP在第三层——Network层,ARP 在第二层——Data Link层。在第二层的数据,咱们把它叫Frame(数据帧),在第三层的数据叫Packet(数据包),第四层的数据叫Segment(数据段)。 同时,咱们须要简单的知道,数据从应用层发下来,会在每一层都会加上头部信息,进行封装,而后再发送到数据接收端。因此数据的发送和接收其实就是数据的封装和解封装的过程。
UDP 是User Datagram Protocol的简称, 中文名是用户数据报协议,是OSI(Open System Interconnection,开放式系统互联) 参考模型中一种无链接的传输层协议,提供面向事务的简单不可靠信息传送服务,IETF RFC 768是UDP的正式规范。UDP在IP报文的协议号是17。与所熟知的TCP(传输控制协议)协议同样,UDP协议直接位于IP(网际协议)协议的顶层。根据OSI(开放系统互连)参考模型,UDP和TCP都属于传输层协议。UDP协议的主要做用是将网络数据流量压缩成数据包的形式。一个典型的数据包就是一个二进制数据的传输单位。每个数据包的前8个字节(16*4位)用来包含报头信息,剩余字节则用来包含具体的传输数据。
TCP拥塞控制原理
拥塞控制:
当网络中某一资源的需求超出了该资源所能提供的可用部分,这时网络的性能就要开始变坏,这种状况就叫作拥塞。而拥塞控制就是为了减小或者避免拥塞对网络性能的影响而作出的一种控制手段。
拥塞控制思路:发送方维持一个叫作拥塞窗口的状态变量,拥塞窗口的大小取决于网络的拥塞程度,而且在动态的变化。发送方让本身的发送窗口等于拥塞窗口,若是在考虑接收方的接收能力,通常发送窗口还要小于拥塞窗口。
慢开始:当主机开始发送数据的时候,由小到大的增大发送窗口,也就是由小到大的增大拥塞窗口。接收方接收到一个报文以后就回传一个确认报文,发送方每接收到一个确认报文,就将拥塞窗口加1,这样每通过一个传输轮次以后,拥塞窗口就增大一倍。
拥塞避免:思路是让拥塞窗口缓慢的增大,即每通过一个往返时间RTT就把发送方的拥塞窗口加1,而不是加倍,这样拥塞窗口就是线性缓慢增长,比慢开始的增加速率缓慢的多。
慢开始门限:为了防止拥塞窗口增加过大引发网络拥塞,还须要设置一个慢开始门限
TCP/UDP区别
1. 通常区别
2. TCP的粘包和UDP的丢包
TCP粘包现象:TCP粘包是指发送方发送的若干包数据到接收方接收时粘成一包,从接收缓冲区看,后一包数据的头紧接着前一包数据的尾。
粘包缘由:
粘包处理:若是黏在一块儿的包是同一个总体,即赞成部分数据分割而来的,那么就不用进行处理。若是是不一样部分的数据粘到一块儿,就须要进行粘包解决:
UDP丢包现象:丢包现象即便用UDP发送时,因为不可靠链接方式,收到各类因素影响,数据包可能会在接受过程当中丢失一部分,从而致使数据不完整。
UDP丢包缘由:
UDP丢包处理:
HTTP是一个客户端和服务器端请求和应答的标准,一般,由HTTP客户端发起一个请求,创建一个到服务器指定端口(默认是80端口)的TCP链接。HTTP服务器则在那个端口监听客户端发送过来的请求。一旦收到请求,服务器(向客户端)发回一个状态行。 HTTP协议的网页 HTTP协议的网页 HTTP使用TCP而不是UDP的缘由在于(打开)一个网页必须传送不少数据,而TCP协议提供传输控制,按顺序组织数据,和错误纠正。
经过HTTP或者HTTPS协议(HTTP协议+SSL协议)请求的资源由统一资源标示符(Uniform Resource Identifiers)(或者,更准确一些,URLs)来标识。HTTP有如下特色:
简单快速:客户向服务器请求服务时,只需传送请求方法和路径。请求方法经常使用的有GET、HEAD、POST。每种方法规定了客户与服务器联系的类型不一样。因为HTTP协议简单,使得HTTP服务器的程序规模小,于是通讯速度很快。
URL是一种特殊类型的URI,包含了用于查找某个资源的足够的信息,URL,全称是UniformResourceLocator, 中文叫统一资源定位符,是互联网上用来标识某一处资源的地址。如下面这个URL为例,介绍下普通URL的各部分组成:
http://www.cnblogs.com:8080/fzz9/index.jsp?id=30303&page=2#name
端口号部分:此网址为8080。跟在域名后面的是端口号,域名和端口之间使用“:”做为分隔符。端口不是一个URL必须的部分,若是省略端口部分,将采用默认端口。
本部分摘自:http://www.javashuo.com/article/p-ewsekudn-dm.html http://www.javashuo.com/article/p-fvcfqfjo-cv.html
超文本传输协议
http请求头部字段:http://www.javashuo.com/article/p-qrnsonao-cy.html
HTTPS 是以安全为目标的 HTTP 通道,简单讲是 HTTP 的安全版,即 HTTP 下加入 SSL 层,HTTPS 的安全基础是 SSL,所以加密的详细内容就须要 SSL。
SSL加密过程:
本部分摘自:http://www.javashuo.com/article/p-axrsxogg-dh.html http://www.javashuo.com/article/p-vurbdisw-cr.html(写的很好呦~)
对于GET方式的请求,浏览器会把http header和data一并发送出去,服务器响应200(返回数据);
而对于POST,浏览器先发送header,服务器响应100 continue,浏览器再发送data,服务器响应200 ok(返回数据)
GET和POST是什么?HTTP协议中的两种发送请求的方法。
HTTP是什么?HTTP是基于TCP/IP的关于数据如何在万维网中如何通讯的协议。
HTTP的底层是TCP/IP。因此GET和POST的底层也是TCP/IP,也就是说,GET/POST都是TCP连接。GET和POST能作的事情是同样同样的。你要给GET加上request body,给POST带上url参数,技术上是彻底行的通的,只要后端支持就好。
实际上,没有本质区别,可是因为HTTP的规定和浏览器/服务器的限制,致使他们在应用过程当中体现出一些不一样。(大多数)浏览器一般都会限制url长度在2K个字节,而(大多数)服务器最多处理64K大小的url。超过的部分,恕不处理。若是你用GET服务,在request body偷偷藏了数据,不一样服务器的处理方式也是不一样的,有些服务器会帮你卸货,读出数据,有些服务器直接忽略,因此,虽然GET能够带request body,也不能保证必定能被接收到哦。
本部分摘自:https://blog.51cto.com/13961945/2287553
Axios 是一个基于 promise 的 HTTP 库,能够用在浏览器和 node.js 中。
它的特性是:
axios包含全部请求方式函数的封装、
axios.get(url [,config]) axios.delete(url [,config]) axios.head(url [,config]) axios.post(url [,data [,config]]) axios.put(url [,data [,config]]) axios.patch(url [,data [,config]])
本部分摘自:https://www.jianshu.com/p/ae8e9edf4460
SYN(synchronous创建联机)
ACK(acknowledgement 确认)
PSH(push传送)
FIN(finish结束)
RST(reset重置)
URG(urgent紧急)
第一次握手:Client将标志位SYN置为1,随机产生一个值seq=J,并将该数据包发送给Server,Client进入SYN_SENT状态,等待Server确认。
第二次握手:Server收到数据包后由标志位SYN=1知道Client请求创建链接,Server将标志位SYN和ACK都置为1,ack (number )=J+1,随机产生一个值seq=K,并将该数据包发送给Client以确认链接请求,Server进入SYN_RCVD状态。
第三次握手:Client收到确认后,检查ack是否为J+1,ACK是否为1,若是正确则将标志位ACK置为1,ack=K+1,并将该数据包发送给Server,Server检查ack是否为K+1,ACK是否为1,若是正确则链接创建成功,Client和Server进入ESTABLISHED状态,完成三次握手,随后Client与Server之间能够开始传输数据了。
为何三次握手?
有这样一种状况,当A发送一个消息给B,可是因为网络缘由,消息被阻塞在了某个节点,而后阻塞的时间超出设定的时间,A会认为这个消息丢失了,而后从新发送消息。
当A和B通讯完成后,这个被A认为失效的消息,到达了B
对于B而言,觉得这是一个新的请求连接消息,就向A发送确认,
对于A而言,它认为没有给B再次发送消息(由于上次的通话已经结束)全部A不会理睬B的这个确认,可是B则会一直等待A的消息
这就致使了B的时间被浪费(对于服务器而言,CPU等资源是一种浪费),这样是不可行的,这就是为何不能两次握手的缘由了。
先由客户端向服务器端发送一个FIN,请求关闭数据传输。
当服务器接收到客户端的FIN时,向客户端发送一个ACK,其中ack的值等于FIN+SEQ
而后服务器向客户端发送一个FIN,告诉客户端应用程序关闭。
当客户端收到服务器端的FIN是,回复一个ACK给服务器端。其中ack的值等于FIN+SEQ
为何要4次挥手?
为何须要TIME_WAIT状态
SYN攻击:
在三次握手过程当中,Server发送SYN-ACK以后,收到Client的ACK以前的TCP链接称为半链接(half-open connect),此时Server处于SYN_RCVD状态,当收到ACK后,Server转入ESTABLISHED状态。SYN攻击就是Client在短期内伪造大量不存在的IP地址,并向Server不断地发送SYN包,Server回复确认包,并等待Client的确认,因为源地址是不存在的,所以,Server须要不断重发直至超时,这些伪造的SYN包将长时间占用未链接队列,致使正常的SYN请求由于队列满而被丢弃,从而引发网络堵塞甚至系统瘫痪。SYN攻击时一种典型的DDOS攻击,检测SYN攻击的方式很是简单,即当Server上有大量半链接状态且源IP地址是随机的,则能够判定遭到SYN攻击了。
本部分摘自:http://www.javashuo.com/article/p-gdgxchwo-cd.html
浏览器的同源策略致使了跨域:同源策略限制了从同一个源加载的文档或脚本如何与来自另外一个源的资源进行交互。这是一个用于隔离潜在恶意文件的重要安全机制。
- 不一样的域名 (好比在网站 example.com 请求 api.com)
- 不一样的子域名 (好比在网站 example.com 请求 api.example.com)
- 不一样的端口 (好比在网站 example.com 请求 example.com:3001)
- 不一样协议 (好比在网站 https://example.com 请求 http://example.com)
浏览器只对XHR(XMLHttpRequest)请求有同源请求限制,而对script标签src属性、link标签ref属性和img标签src属性没有这这种限制,利用这个“漏洞”就能够很好的解决跨域请求。JSONP就是利用了script标签无同源限制的特色来实现的,当向第三方站点请求时,咱们能够将此请求放在<script>标签的src属性里,这就如同咱们请求一个普通的JS脚本,能够自由的向不一样的站点请求:
<script src="http://www.b.com/request?para1=1"></script>
只支持GET,不支持POST请求
/** * JSONP请求工具 * @param url 请求的地址 * @param data 请求的参数 * @returns {Promise<any>} */ const request = ({url, data}) => { return new Promise((resolve, reject) => { // 处理传参成xx=yy&aa=bb的形式 const handleData = (data) => { const keys = Object.keys(data) const keysLen = keys.length return keys.reduce((pre, cur, index) => { const value = data[cur] const flag = index !== keysLen - 1 ? '&' : '' return `${pre}${cur}=${value}${flag}` }, '') } // 动态建立script标签 const script = document.createElement('script') // 接口返回的数据获取 window.jsonpCb = (res) => { document.body.removeChild(script) delete window.jsonpCb resolve(res) } script.src = `${url}?${handleData(data)}&cb=jsonpCb` document.body.appendChild(script) }) } // 使用方式 request({ url: 'http://localhost:9871/api/jsonp', data: { // 传参 msg: 'helloJsonp' } }).then(res => { console.log(res) })
//它的基本思想是,网页经过添加一个<script>元素,向服务器请求JSON数据,这种作法不受同源政策限制;服务器收到请求后,将数据放在一个指定名字的回调函数里传回来。 //首先,网页动态插入<script>元素,由它向跨源网址发出请求。 function addScriptTag(src) { var script = document.createElement('script'); script.setAttribute("type","text/javascript"); script.src = src; document.body.appendChild(script); } window.onload = function () { addScriptTag('http://example.com/ip?callback=foo'); } function foo(data) { console.log('Your public IP address is: ' + data.ip); }; //上面代码经过动态添加<script>元素,向服务器example.com发出请求。注意,该请求的查询字符串有一个callback参数,用来指定回调函数的名字,这对于JSONP是必需的。 //服务器收到这个请求之后,会将数据放在回调函数的参数位置返回。
CORS是一个W3C标准,全称是"跨域资源共享"(Cross-origin resource sharing)
浏览器将CORS请求分红两类:简单请求(simple request)和非简单请求(not-so-simple request)。
只要同时知足如下两大条件,就属于简单请求。
(1) 请求方法是如下三种方法之一:
(2)HTTP的头信息不超出如下几种字段:
这个头部信息由服务器返回,用来明确指定那些客户端的域名容许访问这个资源
简单请求
浏览器会在在header信息里面多加一个字段:
key:origin
value:协议+域名+端口(如https://localhost:8080)
服务器根据对象里的origin值来决定是否赞成此次请求
若是请求经过
请求经过后,服务器会在header里多增长几个字段:
非简单请求
非简单请求的方法就是Put,Delete,或者Content-Type是application/json
非简单请求在发出CORS请求以前,会增长一次HTTP查询请求,也叫预检请求
预检请求成功了,浏览器才能发出XMLHttpRequest,不然报错
若是浏览器发现这是一个非简单请求
就会先发送一个预检请求:
OPTIONS /cors HTTP/1.1 Origin: http://localhost:8088 Access-Control-Request-Method: PUT Access-Control-Request-Headers: token
预测请求的方法名叫OPTIONS
Origin和简单请求同样
Access-Control-Request-Method是请求方法
Access-Control-Request-Headers是额外发送的头信息字段
(tip:预检请求通常缓存下来,以便不须要在每次请求都发送)
若是预检请求经过
咱们来看下服务器发出的回应
HTTP/1.1 200 OK Date: Nov, 01 Dec 2017 01:15:39 GMT Server: Apache/2.0.61 (Unix) Access-Control-Allow-Origin: http://localhost:8088 Access-Control-Allow-Methods: GET, POST, PUT Access-Control-Allow-Headers: token Content-Type: text/html; charset=utf-8 Content-Encoding: gzip Content-Length: 0 Keep-Alive: timeout=2, max=100 Connection: Keep-Alive Content-Type: text/plain
若是预检请求失败
服务器会返回一个HTTP回应(没有CORS的头信息字段)
并在console打出not allowed by Access-Control-Allow-Origin
异常
预检请求经过之后
浏览器发每次出的CORS请求就和简单请求同样
会有一个origin字段
服务器每次回应都会有Access-Control-Allow-Origin
头信息字段
此方案仅限主域相同,子域不一样的跨域应用场景。
实现原理:两个页面都经过js强制设置document.domain为基础主域,就实现了同域。
父窗口(http://www.demo.com/a.html) <iframe id="iframe" src="http://child.demo.com/b.html"></iframe> <script> document.domain = 'demo.com'; var user = 'admin'; </script> 子窗口:(http://child.demo.com/b.html) <script> document.domain = 'demo.com'; // 获取父窗口中变量 alert('get js data from parent ---> ' + window.parent.user); </script>
实现原理: a欲与b跨域相互通讯,经过中间页c来实现。 三个页面,不一样域之间利用iframe的location.hash传值,相同域之间直接js访问来通讯。
具体实现:A域:a.html -> B域:b.html -> A域:c.html,a与b不一样域只能经过hash值单向通讯,b与c也不一样域也只能单向通讯,但c与a同域,因此c可经过parent.parent访问a页面全部对象。
实现原理: a欲与b跨域相互通讯,经过中间页c来实现。 三个页面,不一样域之间利用iframe的location.hash传值,相同域之间直接js访问来通讯。
具体实现:A域:a.html -> B域:b.html -> A域:c.html,a与b不一样域只能经过hash值单向通讯,b与c也不一样域也只能单向通讯,但c与a同域,因此c可经过parent.parent访问a页面全部对象。
window.name属性的独特之处:name值在不一样的页面(甚至不一样域名)加载后依旧存在,而且能够支持很是长的 name 值(2MB)。
postMessage是HTML5 XMLHttpRequest Level 2中的API,且是为数很少能够跨域操做的window属性之一,它可用于解决如下方面的问题:
a.) 页面和其打开的新窗口的数据传递
b.) 多窗口之间消息传递
c.) 页面与嵌套的iframe消息传递
d.) 上面三个场景的跨域数据传递
用法:postMessage(data,origin)方法接受两个参数
data: html5规范支持任意基本类型或可复制的对象,但部分浏览器只支持字符串,因此传参时最好用JSON.stringify()序列化。
origin: 协议+主机+端口号,也能够设置为"*",表示能够传递给任意窗口,若是要指定和当前窗口同源的话设置为"/"。
<iframe id="iframe" src="http://www.demo2.com/b.html" style="display:none;"></iframe> <script> var iframe = document.getElementById('iframe'); iframe.onload = function() { var data = { name: 'aym' }; // 向domain2传送跨域数据 iframe.contentWindow.postMessage(JSON.stringify(data), 'http://www.demo2.com'); }; // 接受domain2返回数据 window.addEventListener('message', function(e) { alert('data from demo2 ---> ' + e.data); }, false); </script> <script> // 接收domain1的数据 window.addEventListener('message', function(e) { alert('data from demo1 ---> ' + e.data); var data = JSON.parse(e.data); if (data) { data.number = 16; // 处理后再发回domain1 window.parent.postMessage(JSON.stringify(data), 'http://www.demo1.com'); } }, false); </script>
本部分摘自:https://segmentfault.com/a/1190000015597029?utm_source=tag-newest
https://segmentfault.com/a/1190000017867312?utm_source=tag-newest
http://www.javashuo.com/article/p-vwlsbjnn-br.html
其原理是攻击者向有 XSS漏洞的网站中输入(传入)恶意的HTML代码,当其它用户浏览该网站时,这段HTML代码会自动执行,从而达到攻击的目的。如,盗取用户 Cookie、破坏页面的正常结构,插入广告等恶意内容、重定向到其它网站,D-doss攻击等;XSS攻击相似于SQL注入攻击,攻击以前,咱们先找到一个存在XSS漏洞的网站。理论上,全部可输入的地方没有对输入数据进行处理的话,都会存在XSS漏洞,漏洞的危害取决于攻击代码的威力。
反射型
发出请求时,XSS代码出如今url中,做为输入提交到服务器端,服务器端解析后响应,XSS代码随响应内容一块儿传回给浏览器,最后浏览器解析执行XSS代码。这个过程像一次反射,因此叫反射型XSS。
存储型
存储型XSS和反射型XSS的差异在于,提交的代码会存储在服务器端(数据库、内存、文件系统等),下次请求时目标页面时不用再提交XSS代码。
防范措施
设置httponly,对cookie进行保护
编码:对用户输入的数据进行 HTML Entity 编码。Encode的做用是将等一些字符进行转化,使得浏览器在最终输出结果上是同样的。
过滤:移除用户输入的和事件相关的属性。如onerror能够自动触发攻击,还有onclick等。移除用户输入的Style节点、Script节点、Iframe节点。(尤为是Script节点,它但是支持跨域的呀,必定要移除)。
校订:避免直接对HTML Entity进行解码。使用DOM Parse转换,校订不配对的DOM标签。
该攻击能够在受害者绝不知情的状况下以受害者名义伪造请求发送给受攻击站点,从而在未受权的状况下执行在权限保护之下的操做,具备很大的危害性。具体来说,能够这样理解CSRF攻击:攻击者盗用了你的身份,以你的名义发送恶意请求,对服务器来讲这个请求是彻底合法的,可是却完成了攻击者所指望的一个操做,好比以你的名义发送邮件、发消息,盗取你的帐号,添加系统管理员,甚至于购买商品、虚拟货币转帐等。
防范措施
方法1、Token 验证:(用的最多)
服务器发送给客户端一个token;
客户端提交的表单中带着这个token。
若是这个 token 不合法,那么服务器拒绝这个请求。
方法二:隐藏令牌:
把 token 隐藏在 http 的 head头中。
方法二和方法一有点像,本质上没有太大区别,只是使用方式上有区别。
方法3、Referer 验证:
Referer 指的是页面请求来源。意思是,只接受本站的请求,服务器才作响应;若是不是,就拦截。
CSRF 和 XSS 的区别
区别一:
CSRF:须要用户先登陆网站A,获取 cookie。
XSS:不须要登陆。
区别二:(原理的区别)
CSRF:是利用网站A自己的漏洞,去请求网站A的api。
XSS:是向网站 A 注入 JS代码,而后执行 JS 里的代码,篡改网站A的内容
本部分摘自:https://blog.csdn.net/m0_37686205/article/details/90030588
websocket是HTML5的一个新协议,它容许服务端向客户端传递信息,实现浏览器和客户端双工通讯。
服务器能够主动向客户端推送信息,客户端也能够主动向服务器发送信息,是真正的双向平等对话,属于服务器推送技术的一种。
本部分摘自:http://www.javashuo.com/article/p-qqicfccz-ec.html
传统的Http应用里都是一次TCP链接一次request。
这种状况下效率有点低:
短链接
所谓短链接,就是每次请求一个资源就创建链接,请求完成后链接立马关闭。每次请求都通过“建立tcp链接->请求资源->响应资源->释放链接”这样的过程
长链接
所谓长链接(persistent connection),就是只创建一次链接,屡次资源请求都复用该链接,完成后关闭。要请求一个页面上的十张图,只须要创建一次tcp链接,而后依次请求十张图,等待资源响应,释放链接。
并行链接
所谓并行链接(multiple connections),其实就是并发的短链接。
(1) client发出的HTTP请求头须要增长Connection:keep-alive字段
(2) Web-Server端要能识别Connection:keep-alive字段,而且在http的response里指定Connection:keep-alive字段,告诉client,我能提供keep-alive服务,而且"应允"client我暂时不会关闭socket链接
在HTTP/1.0里,为了实现client到web-server能支持长链接,必须在HTTP请求头里显示指定
Connection:keep-alive
在HTTP/1.1里,就默认是开启了keep-alive,要关闭keep-alive须要在HTTP请求头里显示指定
Connection:close
如今大多数浏览器都默认是使用HTTP/1.1,因此keep-alive都是默认打开的。一旦client和server达成协议,那么长链接就创建好了。
客户端和服务端在创建链接并完成request后并不会当即断开TCP链接,而是在下次request来临时复用此次TCP链接。可是这里也必需要有TCP链接的timeout时间限制。否则会形成服务端端口被长期占用释放不了。
对于不适用keepalive的request来讲,无论是客户端仍是服务端都是经过TCP的连接的断开知道request的结束(TCP 挥手时会check 数据包的 seq, 保证数据完整性)。
支持keepalive后,如何知道request结束了呢?
在Http1.1的版本里, 解决方案是request 和reponse里使用contentLength来帮助确认是否收到所有数据。
另外一个问题就是在使用keepalive的状况,客户端依然有同时发送多个请求的状况,好比网页加载是须要同时load多个静态资源。好比 浏览器默认最大链接数是6,如今有十个资源同时加载,那么这十个里会有6个并行,4个与前6个串行。
在keepalive里有个问题就是若是能知道每一个repose与其对应的request的话,并发的请求能够只须要一次TCP链接,这也就是http2.0实现的多路复用
本部分摘自(图是别人的,画的巨好,可是没找到原做者):http://www.javashuo.com/article/p-rhbsanol-bo.html
长轮询
AMD、CMD、CommonJs是ES5中提供的模块化编程的方案,import/export是ES6中新增的。
1. AMD-异步模块定义
AMD是RequireJS在推广过程当中对模块定义的规范化产出,它是一个概念,RequireJS是对这个概念的实现,就比如JavaScript语言是对ECMAScript规范的实现。AMD是一个组织,RequireJS是在这个组织下自定义的一套脚本语言。RequireJS:是一个AMD框架,能够异步加载JS文件,按照模块加载方法,经过define()函数定义,第一个参数是一个数组,里面定义一些须要依赖的包,第二个参数是一个回调函数,经过变量来引用模块里面的方法,最后经过return来输出。
2. CMD---是SeaJS在推广过程当中对模块定义的规范化产出,是一个同步模块定义,是SeaJS的一个标准,SeaJS是CMD概念的一个实现,SeaJS是淘宝团队提供的一个模块开发的js框架.
3. CommonJS规范---是经过module.exports定义的,在前端浏览器里面并不支持module.exports,经过node.js后端使用的。Nodejs端是使用CommonJS规范的,前端浏览器通常使用AMD、CMD、ES6等定义模块化开发的。
3. ES6特性,模块化---export/import对模块进行导出导入的。
AMD推崇依赖前置,在定义模块的时候就要声明其依赖的模块
CMD推崇就近依赖,只有在用到某个模块的时候再去require
不少人说requireJS是异步加载模块,SeaJS是同步加载模块,这么理解其实是不许确的,其实加载模块都是异步的,只不过AMD依赖前置,js能够方便知道依赖模块是谁,当即加载,而CMD就近依赖,须要使用把模块变为字符串解析一遍才知道依赖了那些模块,这也是不少人诟病CMD的一点,牺牲性能来带来开发的便利性,实际上解析模块用的时间短到能够忽略