Welcome to mirror list, hosted at ThFree Co, Russian Federation.

gitlab.com/gitlab-org/gitlab-foss.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'spec/frontend/vue_shared/components/awards_list_spec.js')
-rw-r--r--spec/frontend/vue_shared/components/awards_list_spec.js213
1 files changed, 213 insertions, 0 deletions
diff --git a/spec/frontend/vue_shared/components/awards_list_spec.js b/spec/frontend/vue_shared/components/awards_list_spec.js
new file mode 100644
index 00000000000..bb3e60ab9e2
--- /dev/null
+++ b/spec/frontend/vue_shared/components/awards_list_spec.js
@@ -0,0 +1,213 @@
+import { shallowMount } from '@vue/test-utils';
+import AwardsList from '~/vue_shared/components/awards_list.vue';
+
+const createUser = (id, name) => ({ id, name });
+const createAward = (name, user) => ({ name, user });
+
+const USERS = {
+ root: createUser(1, 'Root'),
+ ada: createUser(2, 'Ada'),
+ marie: createUser(3, 'Marie'),
+ jane: createUser(4, 'Jane'),
+ leonardo: createUser(5, 'Leonardo'),
+};
+
+const EMOJI_SMILE = 'smile';
+const EMOJI_OK = 'ok_hand';
+const EMOJI_THUMBSUP = 'thumbsup';
+const EMOJI_THUMBSDOWN = 'thumbsdown';
+const EMOJI_A = 'a';
+const EMOJI_B = 'b';
+const EMOJI_CACTUS = 'cactus';
+const EMOJI_100 = '100';
+
+const TEST_AWARDS = [
+ createAward(EMOJI_SMILE, USERS.ada),
+ createAward(EMOJI_OK, USERS.ada),
+ createAward(EMOJI_THUMBSUP, USERS.ada),
+ createAward(EMOJI_THUMBSDOWN, USERS.ada),
+ createAward(EMOJI_SMILE, USERS.jane),
+ createAward(EMOJI_OK, USERS.jane),
+ createAward(EMOJI_OK, USERS.leonardo),
+ createAward(EMOJI_THUMBSUP, USERS.leonardo),
+ createAward(EMOJI_THUMBSUP, USERS.marie),
+ createAward(EMOJI_THUMBSDOWN, USERS.marie),
+ createAward(EMOJI_THUMBSDOWN, USERS.root),
+ createAward(EMOJI_OK, USERS.root),
+ // Test that emoji list preserves order of occurrence, not alphabetical order
+ createAward(EMOJI_CACTUS, USERS.root),
+ createAward(EMOJI_A, USERS.marie),
+ createAward(EMOJI_B, USERS.root),
+];
+const TEST_ADD_BUTTON_CLASS = 'js-test-add-button-class';
+
+describe('vue_shared/components/awards_list', () => {
+ let wrapper;
+
+ afterEach(() => {
+ wrapper.destroy();
+ wrapper = null;
+ });
+
+ const createComponent = (props = {}) => {
+ if (wrapper) {
+ throw new Error('There should only be one wrapper created per test');
+ }
+
+ wrapper = shallowMount(AwardsList, { propsData: props });
+ };
+ const matchingEmojiTag = name => expect.stringMatching(`gl-emoji data-name="${name}"`);
+ const findAwardButtons = () => wrapper.findAll('[data-testid="award-button"');
+ const findAwardsData = () =>
+ findAwardButtons().wrappers.map(x => {
+ return {
+ classes: x.classes(),
+ title: x.attributes('data-original-title'),
+ html: x.find('[data-testid="award-html"]').element.innerHTML,
+ count: Number(x.find('.js-counter').text()),
+ };
+ });
+ const findAddAwardButton = () => wrapper.find('.js-add-award');
+
+ describe('default', () => {
+ beforeEach(() => {
+ createComponent({
+ awards: TEST_AWARDS,
+ canAwardEmoji: true,
+ currentUserId: USERS.root.id,
+ addButtonClass: TEST_ADD_BUTTON_CLASS,
+ });
+ });
+
+ it('matches snapshot', () => {
+ expect(wrapper.element).toMatchSnapshot();
+ });
+
+ it('shows awards in correct order', () => {
+ expect(findAwardsData()).toEqual([
+ {
+ classes: ['btn', 'award-control'],
+ count: 3,
+ html: matchingEmojiTag(EMOJI_THUMBSUP),
+ title: 'Ada, Leonardo, and Marie',
+ },
+ {
+ classes: ['btn', 'award-control', 'active'],
+ count: 3,
+ html: matchingEmojiTag(EMOJI_THUMBSDOWN),
+ title: 'You, Ada, and Marie',
+ },
+ {
+ classes: ['btn', 'award-control'],
+ count: 2,
+ html: matchingEmojiTag(EMOJI_SMILE),
+ title: 'Ada and Jane',
+ },
+ {
+ classes: ['btn', 'award-control', 'active'],
+ count: 4,
+ html: matchingEmojiTag(EMOJI_OK),
+ title: 'You, Ada, Jane, and Leonardo',
+ },
+ {
+ classes: ['btn', 'award-control', 'active'],
+ count: 1,
+ html: matchingEmojiTag(EMOJI_CACTUS),
+ title: 'You',
+ },
+ {
+ classes: ['btn', 'award-control'],
+ count: 1,
+ html: matchingEmojiTag(EMOJI_A),
+ title: 'Marie',
+ },
+ {
+ classes: ['btn', 'award-control', 'active'],
+ count: 1,
+ html: matchingEmojiTag(EMOJI_B),
+ title: 'You',
+ },
+ ]);
+ });
+
+ it('with award clicked, it emits award', () => {
+ expect(wrapper.emitted().award).toBeUndefined();
+
+ findAwardButtons()
+ .at(2)
+ .trigger('click');
+
+ expect(wrapper.emitted().award).toEqual([[EMOJI_SMILE]]);
+ });
+
+ it('shows add award button', () => {
+ const btn = findAddAwardButton();
+
+ expect(btn.exists()).toBe(true);
+ expect(btn.classes(TEST_ADD_BUTTON_CLASS)).toBe(true);
+ });
+ });
+
+ describe('with numeric award', () => {
+ beforeEach(() => {
+ createComponent({
+ awards: [createAward(EMOJI_100, USERS.ada)],
+ canAwardEmoji: true,
+ currentUserId: USERS.root.id,
+ });
+ });
+
+ it('when clicked, it emits award as number', () => {
+ expect(wrapper.emitted().award).toBeUndefined();
+
+ findAwardButtons()
+ .at(0)
+ .trigger('click');
+
+ expect(wrapper.emitted().award).toEqual([[Number(EMOJI_100)]]);
+ });
+ });
+
+ describe('with no awards', () => {
+ beforeEach(() => {
+ createComponent({
+ awards: [],
+ canAwardEmoji: true,
+ });
+ });
+
+ it('has no award buttons', () => {
+ expect(findAwardButtons().length).toBe(0);
+ });
+ });
+
+ describe('when cannot award emoji', () => {
+ beforeEach(() => {
+ createComponent({
+ awards: [createAward(EMOJI_CACTUS, USERS.root.id)],
+ canAwardEmoji: false,
+ currentUserId: USERS.marie.id,
+ });
+ });
+
+ it('does not have add button', () => {
+ expect(findAddAwardButton().exists()).toBe(false);
+ });
+ });
+
+ describe('with no user', () => {
+ beforeEach(() => {
+ createComponent({
+ awards: TEST_AWARDS,
+ canAwardEmoji: false,
+ });
+ });
+
+ it('disables award buttons', () => {
+ const buttons = findAwardButtons();
+
+ expect(buttons.length).toBe(7);
+ expect(buttons.wrappers.every(x => x.classes('disabled'))).toBe(true);
+ });
+ });
+});