Skip to content

Commit

Permalink
Fix: only hide the welcome modal when client accept term and condition (
Browse files Browse the repository at this point in the history
  • Loading branch information
trankhacvy authored Jan 6, 2020
1 parent 8aef449 commit a3891ca
Show file tree
Hide file tree
Showing 9 changed files with 112 additions and 44 deletions.
14 changes: 13 additions & 1 deletion src/actions/__tests__/auth.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,9 @@ import {
authChangeLoginType,
authSetRefreshSession,
authClear,
toggleFirstLogin
checkFirstTimeLogin,
toggleFirstLogin,
userAcceptTermAndCondition
} from '../auth'
import ActionTypes from '../../constants/action-types'
import { LoginType, LoginSession, LoginMode } from '@reapit/cognito-auth'
Expand Down Expand Up @@ -62,8 +64,18 @@ describe('auth actions', () => {
expect(authClear().data).toEqual(undefined)
})

it('should create a checkFirstTimeLogin action', () => {
expect(checkFirstTimeLogin.type).toEqual(ActionTypes.CHECK_FIRST_TIME_LOGIN)
expect(checkFirstTimeLogin().data).toBeUndefined()
})

it('should create a toggleFirstLogin action', () => {
expect(toggleFirstLogin.type).toEqual(ActionTypes.TOGGLE_FIRST_LOGIN)
expect(toggleFirstLogin(true).data).toBeTruthy()
})

it('should create a userAcceptTermAndCondition action', () => {
expect(userAcceptTermAndCondition.type).toEqual(ActionTypes.USER_ACCEPT_TERM_AND_CONDITION)
expect(userAcceptTermAndCondition().data).toBeUndefined()
})
})
2 changes: 2 additions & 0 deletions src/actions/auth.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,4 +10,6 @@ export const authLogoutSuccess = actionCreator<void>(ActionTypes.AUTH_LOGOUT_SUC
export const authSetRefreshSession = actionCreator<RefreshParams>(ActionTypes.AUTH_SET_REFRESH_SESSION)
export const authChangeLoginType = actionCreator<LoginType>(ActionTypes.AUTH_CHANGE_LOGIN_TYPE)
export const authClear = actionCreator<void>(ActionTypes.AUTH_CLEAR)
export const checkFirstTimeLogin = actionCreator<void>(ActionTypes.CHECK_FIRST_TIME_LOGIN)
export const toggleFirstLogin = actionCreator<boolean>(ActionTypes.TOGGLE_FIRST_LOGIN)
export const userAcceptTermAndCondition = actionCreator<void>(ActionTypes.USER_ACCEPT_TERM_AND_CONDITION)
20 changes: 4 additions & 16 deletions src/components/pages/__tests__/client.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,9 +12,7 @@ import {
mapDispatchToProps,
handleAfterClose,
handleOnChange,
handleOnCardClick,
ClientMappedProps,
userAcceptTerm
handleOnCardClick
} from '../client'
import { addQuery } from '@/utils/client-url-params'
import { AppSummaryModel } from '@reapit/foundations-ts-definitions'
Expand Down Expand Up @@ -57,7 +55,7 @@ const props = (loading: boolean): ClientProps => ({
installationsFormState: 'PENDING',
installationsSetFormState: jest.fn(),
fetchAppDetail: jest.fn(),
setFirstLogin: jest.fn(),
userAcceptTermAndCondition: jest.fn(),
firstLogin: false,
...routerProps
})
Expand Down Expand Up @@ -105,7 +103,7 @@ describe('Client', () => {
setStateViewBrowse: jest.fn(),
installationsSetFormState: jest.fn(),
fetchAppDetail: jest.fn(),
setFirstLogin: jest.fn(),
userAcceptTermAndCondition: jest.fn(),
firstLogin: false,
...routerProps
}
Expand Down Expand Up @@ -136,7 +134,7 @@ describe('Client', () => {
setStateViewBrowse: jest.fn(),
installationsSetFormState: jest.fn(),
fetchAppDetail: jest.fn(),
setFirstLogin: jest.fn(),
userAcceptTermAndCondition: jest.fn(),
firstLogin: false,
...routerProps
}
Expand Down Expand Up @@ -231,16 +229,6 @@ describe('Client', () => {
})
})

describe('handle userAcceptTerm', () => {
it('should run correctly', () => {
const mockProps = {
setFirstLogin: jest.fn()
}
userAcceptTerm(mockProps)
expect(mockProps.setFirstLogin).toBeCalled()
})
})

describe('show welcome modal when firstLogin', () => {
it('should run correctly', () => {
const wrapper = mount(
Expand Down
19 changes: 5 additions & 14 deletions src/components/pages/client.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -17,13 +17,13 @@ import { appInstallationsSetFormState } from '@/actions/app-installations'
import ClientWelcomeMessageModal from '@/components/ui/client-welcome-message'
import { addQuery, getParamValueFromPath, hasFilterParams } from '@/utils/client-url-params'
import { setAppDetailModalStateBrowse } from '@/actions/app-detail-modal'
import { toggleFirstLogin } from '@/actions/auth'
import { userAcceptTermAndCondition } from '@/actions/auth'

export interface ClientMappedActions {
setStateViewBrowse: () => void
fetchAppDetail: (id: string, clientId: string) => void
installationsSetFormState: (formState: FormState) => void
setFirstLogin: (firstLogin: boolean) => void
userAcceptTermAndCondition: () => void
}

export interface ClientMappedProps {
Expand Down Expand Up @@ -61,10 +61,6 @@ export const handleInstallationDone = ({
}
}

export const userAcceptTerm = ({ setFirstLogin }) => {
setFirstLogin(false)
}

export type ClientProps = ClientMappedActions & ClientMappedProps & RouteComponentProps<{ page?: any }>

export const Client: React.FunctionComponent<ClientProps> = ({
Expand All @@ -78,7 +74,7 @@ export const Client: React.FunctionComponent<ClientProps> = ({
installationsFormState,
installationsSetFormState,
firstLogin = false,
setFirstLogin
userAcceptTermAndCondition
}) => {
const pageNumber =
!isNaN(Number(getParamValueFromPath(location.search, 'page'))) &&
Expand Down Expand Up @@ -143,12 +139,7 @@ export const Client: React.FunctionComponent<ClientProps> = ({
)}
</div>
<AppDetailModal visible={visible} afterClose={handleAfterClose({ setVisible })} />
<ClientWelcomeMessageModal
visible={firstLogin}
onAccept={() => {
userAcceptTerm({ setFirstLogin })
}}
/>
<ClientWelcomeMessageModal visible={firstLogin} onAccept={() => userAcceptTermAndCondition()} />
</ErrorBoundary>
)
}
Expand All @@ -165,7 +156,7 @@ export const mapDispatchToProps = (dispatch: any): ClientMappedActions => ({
setStateViewBrowse: () => dispatch(setAppDetailModalStateBrowse()),
fetchAppDetail: (id: string, clientId: string) => dispatch(appDetailRequestData({ id, clientId })),
installationsSetFormState: (formState: FormState) => dispatch(appInstallationsSetFormState(formState)),
setFirstLogin: (firstLogin: boolean) => dispatch(toggleFirstLogin(firstLogin))
userAcceptTermAndCondition: () => dispatch(userAcceptTermAndCondition())
})

export default withRouter(connect(mapStateToProps, mapDispatchToProps)(Client))
2 changes: 2 additions & 0 deletions src/constants/action-types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,9 @@ const ActionTypes = {
AUTH_CHANGE_LOGIN_TYPE: 'AUTH_CHANGE_LOGIN_TYPE',
AUTH_SET_REFRESH_SESSION: 'AUTH_SET_REFRESH_SESSION',
AUTH_CLEAR: 'AUTH_CLEAR',
CHECK_FIRST_TIME_LOGIN: 'CHECK_FIRST_TIME_LOGIN',
TOGGLE_FIRST_LOGIN: 'TOGGLE_FIRST_LOGIN',
USER_ACCEPT_TERM_AND_CONDITION: 'USER_ACCEPT_TERM_AND_CONDITION',

// Error actions
ERROR_THROWN_COMPONENT: 'ERROR_THROWN_COMPONENT',
Expand Down
60 changes: 55 additions & 5 deletions src/sagas/__tests__/auth.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,15 @@
import authSagas, { doLogin, doLogout, loginListen, logoutListen, clearAuthListen, clearAuth } from '../auth'
import authSagas, {
doLogin,
doLogout,
loginListen,
logoutListen,
clearAuthListen,
clearAuth,
setFirstLoginListen,
setFirstTimeLogin,
checkFirstTimeLoginListen,
checkFirstTimeLogin
} from '../auth'
import ActionTypes from '../../constants/action-types'
import { put, all, takeLatest, call, fork } from '@redux-saga/core/effects'
import { authLoginSuccess, authLogoutSuccess, authLoginFailure, toggleFirstLogin } from '../../actions/auth'
Expand Down Expand Up @@ -44,9 +55,6 @@ describe('login submit', () => {
const gen = doLogin(action)
expect(gen.next(mockLoginSession).value).toEqual(call(setUserSession, loginParams))
expect(gen.next(mockLoginSession).value).toEqual(put(authLoginSuccess(mockLoginSession)))
expect(gen.next().value).toEqual(call(getCookieString, COOKIE_FIRST_TIME_LOGIN))
expect(gen.next().value).toEqual(put(toggleFirstLogin(true)))
expect(gen.next().value).toEqual(call(setCookieString, COOKIE_FIRST_TIME_LOGIN, COOKIE_FIRST_TIME_LOGIN))
expect(gen.next().done).toBe(true)
})

Expand Down Expand Up @@ -98,11 +106,35 @@ describe('auth thunks', () => {
})
})

describe('checkFirstTimeLoginListen', () => {
it('should trigger checkFirstTimeLogin action', () => {
const gen = checkFirstTimeLoginListen()
expect(gen.next().value).toEqual(takeLatest(ActionTypes.CHECK_FIRST_TIME_LOGIN, checkFirstTimeLogin))
expect(gen.next().done).toBe(true)
})
})

describe('setFirstLoginListen', () => {
it('should trigger setFirstTimeLogin action', () => {
const gen = setFirstLoginListen()
expect(gen.next().value).toEqual(takeLatest(ActionTypes.USER_ACCEPT_TERM_AND_CONDITION, setFirstTimeLogin))
expect(gen.next().done).toBe(true)
})
})

describe('itemSagas', () => {
it('should wait for login and logout action get called', () => {
const gen = authSagas()

expect(gen.next().value).toEqual(all([fork(loginListen), fork(logoutListen), fork(clearAuthListen)]))
expect(gen.next().value).toEqual(
all([
fork(loginListen),
fork(logoutListen),
fork(clearAuthListen),
fork(checkFirstTimeLoginListen),
fork(setFirstLoginListen)
])
)
expect(gen.next().done).toBe(true)
})
})
Expand All @@ -115,4 +147,22 @@ describe('auth thunks', () => {
expect(gen.next().done).toBe(true)
})
})

describe('setFirstTimeLogin', () => {
it('should run correctly', () => {
const gen = cloneableGenerator(setFirstTimeLogin)()
expect(gen.next().value).toEqual(call(setCookieString, COOKIE_FIRST_TIME_LOGIN, COOKIE_FIRST_TIME_LOGIN))
expect(gen.next().value).toEqual(put(toggleFirstLogin(false)))
expect(gen.next().done).toBe(true)
})
})

describe('checkFirstTimeLogin', () => {
it('should run correctly', () => {
const gen = cloneableGenerator(checkFirstTimeLogin)()
expect(gen.next().value).toEqual(call(getCookieString, COOKIE_FIRST_TIME_LOGIN))
expect(gen.next().value).toEqual(put(toggleFirstLogin(true)))
expect(gen.next().done).toBe(true)
})
})
})
35 changes: 28 additions & 7 deletions src/sagas/auth.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,12 +13,6 @@ export const doLogin = function*({ data }: Action<LoginParams>) {
const loginSession: LoginSession | null = yield call(setUserSession, data)
if (loginSession) {
yield put(authLoginSuccess(loginSession))
const firstLoginCookie = yield call(getCookieString, COOKIE_FIRST_TIME_LOGIN)
if (!firstLoginCookie) {
// TODO need to get createdDate from api , refer to https://reapit.atlassian.net/browse/CLD-593
yield put(toggleFirstLogin(true))
yield call(setCookieString, COOKIE_FIRST_TIME_LOGIN, COOKIE_FIRST_TIME_LOGIN)
}
} else {
yield put(authLoginFailure())
}
Expand Down Expand Up @@ -49,6 +43,19 @@ export const clearAuth = function*() {
}
}

export const checkFirstTimeLogin = function*() {
const firstLoginCookie = yield call(getCookieString, COOKIE_FIRST_TIME_LOGIN)
if (!firstLoginCookie) {
// TODO need to get createdDate from api , refer to https://reapit.atlassian.net/browse/CLD-593
yield put(toggleFirstLogin(true))
}
}

export const setFirstTimeLogin = function*() {
yield call(setCookieString, COOKIE_FIRST_TIME_LOGIN, COOKIE_FIRST_TIME_LOGIN)
yield put(toggleFirstLogin(false))
}

export const loginListen = function*() {
yield takeLatest(ActionTypes.AUTH_LOGIN, doLogin)
}
Expand All @@ -61,8 +68,22 @@ export const clearAuthListen = function*() {
yield takeLatest(ActionTypes.AUTH_CLEAR, clearAuth)
}

export const checkFirstTimeLoginListen = function*() {
yield takeLatest(ActionTypes.CHECK_FIRST_TIME_LOGIN, checkFirstTimeLogin)
}

export const setFirstLoginListen = function*() {
yield takeLatest(ActionTypes.USER_ACCEPT_TERM_AND_CONDITION, setFirstTimeLogin)
}

const authSaga = function*() {
yield all([fork(loginListen), fork(logoutListen), fork(clearAuthListen)])
yield all([
fork(loginListen),
fork(logoutListen),
fork(clearAuthListen),
fork(checkFirstTimeLoginListen),
fork(setFirstLoginListen)
])
}

export default authSaga
2 changes: 2 additions & 0 deletions src/utils/route-dispatcher.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,11 +13,13 @@ import { submitAppRequestData } from '../actions/submit-app'
import { getAccessToken } from './session'
import { requestDeveloperData } from '@/actions/settings'
import { getParamsFromPath } from '@/utils/client-url-params'
import { checkFirstTimeLogin } from '@/actions/auth'

const routeDispatcher = async (route: RouteValue, params?: StringMap, search?: string) => {
await getAccessToken()
switch (route) {
case Routes.CLIENT:
store.dispatch(checkFirstTimeLogin())
store.dispatch(clientRequestData(getParamsFromPath(search || '')))
break
case Routes.INSTALLED_APPS:
Expand Down
2 changes: 1 addition & 1 deletion yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -5800,7 +5800,7 @@ husky@~2.3.0:
run-node "^1.0.0"
slash "^3.0.0"

[email protected], iconv-lite@^0.4.17, iconv-lite@^0.4.24, iconv-lite@~0.4.13:
[email protected], iconv-lite@^0.4.17, iconv-lite@^0.4.24, iconv-lite@^0.4.5, iconv-lite@~0.4.13:
version "0.4.24"
resolved "https://registry.yarnpkg.com/iconv-lite/-/iconv-lite-0.4.24.tgz#2022b4b25fbddc21d2f524974a474aafe733908b"
integrity sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==
Expand Down

0 comments on commit a3891ca

Please sign in to comment.