guestPaystack.spec.js 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111
  1. /* eslint-env jest */
  2. import Vue from 'vue'
  3. import GuestPaystack from '@/ui-refactor/views/signup/components/GuestPaystack'
  4. describe('Guest Paystack component', () => {
  5. let vm
  6. let script
  7. let resumeTransaction
  8. let originalPopup
  9. beforeEach(() => {
  10. originalPopup = window.PaystackPop
  11. resumeTransaction = jest.fn()
  12. window.PaystackPop = jest.fn(() => ({ resumeTransaction }))
  13. vm = new Vue({
  14. ...GuestPaystack,
  15. propsData: {
  16. paystackkey: 'pk_test_stub', email: 'test@example.invalid', amount: 873400,
  17. reference: 'test-reference', accessCode: 'test-access-code',
  18. callback: jest.fn(), close: jest.fn()
  19. }
  20. })
  21. const scripts = document.querySelectorAll('script[src="https://js.paystack.co/v2/inline.js"]')
  22. script = scripts[scripts.length - 1]
  23. })
  24. afterEach(() => {
  25. vm.$destroy()
  26. script.remove()
  27. window.PaystackPop = originalPopup
  28. })
  29. it('uses the inherited component with V2 and resumes only the server access code', async() => {
  30. expect(script).toBeDefined()
  31. const pending = vm.payWithPaystack()
  32. vm.payWithPaystack()
  33. expect(resumeTransaction).not.toHaveBeenCalled()
  34. script.onload()
  35. await pending
  36. expect(window.PaystackPop).toHaveBeenCalledTimes(1)
  37. expect(resumeTransaction).toHaveBeenCalledTimes(1)
  38. expect(resumeTransaction).toHaveBeenCalledWith('test-access-code', {
  39. onSuccess: expect.any(Function), onCancel: expect.any(Function), onError: expect.any(Function)
  40. })
  41. expect(resumeTransaction.mock.calls[0][1]).not.toHaveProperty('amount')
  42. expect(resumeTransaction.mock.calls[0][1]).not.toHaveProperty('reference')
  43. })
  44. it('forwards the successful transaction reference', async() => {
  45. script.onload()
  46. await vm.payWithPaystack()
  47. const response = { reference: 'test-reference' }
  48. resumeTransaction.mock.calls[0][1].onSuccess(response)
  49. expect(vm.callback).toHaveBeenCalledWith(response)
  50. expect(vm.opening).toBe(false)
  51. })
  52. it('opens checkout from the original component button', async() => {
  53. vm.$mount()
  54. expect(vm.$el.tagName).toBe('BUTTON')
  55. script.onload()
  56. vm.$el.click()
  57. await Promise.resolve()
  58. await Promise.resolve()
  59. expect(resumeTransaction).toHaveBeenCalledWith('test-access-code', expect.any(Object))
  60. })
  61. it('allows the same transaction to reopen after cancellation', async() => {
  62. script.onload()
  63. await vm.payWithPaystack()
  64. resumeTransaction.mock.calls[0][1].onCancel()
  65. expect(vm.close).toHaveBeenCalledTimes(1)
  66. expect(vm.opening).toBe(false)
  67. await vm.payWithPaystack()
  68. expect(resumeTransaction).toHaveBeenCalledTimes(2)
  69. expect(resumeTransaction.mock.calls.map(call => call[0])).toEqual(['test-access-code', 'test-access-code'])
  70. })
  71. it('reports SDK load failures and does not start a payment', async() => {
  72. const errorHandler = jest.fn()
  73. vm.$on('error', errorHandler)
  74. script.onerror()
  75. await vm.payWithPaystack()
  76. expect(errorHandler).toHaveBeenCalledWith(expect.any(Error))
  77. expect(resumeTransaction).not.toHaveBeenCalled()
  78. expect(vm.opening).toBe(false)
  79. })
  80. it('reports errors from the checkout and permits retrying the same transaction', async() => {
  81. const errorHandler = jest.fn()
  82. vm.$on('error', errorHandler)
  83. script.onload()
  84. await vm.payWithPaystack()
  85. const error = new Error('Test checkout failure')
  86. resumeTransaction.mock.calls[0][1].onError(error)
  87. expect(errorHandler).toHaveBeenCalledWith(error)
  88. expect(vm.opening).toBe(false)
  89. await vm.payWithPaystack()
  90. expect(resumeTransaction).toHaveBeenCalledTimes(2)
  91. })
  92. it('does not initialize a payment without an access code', async() => {
  93. const errorHandler = jest.fn()
  94. vm.$on('error', errorHandler)
  95. vm.accessCode = ''
  96. script.onload()
  97. await vm.payWithPaystack()
  98. expect(errorHandler).toHaveBeenCalledWith(expect.any(Error))
  99. expect(resumeTransaction).not.toHaveBeenCalled()
  100. })
  101. })