diff --git a/src/app.node.test.js b/src/app.node.test.js new file mode 100644 index 00000000..de0cfbbb --- /dev/null +++ b/src/app.node.test.js @@ -0,0 +1,92 @@ +/** + * @jest-environment node + */ + +import React from 'react'; +import ReactDOM from 'react-dom'; +import ReactDOMServer from 'react-dom/server'; +import Helmet from 'react-helmet'; +import forEach from 'lodash/forEach'; +import { ClientApp, ServerApp } from './app'; +import configureStore from './store'; + +const render = (url, context) => { + const store = configureStore(); + const body = ReactDOMServer.renderToString( + + ); + const head = Helmet.peek(); + return { head, body }; +}; + +describe('Application - node environment', () => { + it('renders in the server without crashing', () => { + render('/', {}); + }); + + it('renders the styleguide without crashing', () => { + render('/styleguide', {}); + }); + + it('server renders pages that do not require authentication', () => { + const urlTitles = { + '/': 'LandingPage.schemaTitle', + '/s': 'SearchPage.schemaTitle', + '/l/listing-title-slug/1234': 'ListingPage.loadingListingTitle', + '/l/1234': 'ListingPage.loadingListingTitle', + '/u/1234': 'ProfilePage.schemaTitle', + '/login': 'AuthenticationPage.schemaTitleLogin', + '/signup': 'AuthenticationPage.schemaTitleSignup', + '/recover-password': 'PasswordRecoveryPage.title', + '/this-url-should-not-be-found': 'NotFoundPage.title', + '/reset-password?t=token&e=email': 'PasswordResetPage.title', + }; + forEach(urlTitles, (title, url) => { + const context = {}; + const { head, body } = render(url, context); + + expect(head.title.toString()).toContain(title); + + // context.url will contain the URL to redirect to if a was used + expect(context.url).not.toBeDefined(); + }); + }); + + it('server renders redirects for pages that require authentication', () => { + const loginPath = '/login'; + const signupPath = '/signup'; + const urlRedirects = { + '/l/new': signupPath, + '/l/listing-title-slug/1234/new/description': signupPath, + '/l/listing-title-slug/1234/checkout': signupPath, + '/profile-settings': loginPath, + '/inbox': loginPath, + '/inbox/orders': loginPath, + '/inbox/sales': loginPath, + '/order/1234': loginPath, + '/order/1234/details': loginPath, + '/sale/1234': loginPath, + '/sale/1234/details': loginPath, + '/listings': loginPath, + '/account': loginPath, + '/account/contact-details': loginPath, + '/account/change-password': loginPath, + '/account/payments': loginPath, + '/verify-email': loginPath, + }; + forEach(urlRedirects, (redirectPath, url) => { + const context = {}; + const { body } = render(url, context); + expect(context.url).toEqual(redirectPath); + }); + }); + + it('redirects to correct URLs', () => { + const urlRedirects = { '/l': '/', '/u': '/' }; + forEach(urlRedirects, (redirectPath, url) => { + const context = {}; + const { body } = render(url, context); + expect(context.url).toEqual(redirectPath); + }); + }); +}); diff --git a/src/app.test.js b/src/app.test.js index e666696b..4229f3fe 100644 --- a/src/app.test.js +++ b/src/app.test.js @@ -1,20 +1,8 @@ import React from 'react'; import ReactDOM from 'react-dom'; -import ReactDOMServer from 'react-dom/server'; -import Helmet from 'react-helmet'; -import forEach from 'lodash/forEach'; -import { ClientApp, ServerApp } from './app'; +import { ClientApp } from './app'; import configureStore from './store'; -const render = (url, context) => { - const store = configureStore(); - const body = ReactDOMServer.renderToString( - - ); - const head = Helmet.peek(); - return { head, body }; -}; - const jsdomScroll = window.scroll; beforeAll(() => { // Mock window.scroll - otherwise, Jest/JSDOM will print a not-implemented error. @@ -25,7 +13,7 @@ afterAll(() => { window.scroll = jsdomScroll; }); -describe('Application', () => { +describe('Application - JSDOM environment', () => { it('renders in the client without crashing', () => { window.google = { maps: {} }; const store = configureStore(); @@ -33,74 +21,4 @@ describe('Application', () => { ReactDOM.render(, div); delete window.google; }); - - it('renders in the server without crashing', () => { - render('/', {}); - }); - - it('renders the styleguide without crashing', () => { - render('/styleguide', {}); - }); - - it('server renders pages that do not require authentication', () => { - const urlTitles = { - '/': 'LandingPage.schemaTitle', - '/s': 'SearchPage.schemaTitle', - '/l/listing-title-slug/1234': 'ListingPage.loadingListingTitle', - '/l/1234': 'ListingPage.loadingListingTitle', - '/u/1234': 'ProfilePage.schemaTitle', - '/login': 'AuthenticationPage.schemaTitleLogin', - '/signup': 'AuthenticationPage.schemaTitleSignup', - '/recover-password': 'PasswordRecoveryPage.title', - '/this-url-should-not-be-found': 'NotFoundPage.title', - '/reset-password?t=token&e=email': 'PasswordResetPage.title', - }; - forEach(urlTitles, (title, url) => { - const context = {}; - const { head, body } = render(url, context); - - expect(head.title).toContain(title); - - // context.url will contain the URL to redirect to if a was used - expect(context.url).not.toBeDefined(); - }); - }); - - it('server renders redirects for pages that require authentication', () => { - const loginPath = '/login'; - const signupPath = '/signup'; - const urlRedirects = { - '/l/new': signupPath, - '/l/listing-title-slug/1234/new/description': signupPath, - '/l/listing-title-slug/1234/checkout': signupPath, - '/profile-settings': loginPath, - '/inbox': loginPath, - '/inbox/orders': loginPath, - '/inbox/sales': loginPath, - '/order/1234': loginPath, - '/order/1234/details': loginPath, - '/sale/1234': loginPath, - '/sale/1234/details': loginPath, - '/listings': loginPath, - '/account': loginPath, - '/account/contact-details': loginPath, - '/account/change-password': loginPath, - '/account/payments': loginPath, - '/verify-email': loginPath, - }; - forEach(urlRedirects, (redirectPath, url) => { - const context = {}; - const { body } = render(url, context); - expect(context.url).toEqual(redirectPath); - }); - }); - - it('redirects to correct URLs', () => { - const urlRedirects = { '/l': '/', '/u': '/' }; - forEach(urlRedirects, (redirectPath, url) => { - const context = {}; - const { body } = render(url, context); - expect(context.url).toEqual(redirectPath); - }); - }); });