前端单页面拆分多个单页面
问题现状
- 后端采用 ==多服务 + nginx== 的技术架构 根据业务拆分成不同的项目,具体服务通过location由nginx转发代理到不同的机器(端口)上。
- 前端采用的是 ==dva + roadhog== 的 ==SPA== 页面。在前期路由少,页面小的情况下,开发顺畅无压力。
- 随着开发的不断进行,前端开发的瓶颈渐显,前端代码量不断增加,引入的第三方包不断扩大,每次动态编译花费时间不断加大,最终打包文件不断变大。
- 每次发布版本必须全量发布,即使是改动一点点的功能,无法按模块发布前端代码。
- 开发人员在开发阶段必须通过
--max_old_space_size
命令强制分配内存来避免node进程out of memory
项目前端相关指标:
\ | 业务代码大小 | 打包后代码总量 | 路由数量 | 编译总时长 | 热加载时长 |
---|---|---|---|---|---|
总量 | 5.26 MB | 35.5MB | 近100个 | 20分 | 45 s |
==可以看到前端编译的时间已经极大的影响了开发人员的开发时间和开发效率==
改进目标
- 以
功能模块
为第一维度分割大项目。 - 尽量不影响用户体验。
- 切换到新页面同步左侧菜单栏的状态。
- 子项目可以分开独立发布上线。
解决思路
- 将旧项目的部分功能拉出来,独立成多个单独可正常运行的子项目。
- 借鉴后端 ==nginx== 的分发思想,通过
location
分发到不同静态目录。 - 将子项目前端代码部署到多个路径(甚至是机器),每个子项目独立发布,互不影响。
实现步骤
1. 前端项目拆分
- 更新前端路由模式,从
hash
模式改为history
模式
/src/index.js:
import browserHistory from 'history/createBrowserHistory';
const app = dva({history: browserHistory(),
});
- 修改路由配置,删除非本项目的路由
- 从model、service、route删除非本项目的文件
- 删除非本项目的依赖,并更新
package.json
- 删除
/src/index.ejs
首页文件中非本项目的文件引入
2. nginx分发
- 增加子路径的分发,有多个增加多个
nginx.conf:
location /sub-path/ {alias /xxx/dist/; #静态文件路径try_files $uri $uri/ /xxx/dist/index.html; #404时重新定向到静态文件目录下的index.html下
}
- 修改根目录的处理方式,由root更新为alias(防止root权重问题导致nginx不执行try_files)
nginx.conf:
location / {alias /xxxx/dist/; #静态文件路径try_files $uri $uri/ /xxxx/dist/index.html; #404时重新定向到静态文件目录下的index.html下
}
3. 404路径优化
- 前端404路由由渲染页面优化为重定向资源,把路由控制权转交给
nginx
- 为防止
前端404路由
和nginx404路由
同时存在导致无限刷新需缓存一个更新状态在本地,防止死刷新
tryRefresh() {if (window.sessionStorage.getItem('refresh') === 'true') {window.sessionStorage.removeItem('refresh');this.show404 = true;} else {window.sessionStorage.refresh = 'true';this.show404 = false;window.location.href = window.location.href;}
}
4. 菜单状态同步
- 根据url路径,同步更新左侧菜单栏的状态
setDefaultOpenKeys() {try {const { location: { pathname } } = this.props;let keys = [];const pathItems = pathname.replace('/', '', 1).split('/');const pathItemsWithoutLast = pathItems.slice(0, pathItems.length-1);this.setState({openKeys: pathItemsWithoutLast,});} catch (err) {// what you do}
}
5. 配置项目自动发布
- 配置发布相关,自测,上线代码
最终结果
将前端代码拆分成为一个基础模板和3个子项目。
- 前后数据对比:
\ | 业务代码大小 | 打包后代码总量 | 路由数量 | 编译总时长 | 热加载时长 |
---|---|---|---|---|---|
==项目 - 旧== | ==5.26 MB== | ==35.5MB== | ==近100个== | ==20分== | ==45 s== |
项目模板 | 0.45 MB | 2MB | 2个 | 15s | 1 s |
子项目一 | 3.5 MB | 28MB | 近70个 | 12分 | 7 s |
子项目二 | 4.2 MB | 12MB | 10个 | 4分 | 5 s |
子项目三 | 2 MB | 9.16MB | 16个 | 1.5分 | 2 s |
待优化点
- 有些公共的文件没有抽离出来,导致子项目总和是大于原项目的。抽离出公共文件和依赖,防止资源浪费。
- 常量的公共接口可以做sesionStorage缓存(例如菜单栏),防止项目切换重复调用接口造成浪费。
转载于:https://www.cnblogs.com/shenshangzz/p/10035197.html
前端单页面拆分多个单页面相关推荐
- 实用常识 | 将PDF文件页面拆分成两个页面(老白嫖怪了)
续<实用常识 | 分享一个好用的插件解决浏览器图片下载问题(老白嫖怪了)> 正值Yi情肆虐于我燕赵大地,时至年关Bing毒多处零散爆发.老弟今年12岁整,本命年,恰是小升初的关键时刻,学校 ...
- 前端程序猿必知:单页面应用的核心
这几年里.单页面应用的框架令人应接不暇,各种新的概念也层出不穷.从过去的 jQuery Mobie.Backbone 到今天的 Angular 2.React.Vue 2,除了版本不同,他们还有非常多 ...
- 前端页面与form表单提交:代码分享
今天分享下"前端页面与form表单提交:代码分享"这篇文章,文中根据实例编码详细介绍,或许对大家的编程之路有着一定的参考空间与使用价值,需要的朋友接下来跟着云南仟龙Mark一起学习 ...
- 前端程序员必知:单页面应用的核心
这几年里,单页面应用的框架令人应接不暇,各种新的概念也层出不穷.从过去的 jQuery Mobie.Backbone 到今天的 Angular 2.React.Vue 2,除了版本号不同,他们还有很多 ...
- web前端学习笔记26-事件类型——一般事件、页面事件、表单事件
一.事件类型的分类 事件分为一般事件.页面事件和表单事件 二.一般事件 关键字 释义 关键字 释义 click 单击事件 dblclick 双击事件 mousemove 鼠标移动事件 mouseove ...
- 前端:你要懂的单页面应用和多页面应用
单页面应用(SinglePage Web Application,SPA) 只有一张Web页面的应用,是一种从Web服务器加载的富客户端,单页面跳转仅刷新局部资源 ,公共资源(js.css等)仅需加载 ...
- Django学习笔记(10)——Book单表的增删改查页面
一,项目题目:Book单表的增删改查页面 该项目主要练习使用Django开发一个Book单表的增删改查页面,通过这个项目巩固自己这段时间学习Django知识. 二,项目需求: 开发一个简单的Book增 ...
- [html] From表单提交时为什么会刷新页面?怎么预防刷新?
[html] From表单提交时为什么会刷新页面?怎么预防刷新? 因为早期网页交互模型只能是浏览器提交数据给服务器,服务器做出响应重新返回一个页面,浏览器加载这个页面进行显示.早期前端没有编程式发送网 ...
- SPA(单页面应用)和MPA(多页面应用)
单页面应用 第一次进入页面时会请求一个html文件,刷新清除一下,切换到其他组件,此时路径也相应变化,但是并没有新的html文件请求,页面内容却变化了. 原理:js会感知到url的变化,通过这一点可以 ...
最新文章
- GPS经纬度算附近有什么 --- GeoHash核心原理解析
- Netty 系列一(核心组件和实例).
- springmvc 传参Required String parameter 'xxxx' is not present
- BOOST_TEST_TRAIT_SAME的用法实例
- 利用 exe4j 将 JAR 包制成免安装 JDK 的 EXE 文件
- java 自定义解码_[求助],java如何使用自定义注解对入参进行解密?
- 打孔怎么定位_电视机挂架怎么安装
- G1垃圾收集器之SATB
- 润乾单元格加html点击事件_报表输入页码翻页(润乾 V2018)
- 如何使用AOP改进.NET应用程序
- 模型操作_77个典型岗位员工胜任素质模型操作指导手册
- [转帖]我们是OIer、
- es 多索引联合查询_HBase二级索引设计思想
- 运用Android ROM Manager应用安装ClockworkMod Recovery的详细教程
- 数据库锁 与 事务隔离级别
- 像外行一样思考,像专家一样实践——科研成功之道(修订版)
- 计算机前置usb应用,usb前面不能用,教您解决电脑前置USB接口不能使用
- U3D DotH教程3
- 飞腾笔记本/银河麒麟桌面操作系统键盘无法使用
- 总结清楚浮动的几种方法
热门文章
- 包含头文件的问题之1.7编程基础之字符串 24:单词的长度
- php pathinfo()函数
- IP addresses in C#
- Javascript 的模块化编程及加载模块【转载+整理】
- 话里话外:企业ERP实施的前前后后(二)
- 理解 XML Schema:XML Schema 初步 (I)
- clark变换_电力变换器PWM原理与实践,p43页,空间矢量理解
- 自动建议下拉菜单_word排版技巧:如何撤销删除自动编号
- keras中Dense()和Flatten()不同
- Bots Inc宣布订购1000台比特币矿机,价值400万美元