Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How can I call VueJS method in jest of typescript?

I'm writing test code in VueCLI with TypeScript and Jest.

I called Vue file's method to test the method.

However, an error has occurred as follows.

HelloWorld.vue:

<template>
    <div class="hello">
    </div>
</template>

<script lang="ts">
import { Component, Prop, Vue } from 'vue-property-decorator';

@Component
export default class HelloWorld extends Vue {
    public testMethod() {
        return true;
    }
}
</script>

<style scoped lang="scss">
</style>

example.spec.ts:

import { shallowMount } from '@vue/test-utils';
import HelloWorld from '@/components/HelloWorld.vue';

describe('HelloWorld.vue', () => {
    it('testMethod', () => {
        const wrapper = shallowMount(HelloWorld, {
            propsData: { 'test' },
        });
        expect(wrapper.testMethod()).toBeTruthy();
    });
});

An error occurred after unit test command execution.

tests/unit/example.spec.ts:9:20 - error TS2551: Property 'testMethod' does not exist on type 'Wrapper<CombinedVueInstance<Vue, object, object, object, Record<never, any>>>'. Did you mean 'setMethods'?
9 expect(wrapper.testMethod()).toBeTruthy();

Why can't the test call the methods in Vue JS?

like image 792
Passionate Engineer Avatar asked Apr 03 '19 13:04

Passionate Engineer


People also ask

Can I use Vue with typescript?

Using Vue.js with TypeScript Vue.js is an amazing, lightweight, and progressive frontend framework. Since Vue.js is flexible, users are not forced to use TypeScript. And unlike Angular, older versions of Vue did not have proper support for TypeScript.

How to test if a function is called in jest?

The key is using jests spyOn method on the object's prototype. It should be like this: const spy = jest.spyOn (Component.prototype, 'methodName'); const wrapper = mount (<Component {...props} />); wrapper.instance ().methodName (); expect (spy).toHaveBeenCalled (); As found here e.g.: Test if function is called react and enzyme

What is the difference between Vue-TS and T in Vue?

That means components imported in .vue are typed correctly while components imported in .ts are not. To be available typed components in .ts, we should use TypeScript plugin vue-ts-plugin or generate .d.ts for each .vue file by using vuetype.

How to add typed components to a VUE project?

To be available typed components in .ts, we should use TypeScript plugin vue-ts-plugin or generate .d.ts for each .vue file by using vuetype. But they are still experimental and might not be able to be used in practical projects.


2 Answers

try this way

 expect(wrapper.vm.testMethod).toBe(true);
like image 136
Tony Tom Avatar answered Nov 11 '22 11:11

Tony Tom


The issue has to do with the type being associated with your const wrapper. I had the same problem and solved for this by saying:

let wrapper: any
...
wrapper = shallowMount(HelloWorld, {
            propsData: { 'test' },
        });

This allowed me to then make references to defined data/variables and methods of the component like so:

wrapper.vm.data
wrapper.vm.method()

Even better would be to define an interface for your component to extend which would allow TypeScript to understand the methods available to the instance, rather than taking the easy way out of typing as any. There's an answer to another question here on Stack Overflow that dives into that approach.

like image 35
Mike Wright Avatar answered Nov 11 '22 10:11

Mike Wright