• 浏览器---浏览器/http相关面试题


    1.localStorage和sessionStorage

    共同点:二者都是以key-value的键值对方式存储在浏览器端,大小大概在5M。

    区别:

    (1)数据有效期不同:sessionStorage仅在当前浏览器窗口关闭之前有效;localStorage始终有效,窗口或浏览器关闭也一直保存,因此用作持久数据;

    (2)作用域不同:sessionStorage数据只能在同一个域的同一页面使用;localstorage在所有同源窗口中都是共享的,用在多窗口(页面)共享数据。需要注意的页面仅指顶级窗口,如果一个页面包多个iframe且他们属于同源页面,那么他们之间可以共享sessionStorage

    (3)使用场景:localStoragese常用于长期登录(+判断用户是否已登录),适合长期保存在本地的数据。sessionStorage敏感账号一次性登录。

    2.cookie、sessionlocalStoragesessionStorage

    会话(Session)跟踪是Web程序中常用的技术,用来跟踪用户的整个会话。常用的会话跟踪技术是Cookie与Session。Cookie通过在客户端记录信息确定用户身份,Session通过在服务器端记录信息确定用户身份。

    (1)存放位置不同:Cookie、localStorage、sessionStroge保存在客户端,Session保存在服务端。

    (2)存储大小限制不同:cookie数据不能超过4K,同时因为每次http请求都会携带cookie、所以cookie只适合保存很小的数据,如会话标识。Session一般情况下没有上限,不过建议不要存放太多东西,否则影响性能;sessionStorage和localStorage虽然也有存储大小的限制,但比cookie大得多,可以达到5M或更大 

    (3)数据共享/作用域不同:cookie localStorage sessionStorage数据遵循同源原则; SessionStorage还限制必须是同一个页面。

    (4)数据有效期不同:cookie:只在设置的cookie过期时间之前有效,即使窗口关闭或浏览器关闭 ;由于Session依赖于名为JSESSIONID的Cookie,而Cookie JSESSIONID的过期时间默许为–1,只需关闭了浏览器(一次会话结束),该Session就会失效sessionStorage:仅在当前浏览器窗口关闭之前有效;localStorage:始终有效,窗口或浏览器关闭也一直保存,因此用作持久数据;

    (5)安全性(隐私策略)不同 :Cookie存储在浏览器中,对客户端是可见的,客户端的一些程序可能会窥探、复制以至修正Cookie中的内容。而Session存储在服务器上,对客户端是透明的,不存在敏感信息泄露的风险。 假如选用Cookie,比较好的方法是,敏感的信息如账号密码等尽量不要写到Cookie中。Cookie信息最好加密,提交到服务器后再进行解密。而假如选择Session就省事多了,反正是放在服务器上,Session里任何隐私都能够有效的保护。

    (6)对服务器造成的压力不同 :Cookie保管在客户端,不占用服务器资源。假如并发阅读的用户十分多,Cookie是很好的选择。Session是保管在服务器端的,每个用户都会产生一个Session。假如并发访问的用户十分多,会产生十分多的Session,耗费大量的内存。

    (7)是否参与http通信:cookie和session都是参与服务器通信的,而localStorage和sessionStorage不参与服务器通信。

    (8)web Storage支持事件通知机制,可以将数据更新的通知发送给监听者

    (9)web Storage的api接口使用更方便,localStorage, sessionStorage有现成的API, cookie需要程序员手动封装,Web Storage拥有setItem,getItem等方法,cookie需要前端开发者自己封装setCookie,getCookie

    3.常用浏览器内核

    • IE浏览器内核:Trident内核,也是俗称的IE内核;
    • Chrome浏览器内核:统称为Chromium内核或Chrome内核,以前是Webkit内核,现在是Blink内核;
    • Firefox浏览器内核:Gecko内核,俗称Firefox内核;
    • Safari浏览器内核:Webkit内核;
    • Opera浏览器内核:最初是自己的Presto内核,后来是Webkit,现在是Blink内核;
    • 360浏览器、猎豹浏览器内核:IE+Chrome双内核;
    • 搜狗、遨游、QQ浏览器内核:Trident(兼容模式)+Webkit(高速模式)。

    4.对浏览器内核的理解

    主要分成两部分:渲染引擎(layout engineer或Rendering Engine)和JS引擎。

    渲染引擎:负责取得网页的内容(HTML、XML、图像等等)、整理讯息(例如加入CSS等),以及计算网页的显示方式,然后会输出至显示器或打印机。

    浏览器的内核的不同对于网页的语法解释会有不同,所以渲染的效果也不相同。所有网页浏览器、电子邮件客户端以及其它需要编辑、显示网络内容的应用程序都需要内核。

    JS引擎:解析和执行javascript来实现网页的动态效果。

    最开始渲染引擎和JS引擎并没有区分的很明确,后来JS引擎越来越独立,内核就倾向于只指渲染引擎。

    5.浏览器缓存机制

    缓存可以显著减少网络传输所带来的损耗,是性能优化中简单高效的一种优化方式

    对于一个数据请求来说,可以分为发起网络请求、后端处理、浏览器响应三个步骤。浏览器缓存可以帮助我们在第一和第三步骤中优化性能。比如说直接使用缓存而不发起请求,或者发起了请求但后端存储的数据和前端一致,那么就没有必要再将数据回传回来,这样就减少了响应数据。

    从缓存位置上来说分为四种,并且各自有优先级,当依次查找缓存且都没有命中的时候,才会去请求网络

    (Service Worker-Memory Cache-Disk Cache-Push Cache-网络请求

    通常浏览器缓存策略分为两种:强缓存和协商缓存,并且缓存策略都是通过设置 HTTP Header 来实现的

    6.http缓存

    http---HTTP缓存_http缓存csdn-CSDN博客

    HTTP 缓存是web性能优化的重要手段,通过复用缓存资源,减少了服务器和客户端的通信次数,降低网络延迟,加速页面加载,降低服务器端的压力。显著提升网站和应用的性能,提高用户体验。缺点:占内存。

    http缓存主要是针对html,css,img等静态资源,常规情况下,我们不太会去缓存一些动态资源,因为缓存动态资源的话,数据的实时性就不能保证,所以我们一般都只会去缓存一些不太容易被改变的静态资源。

    HTTP 缓存策略分为两种:强缓存和协商缓存 ,优先级: 强缓存 > 协商缓存

    强缓存:强缓存即强制直接使用缓存 Exipres,Cache-Control

    cache-control是expires的完全替代方案,在可以使用cache-control的情况下就不要使用expires

    强缓存不会向服务器发送请求,直接从缓存中读取资源,状态码200,并且size显示from disk cache或from memory cache;

    Expires:new Date("2023-2-2 23:59:59");设置一个过期时间(服务器端返回,在响应头中携带该参数),存在问题:本地时间和服务器时间不同步的问题.

    Cache-control:max-age=N,N就是需要缓存的秒数(服务器端返回,在响应头中携带该参数)。从第一次请求资源的时候开始,往后N秒内,资源若再次请求,则直接从磁盘(或内存)中读取,不与服务器做任何交互。

    协商缓存:协商缓存就得和服务器协商确认下这个缓存能不能用。 Last-Modified / If-Modified-Since, Etag /If-None-Match

    ETag并不是last-modified的完全替代方案,而是补充方案,具体用哪一个,取决于项目业务场景,无孰好孰坏之分

    协商缓存会先向服务器发送一个请求,服务器会根据这个请求的 request header 的一些参数来判断是否命中协商缓存,如果命中,则返回 304 状态码并带上新的 response header 通知浏览器从缓存中读取资源

    基于last-modified的协商缓存(通过比对资源文件的修改时间进行协商缓存)

    Response Headers携带:Last-Modified:<昨天>

    Request Headers携带:IF-Modified-Since:<昨天>

    缺点:

    • 在文件内容本身不修改的情况下,依然有可能更新文件修改时间(比如修改文件名再改回来),此时文件内容并没有修改,缓存依然失效了
    • 因为文件修改时间记录的最小单位是秒,所以当文件在几百毫秒内完成修改的时候,文件修改时间并不会改变,这样,即使文件内容修改了,依然不会返回新的文件

    基于ETag的协商缓存(通过生成文件内容的唯一哈希值,即文件指纹进行协商缓存)

    采用了一串编码来标记内容,称为ETag

    Response Headers携带:E-Tag:1234567

    Request Headers携带:If-None-Match:1234567

    ETag就是将原先协商缓存的比较时间戳的形式修改成了比较文件指纹。

    如果两个文件指纹完全吻合,说明文件没有被改变,则直接返回304状态码和一个空的响应体并return。如果两个文件指纹不吻合,则说明文件被更改,那么将新的文件指纹重新存储到响应头的ETag中并返回给客户端

    缺点:

    • 需要文件尺寸大,数量多,并且计算频繁,那么服务端就需要更多的计算开销,从而影响服务器的性能
    • ETag有强验证和弱验证,所谓强验证,ETag生成的哈希值深入到每个字节,从而保证文件内容绝对的不变,非常消耗计算量;弱验证则是提取文件的部分属性来生成哈希值,因此不必精确到每个字节,所以整体速度会比强验证快,但是精确率不高,会降低协商缓存的有效性

    7.从输入URL 到网页显示的完整过程

    • DNS域名解析,解析到真正的IP地址;
    • 客户端与服务端建立TCP连接TCP/IP连接(通过三次握手);
    • 客户端发送Http请求(封装HTTP报文,TCP报文头,IP报文头...);
    • 服务器接收到http请求,根据请求报文头中的信息执行对应的处理,并返回HTML文件给客户端浏览器;
    • 客户端接收到HTML文件后,开始解析、渲染并展示网页(DOM树、STYLE树、渲染树、绘制页面);
    • 数据传输完毕,关闭客户端与服务器端的双工连接(通过四次挥手)。

    8.重排和重绘

    重排(reflow):重新生成布局,重新排列元素。

    当DOM的变化影响了元素的几何信息(元素的的位置和尺寸大小),浏览器需要重新计算元素的几何属性,将其安放在界面中的正确位置,这个过程叫做重排。重排也叫回流,简单的说就是重新生成布局,重新排列元素。

    重绘(repaint):某些元素的外观被改变,例如:元素的填充颜色, 背景色

    当一个元素的外观发生改变,但没有改变布局,重新把元素外观绘制出来的过程,叫做重绘。

    注意:重绘不一定导致重排,但重排一定会导致重绘。重排开销更大。

    如何避免重绘或者重排?

    • 集中改变样式,不要一条一条地修改 DOM 的样式,集中改样式可先把所有样式给class,然后再给标签。
    • 不要把 DOM 结点的属性值放在循环里当成循环里的变量。
    • 为动画的 HTML 元件使用 固定定位(fixed) 或 绝对定位(absoult) ,那么修改他们的 CSS 是不会 重排的。
    • 不使用 table 布局。因为可能很小的一个小改动会造成整个 table 的重新布局。
    • 尽量只修改固定定位(fixed) 或 绝对定位(absoult) 元素,对其他元素影响不大
    • 使用BFC特性,不影响其他元素位置
    • 频繁触发(resize、scroll)使用节流和防抖
    • 使用createDocumentFragment批量操作DOM
    • 编码上,避免连续多次修改,可通过合并修改,一次触发
    • 对于大量不同的 dom 修改,可以先将其脱离文档流,比如使用绝对定位,或者 display:none,在文档流外修改完成后再放回文档里中
    • 动画实现的速度的选择,动画速度越快,回流次数越多,也可以选择使用 requestAnimationFrame
    • css3 硬件加速,transform、opacity、filters,开启后,会新建渲染层

    9.跨域

    跨域:指的是浏览器不能执行其他网站的脚本。它是由浏览器的同源策略造成的,是浏览器对javascript施加的安全限制。当一个请求url的协议、域名、端口三者之间任意一个与当前页面url不同即为跨域。

    注意:跨域限制访问,其实是浏览器的限制。理解这一点很重要!!!

    同源策略:是指协议,域名,端口都要相同,其中有一个不同都会产生跨域;

    (1)vue正向代理

    vue正向代理(proxy):利用浏览器跨域但是服务器没有跨域限制通过中间服务器转发数据

    当进行跨域访问时,vue会生成一个同源的虚拟服务器,请求将发送到虚拟服务器,由虚拟服务器访问目标服务器并转发数据。

    在vue.js开发环境下调用接口,如何避免跨域

    借助vue-cli脚手架开启代理服务器,在vue.config.js文件中配置proxy

    在工程目录【config/index.js】中对proxyTable项进行如下配置

    1. proxyTable: {
    2.    "/api": {
    3.         target"http://192.168.43.37:80/",
    4.         changeOrigintrue,
    5.         pathRewrite: {
    6.           "^/api"""
    7.         }
    8.      }
    9.  },

    如上述配置后,调用接口,http://xxxx:80/login可以简写成/api/login,本地会虚拟化一个服务器并帮你把这个请求转发给后台,从而避免跨域问题。

    (2)Nginx反向代理

    跨域请求限制是浏览器的安全策略,服务器端并不存在跨域访问这一说。利用Nginx的地址映射,将请求发送在一个同源的中间层,但是服务器实际请求地址为目标服务器,这样就不存在跨域访问了。

    例如前端项目放在"地址A",接口放在"地址B",Nginx服务器放在"nginxIpAddress:3000"地址。

    当访问项目的时候,你访问的是nginxIpAddress:3000,nginx将你的请求映射到项目的真实地址A,同理项目中的接口请求例如nginxIpAddress:3000/api/*,nginx将接口请求映射到接口服务的真实地址B。你始终访问的是nginxIpAddress:3000端口下的地址,自然不会存在跨域问题。

    (3)利用Nginx为响应添加跨域头解决

    将原本要请求的服务地址,改为请求nginx服务器,利用nginx地址映射将请求映射到真实的服务地址,同时需要添加两个响应头信息,一个是Access-Control-Allow-Origin,Access-Control-Allow-Methods。

    Access-Control-Allow-Origin:直译过来是允许跨域访问的源地址信息,可以配置多个(多个用逗号分隔),也可以使用*代表所有源。

    Access-Control-Allow-Methods:直译过来是允许跨域访问的请求方式,值可以为 GET POST PUT DELETE…,可以全部设置,也可以根据需要设置,多个用逗号分隔。

    4)cors(Cross-Origin Resource Sharing,跨域资源共享) 

    原理:它允许浏览器向跨源服务器,发出XMLHttpRequest请求(配置响应头Accesse-Control-Allow-Origin:"*",违背任意一条同源策略都能访问响应数据),从而克服了AJAX只能同源使用的限制。缺点:这样会造成任何人都能向这台服务器要数据。

    5)jsonp跨域:利用script标签可以跨域请求资源,将回调函数作为参数拼接在url中。后端收到请求,调用该回调函数,并将数据作为参数返回回去,注意设置响应头返回文档类型,应该设置成javascript;请求数据类型dataType为jsonp。缺陷是只支持get请求,且存在一些安全隐患。

    ps:不存在跨域问题的几个标签 ,