I'm having a difficult time mocking a composable inside of a component.
Looking to see if a function from the composable was called after a button was clicked.
The composable is quite simple:
export default function useForm() {
const form = ref({})
const submit = () => {
console.log('submit this amazing form')
}
return {
form,
submit,
}
}
The component is also quite simple:
<template>
<form>
<input v-model="form.name" type="text" />
<button class="submit-button" @click="submit">Submit</button>
</form>
</template>
<script setup>
import useForm from '@/composable/useForm'
const { form, submit } = useForm()
</script>
Now lets test!
Component.spec.js:
import { mount } from '@vue/test-utils'
import Component from '@/component/Component.vue'
vi.mock('@/composables/useForm.js', async (importOriginal) => {
const composable = await importOriginal()
return {
...composable,
submit: vi.fn(),
}
})
describe('Component', () => {
let wrapper
beforeEach(() => {
wrapper = mount(Component)
})
it('should call submit function when button is clicked', async () => {
await wrapper.find('button.submit-button').trigger('click')
const spy = vi.spyOn(wrapper.vm, 'submit')
expect(spy).toHaveBeenCalled() // This does not work
})
})
I don't need to call the function, just determine that it was called. The wrapper object doesn't seem to have the submit available and the mock doesn't seem to help.
Any help would be appreciated.
EDIT:
I did get something to work with doMock:
import { mount } from '@vue/test-utils'
import BaseForm from '../BaseForm.vue'
describe('BaseForm', () => {
it('submits form', async () => {
vi.doMock('../../composables/useForm.ts', () => ({
submit: vi.fn()
}))
const wrapper = mount(BaseForm, {})
const spy = vi.spyOn(wrapper.vm, 'submit')
await wrapper.find('button').trigger('click')
expect(spy).toHaveBeenCalled()
})
})
It seems that submit is now part of the Components (I'm going to say the wrong thing here) 'structure' and now can be referenced with wrapper.vm.