Vue项目代码只执行一次:所有方案完整合集(Vue2+Vue3全覆盖)

更新日期: 2026-04-04 阅读: 34 标签: 代码

在Vue开发中,让某段代码只执行一次是非常高频的需求。不管是初始化请求接口、全局配置、监听触发一次,还是执行初始化逻辑,核心诉求都是:确保指定代码在指定时机只会被执行一次,后续无论组件刷新、数据变化、页面重渲染都不会重复执行。

Vue中针对代码只执行一次有精准的、分场景的最优方案。下面按使用频率和优先级从高到低排序,覆盖99%的业务场景,区分Vue2和Vue3两种主流写法(选项式/组合式),代码可直接复制使用。


一、重要前提:先明确执行时机

所有方案的选择,只取决于一个问题:你希望这段只执行一次的代码,在什么时机执行?

Vue中只有3类核心执行时机,对应不同最优方案:

时机1:组件初始化完成后,永久只执行一次(99%的业务场景,最常用)

场景举例:组件加载后只请求一次初始化接口、只创建一次定时器或监听事件、只初始化一次第三方插件(echarts、地图)、只执行一次数据初始化逻辑

核心特点:组件从创建到销毁,这段代码只会执行1次

时机2:监听某个变量变化时,只执行1次

场景举例:监听父组件传入的props变量、监听自身的data或ref变量,变量第一次变化时执行代码,后续再变化不再执行

时机3:整个项目运行期间,永久只执行1次

场景举例:项目启动后只请求一次用户信息或全局配置、只初始化一次全局过滤器或全局指令、只执行一次全局初始化逻辑

核心特点:项目从启动到关闭,这段代码全程只会执行1次,哪怕切换所有页面、刷新组件都不会重复执行


二、方案一:组件初始化后永久执行一次(最优首选)

核心原理

利用Vue的生命周期钩子函数。Vue组件有固定的生命周期,其中初始化阶段的钩子函数,组件的一生只会触发一次。这是Vue官方设计的、专门用来执行组件初始化一次性逻辑的方案,无任何副作用、性能最优、写法最简单,优先级最高。

Vue2写法(选项式API)

Vue2中,组件初始化阶段有两个核心钩子,都满足只执行一次:

  • created:组件数据初始化完成就执行(DOM还未渲染),适合纯数据逻辑(请求接口、数据处理)

  • mounted:组件DOM渲染完成、挂载到页面后执行,适合所有逻辑(既可以处理数据,也可以操作DOM)

推荐用mounted,兼容所有场景。

<template>
  <div>Vue2 组件</div>
</template>

<script>
export default {
  data() {
    return {
      msg: "Vue2 只执行一次"
    };
  },
  mounted() {
    console.log("这段代码,组件一辈子只会执行一次");
    this.initData();
  },
  methods: {
    initData() {
      console.log("执行初始化逻辑,只执行一次");
      // 示例:请求初始化接口
      // this.$axios.get("/api/init").then(res => {})
    }
  }
};
</script>

Vue3写法

写法一:Vue3选项式API(和Vue2完全一致)

<script>
export default {
  mounted() {
    console.log("Vue3选项式 - 代码只执行一次");
    this.initData();
  },
  methods: {
    initData() {
      // 你的一次性逻辑
    }
  }
};
</script>

写法二:Vue3组合式API script setup(官方推荐)

<template>
  <div>Vue3 组件</div>
</template>

<script setup>
import { onMounted } from 'vue'

onMounted(() => {
  console.log("Vue3组合式 - 这段代码只执行一次");
  initData();
})

const initData = () => {
  console.log("Vue3 初始化逻辑执行");
  // 你的业务代码:请求接口、初始化插件等
}
</script>

补充说明:Vue3的<script setup>里的顶层代码(不在任何函数内的代码),也是组件初始化时执行一次,效果等价于created。

<script setup>
console.log("这段顶层代码,也是组件初始化只执行一次");
import { onMounted } from 'vue'
onMounted(() => { console.log("挂载后执行一次") })
</script>

三、方案二:监听变量变化时只执行1次代码(精准场景)

适用场景

监听props变量、自身变量、全局变量,变量第一次发生变化时执行一次指定代码,后续再变化不再执行。

场景举例:父组件传值给子组件,子组件监听到值变化后只请求一次接口;监听搜索关键词,只在关键词第一次变化时执行一次过滤逻辑。

方式1:监听中执行后立即取消监听(最推荐,逻辑最优雅)

核心原理:给监听绑定一个停止监听函数,在监听的回调函数中执行完代码后立即调用这个函数停止监听,后续变量再变化监听就失效了。

