Access This.$root In Vue.js 3 Setup()
Solution 1:
You could define global property in vue 3 :
app.config.globalProperties.appName= 'vue3'
With setup
(composition api) you could use getcurrentinstance to get access to that property:
import { getCurrentInstance } from'vue'
...
setup() {
const app= getCurrentInstance()
console.log(app.appContext.config.globalProperties.appName)
Since you're still able to use the options api you could simply do :
mounted(){
console.log(this.appName)
}
Solution 2:
It seems you need provide / inject. In your App.vue
:
import { provide } from'vue';
exportdefault {
setup() {
provide('appName', 'vue3')
}
}
Or provide
it with your app
:
const app = createApp(App);
app.mount('#app');
app.provide('appName', 'Vue3');
And then in any child component where you want to access this variable, inject
it:
import { inject } from'vue'exportdefault {
setup() {
const appName = inject('appName');
}
}
Solution 3:
If all you want is to replace {{ appName }}
in any any template with 'Vue 3'
(string), without having to import anything, the cleanest way would be using config.globalProperties, as suggested by other answers:
const app = createApp(App).mount('#app');
app.config.globalProperties.appName = 'Vue 3'
However, you should try not to overuse this pattern. It goes against the reusability and modularization principles which drove the development of Composition API.
The main reason why you should avoid polluting globalProperties
is because it serves as pollution field across Vue3 apps, so many plugin devs might decide to provide their plugin instance using it. (Obviously, nobody will ever name a plugin appName
, so you run no risk in this particular case).
The recommended alternative to globalization is exporting a useStuff()
function.
In your case:
exportfunctionuseAppName () { return'Vue 3' }
// or even:exportconstuseAppName = () => 'Vue 3'
In any component:
import { useAppName } from'@/path/to/function'
setup () {
const appName = useAppName()
return {
appName // make it available in template and hooks
}
}
The advantages:
- it uses the Composition API naming convention
- when sharing something more complex than a primitive (could be a module, a set of functions, a service, etc...) all types are inferred, out of the box. This is particularly useful in
setup()
functions. - you only expose and scope your
stuff
where you need it exposed, not in every single component of your app. Another advantage is: if you only need it insetup()
function, you don't have to expose it to template or hooks.
Example usage with a random (but real) plugin:
Create a plugin file (i.e: /plugins/gsap.ts
):
import gsap from'gsap'importScrollToPluginfrom'gsap/ScrollToPlugin'// configure the plugin globally
gsap.registerPlugin(ScrollToPlugin)
exportfunctionuseGsap () {
return gsap
}
In any component:
import { defineComponent } from'vue'import { useGsap } from'@/plugins/gsap'exportdefineComponent({
setup () {
const gsap = useGsap()
// gsap here is typed correctly (if the plugin has typings)// no need for castingreturn {
gsap // optionally provide it to hooks and template
} // if needed outside setup()
}
})
Solution 4:
For anyone wondering how they can simply access this
inside setup()
, one way is to set this
to a memoized variable in the created()
hook and use nextTick()
to access it:
const app = createApp(App);
app.config.globalProperties.$appName = 'Hello!';
<script>import { nextTick } from'vue';
let self;
exportdefault {
name: 'HelloWorld',
setup() {
nextTick(() =>console.log(self.$appName)); // 'Hello!'
},
created() {
self = this;
},
};
</script>
@Psidom's answer is better practice in my opinion, but, this is just another way.
Post a Comment for "Access This.$root In Vue.js 3 Setup()"