Code前端首页关于Code前端联系我们

Vue3 watch route.query怎么变化才生效?电商/筛选/分页场景常见避坑指南

terry 4小时前 阅读数 46 #Vue

最近整理项目库的时候,发现好多刚转Vue3的开发同学甚至是有1-2年Vue3经验的人,都踩过watch监听路由查询参数不生效的坑——比如电商搜索框换关键词、价格区间筛选、分页跳转后,页面还是之前的内容,控制台也没有报错,排查半天找不到原因。

今天就以问答的形式,把Vue3中监听route.query的所有关键点、常见场景、避坑方法都讲透,不管你是写列表页、筛选页还是带链接跳转带参的详情补充页,看完这篇应该都能解决问题。

为什么会出现watch route.query不生效的情况?

很多人第一反应都是“我明明用官方的useRoute拿到了query,用watch监听了,怎么没反应?”其实问题大多出在3个地方,第一个是监听的对象不对,第二个是没有开启深度监听或者immediate,第三个是路由懒加载或者组件复用的机制导致的。

首先说监听对象,在Vue3中,useRoute返回的是一个响应式对象,但route.query本身是一个嵌套的普通对象——如果你直接监听“route.query”本身,Vue只会检查这个对象的引用有没有变化,而不会检查里面的属性,比如你从“?page=1”改成“?page=2”,其实route.query这个对象的引用还是同一个,Vue3的浅监听(默认)就会忽略掉这个变化。

immediate选项,有些时候页面第一次加载时,query已经有值了——比如用户直接复制带筛选条件的链接进来,或者详情页的补充参数,这时候如果watch没有设置immediate: true,组件挂载时的第一次query变化(其实是初始赋值)是不会触发回调的,页面就只会显示默认内容,不会加载带参数据。

组件复用的问题,在Vue Router4中,默认情况下,当你在同一个路由路径下切换query或者params时,对应的组件是不会被销毁再重建的——比如你从“/list?page=1”跳到“/list?page=2”,List组件的mounted和unmounted都不会触发,只会触发beforeRouteUpdate(如果你用了组合式API的onBeforeRouteUpdate的话),这时候如果你的watch监听有问题,或者数据更新的逻辑写在mounted里,肯定不会生效。

怎么正确监听Vue3的route.query变化?

现在知道了原因,解决方法就很清晰了,而且有好几种方式,你可以根据自己的项目场景来选。

开启深度监听+immediate

这是最直接、最常用的方式,适合90%以上的场景——比如列表页的分页、搜索框的关键词实时搜索、价格区间、分类标签的切换。

具体的写法很简单,在组合式API的