import { fireEvent, render, waitFor } from '@testing-library/react-native' import * as React from 'react' import { Text } from 'react-native' import { Provider } from 'react-redux' import { chooseCreateAccount, chooseRestoreAccount } from 'src/account/actions' import AppAnalytics from 'src/analytics/AppAnalytics' import { OnboardingEvents } from 'src/analytics/Events' import { getAppConfig } from 'src/appConfig' import { navigate } from 'src/navigator/NavigationService' import { Screens } from 'src/navigator/Screens' import { firstOnboardingScreen } from 'src/onboarding/steps' import Welcome from 'src/onboarding/welcome/Welcome' import { PublicAppConfig } from 'src/public/types' import { patchUpdateStatsigUser } from 'src/statsig' import { createMockStore } from 'test/utils' jest.mock('src/appConfig') jest.mock('src/onboarding/steps') jest.mock('src/statsig', () => ({ patchUpdateStatsigUser: jest.fn(), })) const mockGetAppConfig = jest.mocked(getAppConfig) const defaultConfig: PublicAppConfig = { registryName: 'test', displayName: 'test', deepLinkUrlScheme: 'test', } describe('Welcome', () => { beforeAll(() => { jest.spyOn(Date, 'now').mockImplementation(() => 123) jest.mocked(firstOnboardingScreen).mockReturnValue(Screens.PincodeSet) }) beforeEach(() => { jest.clearAllMocks() mockGetAppConfig.mockReturnValue(defaultConfig) }) describe('Welcome', () => { it('renders components', async () => { const store = createMockStore() const { getByTestId, queryByTestId } = render( ) expect(getByTestId('CreateAccountButton')).toBeTruthy() expect(getByTestId('RestoreAccountButton')).toBeTruthy() expect(queryByTestId('TermsCheckbox/unchecked')).toBeFalsy() expect(queryByTestId('TermsCheckbox/checked')).toBeFalsy() }) it('create updates statsig, fires action and navigates to terms screen for first time onboarding', async () => { const store = createMockStore() const { getByTestId } = render( ) fireEvent.press(getByTestId('CreateAccountButton')) await waitFor(() => expect(patchUpdateStatsigUser).toHaveBeenCalledWith({ custom: { startOnboardingTime: 123 }, }) ) expect(store.getActions()).toEqual([chooseCreateAccount(123)]) expect(navigate).toHaveBeenCalledTimes(1) expect(navigate).toHaveBeenCalledWith(Screens.RegulatoryTerms) expect(AppAnalytics.track).toHaveBeenCalledTimes(1) expect(AppAnalytics.track).toHaveBeenCalledWith(OnboardingEvents.create_account_start) }) it('create skips statsig update if not onboarding the first time', () => { const store = createMockStore({ account: { startOnboardingTime: 111, }, }) const { getByTestId } = render( ) fireEvent.press(getByTestId('CreateAccountButton')) expect(store.getActions()).toEqual([chooseCreateAccount(123)]) expect(navigate).toHaveBeenCalledTimes(1) expect(navigate).toHaveBeenCalledWith(Screens.RegulatoryTerms) expect(patchUpdateStatsigUser).not.toHaveBeenCalled() expect(AppAnalytics.track).toHaveBeenCalledTimes(1) expect(AppAnalytics.track).toHaveBeenCalledWith(OnboardingEvents.create_account_start) }) it('restore fires action and navigates to terms screen', () => { const store = createMockStore() const { getByTestId } = render( ) fireEvent.press(getByTestId('RestoreAccountButton')) expect(navigate).toHaveBeenCalledTimes(1) expect(navigate).toHaveBeenCalledWith(Screens.RegulatoryTerms) expect(store.getActions()).toEqual([chooseRestoreAccount()]) expect(AppAnalytics.track).toHaveBeenCalledTimes(1) expect(AppAnalytics.track).toHaveBeenCalledWith(OnboardingEvents.restore_account_start) }) it.each([ { buttonId: 'CreateAccountButton', action: chooseCreateAccount(123), event: OnboardingEvents.create_account_start, }, { buttonId: 'RestoreAccountButton', action: chooseRestoreAccount(), event: OnboardingEvents.restore_account_start, }, ])( '$buttonId goes to the onboarding screen if terms already accepted', ({ buttonId, action, event }) => { const store = createMockStore({ account: { acceptedTerms: true, startOnboardingTime: 111, }, }) const { getByTestId } = render( ) fireEvent.press(getByTestId(buttonId)) expect(firstOnboardingScreen).toHaveBeenCalled() expect(navigate).toHaveBeenCalledTimes(1) expect(navigate).toHaveBeenCalledWith(Screens.PincodeSet) expect(store.getActions()).toEqual([action]) expect(AppAnalytics.track).toHaveBeenCalledTimes(1) expect(AppAnalytics.track).toHaveBeenCalledWith(event) } ) it('shows a custom logo when configured', () => { mockGetAppConfig.mockReturnValue({ ...defaultConfig, themes: { default: { assets: { welcomeLogo: () => Custom Logo, }, }, }, }) const store = createMockStore() const { getByText } = render( ) expect(getByText('Custom Logo')).toBeTruthy() }) it('shows a custom background image when configured', () => { const customBackground = { uri: 'custom-background.png' } as any mockGetAppConfig.mockReturnValue({ ...defaultConfig, themes: { default: { assets: { welcomeBackgroundImage: customBackground, }, }, }, }) const store = createMockStore() const { UNSAFE_getByProps } = render( ) const backgroundImage = UNSAFE_getByProps({ source: customBackground }) expect(backgroundImage).toBeTruthy() }) }) })