Vue项目刷新页面出现ReferenceError: navigator is not defined报错如何解决
问题根因
从错误栈的vue-server-renderer可以判断你的项目使用了Vue服务端渲染(SSR)架构,navigator是浏览器端专属API,Node.js运行环境下不存在该对象。
你从根路径跳转至/test/路径时走的是客户端路由切换逻辑,全程在浏览器环境执行,所以不会报错;直接刷新/test/路径时,请求会先触发服务端渲染流程,Node环境执行isMobile方法时找不到navigator对象,就抛出了该错误。
修复方案
方案1:修改isMobile方法,增加环境判断
最简单的修复方式是在执行判断前先校验navigator是否存在,服务端渲染阶段直接返回默认值即可:
isMobile() { // 非浏览器环境直接返回false if (typeof navigator === 'undefined') return false return /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(navigator.userAgent) }
如果你的项目是基于Nuxt.js搭建的,也可以用process.client判断是否是客户端环境:
isMobile() { if (!process.client) return false return /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(navigator.userAgent) }
方案2:将判断逻辑放在客户端生命周期执行,避免重复计算
直接在模板中调用方法会导致每次组件重渲染都执行一次正则判断,性能较低,你可以用响应式变量存储判断结果,仅在客户端挂载完成后赋值:
// data中定义响应式变量 data() { return { isMobile: false } }, // mounted仅在客户端执行 mounted() { this.isMobile = /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(navigator.userAgent) }
模板直接使用变量即可:
<template #default> <u-modal v-model="reportUser" :min-width="isMobile ? '150px' : '700px'" :max-width="isMobile ? '300px' : '1000px'"> <report-user-form :reportUser="reportUser" :user="user" @close="reportUser=false"/> </u-modal> </template>
方案3:使用client-only标签包裹客户端专属组件
如果是Nuxt项目,你还可以用client-only标签包裹模态框组件,告诉服务端渲染阶段跳过该部分内容,仅在客户端加载完成后渲染:
<template #default> <client-only> <u-modal v-model="reportUser" :min-width="isMobile() == true ? '150px' : '700px'" :max-width="isMobile() == true ? '300px' : '1000px'"> <report-user-form :reportUser="reportUser" :user="user" @close="reportUser=false"/> </u-modal> </client-only> </template>
内容的提问来源于stack exchange,提问作者Mark
相关产品推荐
相关产品推荐

