当前位置:首页 » 硬盘大全 » vue304缓存
扩展阅读
webinf下怎么引入js 2023-08-31 21:54:13
堡垒机怎么打开web 2023-08-31 21:54:11

vue304缓存

发布时间: 2023-01-10 08:18:54

A. 在Vue中如何缓存页面

在Vue中经常会遇到需要缓存页面的情况,如果不对Vue进行处理,那么Vue默认是不会缓存页面的。例如从菜谱列表界面进入到菜谱的详情页后,再从菜谱详情页中返回到菜谱列表页面中时,菜谱列表是不需要进行刷新的,一个是增加了不必要的网路请求,第二个是如推荐菜谱后台是实时推荐的,每次请求的数据都不一定一样的,这样在用户退出后甚至找不到之前的进入位置,造成了很不好的用户体验。类似的情况还有很多,那么如何在Vue中控制页面是否刷新呢?

设置方法

注意:以上两种方法都可以对路由是否缓存进行设置,如果不论何种情况下都要缓存页面,可以直接采用第一种方法,当然第二种情况同样可以满足情况;但是如果需要区分从不同页面跳转的情况来确定是否需要缓存的话,就需要用到第二种方法。

B. Vue组件传值及页面缓存问题

关于父组件的传值类型和props更多的定义详见官网 : vue官网
(2)子组件向父组件传值

(3)通过 chlidren等方法调取用层级关系的组件内的数据和方法。

有很多时候根据业务需求要在同级组件或页面间传值,此处提供以下几种方法作为参考:
(1)通过router-link进行跳转

(2) this.$router.push()
此方法同样是有path+query和name+params两种方式:

总结:使用query,传输的值会在url后面以参数的形式显示出来,可以刷新页面,数据不变,但会是页面路由过长;而params只要一刷新传递的参数就没了。
(3)LocalStorage缓存传值

注意:简单的小项目可以这么做,如果项目很大,建议直接用vuex。
(4)通过Vuex进行传值

(5)发布订阅模式(也叫eventBus或事件总线)
在Vue的原型上定义一个变量eventBus,所有所有Vue的实例或组件都将共享这个eventBus,可以用eventBus来发布自定义事件,然后在组件中用eventBus订阅自定义事件。就可以实现传值。

详细讲解可看 链接
(6)Vue.observable

index.vue组件中触发:

Vue中如何在切换组件过程中,将状态保存到内存中,防止DOM重新渲染,通俗的讲就是实现如何在一个页面输入部分数据后到了另一个页面再返回该页面,数据还在。
需求分析:Page1中录入信息,页面跳转带Page2,然后再返回Page1,之前Page1录入的信息还存在。

现在更改需求为:
首页是A页面
A页面跳转到B,B页面不需要缓存
B页面跳转到C,C页面不需要被缓存
C页面返回到B,B页面需要缓存
B页面返回到A,
A再次跳转到B

(1)此时思路是在每个路由的beforeRouteLeave(to, from, next)钩子中设置to.meta.keepAlive
beforeRouteLeave讲解

PageA页面:

PageB页面:

(2)用eventBus解决此问题
需要注意的一点是发布订阅第一次会无效,因为订阅的组件还没创建。解决方法就是首次进入pageB页面时接收pageA页面params里传递的参数。

C. 前端性能优化总结

gzip压缩

gzip压缩效率很高,可以达到70%的压缩率

//npm i -D compression-webpack-plugin 安装插件依赖
configureWebpack: config => {
const CompressionPlugin = require('compression-webpack-plugin')
config.plugins.push(new CompressionPlugin())
}

去掉console.log

生产环境中,不需要打印日志。通过对webpack进行配置,打包时自动去掉console.log

//npm i -D terser-webpack-plugin
configureWebpack:config =>{
const TerserPlugin = require('terser-webpack-pulugin')
config.optimzation.minimizer.push(
new TerserPlugin({
extractComments:false,
terserOptions:{compress:{drop_console:true}} //插件配置项 移除console
})
)
}

去除SourceMap

代码压缩后进行调bug定位将非常困难,于是引入sourcemap记录压缩前后的位置信息记录,当产生错误时直接定位到未压缩前的位置,将大大的方便我们调试。

sourcemap附带了很多信息,如果build需要生成sourcemap,将会大大降低build的速度,还会增加包的体积。

//vue 中
mole.exports = {
proctionSourceMap: false,
}

//react中
//打开webpack.config.prod.js
const shouldUseSourceMap = false

CDN

内容分发网络,它能够实时地根据网络流量和各节点的连接、负载状况以及到用户的距离和响应时间等综合信息将用户的请求重新导向离用户最近的服务节点上。其目的是使用户可就近取得所需内容,解决 Internet网络拥挤的状况,提高用户访问网站的响应速度。所以可以通过将资源部署在CDN上来提高响应速度,提高用户体验
预渲染