Vue2写法

<script>
export default {
  props: {
    initVal: { type: Number, default: 0 }
  },
  watch: {
    initVal(newVal) {
      console.log("监听变量变化,执行一次代码");
      this.doSomething(newVal);
      this.$watch('initVal', () => {}).unwatch();
    }
  },
  methods: {
    doSomething(val) {
      // 你的业务逻辑,只执行一次
    }
  }
};
</script>

Vue3组合式写法

<script setup>
import { watch } from 'vue'

const props = defineProps({ initVal: { type: Number, default: 0 } })

const stopWatch = watch(
  () => props.initVal,
  (newVal) => {
    console.log("Vue3监听变量,只执行一次");
    doSomething(newVal);
    stopWatch();
  }
)

const doSomething = (val) => {
  // 你的代码
}
</script>

方式2:通过开关变量做标记控制执行(万能通用)

核心原理:定义一个布尔类型的开关变量(比如isExecuted),默认false。在监听回调中先判断开关是否为false,如果是则执行代码并把开关设为true。后续变量变化时开关是true,就不会再执行。

优点:逻辑简单、易理解、无任何API依赖、Vue2/Vue3通用、可灵活控制开关。

Vue3组合式写法

<script setup>
import { ref, watch } from 'vue'

const props = defineProps({ initVal: Number })
const isExecuted = ref(false)

watch(
  () => props.initVal,
  (newVal) => {
    if (!isExecuted.value) {
      console.log("通过开关标记,代码只执行一次");
      doSomething(newVal);
      isExecuted.value = true;
    }
  }
)

const doSomething = (val) => {
  // 业务逻辑
}
</script>

Vue2写法

<script>
export default {
  data() {
    return { isExecuted: false }
  },
  props: { initVal: Number },
  watch: {
    initVal(newVal) {
      if (!this.isExecuted) {
        this.doSomething(newVal);
        this.isExecuted = true;
      }
    }
  },
  methods: {
    doSomething(val) {
      // 业务逻辑
    }
  }
};
</script>

四、方案三:整个项目运行期间代码只执行一次(全局一次性逻辑)

适用场景

代码从项目启动到项目关闭全程只会执行1次,哪怕切换所有页面、刷新所有组件、路由跳转无数次,都绝对不会重复执行。

场景举例:项目初始化时只请求一次用户信息(token、个人资料)、只初始化一次全局配置(主题、语言)、只注册一次全局插件或全局指令、只执行一次全局埋点逻辑。

方案:在main.js中直接执行(最优首选)

核心原理:main.js是Vue项目的入口文件,项目启动时只会加载和执行一次main.js中的代码,后续所有操作都不会再重新执行这个文件。

Vue2的main.js写法

// src/main.js
import Vue from 'vue'
import App from './App.vue'
import router from './router'
import store from './store'

Vue.config.productionTip = false

// 这里的代码,项目运行期间只执行一次
console.log("全局一次性逻辑:项目启动时执行");
// 示例1:请求全局用户信息
Vue.prototype.$axios.get("/api/getUserInfo").then(res => {
  Vue.prototype.$userInfo = res.data;
})
// 示例2:初始化全局配置
localStorage.setItem("theme", "light");

new Vue({
  router,
  store,
  render: h => h(App)
}).$mount('#app')

Vue3的main.js写法

// src/main.js
import { createApp } from 'vue'
import App from './App.vue'
import router from './router'
import pinia from './stores'

// 这里的代码,项目运行期间只执行一次
console.log("Vue3全局一次性逻辑");
// 示例:请求全局配置接口
fetch("/api/globalConfig").then(res => res.json()).then(data => {
  console.log("全局配置初始化完成");
})

const app = createApp(App)
app.use(router).use(pinia).mount('#app')

五、补充:Vue模板中内容只渲染一次(v-once指令)

适用场景

不是代码逻辑只执行一次,而是模板中的DOM内容只渲染一次,后续组件重渲染时这个DOM不会再重新渲染,能优化性能。

核心用法

Vue提供了内置指令v-once,给模板标签加上这个指令后,该标签及其子标签的内容只会被渲染一次,后续无论数据怎么变化都不会再更新渲染。

<template>
  <div>
    <div>普通渲染:{{ msg }}</div>
    <div v-once>只渲染一次:{{ msg }}</div>
    <button @click="msg = '新内容'">修改msg</button>
  </div>
</template>

<script setup>
import { ref } from 'vue'
const msg = ref("初始内容")
</script>

效果:点击按钮修改msg,普通标签会显示新内容,带v-once的标签永远显示初始内容。


