diff --git a/frontend/components/App/App.jsx b/frontend/components/App/App.jsx index 91918c23a9..e7f7da5b84 100644 --- a/frontend/components/App/App.jsx +++ b/frontend/components/App/App.jsx @@ -23,7 +23,8 @@ export class App extends Component { const { dispatch, user } = this.props; if (!user && !!authToken()) { - dispatch(fetchCurrentUser()); + dispatch(fetchCurrentUser()) + .catch(() => { return false; }); } return false; diff --git a/frontend/components/App/App.tests.jsx b/frontend/components/App/App.tests.jsx index 3d6ac52915..aef1c351be 100644 --- a/frontend/components/App/App.tests.jsx +++ b/frontend/components/App/App.tests.jsx @@ -1,13 +1,21 @@ -import React from 'react'; import expect, { spyOn, restoreSpies } from 'expect'; import { mount } from 'enzyme'; -import ConnectedApp, { App } from './App'; +import ConnectedApp from './App'; import * as authActions from '../../redux/nodes/auth/actions'; import helpers from '../../test/helpers'; import local from '../../utilities/local'; +const { + connectedComponent, + reduxMockStore, +} = helpers; + describe('App - component', () => { - const component = mount(); + const store = { app: {}, auth: {} }; + const mockStore = reduxMockStore(store); + const component = mount( + connectedComponent(ConnectedApp, { mockStore }) + ); afterEach(() => { restoreSpies(); @@ -22,11 +30,12 @@ describe('App - component', () => { local.setItem('auth_token', 'ABC123'); const spy = spyOn(authActions, 'fetchCurrentUser').andCall(() => { - return { type: 'LOAD_USER_ACTION' }; + return (dispatch) => { + dispatch({ type: 'LOAD_USER_ACTION' }); + return Promise.resolve(); + }; }); - const store = { app: {}, auth: {} }; - const mockStore = helpers.reduxMockStore(store); - const application = helpers.connectedComponent(ConnectedApp, { mockStore }); + const application = connectedComponent(ConnectedApp, { mockStore }); mount(application); expect(spy).toHaveBeenCalled(); @@ -38,7 +47,7 @@ describe('App - component', () => { const spy = spyOn(authActions, 'fetchCurrentUser').andCall(() => { return { type: 'LOAD_USER_ACTION' }; }); - const store = { + const storeWithUser = { app: {}, auth: { user: { @@ -47,8 +56,8 @@ describe('App - component', () => { }, }, }; - const mockStore = helpers.reduxMockStore(store); - const application = helpers.connectedComponent(ConnectedApp, { mockStore }); + const mockStoreWithUser = reduxMockStore(storeWithUser); + const application = connectedComponent(ConnectedApp, { mockStore: mockStoreWithUser }); mount(application); expect(spy).toNotHaveBeenCalled(); @@ -60,9 +69,7 @@ describe('App - component', () => { const spy = spyOn(authActions, 'fetchCurrentUser').andCall(() => { return { type: 'LOAD_USER_ACTION' }; }); - const store = { app: {}, auth: {} }; - const mockStore = helpers.reduxMockStore(store); - const application = helpers.connectedComponent(ConnectedApp, { mockStore }); + const application = connectedComponent(ConnectedApp, { mockStore }); mount(application); expect(spy).toNotHaveBeenCalled(); diff --git a/frontend/pages/LoginPage/LoginPage.jsx b/frontend/pages/LoginPage/LoginPage.jsx index 7554f8fefa..40cf4496df 100644 --- a/frontend/pages/LoginPage/LoginPage.jsx +++ b/frontend/pages/LoginPage/LoginPage.jsx @@ -1,5 +1,6 @@ import React, { Component, PropTypes } from 'react'; import { connect } from 'react-redux'; +import { includes } from 'lodash'; import { push } from 'react-router-redux'; import ReactCSSTransitionGroup from 'react-addons-css-transition-group'; import { clearAuthErrors, loginUser } from '../../redux/nodes/auth/actions'; @@ -10,6 +11,8 @@ import LoginSuccessfulPage from '../LoginSuccessfulPage'; import paths from '../../router/paths'; import './styles.scss'; +const WHITELIST_ERRORS = ['Unable to authenticate the current user']; + export class LoginPage extends Component { static propTypes = { @@ -60,7 +63,7 @@ export class LoginPage extends Component { serverErrors = () => { const { error } = this.props; - if (!error) return undefined; + if (!error || includes(WHITELIST_ERRORS, error)) return undefined; return { username: error, diff --git a/frontend/pages/LoginPage/LoginPage.tests.jsx b/frontend/pages/LoginPage/LoginPage.tests.jsx index e9d6ee1b9b..cb9216944c 100644 --- a/frontend/pages/LoginPage/LoginPage.tests.jsx +++ b/frontend/pages/LoginPage/LoginPage.tests.jsx @@ -15,6 +15,22 @@ describe('LoginPage - component', () => { }); }); + context('when the users session is not recognized', () => { + const mockStore = reduxMockStore({ + auth: { + error: 'Unable to authenticate the current user', + }, + }); + + it('renders the LoginForm without displaying errors', () => { + const page = mount(connectedComponent(LoginPage, { mockStore })); + const loginForm = page.find('LoginForm'); + + expect(loginForm.length).toEqual(1); + expect(loginForm.prop('serverErrors')).toEqual({}); + }); + }); + context('when the user is logged in', () => { beforeEach(() => { local.setItem('auth_token', 'fake-auth-token');