Search code examples
unit-testingvue.jsvue-test-utils

How to write a unit test with data fetching, that alters data based on respone in vuejs?


I am trying to write a unit test for a function that does an async call, but it doesnt seem to alter the data prop, maybe I am doing something wrong.

Check the code below:

getSomething() {
  MyService.getThis().then(
    response => {
    this.status = true;
  }
).catch(error => {})
}

TestCase:

describe('test', () => {
  beforeEach(() => {
// To ignore the created hook, but this doesnt work, any idea?
  spyOn(CustomerData, 'created');
  spyOn(MyService, 'getThis').and.returnValue(Promise.resolve(list));
});

wrapper = shallowMount(MyComponent, {
  propsData: {
    data: {}
  },
});

it('should work', () => {
  wrapper.vm.getSomething();
  expect(wrapper.vm.status).toBeTruthy();
    });
  });
}

The status should be true, but it is false, but if I print the value of status in the getSomething() function it is indeed true. I have no idea what the issue can be.

update:

In the test case I wrote

it('should work', async () => {
await wrapper.vm.getSomething();
expect(wrapper.vm.status).toBeTruthy();
}

and this seems to work. Is this a good way to solve it? Would love to hear other solutions.

Also I am very interested if it is possible to ignore the created hook, I havent been able to figure that out yet.


Solution

  • Code that running inside getSomething() is asynchronous. MyService.getThis() returns promise, and its execution takes time, in case if you fetching some data from remote serivce.

    So first of all you need to return promise from getSomething()

    getSomething() {
      return MyService.getThis()
        .then(response => { this.status = true; })
        .catch(error => {})
    }
    

    And inside the test you need to return promise outside, to let jest know that your test is asynchronous.

    it('should work', () => {
      return wrapper.vm.getSomething().then(() => {
        expect(wrapper.vm.status).toBeTruthy();
      });
    });
    

    Or as you mentioned in the edited part you can use async version:

    it('should work', async () => {
      await getSomething();
      expect(wrapper.vm.status).toBeTruthy();
    });