shop-customer.e2e-spec.ts 7.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222
  1. /* tslint:disable:no-non-null-assertion */
  2. import { CreateAddressInput, UpdateAddressInput, UpdateCustomerInput } from '@vendure/common/lib/generated-shop-types';
  3. import { AttemptLogin, GetCustomer } from '@vendure/common/lib/generated-types';
  4. import gql from 'graphql-tag';
  5. import path from 'path';
  6. import { ATTEMPT_LOGIN } from '../../../admin-ui/src/app/data/definitions/auth-definitions';
  7. import { CUSTOMER_FRAGMENT, GET_CUSTOMER } from '../../../admin-ui/src/app/data/definitions/customer-definitions';
  8. import { TEST_SETUP_TIMEOUT_MS } from './config/test-config';
  9. import { TestAdminClient, TestShopClient } from './test-client';
  10. import { TestServer } from './test-server';
  11. import { assertThrowsWithMessage } from './utils/assert-throws-with-message';
  12. describe('Shop customers', () => {
  13. const shopClient = new TestShopClient();
  14. const adminClient = new TestAdminClient();
  15. const server = new TestServer();
  16. let customer: GetCustomer.Customer;
  17. beforeAll(async () => {
  18. const token = await server.init({
  19. productsCsvPath: path.join(__dirname, 'fixtures/e2e-products-full.csv'),
  20. customerCount: 2,
  21. });
  22. await shopClient.init();
  23. await adminClient.init();
  24. // Fetch the first Customer and store it as the `customer` variable.
  25. const { customers } = await adminClient.query(gql`
  26. query {
  27. customers {
  28. items {
  29. id
  30. }
  31. }
  32. }
  33. `);
  34. const result = await adminClient.query<GetCustomer.Query, GetCustomer.Variables>(GET_CUSTOMER, {
  35. id: customers.items[0].id,
  36. });
  37. customer = result.customer!;
  38. }, TEST_SETUP_TIMEOUT_MS);
  39. afterAll(async () => {
  40. await server.destroy();
  41. });
  42. it(
  43. 'updateCustomer throws if not logged in',
  44. assertThrowsWithMessage(async () => {
  45. const input: UpdateCustomerInput = {
  46. firstName: 'xyz',
  47. };
  48. await shopClient.query(UPDATE_CUSTOMER, { input });
  49. }, 'You are not currently authorized to perform this action'),
  50. );
  51. it(
  52. 'createCustomerAddress throws if not logged in',
  53. assertThrowsWithMessage(async () => {
  54. const input: CreateAddressInput = {
  55. streetLine1: '1 Test Street',
  56. countryCode: 'GB',
  57. };
  58. await shopClient.query(CREATE_ADDRESS, { input });
  59. }, 'You are not currently authorized to perform this action'),
  60. );
  61. it(
  62. 'updateCustomerAddress throws if not logged in',
  63. assertThrowsWithMessage(async () => {
  64. const input: UpdateAddressInput = {
  65. id: 'T_1',
  66. streetLine1: 'zxc',
  67. };
  68. await shopClient.query(UPDATE_ADDRESS, { input });
  69. }, 'You are not currently authorized to perform this action'),
  70. );
  71. it(
  72. 'deleteCustomerAddress throws if not logged in',
  73. assertThrowsWithMessage(async () => {
  74. await shopClient.query(DELETE_ADDRESS, { id: 'T_1' });
  75. }, 'You are not currently authorized to perform this action'),
  76. );
  77. describe('logged in Customer', () => {
  78. let addressId: string;
  79. beforeAll(async () => {
  80. await shopClient.query<AttemptLogin.Mutation, AttemptLogin.Variables>(ATTEMPT_LOGIN, {
  81. username: customer.emailAddress,
  82. password: 'test',
  83. rememberMe: false,
  84. });
  85. });
  86. it('updateCustomer works', async () => {
  87. const input: UpdateCustomerInput = {
  88. firstName: 'xyz',
  89. };
  90. const result = await shopClient.query(UPDATE_CUSTOMER, { input });
  91. expect(result.updateCustomer.firstName).toBe('xyz');
  92. });
  93. it('createCustomerAddress works', async () => {
  94. const input: CreateAddressInput = {
  95. streetLine1: '1 Test Street',
  96. countryCode: 'GB',
  97. };
  98. const { createCustomerAddress } = await shopClient.query(CREATE_ADDRESS, { input });
  99. expect(createCustomerAddress).toEqual({
  100. id: 'T_3',
  101. streetLine1: '1 Test Street',
  102. country: {
  103. code: 'GB',
  104. },
  105. });
  106. addressId = createCustomerAddress.id;
  107. });
  108. it('updateCustomerAddress works', async () => {
  109. const input: UpdateAddressInput = {
  110. id: addressId,
  111. streetLine1: '5 Test Street',
  112. countryCode: 'AT',
  113. };
  114. const result = await shopClient.query(UPDATE_ADDRESS, { input });
  115. expect(result.updateCustomerAddress.streetLine1).toEqual('5 Test Street');
  116. expect(result.updateCustomerAddress.country.code).toEqual('AT');
  117. });
  118. it(
  119. 'updateCustomerAddress fails for address not owned by Customer',
  120. assertThrowsWithMessage(async () => {
  121. const input: UpdateAddressInput = {
  122. id: 'T_2',
  123. streetLine1: '1 Test Street',
  124. };
  125. await shopClient.query(UPDATE_ADDRESS, { input });
  126. }, 'You are not currently authorized to perform this action'),
  127. );
  128. it('deleteCustomerAddress works', async () => {
  129. const result = await shopClient.query(DELETE_ADDRESS, { id: 'T_3' });
  130. expect(result.deleteCustomerAddress).toBe(true);
  131. });
  132. it(
  133. 'deleteCustomerAddress fails for address not owned by Customer',
  134. assertThrowsWithMessage(async () => {
  135. await shopClient.query(DELETE_ADDRESS, { id: 'T_2' });
  136. }, 'You are not currently authorized to perform this action'),
  137. );
  138. it(
  139. 'updatePassword fails with incorrect current password',
  140. assertThrowsWithMessage(async () => {
  141. await shopClient.query(UPDATE_PASSWORD, { old: 'wrong', new: 'test2' });
  142. }, 'The credentials did not match. Please check and try again'),
  143. );
  144. it('updatePassword works', async () => {
  145. const response = await shopClient.query(UPDATE_PASSWORD, { old: 'test', new: 'test2' });
  146. expect(response.updateCustomerPassword).toBe(true);
  147. // Log out and log in with new password
  148. const loginResult = await shopClient.asUserWithCredentials(customer.emailAddress, 'test2');
  149. expect(loginResult.user.identifier).toBe(customer.emailAddress);
  150. });
  151. });
  152. });
  153. const CREATE_ADDRESS = gql`
  154. mutation CreateAddress($input: CreateAddressInput!) {
  155. createCustomerAddress(input: $input) {
  156. id
  157. streetLine1
  158. country {
  159. code
  160. }
  161. }
  162. }
  163. `;
  164. const UPDATE_ADDRESS = gql`
  165. mutation UpdateAddress($input: UpdateAddressInput!) {
  166. updateCustomerAddress(input: $input) {
  167. streetLine1
  168. country {
  169. code
  170. }
  171. }
  172. }
  173. `;
  174. const DELETE_ADDRESS = gql`
  175. mutation DeleteAddress($id: ID!) {
  176. deleteCustomerAddress(id: $id)
  177. }
  178. `;
  179. const UPDATE_CUSTOMER = gql`
  180. mutation UpdateCustomer($input: UpdateCustomerInput!) {
  181. updateCustomer(input: $input) {
  182. ...Customer
  183. }
  184. }
  185. ${CUSTOMER_FRAGMENT}
  186. `;
  187. const UPDATE_PASSWORD = gql`
  188. mutation UpdatePassword($old: String!, $new: String!) {
  189. updateCustomerPassword(currentPassword: $old, newPassword: $new)
  190. }
  191. `;