浏览器相关知识点总结

2023-05-16

今天说说浏览器相关问题:

  1. 常见的浏览器内核,参见下表:
     

    浏览器/RunTime内核(渲染引擎)JavaScript 引擎
    ChromeBlink(28~)
    Webkit(Chrome 27)
    V8
    FireFoxGeckoSpiderMonkey
    SafariWebkitJavaScriptCore
    EdgeEdgeHTMLChakra(for JavaScript)
    IETridentChakra(for JScript)
    PhantomJSWebkitJavaScriptCore
    Node.js-V8

  2. 判断浏览器内核

    判断是否原生Chrome:
    只有原生Chrome中存在一种MimeType“application/vnd.chromium.remoting-viewer”,由此可以判断浏览器是加壳Chrome或是原生Chrome。 
    判断是否为IE浏览器:只有IE内核的浏览器存在ActiveXObject对象。由此可以判断是否为IE浏览
     

  3. 从输入 URL 到页面加载完成,发生了什么?
    首先我们需要通过 DNS(域名解析系统)将 URL 解析为对应的 IP 地址,然后与这个 IP 地址确定的那台服务器建立起 TCP 网络连接,随后我们向服务端抛出我们的 HTTP 请求,服务端处理完我们的请求之后,把目标数据放在 HTTP 响应里返回给客户端,拿到响应数据的浏览器就可以开始走一个渲染的流程。渲染完毕,页面便呈现给了用户。
    0)输入url 读取浏览器缓存 系统缓存 路由缓存,若匹配到则直接展示
    1)DNS 解析
    :
    2) TCP 连接:
    3) HTTP 请求抛出
    4) 服务端处理请求,HTTP 响应返回
    5) 浏览器拿到响应数据,解析响应内容,把解析的结果展示给用户

     

  4. 浏览器重绘与重排的区别?

    重排: 部分渲染树(或者整个渲染树)需要重新分析并且节点尺寸需要重新计算,表现为重新生成布局,重新排列元素
    重绘: 由于节点的几何属性发生改变或者由于样式发生改变,例如改变元素背景色时,屏幕上的部分内容需要更新,表现为某些元素的外观被改变

    单单改变元素的外观,肯定不会引起网页重新生成布局,但当浏览器完成重排之后,将会重新绘制受到此次重排影响的部分

    重排和重绘代价是高昂的,它们会破坏用户体验,并且让UI展示非常迟缓,而相比之下重排的性能影响更大,在两者无法避免的情况下,一般我们宁可选择代价更小的重绘。

    『重绘』不一定会出现『重排』,『重排』必然会出现『重绘』。

     

  5. 如何触发重排和重绘?
    任何改变用来构建渲染树的信息都会导致一次重排或重绘:
    添加、删除、更新DOM节点
    通过display: none隐藏一个DOM节点-触发重排和重绘
    通过visibility: hidden隐藏一个DOM节点-只触发重绘,因为没有几何变化
    移动或者给页面中的DOM节点添加动画
    添加一个样式表,调整样式属性
    用户行为,例如调整窗口大小,改变字号,或者滚动
     

  6. 如何避免重绘或者重排?

    集中改变样式:通过改变class的方式来集中改变样式

    // 判断是否是黑色系样式
    const theme = isDark ? 'dark' : 'light'
    
    // 根据判断来设置不同的class
    ele.setAttribute('className', theme)

    使用DocumentFragment:通过createDocumentFragment创建一个游离于DOM树之外的节点,然后在此节点上批量操作,最后插入DOM树中,因此只触发一次重排

    var fragment = document.createDocumentFragment();
    
    for (let i = 0;i<10;i++){
      let node = document.createElement("p");
      node.innerHTML = i;
      fragment.appendChild(node);
    }
    
    document.body.appendChild(fragment);

    提升为合成层:提升合成层的最好方式是使用 CSS 的 will-change 属性

    #target {
      will-change: transform;
    }

  7. 前端如何实现即时通讯?
    1)短轮询
    2)comet
    3)SSE
    4)Websocket
    5)Web Worker
    6)Service workers

    HTTP 协议有一个缺陷:通信只能由客户端发起。举例来说,我们想了解今天的天气,只能是客户端向服务器发出请求,服务器返回查询结果。HTTP 协议做不到服务器主动向客户端推送信息。这种单向请求的特点,注定了如果服务器有连续的状态变化,客户端要获知就非常麻烦。我们只能使用"轮询":每隔一段时候,就发出一个询问,了解服务器有没有新的信息。最典型的场景就是聊天室。轮询的效率低,非常浪费资源(因为必须不停连接,或者 HTTP 连接始终打开)。因此,可以用另一种方法  WebSocket 。

  8. Websocket

    WebSocket 协议最大特点就是,服务器可以主动向客户端推送信息,客户端也可以主动向服务器发送信息,是真正的双向平等对话,属于服务器推送技术的一种。

    特点包括:
    (1)建立在 TCP 协议之上,服务器端的实现比较容易。
    (2)与 HTTP 协议有着良好的兼容性。默认端口也是80和443,并且握手阶段采用 HTTP 协议,因此握手时不容易屏蔽,能通过各种 HTTP 代理服务器。
    (3)数据格式比较轻量,性能开销小,通信高效。
    (4)可以发送文本,也可以发送二进制数据。
    (5)没有同源限制,客户端可以与任意服务器通信。
    (6)协议标识符是ws(如果加密,则为wss),服务器网址就是 URL。

    WebSocket 的用法

    var ws = new WebSocket("wss://echo.websocket.org");
    
    ws.onopen = function(evt) { 
      console.log("Connection open ..."); 
      ws.send("Hello WebSockets!");
    };
    
    ws.onmessage = function(evt) {
      console.log( "Received Message: " + evt.data);
      ws.close();
    };
    
    ws.onclose = function(evt) {
      console.log("Connection closed.");
    };

    客户端的 API

    1)WebSocket() 构造函数,用于新建 WebSocket 实例。执行下面语句之后,客户端就会与服务器进行连接。
    var ws = new WebSocket('ws://localhost:8080');
    2)webSocket.readyState

    3)webSocket.onopen

    4)webSocket.onclose

    5)webSocket.onmessage

    6)webSocket.send()

    7)webSocket.bufferedAmount

    8)webSocket.onerror


    服务端的实现

    常用的 Node 实现有以下三种
    µWebSockets
    Socket.IO
    WebSocket-Node

    推荐一款非常特别的 WebSocket 服务器:Websocketd。
     

  9. 浏览器跨域问题解决(九种跨域方式
    最经典的跨域方案jsonp
    最流行的跨域方案cors
    最方便的跨域方案nginx反向代理
    postMessage()
    websocket
    window.name + iframe
    location.hash + iframe
    二级域名相同  document.domain + iframe
    其它跨域方案: node中间件代理
  10. 常见web安全及防护
    web安全受到的威胁来自于以下几种攻击方式:
    sql注入,
    xss(恶意注入js和网页元素),
    csrf(代替用户完成交互并访问危险网站)

    我们的防护:
    1)对用户输入内容进行限制和校验
    2)对所有关键数据进行加密
    3)接口提交方式严格规范,数据提交不使用get

  11. 浏览器存储和服务端存储
    cookie和session的区别

    1)存储位置有区分,cookie存在浏览器缓存中,session存储在服务器上
    2)存储大小和数量 cookie小于session
    3)保密性 cookie对游览器和用户可见 session存在服务器上,保密性更佳
    4)服务器压力 session对服务器压力更大
    在实际开发过程中,cookie和session都很少使用,更为常用的是token,它比上两个优势更大,更好用,安全性高,可扩展性强,多平台跨域,无状态。可实现,单点登录和多点登录等功能。

    不要混淆session和session Storage
    session是身份验证(类似于令牌),session是一次浏览器和服务器的交互的会话,当访问服务器这个网页的时候,会在服务器端的内存里开辟一块内存,这块内存就叫做session,而这个内存是跟浏览器关联在一起的。这个浏览器指的是浏览器窗口或浏览器的子窗口,意思就是,只允许当前这个session对应的浏览器访问,就算是在同一个机器上新启的浏览器也是无法访问的。而另外一个浏览器也需要记录session的话,就会再启一个属于自己的session
    session Storage是一种存储方式,数据保存在浏览器缓存中,关闭浏览器和标签页就会消失。特别的一点在于,即便是相同域名下的两个页面,只要它们不在同一个浏览器窗口中打开,那么它们的 Session Storage 内容便无法共享。
    local Storage存储在本地需要手动删除才会消失,理论上 Cookie 无法胜任的、可以用简单的键值对来存取的数据存储任务,都可以交给 Local Storage 来做。存储一些内容稳定的资源。比如图片内容丰富的电商网站会用它来存储 Base64 格式的图片字符串,存储一些不经常更新的 CSS、JS 等静态资源。

    cookie是把少量的信息存储在用户端浏览器缓存中,它是全局的,在同一个域名下的所有请求,都会携带 Cookie。很快速方便。而且它本身存储的尺寸大小也有限 4k左右,最关键是用户是可见的,并可以随意的修改,很不安全。Cookie 虽然小,请求却可以有很多,随着请求的叠加,这样的不必要的 Cookie 带来的开销将是无法想象的。静态资源往往并不需要 Cookie 携带什么认证信息。把静态资源和主页面置于不同的域名下,完美地避免了不必要的 Cookie 的出现!
    cookies和localStorage和sessionStorage是同一类,都是储存方式,都遵循同源策略。只是大小,保存位置,保存时间不一样 大小 cookies<sessionStorage=localStorage 5-10M 之间
    保存位置 本地

     IndexedDB
    IndexedDB 是没有存储上限的(一般来说不会小于 250M)
    IndexedDB 可以看做是 LocalStorage 的一个升级,当数据的复杂度和规模上升到了 LocalStorage 无法解决的程度,我们毫无疑问可以请出 IndexedDB 来帮忙。

  12. 前端造成内存泄漏的操作
    1)闭包由于闭包会使得函数中的变量都被保存在内存中,内存消耗很大,过多的使用闭包,不及时释放,会导致内存泄漏。
    2)意外全局函数中定义参数,var 定义,会成为全局变量,使用es6的let可以避免这种情况。
    3)定时器
    4)生命周期中使用全局函数,未释放
    5)echarts
    6)keep-alive组件

    什么是内存泄漏?
    基于垃圾回收机制,当有变量和对象应该被回收而没有被回收时,一直占用和停留在堆内存中,这就产生内存泄漏。
    内存泄漏会导致内存被占用过多无法释放,从而导致系统内存分配不足,造成了内存溢出从而导致应用Crash(浏览器崩溃)。
    还有对于现在电脑来说,一些内存泄漏并不影响。

     
  13. 性能监控
    performance

     function getsec(time) {
          return time / 1000 + 's'
        }
        window.onload = function () {
          var per = window.performance.timing;
          console.log('DNS查询耗时' + getsec(per.domainLookupEnd - per.domainLookupStart))
          console.log('TCP链接耗时' + getsec(per.connectEnd - per.connectStart))
          console.log('request请求响应耗时' + getsec(per.responseEnd - per.responseStart))
          console.log('dom渲染耗时' + getsec(per.domComplete - per.domInteractive))
          console.log('白屏时间' + getsec(firstPaint - pageStartTime))
          console.log('domready可操作时间' + getsec(per.domContentLoadedEventEnd - per.fetchStart))
        }


  14.  
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

浏览器相关知识点总结 的相关文章

随机推荐