Skip to content

Commit

Permalink
fix(tests): use bus in tests
Browse files Browse the repository at this point in the history
  • Loading branch information
annacv committed Mar 25, 2024
1 parent 10b23e8 commit 37f3fa5
Show file tree
Hide file tree
Showing 7 changed files with 122 additions and 66 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@ import { mount, Wrapper } from '@vue/test-utils';
import Vue from 'vue';
import { getDataTestSelector, installNewXPlugin } from '../../../__tests__/utils';
import BaseIdModalClose from '../base-id-modal-close.vue';
import { bus } from '../../../plugins/index';
import { dummyCreateEmitter } from '../../../__tests__/bus.dummy';

/**
* Renders the {@link BaseIdModalClose} with the provided options.
Expand All @@ -13,6 +15,9 @@ function renderBaseIdModalClose({
id = 'random',
template = `<BaseIdModalClose modalId="${id}" v-bind="$attrs"/>`
}: RenderBaseIdModalCloseOptions = {}): RenderBaseIdModalCloseAPI {
// Making bus not repeat subjects
jest.spyOn(bus, 'createEmitter' as any).mockImplementation(dummyCreateEmitter.bind(bus) as any);

const [, localVue] = installNewXPlugin();
const containerWrapper = mount(
{
Expand All @@ -32,15 +37,20 @@ function renderBaseIdModalClose({
modalId,
async click() {
await wrapper.trigger('click');
jest.runAllTimers();
}
};
}

describe('testing Close Button component', () => {
beforeAll(() => {
jest.useFakeTimers();
});

it("emits UserClickedCloseModal with the component's id as payload", async () => {
const { wrapper, modalId, click } = renderBaseIdModalClose();
const { modalId, click } = renderBaseIdModalClose();
const listener = jest.fn();
wrapper.vm.$x.on('UserClickedCloseModal').subscribe(listener);
bus.on('UserClickedCloseModal').subscribe(listener);

await click();

Expand Down Expand Up @@ -69,20 +79,22 @@ describe('testing Close Button component', () => {
});

const listener = jest.fn();
wrapper.vm.$x.on('UserClickedCloseModal').subscribe(listener);
bus.on('UserClickedCloseModal').subscribe(listener);

await click();

expect(listener).toHaveBeenCalledTimes(0);

wrapper.find(getDataTestSelector('custom-close-modal')).trigger('click');
jest.runAllTimers();

expect(listener).toHaveBeenCalledTimes(1);
expect(listener).toHaveBeenCalledWith(modalId);
});
});

interface RenderBaseIdModalCloseOptions {
/** Id of the modal to close. */
/** The id of the modal to close. */
id?: string;
/** The template to render. */
template?: string;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@ import { mount, Wrapper } from '@vue/test-utils';
import Vue from 'vue';
import { getDataTestSelector, installNewXPlugin } from '../../../__tests__/utils';
import BaseIdModalOpen from '../base-id-modal-open.vue';
import { bus } from '../../../plugins/x-bus';
import { dummyCreateEmitter } from '../../../__tests__/bus.dummy';

/**
* Renders the {@link BaseIdModalOpen} with the provided options.
Expand All @@ -13,6 +15,9 @@ function renderBaseIdModalOpen({
id = 'myModal',
template = `<BaseIdModalOpen modalId="${id}" v-bind="$attrs"/>`
}: RenderBaseIdModalOpenOptions = {}): RenderBaseIdModalOpenAPI {
// Making bus not repeat subjects
jest.spyOn(bus, 'createEmitter' as any).mockImplementation(dummyCreateEmitter.bind(bus) as any);

const [, localVue] = installNewXPlugin();
const containerWrapper = mount(
{
Expand All @@ -21,7 +26,10 @@ function renderBaseIdModalOpen({
},
template
},
{ propsData: { modalId: id }, localVue }
{
propsData: { modalId: id },
localVue
}
);

const wrapper = containerWrapper.findComponent(BaseIdModalOpen);
Expand All @@ -32,15 +40,20 @@ function renderBaseIdModalOpen({
modalId,
async click() {
await wrapper.trigger('click');
jest.runAllTimers();
}
};
}

describe('testing Open Button component', () => {
beforeAll(() => {
jest.useFakeTimers();
});

it("emits UserClickedOpenModal with the component's id as payload", async () => {
const { wrapper, modalId, click } = renderBaseIdModalOpen();
const { modalId, click } = renderBaseIdModalOpen();
const listener = jest.fn();
wrapper.vm.$x.on('UserClickedOpenModal').subscribe(listener);
bus.on('UserClickedOpenModal').subscribe(listener);

await click();

Expand Down Expand Up @@ -69,20 +82,22 @@ describe('testing Open Button component', () => {
});

const listener = jest.fn();
wrapper.vm.$x.on('UserClickedOpenModal').subscribe(listener);
bus.on('UserClickedOpenModal').subscribe(listener);

await click();

expect(listener).toHaveBeenCalledTimes(0);

wrapper.find(getDataTestSelector('custom-open-modal')).trigger('click');
jest.runAllTimers();

expect(listener).toHaveBeenCalledTimes(1);
expect(listener).toHaveBeenCalledWith(modalId);
});
});

interface RenderBaseIdModalOpenOptions {
/** Id of the modal to open. */
/** The id of the modal to open. */
id?: string;
/** The template to render. */
template?: string;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,8 @@ import { Result } from '@empathyco/x-types';
import { mount, WrapperArray } from '@vue/test-utils';
import { createResultStub } from '../../../__stubs__/results-stubs.factory';
import { getDataTestSelector, installNewXPlugin } from '../../../__tests__/utils';
import { XComponentBusAPI } from '../../../plugins/x-plugin.types';
import BaseResultRating from '../base-result-rating.vue';
import { bus } from '../../../plugins/index';

