页面加载和渲染过程,性能优化问题,安全问题

1、js运行环境

  运行环境即浏览器(server端有nodejs)

  浏览器要下载网页代码,渲染出页面,期间会执行若干JS

 要保证代码在浏览器中:稳定且高效

2、网页加载过程

   加载资源的形式 :html代码,

            媒体文件,如图片、视频等

                                 javascript 

         css

   加载资源的过程:DNS解析:域名--->IP地址

           浏览器根据IP地址向服务器发起http请求

           服务器处理http请求,并返回给浏览器

   渲染资源的过程:根据HTML代码生成--->DOM Tree

         根据css代码 ----> CSSOM

         将DOM Tree 和 CSSOM整合Render Tree

                                根据Render Tree渲染页面

         遇到<script>则暂停渲染,优先加载并执行JS代码,完成再继续(DOM渲染和js执行公用一个线程)

         直至把Render Tree渲染完成

引出问题

  1、从输入url到渲染出页面的整个过程?

     2、window.load和DOMContentLoaded的区别?

   <img id="img" src="https://timgsa.baidu.com/timg?image&quality=80&size=b9999_10000&sec=1594278708278&di=1c8a248fd269ca7495b65c017fe8ba0e&imgtype=0&src=http%3A%2F%2Fa3.att.hudong.com%2F14%2F75%2F01300000164186121366756803686.jpg" alt="">
    <script>
        var img= document.getElementById('img')
        img.onload=function(){
            console.log('img load') //2
        }
        window.addEventListener('load',function(){
            //页面资源全部加载完成,包括图片、视频等
            console.log('all load') //3
        })
        document.addEventListener('DOMContentLoaded',function(){
            // DOM 渲染完成即可执行,此时图片、视频可能还没有加载完
            console.log('dom load')  //1
        })
    </script>

   3、为什么要把css放在head中?

   4、为什么要把js放在body最下面?

 

3、性能优化

 性能优化原则: 多使用内存、缓存或其他方法

         减少CPU计算量,减少网络加载耗时

( 适用于所有编程的性能优化-----空间换时间,chrome浏览器就是个典型,每个标签页一个进程,每个标签互不干扰,空间大了,性能也提上去了)

 从何入手:让加载更快

        减少资源体积:压缩代码(webpack的mode:production)

        减少访问次数:合并代码:webpack

                                                SSR服务器渲染:将网页和数据一起加载,一起渲染

                         非SSR(前后端分离):先加载网页,在加载数据,再渲染数据

                      最早的JSP ASP PHP,现在的vue React SSR

                 缓存( 静态资源加hash后缀,根据文件内容计算hash

                 文件内容不变,则hash不变,则url不变

                 url 和 文件不变,则自动触发http缓存机制,返回304

                )

        使用更快的网络:CDN

      让渲染更快

       Css放在head,JS放在body最下面

       尽早开始执行JS,用DOMContentLoaded触发

       懒加载(图片懒加载,上滑加载更多),现在vue和react中可以只用插件

       将页面里所有img属性src属性用data-xx代替,当页面滚动直至此图片出现在可视区域时,用js取到该图片的data-xx的值赋给src

   <img id="img1" src="preview.png"  data-realsrc="abc.png" alt="">
    <script>
        var img1 = document.getElementById('img1')
        img1.src = img1.getAttribute('data-realsrc')
    </script>

          对DOM操作查询进行缓存

  var pList = document.getElementsByTagName('p')
        const length = pList.length
        for(i=0;i<length;i++){
            //缓存length,只进行一次DOM查询
        }

        频繁DOM操作,合并到一起插入DOM结构

       节流throttle  防抖 debounce 让渲染更流畅

 

       // 防抖
        // 监听输入框,文字变化后触发change事件
        // 直接keyup,则会频繁触发onchange

        var input  = document.getElementById('input')

        // 实现功能
        let timer = null
        input.addEventListener('keyup',function(){
            if(timer){
                clearTimeout(timer)
            }
            timer = setTimeout(()=>{

                console.log(input.value)

                timer=null
            },500)
        })

        // 可以封装起来
        function deboundce(fn,delay){
            // timer实在闭包中
            let timer = null;

            return function(){
                if(timer){
                    clearTimeout(timer)
                }
                timer = setTimeout(()=>{
                    fn.apply(this,arguments)
                    timer=null
                },delay)
            }
        }

        input.addEventListener('keyup',deboundce(()=>{
            console.log(input.value)
        },500))
// 节流 
        // 拖拽一个元素的时候,要随时拿到该元素被拖拽的位置
        // 直接用drag事件,则会频繁触发,很容易导致卡顿
        const div1 = document.getElementById('drag')
        let timer = null
        div1.addEventListener('drag',function(e){
            if(timer){
                return
            }
            timer = setTimeout(()=>{
                console.log(e.offsetX)
                timer=null
            },100)
        })
        
        function throlle(fn,delay){
            var timer=null;
            return function(){
                if(timer){
                    return
                }
                timer = setTimeout((e)=>{
                    fn.apply(this,arguments)
                    timer=null
                },500)
            }
        }
        div1.addEventListener('drag',throlle(function(e){
            console.log(e.offsetX)
        },500))

4、安全

  XSS

  XSRF

 

posted on 2020-07-09 13:17  猪mother  阅读(353)  评论(0编辑  收藏  举报