全局混入必须在main.js中createApp(App)后、app.mount()前注册,否则无效;onShareAppMessage等仅微信小程序生效,H5需单独处理;页面级定义会完全替换而非合并全局混入;mixins的data是独立副本,不共享状态。
全局混入必须在 main.js(或 main.ts)里注册,不能写在 App.vue 或页面里
很多人试过把 vue.mixin() 或 app.mixin() 放在 app.vue 的 setup 或 onlaunch 里,结果发现没生效——因为混入必须在 vue 实例创建前就注册,否则新创建的页面实例根本“看不见”它。
- uni-app(Vue3 + Vite)中,
app.mixin(shareMixin)必须放在createApp(App)之后、app.mount()之前 - uni-app(Vue2 + webpack)中,
Vue.mixin(shareMixin)要放在new Vue({ ... })创建实例之前 - 错误示范:
export default { onLaunch() { app.mixin(...) } }—— 此时所有页面实例早已创建完毕,混入无效
onShareAppMessage 和 onShareTimeline 是微信小程序专属生命周期,混入后只在小程序端起作用
这两个函数不是 Vue 生命周期,而是微信小程序平台提供的原生回调。uni-app 把它们“翻译”成可被混入的选项,但仅限于编译到微信小程序时才触发;H5、App 端不会调用,也不会报错,只是静默忽略。
- 混入里写了
onShareAppMessage,但 H5 页面点右上角没反应?正常,H5 没这个机制 - 想让 H5 也支持分享?得单独加
uni.shareAPI 或自定义按钮,和混入无关 - 小程序真机调试时发现分享按钮仍是灰色?检查是否已登录、是否在开发者工具里开了“调试基础库版本 ≥ 2.27.0”,以及
manifest.json中是否启用了 share 模块(虽非强制,但部分低版本需显式配置)
页面级定义会自动覆盖全局混入,但覆盖方式有陷阱
你可以在某个页面里重新写 onShareAppMessage,它确实会屏蔽全局混入里的同名函数——但注意:这不是“合并”,而是彻底替换。如果你只想改标题,却忘了返回 path 或 imageUrl,分享就会失败(卡片无图、跳转 404)。
- 安全做法:在页面里调用
this.$options.mixins[0].onShareAppMessage.call(this)获取全局默认值,再做局部修改 - 更推荐:混入里把默认值抽成方法,比如
getDefaultShare(),页面里return { ...this.getDefaultShare(), title: '新标题' } - 别直接 return 字面量对象,否则一旦全局混入后续加了新字段(如
extraData),你的页面就漏掉了
全局混入不等于全局状态共享,data 是每个组件独立的
有人以为在混入里写 data() { return { userInfo: null } },就能让所有页面共用一个 userInfo——错了。mixins 的 data 是函数,每次组件实例化时都会执行一次,生成全新副本。
- 需要跨页面共享数据?用
globalData(uni.getStorageSync)、Pinia,或app.config.globalProperties挂载工具方法 - 混入适合放“行为”(methods、生命周期)和“模板无关的状态结构”(比如统一的
loading、error字段),而不是真实业务数据 - 常见误用:在混入里
uni.login()一次,以为后续所有页面都能读到 token——实际每个页面的data里都是空的,token 没传递出去