六、所有方案优先级和场景总结

核心优先级排序(从上到下,优先选上面的)

  1. 组件内代码只执行一次 → 用mounted(Vue2)或onMounted(Vue3),99%场景首选

  2. 监听变量变化只执行一次 → 用执行后取消监听或开关标记,精准场景首选

  3. 全局代码只执行一次 → 直接在main.js中写代码,全局场景唯一最优解

  4. 模板内容只渲染一次 → 用v-once指令,模板优化专用

避坑提醒

  1. 不要用computed实现代码只执行一次。computed是计算属性,侧重计算值,不是执行逻辑,且会随依赖变化重复执行

  2. 不要滥用全局变量标记。组件内的一次性逻辑用生命周期就够了,全局标记只用于全局场景

  3. Vue3的<script setup>顶层代码虽然也只执行一次,但推荐用onMounted。逻辑更清晰,且能操作DOM,无任何限制


一句话速记

组件内一次用mounted,监听一次关监听,全局一次写main,模板一次v-once。

本文内容仅供个人学习、研究或参考使用,不构成任何形式的决策建议、专业指导或法律依据。未经授权,禁止任何单位或个人以商业售卖、虚假宣传、侵权传播等非学习研究目的使用本文内容。如需分享或转载,请保留原文来源信息,不得篡改、删减内容或侵犯相关权益。感谢您的理解与支持!

链接: https://fly63.com/article/detial/13588

相关推荐

减少嵌套,降低代码复杂度

减少嵌套会让代码可读性更好,同时也能更容易的找出bug,开发人员可以更快的迭代,程序也会越来越稳定。简化代码,让编程更轻松!

js高亮显示关键词_页面、搜索关键词高亮显示

页面实现关键词高亮显示:在项目期间遇到一个需求,就是搜索关键词时需要高亮显示,主要通过正则匹配来实现页面关键词高亮显示。在搜索结果中高亮显示关键词:有一组关键词数组,在数组中筛选出符合关键字的内容并将关键字高亮

Js代码压缩工具推荐

JavaScript 代码压缩是指去除源代码里的所有不必要的字符,而不改变其功能的过程。这些不必要的字符通常包括空格字符,换行字符,注释以及块分隔符等用来增加可读性的代码,但并不需要它来执行。

源代码是什么意思

源代码(也称源程序),是指一系列人类可读的计算机语言指令。 在现代程序语言中,源代码可以是以书籍或者磁带的形式出现,但最为常用的格式是文本文件,这种典型格式的目的是为了编译出计算机程序。

tinymce与prism代码高亮实现及汉化的配置

TinyMCE是一个轻量级的基于浏览器的所见即所得编辑器,由JavaScript写成。它对IE6+和Firefox1.5+都有着非常良好的支持。功能方强大,并且功能配置灵活简单。另一特点是加载速度非常快的。

Google内部在代码质量上的实践

良好的编程习惯涉及到很多方面,但在软件行业内,大多数的公司或组织都不会把良好的编程习惯列为主要关注点。 例如,具有可读性和可维护性的代码比编写好的测试代码或使用正确的工具更有意义,前者的意义在于可以让代码更易于理解和修改。

接手代码太烂,要不要辞职?

朋友发表了一条说说:入职新公司,从重构代码到放弃”,我就问他怎么了?他说,刚进一家新公司,接手代码太烂,领导让我先熟悉业务逻辑,然后去修复之前项目中遗留的bug,实在不行就重构

网站加入收藏、设为首页Js代码(兼容各种浏览器)

这里虽然说是兼容,但是有些浏览器的设置就是不支持用js来把页面设为首页,加入收藏夹,只能让用户手动去在浏览器或者按键去设置这些功能,这里说的兼容是指当浏览器有这个设置的时候js会有提示

提升JavaScript代码质量的最佳实践

在JavaScript编程中,代码质量优化是一项重要的技能。它可以帮助我们提高代码的可读性、可维护性和性能。本文将通过一些实际优化过程中的案例,展示如何通过一些技巧和最佳实践,使我们的代码更加优雅。

javascript代码语句结束要不要加分号?

在 C 语言中,分号是语句结束的标志,在语句结束的地方一定要以分号结束。而 JavaScript 的分号却是可选的,若语句都各占一行,则可以省略分号。avaScript 中的 ASI 机制,允许我们省略分号。ASI 机制不是说在解析过程中解析器自动把分号添加到代码中

点击更多...

内容以共享、参考、研究为目的,不存在任何商业目的。其版权属原作者所有,如有侵权或违规,请与小编联系!情况属实本人将予以删除!