简单来说,就是将浏览器解析JavaScript动态渲染的工作,在打包阶段完成了(只构建了静态数据)。换个说法,在构建过程中,webpack通过使用prerender-spa-plugin插件生成静态结构的html

// 1、安装prerender-spa-plugin
npm install prerender-spa-plugin --save-dev

// 2、安装vue-meta-info
npm install vue-meta-info --save-dev

// 3、相关配置

// 预渲染配置:在webpack.prod.conf文件中加入
const PrerenderSPAPlugin = require('prerender-spa-plugin')
const Renderer = PrerenderSPAPlugin.PuppeteerRenderer

// 在 plugins 中加入
new PrerenderSPAPlugin({
// 生成文件的路径,也可以与webpakc打包的一致。
// 下面这句话非常重要!!!
// 这个目录只能有一级,如果目录层次大于一级,在生成的时候不会有任何错误提示,在预渲染的时候只会卡着不动。
staticDir: path.join(__dirname, '../dist'),

// 对应自己的路由文件,比如a有参数,就需要写成 /a/param1。
routes: ['/', '/first', '/second', '/third', '/fourth', '/userCenter/userFirst','/userCenter/userSecond','/userCenter/userThird'],

// 这个很重要,如果没有配置这段,也不会进行预编译
renderer: new Renderer({
inject: {
foo: 'bar'
},
// headless: false,
renderAfterDocumentEvent: 'render-event', // 在 main.js 中 document.dispatchEvent(new Event('render-event')),两者的事件名称要对应上。
args: ['--no-sandbox', '--disable-setuid-sandbox']
})
})

// 4、在main.js中
import MetaInfo from 'vue-meta-info'

new Vue({
el: '#app',
router,
components: { App },
template: '',
// 添加mounted,不然不会执行预编译
mounted () {
document.dispatchEvent(new Event('render-event'))
}
})

注意:路由模式必须为 history ,如果不设置 history 模式,也能运行和生成文件,每个 index.html 文件的内容都会是一样的
Service Worker

ServiceWorker 是运行在浏览器后台进程里的一段 JS,它可以做许多事情,比如拦截客户端的请求、向客户端发送消息、向服务器发起请求等等,其中最重要的作用之一就是离线资源缓存。

ServiceWorker 拥有对缓存流程丰富灵活的控制能力,当页面请求到 ServiceWorker 时,ServiceWorker 同时请求缓存和网络,把缓存的内容直接给用户,而后覆盖缓存

注意:需要HTTPS才能使用ServiceWorker
HTTP缓存

HTTP缓存一般分为两类:强缓存(本地缓存)、协商缓存(304缓存)

普通刷新会启用协商缓存

在地址栏输入网址、通过链接引入资源等情况下,浏览器才启用强缓存

强缓存(200)。本地缓存是最快速的一种缓存方式,只要资源还在缓存有效期内,浏览器就会直接在本地读取,不会请求服务端。在chrome控制台的Network选项中可以看到该请求返回200的状态码,并且Size显示from disk cache或from memory cache。强缓存可以通过设置两种 HTTP Header 实现:Expires 和 Cache-Control。

协商缓存(304)。协商缓存,顾名思义是经过浏览器与服务器之间协商过之后,在决定是否读取本地缓存,如果服务器通知浏览器可以读取本地缓存,会返回304状态码,并且协商过程很简单,只会发送头信息,不会发送响应体。

协商缓存可以通过设置两种 HTTP Header 实现:Last-Modified 和 ETag

首先在精确度上,Etag要优于Last-Modified

第二在性能上,Etag要逊于Last-Modified,毕竟Last-Modified只需要记录时间,而Etag需要服务器通过算法来计算出一个hash值

第三在优先级上,服务器校验优先考虑Etag

缓存优先级:Service Worker -> Memory Cache(内存缓存) -> Disk Cache(硬盘缓存) -> Push Cache(推送缓存)

Push Cache 只在会话(session)中存在,会话结束就被释放,而且缓存时间很短
HTTP2

HTTP2 四个新特性:

多路复用,无需多个TCP连接,因为其允许在单一的HTTP2连接上发起多重请求,因此可以不用依赖建立多个TCP连接。
二进制分帧,将所有要传输的消息采用二进制编码,并且会将信息分割为更小的消息块。
头部压缩,用HPACK技术压缩头部,减小报文大小
服务端推送,服务端可以在客户端发起请求前发送数据,换句话说,服务端可以对客户端的一个请求发送多个相应,并且资源可以正常缓存。

。。。。。。。。。。。。。

作者:MonkeySoft

篇幅有限更多请见扩展链接:http://www.mark-to-win.com/tutorial/50671.html

D. vue 缓存组件keep-alive

kee-alive 是 Vue 内置的一个组件, 可以使被包含的组件保留状态,或避免重新渲染 。也就是所谓的组件缓存

