summaryrefslogtreecommitdiff
path: root/spec/frontend/commons/nav/user_merge_requests_spec.js
blob: 4da6d53557a315bb73d98b01221a0a045fecc502 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
import {
  openUserCountsBroadcast,
  closeUserCountsBroadcast,
  refreshUserMergeRequestCounts,
} from '~/commons/nav/user_merge_requests';
import Api from '~/api';

jest.mock('~/api');

const TEST_COUNT = 1000;
const MR_COUNT_CLASS = 'merge-requests-count';

describe('User Merge Requests', () => {
  let channelMock;
  let newBroadcastChannelMock;

  beforeEach(() => {
    global.gon.current_user_id = 123;

    channelMock = {
      postMessage: jest.fn(),
      close: jest.fn(),
    };
    newBroadcastChannelMock = jest.fn().mockImplementation(() => channelMock);

    global.BroadcastChannel = newBroadcastChannelMock;
    setFixtures(`<div class="${MR_COUNT_CLASS}">0</div>`);
  });

  const findMRCountText = () => document.body.querySelector(`.${MR_COUNT_CLASS}`).textContent;

  describe('refreshUserMergeRequestCounts', () => {
    beforeEach(() => {
      Api.userCounts.mockReturnValue(
        Promise.resolve({
          data: { merge_requests: TEST_COUNT },
        }),
      );
    });

    describe('with open broadcast channel', () => {
      beforeEach(() => {
        openUserCountsBroadcast();

        return refreshUserMergeRequestCounts();
      });

      it('updates the top count of merge requests', () => {
        expect(findMRCountText()).toEqual(TEST_COUNT.toLocaleString());
      });

      it('calls the API', () => {
        expect(Api.userCounts).toHaveBeenCalled();
      });

      it('posts count to BroadcastChannel', () => {
        expect(channelMock.postMessage).toHaveBeenCalledWith(TEST_COUNT);
      });
    });

    describe('without open broadcast channel', () => {
      beforeEach(() => refreshUserMergeRequestCounts());

      it('does not post anything', () => {
        expect(channelMock.postMessage).not.toHaveBeenCalled();
      });
    });
  });

  describe('openUserCountsBroadcast', () => {
    beforeEach(() => {
      openUserCountsBroadcast();
    });

    it('creates BroadcastChannel that updates DOM on message received', () => {
      expect(findMRCountText()).toEqual('0');

      channelMock.onmessage({ data: TEST_COUNT });

      expect(findMRCountText()).toEqual(TEST_COUNT.toLocaleString());
    });

    it('closes if called while already open', () => {
      expect(channelMock.close).not.toHaveBeenCalled();

      openUserCountsBroadcast();

      expect(channelMock.close).toHaveBeenCalled();
    });
  });

  describe('closeUserCountsBroadcast', () => {
    describe('when not opened', () => {
      it('does nothing', () => {
        expect(channelMock.close).not.toHaveBeenCalled();
      });
    });

    describe('when opened', () => {
      beforeEach(() => {
        openUserCountsBroadcast();
      });

      it('closes', () => {
        expect(channelMock.close).not.toHaveBeenCalled();

        closeUserCountsBroadcast();

        expect(channelMock.close).toHaveBeenCalled();
      });
    });
  });
});