'How to add third party functions to methods in Vue3
I am using Vue 3 to build an app with a third party library (Azure Communication Calling). I'm using the options API. My issue is that I need event handlers that call functions initialized by the third party library. The only way I can find to do this is to assign the entire object created by the third party constructor to Vue's component data. I realize this is not best practice (although it does work). Is there a better way?
I am initializing the Constructor in the Mounted hook. My event handlers need access to methods inside the object created in the Constructor. It seems like you should be able to assign event handlers in Mounted, or assign methods in Mounted. I can't get either of these ideas to work.
My template is like this:
<template>
<div>
<child-component @someEvent="doSomething">
</child-component>
<div>
The rest of the app goes here..
</div>
</div>
</template>
<script>
import {Constructor} from 'third-party-library'
import ChildComponent from './components/ChildComponent'
export default {
data() {
return {
complexObject: null
}
},
components: {
ChildComponent
},
mounted() {
this.complexObject = new Constructor()
},
methods: {
doSomething() {
this.complexObject.thirdPartyMethod()
}
}
}
</script>
Solution 1:[1]
I just thought you weren't supposed to put objects with their own methods in data. I thought data is only for primitive data types.
That's not true. It's acceptable to return non-primitives from data(). Normally, data() is used to specify properties intended for reactivity (e.g., in the template). However, you could also specify non-reactive data by Object.freeze-ing the property:
export default {
data() {
return {
complexObject: Object.freeze(new Constructor()) // non-reactive
}
},
}
Alternatively, you could attach the property in created():
export default {
data() {
return {
// complexObject: null, ? remove this
}
},
created() {
this.complexObject = new Constructor() ?
},
}
If using TypeScript, the downside here is there would be no type inference for the attached property.
Solution 2:[2]
Did you try to use mixins? https://vuejs.org/api/options-composition.html#mixins This way you can also use this mixin for other components too.
Solution 3:[3]
I solved this issue, in a similar way to Tony19's second suggestion. This turned out to be much simpler than I expected. Unless there is some reason why I should not create a new top-level property on a Vue component, this seems best.
export default {
complexObject: null,
mounted() {
this.complexObject = new Constructor()
},
}
The constructor does have to be in the mounted hook, BTW.
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 | tony19 |
| Solution 2 | gguney |
| Solution 3 |
