Ch3nyang's blog

home

home

person

about

hive

project

collections_bookmark

mindclip

rss_feed

rss

前端框架是怎么实现的

calendar_month 2024-05
archive 前端
tag vue tag react tag angular tag svelte

本文主要介绍前端框架是如何实现的。

打包过程

程序员使用框架编写好网页后,往往需要执行 npm run build 之类的东西,把代码转换为浏览器可以直接运行的代码。这个过程一般包括以下几个步骤:

  1. 将每个 component 转换为 JavaScript
  2. 将所有 component 合成单个 JavaScript 文件 app.bundle.js(对于部分 lazy-load 的页面,可能会合成多个)
  3. 将第三方的包和框架本身合成单个 JavaScript 文件 vendor.bundle.js
  4. 将所有 CSS 合成单个 CSS 文件 bundle.css(同样可能会有多个)
  5. 生成或者直接从静态文件中获取 index.html
  6. 将静态文件(图片、字体等)复制到输出目录

因此,最终的输出目录结构可能如下:

dist/
 ├──index.html
 ├──app.bundle.js
 ├──vendor.bundle.js
 ├──bundle.css
 └──...

之后,只需要上传到服务器就可以了。

SPA 访问过程

当用户使用浏览器访问打包好的 SPA(单页应用)网页时,通常会经历以下几个步骤:

  1. 浏览器向服务器请求 index.html。该文件几乎为空,其中通常包含

    <link rel="stylesheet" href="bundle.css">
    <script src="app.bundle.js"></script>
    <script src="vendors.bundle.js"></script>
    
  2. 浏览器解析 index.html,并向服务器请求其中的 bundle.cssapp.bundle.jsvendors.bundle.js

  3. Mountingvendor.bundle.js 中的框架代码会读取 app.bundle.js 中需要被渲染的 component;然后使用 Document API 程序化生成 HTML 内容,并插入到 index.html

  4. Patching:当用户与页面交互时,框架会根据用户的操作,动态地修改页面的内容。框架通常会修改尽量少的 DOM 元素,以优化性能。

    要想修改尽量少的 DOM 元素,通常有以下几种方法:

    • 绝大多数框架(React、Vue 等)会维护一个 Virtual DOM,当需要修改页面时,先修改 Virtual DOM,然后比较 Virtual DOM 和真实 DOM 的差异,最后只修改差异部分。

      为了知道何时需要修改 Virtual DOM,React 监控组件的 state 和 props 的变化;Vue 则通过响应式数据层,当数据变化时会触发 setter,从而通知框架重新渲染。

    • Svelte 会在编译时就确定可能会变化的部分,然后生成对应的 JavaScript 代码。这使得它在运行时的性能更好,但编译时间更长。

    • Angular 则使用了 Change detection,通过 Zone.js 捕获异步事件(event listener、HTTP 请求、或者其它事件循环中的事件),然后在事件处理函数执行完毕后,检查所有组件的状态是否发生变化,如果有变化则更新。

  5. 当用户点击内部链接时,框架会拦截这个事件,由 router 选择需要展示的 view,然后重新渲染;同时修改 URL。这样就实现了 SPA 的单页切换效果,此过程无需再与服务器通信。

SSR 访问过程

SSR(服务器端渲染)是指在服务器端生成 HTML,然后再发送给浏览器。在使用 SSR 时,通常会经历以下几个步骤:

  1. 浏览器向服务器请求页面,服务器根据 URL,将需要渲染的 component 组装成 HTML,然后返回给浏览器
  2. Hydrating:浏览器接收到 HTML 后,会根据其要求,从服务器请求 JavaScript 和 CSS 文件。然后浏览器会将接收到的 HTML 链接到 Virtual DOM 上
  3. 当用户与页面交互时,过程和 SPA 类似
  4. 当用户点击内部链接时,浏览器会向服务器请求新的页面,然后再次执行上述过程

Comments

Share This Post