const result = createResultStub('Product Test', {
rating: {
Expand Down Expand Up @@ -37,13 +37,17 @@ function renderBaseResultRating({
getEmptyIcons: (): WrapperArray<Vue> =>
wrapper.find(getDataTestSelector('rating-empty')).findAll(':scope > *'),
clickRating: async () => {
wrapper.findComponent(BaseResultRating).trigger('click');
return await wrapper.vm.$nextTick();
},
on: wrapper.vm.$x.on
await wrapper.findComponent(BaseResultRating).trigger('click');
jest.runAllTimers();
}
};
}

describe('testing BaserResultRating component', () => {
beforeAll(() => {
jest.useFakeTimers();
});

it('renders the default icons a number of times based on the max prop', () => {
const { getFilledIcons, getEmptyIcons } = renderBaseResultRating({
template: `<BaseResultRating :result="result" :max="10" />`,
Expand Down Expand Up @@ -76,27 +80,32 @@ describe('testing BaserResultRating component', () => {
});

it('emits event when clicked with the result as payload', async () => {
const { on, clickRating } = renderBaseResultRating({
const { clickRating } = renderBaseResultRating({
template: `<BaseResultRating :result="result" :max="10" />`,
result
});
const eventListener = jest.fn();
on('UserClickedAResultRating').subscribe(eventListener);
bus.on('UserClickedAResultRating').subscribe(eventListener);

await clickRating();
expect(eventListener).toHaveBeenCalledWith(result);
});
});

interface RenderBaseResultRatingOptions {
/** The template to render. */
template: string;
/** The result with the rating to be interacted with. */
result: Result;
}

interface RenderBaseResultRatingApi {
/** Retrieves the wrapper with the main html content. */
getHtml: () => string;
/** Retrieves the wrapper that matches the rating filled icons. */
getFilledIcons: () => WrapperArray<Vue>;
/** Retrieves the wrapper that matches the rating empty icons. */
getEmptyIcons: () => WrapperArray<Vue>;
/** Clicks the rating icons and waits for the view to update. */
clickRating: () => Promise<void>;
on: XComponentBusAPI['on'];
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,45 +5,51 @@ import { getDataTestSelector, installNewXPlugin } from '../../../../__tests__/ut
import { getXComponentXModuleName, isXComponent } from '../../../../components/x-component.utils';
import { WireMetadata } from '../../../../wiring/wiring.types';
import { default as NextQueryComponent } from '../next-query.vue';
import { XComponentAPI } from '../../../../plugins/x-plugin.types';
import { bus } from '../../../../plugins/index';
import { dummyCreateEmitter } from '../../../../__tests__/bus.dummy';

describe('testing next query item component', () => {
function renderNextQuery({
suggestion = createNextQueryStub('milk'),
template = '<NextQuery :suggestion="suggestion" />'
}: RenderNextQueryOptions = {}): RenderNextQueryAPI {
const [, localVue] = installNewXPlugin();
const wrapperTemplate = mount(
{
props: ['suggestion', 'highlightCurated'],
components: {
NextQuery: NextQueryComponent
},
template
},
{
localVue,
propsData: { suggestion }
}
);
const wrapper = wrapperTemplate.findComponent(NextQueryComponent);
const $x = wrapperTemplate.vm.$x;

return {
wrapper,
$x,
suggestion,
async clickNextQuery() {
wrapper.trigger('click');
await localVue.nextTick();
function renderNextQuery({
suggestion = createNextQueryStub('milk'),
template = '<NextQuery :suggestion="suggestion" />'
}: RenderNextQueryOptions = {}): RenderNextQueryAPI {
// Making bus not repeat subjects
jest.spyOn(bus, 'createEmitter' as any).mockImplementation(dummyCreateEmitter.bind(bus) as any);

const [, localVue] = installNewXPlugin();
const wrapperTemplate = mount(
{
props: ['suggestion', 'highlightCurated'],
components: {
NextQuery: NextQueryComponent
},
hasIsCuratedClass() {
return wrapper
.find(getDataTestSelector('next-query'))
.element.classList.contains('x-next-query--is-curated');
}
};
}
template
},
{
localVue,
propsData: { suggestion }
}
);
const wrapper = wrapperTemplate.findComponent(NextQueryComponent);

return {
wrapper,
suggestion,
async clickNextQuery() {
wrapper.trigger('click');
await localVue.nextTick();
},
hasIsCuratedClass() {
return wrapper
.find(getDataTestSelector('next-query'))
.element.classList.contains('x-next-query--is-curated');
}
};
}

describe('testing next query item component', () => {
beforeAll(() => {
jest.useFakeTimers();
});

it('is an XComponent and has an XModule', () => {
const { wrapper } = renderNextQuery();
Expand All @@ -52,10 +58,12 @@ describe('testing next query item component', () => {
});

it('emits UserSelectedANextQuery when a next query is selected', async () => {
const { clickNextQuery, suggestion, wrapper } = renderNextQuery();
const listener = jest.fn();
const { $x, clickNextQuery, suggestion, wrapper } = renderNextQuery();
$x.on('UserSelectedANextQuery', true).subscribe(listener);
bus.on('UserSelectedANextQuery', true).subscribe(listener);

await clickNextQuery();
jest.runAllTimers();

expect(listener).toHaveBeenCalled();
expect(listener).toHaveBeenCalledWith({
Expand Down Expand Up @@ -111,17 +119,17 @@ describe('testing next query item component', () => {
interface RenderNextQueryOptions {
/** The next query data to render. */
suggestion?: NextQuery;
/** The template to render. Receives the `nextQuery` via prop, and has registered the
* {@link NextQueryComponent} as `NextQuery`. */
/**
* The template to render. Receives the `nextQuery` via prop, and has registered the
* {@link NextQueryComponent} as `NextQuery`.
*/
template?: string;
}

interface RenderNextQueryAPI {
/** The Vue testing utils wrapper for the {@link NextQueryComponent}. */
wrapper: Wrapper<Vue>;
/** The {@link XComponentAPI} used by the rendered {@link NextQueryComponent}. */
$x: XComponentAPI;
/** The rendered next query data. */
suggestion: NextQuery;
/** Clicks the next query and waits for the view to update. */
clickNextQuery: () => Promise<void>;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,11 @@ import Vuex, { Store } from 'vuex';
import { createPopularSearch } from '../../../../__stubs__/popular-searches-stubs.factory';
import { installNewXPlugin } from '../../../../__tests__/utils';
import { getXComponentXModuleName, isXComponent } from '../../../../components/x-component.utils';
import { XPlugin } from '../../../../plugins/x-plugin';
import { RootXStoreState } from '../../../../store/store.types';
import { WireMetadata } from '../../../../wiring/wiring.types';
import { popularSearchesXModule } from '../../x-module';
import PopularSearch from '../popular-search.vue';
import { bus } from '../../../../plugins/index';

function renderPopularSearch({
suggestion = createPopularSearch('baileys'),
Expand Down Expand Up @@ -38,11 +38,15 @@ function renderPopularSearch({
return {
wrapper: wrapper.findComponent(PopularSearch),
suggestion,
emitSpy: jest.spyOn(XPlugin.bus, 'emit')
emitSpy: jest.spyOn(bus, 'emit')
};
}

describe('testing popular-search component', () => {
beforeAll(() => {
jest.useFakeTimers();
});

it('is an XComponent that belongs to the popular searches', () => {
const { wrapper } = renderPopularSearch();
expect(isXComponent(wrapper.vm)).toEqual(true);
Expand Down
Loading

0 comments on commit 37f3fa5

Please sign in to comment.