keep-alive是一个抽象的组件,缓存的组件不会被mounted,为此提供activated和deactivated钩子函数
在2.1.0 版本后keep-alive新加入了两个属性: include(包含的组件缓存生效) 与 exclude(排除的组件不缓存,优先级大于include) 。

keep-alive可以接收3个属性做为参数进行匹配对应的组件进行缓存:

include 包含的组件(可以为字符串,数组,以及正则表达式,只有匹配的组件会被缓存)

exclude 排除的组件(以为字符串,数组,以及正则表达式,任何匹配的组件都不会被缓存)

max 缓存组件的最大值(类型为字符或者数字,可以控制缓存组件的个数)

配合router使用

1.keep-alive 先匹配被包含组件的 name 字段,如果 name 不可用,则匹配当前组件 components 配置中的注册名称。
2.keep-alive 不会在函数式组件中正常工作,因为它们没有缓存实例。
3.当匹配条件同时在 include 与 exclude 存在时,以 exclude 优先级最高(当前vue 2.4.2 version)。比如:包含于排除同时匹配到了组件A,那组件A不会被缓存。
4.包含在 keep-alive 中,但符合 exclude ,不会调用activated和 deactivated。

参考 https://juejin.cn/post/6844903918313406472
参考 https://www.imooc.com/article/302879

E. 如何解决h5、vue、uniapp等项目缓存问题

我们再开发web项目时,经常会遇到修改了css、js、html等静态文件,并部署到服务器之后。使用浏览器进行访问的时候,发现并没有什么变化,这就是静态缓存。我们应该如何处理静态缓存呢?首先我们先了解什么是静态缓存。

html文件添加Expires时间

CDN是静态缓存加速最典型的代表。CDN技术并不是一门新的技术,它是基于传统 nginx、squid、varnish 等 web 缓存技术,结合 DNS 智能解析的静态缓存加速技术。

方式二:

uniapp解决缓存的方式与vue一样,但是uniapp兼容了很多平台,所以修改vue.config.js又不太一样。如果uniapp根目录下面没有vue.config.js,则新建vue.config.js文件即可。

F. vue页面缓存设置,动态设置页面缓存

情景:A页面—>B页面—>C页面,A页面去B页面期望B页面不缓存,B页面去C页面时,期望B页面可以被缓存。(实际场景可以是:A为首页,B为列表页,C为详情页,B滚动翻页后,从C返回B,记录滚动位置。)
通过路由访问钩子设置B页面的keepAlive为true或者false。
离开路由后,判断to.name是否是A的路由名,是的话设置为false,否则设置为true。注意B页面的keepAlive要设置为true。

2.通过vuex结合路由的includes功能以及路由钩子函数实现。(推荐,实现起来优雅)
3.声明一个初始化页面状态,内部变量的函数,从a 页面进入执行初始化函数,其余情况不执行。视图依赖数据驱动,所以可以实现效果。

G. vue 路由缓存

在写一个移动端项目时遇到了一个问题,每一个tab栏所对应的页面被封装成一个组件进行

复用,结果会导致他们共用一个滚动条。解决办法是给这个子组件加固定的高度(例如

height:100vh),同时加一个属性overflow-y:auto,这样就可以解决这个问题。之后发现每当进

入主页中任意一篇文章再退出时,页面重新加载渲染了,之前的文章消失了,所有在这里想到

了路由缓存。

先说一下keep-alive的属性和用法。

Props

用法

<keep-alive> 包裹动态组件时,会缓存不活动的组件实例,而不是销毁它们。

<keep-alive> 是一个抽象组件:它自身不会渲染一个 DOM 元素,也不会出现在组件的父组件链中。

当组件在 <keep-alive> 内被切换,它的 activated 和 deactivated 这两个生命周期钩子函数将会被对应执行。

(只有被<keep-alive>包裹的组件才具有这两个钩子函数)

其实不太建议使用include的,因为如果多个组件中都包括include中匹配到的组件,想单独

的让其中某个组件缓存是不太方便的。所以可以在分发路由时,在需要缓存的路由中把额外标

记的属性写在meta中,如图1。

使用的时候可以在根组件中通过$route.meta.keepAlive取到该值,然后进行v-if判断即可,如图

2,这样使用起来相对灵活一点。

使用keep-alive缓存路由后,已经解决了主要问题,但是有新的问题出现。缓存过的组件重

新被激活时不会记录滚动条的状态,默认置顶,所以应该监听这个被复用的组件的onscroll事

件,动态记录滚动条的位置状态,然后重新赋值给scrollTop(如果还想优化最好给滚动事件来

一个防抖处理)。那么问题来了,应该在何时重新赋值呢?上面用法中提到了当组件在<keep-

alive> 内被切换时会触发activated这个钩子函数,所以应在这里赋值。

H. vue 不是路由跳转的页面怎么缓存

vue缓存主要四种方式:

  1. 使用vuex

  2. 存放在cookie中

  3. 存放在localStorage或者sessionStorage中

  4. 存放在路由集合中