index.spec.tsx 5.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193
  1. import {
  2. act,
  3. renderGlobalModal,
  4. screen,
  5. userEvent,
  6. waitForElementToBeRemoved,
  7. } from 'sentry-test/reactTestingLibrary';
  8. import {closeModal, openModal} from 'sentry/actionCreators/modal';
  9. import ModalStore from 'sentry/stores/modalStore';
  10. describe('GlobalModal', function () {
  11. beforeEach(() => {
  12. jest.resetAllMocks();
  13. ModalStore.reset();
  14. });
  15. it('uses actionCreators to open and close Modal', async function () {
  16. renderGlobalModal();
  17. act(() => openModal(() => <div data-test-id="modal-test">Hi</div>));
  18. expect(screen.getByTestId('modal-test')).toBeInTheDocument();
  19. act(() => closeModal());
  20. await waitForElementToBeRemoved(screen.queryByTestId('modal-test'));
  21. expect(screen.queryByTestId('modal-test')).not.toBeInTheDocument();
  22. });
  23. it('calls onClose handler when close button is clicked', async function () {
  24. renderGlobalModal();
  25. const closeSpy = jest.fn();
  26. act(() =>
  27. openModal(
  28. ({Header}) => (
  29. <div id="modal-test">
  30. <Header closeButton>Header</Header>Hi
  31. </div>
  32. ),
  33. {onClose: closeSpy}
  34. )
  35. );
  36. await userEvent.click(screen.getByRole('button', {name: 'Close Modal'}));
  37. expect(closeSpy).toHaveBeenCalled();
  38. });
  39. it('calls onClose handler when modal is clicked out of', async function () {
  40. renderGlobalModal();
  41. const closeSpy = jest.fn();
  42. act(() =>
  43. openModal(
  44. ({Header}) => (
  45. <div id="modal-test">
  46. <Header closeButton>Header</Header>Hi
  47. </div>
  48. ),
  49. {onClose: closeSpy}
  50. )
  51. );
  52. await userEvent.click(screen.getByTestId('modal-backdrop'));
  53. expect(closeSpy).toHaveBeenCalled();
  54. });
  55. it('calls onClose handler when escape key is pressed', async function () {
  56. renderGlobalModal();
  57. const closeSpy = jest.fn();
  58. act(() =>
  59. openModal(
  60. ({Header}) => (
  61. <div id="modal-test">
  62. <Header closeButton>Header</Header>Hi
  63. </div>
  64. ),
  65. {onClose: closeSpy}
  66. )
  67. );
  68. expect(screen.getByText('Hi')).toBeInTheDocument();
  69. await userEvent.keyboard('{Escape}');
  70. expect(closeSpy).toHaveBeenCalled();
  71. });
  72. it('calls onClose handler when closeModal prop is called', async function () {
  73. renderGlobalModal();
  74. const closeSpy = jest.fn();
  75. act(() =>
  76. openModal(({closeModal: cm}) => <button onClick={cm}>Yo</button>, {
  77. onClose: closeSpy,
  78. })
  79. );
  80. await userEvent.click(screen.getByRole('button', {name: 'Yo'}));
  81. expect(closeSpy).toHaveBeenCalled();
  82. });
  83. it("ignores click out with closeEvents: 'escape-key'", async function () {
  84. const {waitForModalToHide} = renderGlobalModal();
  85. const closeSpy = jest.fn();
  86. act(() =>
  87. openModal(
  88. ({Header}) => (
  89. <div data-test-id="modal-test">
  90. <Header closeButton>Header</Header>Hi
  91. </div>
  92. ),
  93. {closeEvents: 'escape-key', onClose: closeSpy}
  94. )
  95. );
  96. expect(screen.getByTestId('modal-test')).toBeInTheDocument();
  97. // Clicking outside of modal doesn't close
  98. await userEvent.click(screen.getByTestId('modal-backdrop'));
  99. expect(screen.getByTestId('modal-test')).toBeInTheDocument();
  100. expect(closeSpy).not.toHaveBeenCalled();
  101. // Pressing escape _does_ close
  102. await userEvent.keyboard('{Escape}');
  103. await waitForModalToHide();
  104. expect(closeSpy).toHaveBeenCalled();
  105. });
  106. it("ignores escape key with closeEvents: 'backdrop-click'", async function () {
  107. const {waitForModalToHide} = renderGlobalModal();
  108. const closeSpy = jest.fn();
  109. act(() =>
  110. openModal(
  111. ({Header}) => (
  112. <div data-test-id="modal-test">
  113. <Header closeButton>Header</Header>Hi
  114. </div>
  115. ),
  116. {closeEvents: 'backdrop-click', onClose: closeSpy}
  117. )
  118. );
  119. expect(screen.getByTestId('modal-test')).toBeInTheDocument();
  120. // Pressing escape doesn't close
  121. await userEvent.keyboard('{Escape}');
  122. expect(screen.getByTestId('modal-test')).toBeInTheDocument();
  123. expect(closeSpy).not.toHaveBeenCalled();
  124. // Clicking outside of modal _does_ close
  125. await userEvent.click(screen.getByTestId('modal-backdrop'));
  126. expect(closeSpy).toHaveBeenCalled();
  127. await waitForModalToHide();
  128. });
  129. it("ignores backdrop click and escape key when with closeEvents: 'none'", async function () {
  130. const {waitForModalToHide} = renderGlobalModal();
  131. const closeSpy = jest.fn();
  132. act(() =>
  133. openModal(
  134. ({Header}) => (
  135. <div data-test-id="modal-test">
  136. <Header closeButton>Header</Header>Hi
  137. </div>
  138. ),
  139. {closeEvents: 'none', onClose: closeSpy}
  140. )
  141. );
  142. expect(screen.getByTestId('modal-test')).toBeInTheDocument();
  143. // Clicking outside of modal doesn't close
  144. await userEvent.click(screen.getByTestId('modal-backdrop'));
  145. expect(closeSpy).not.toHaveBeenCalled();
  146. // Pressing escape doesn't close
  147. await userEvent.keyboard('{Escape}');
  148. expect(closeSpy).not.toHaveBeenCalled();
  149. // Clicking an explicit close button does close
  150. await userEvent.click(screen.getByRole('button', {name: 'Close Modal'}));
  151. expect(closeSpy).toHaveBeenCalled();
  152. await waitForModalToHide();
  153. });
  154. });