Skip to content

Commit abd26cd

Browse files
committed
ui: improve initial assets load speed
Does not split code into chunks, based on routes anymore. Since this ends up a lot of dependencies duplicated in multiple bundles. Although in theory this increases size of assets that need to be downloaded to render a route, in practice, our preloading strategy does not work as inteded so the browser ends up downloading most of the whole bundle sometimes. So for now admin route and submissions routes are async, others are not. And there is no preloading as of now, but planned to be introduce in the future. (Also adds `yarn analyze` to see report for generated bundle by `yarn build`) INSPIR-3232
1 parent b6687c4 commit abd26cd

File tree

10 files changed

+330
-160
lines changed

10 files changed

+330
-160
lines changed

ui/package.json

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
"bundlesize": [
77
{
88
"path": "./build/**/*.js",
9-
"maxSize": "375 kB"
9+
"maxSize": "900 kB"
1010
}
1111
],
1212
"scripts": {
@@ -17,6 +17,7 @@
1717
"test:unit": "craco test",
1818
"test:unit:log": "craco test --verbose=false",
1919
"test:size": "bundlesize",
20+
"analyze": "source-map-explorer 'build/static/js/*.js'",
2021
"eject": "react-scripts eject",
2122
"lint":
2223
"./node_modules/eslint/bin/eslint.js ./src --ext .js,.jsx --config .eslintrc"
@@ -89,6 +90,7 @@
8990
"react-test-renderer": "^16.2.0",
9091
"redux-logger": "^3.0.6",
9192
"redux-mock-store": "^1.5.1",
93+
"source-map-explorer": "^2.3.1",
9294
"webpack-filter-warnings-plugin": "^1.2.1"
9395
},
9496
"browserslist": [">0.2%", "not dead", "not ie <= 11", "not op_mini all"]

ui/src/App.jsx

Lines changed: 14 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -28,51 +28,26 @@ import {
2828
import UserFeedback from './common/components/UserFeedback';
2929
import { setUserCategoryFromRoles } from './tracker';
3030
import { fetchLoggedInUser } from './actions/user';
31+
import Home from './home';
32+
import Literature from './literature';
33+
import Conferences from './conferences';
34+
import Authors from './authors';
35+
import Jobs from './jobs';
36+
import User from './user';
37+
import Errors from './errors';
3138

3239
const Holdingpen$ = Loadable({
3340
loader: () => import('./holdingpen'),
3441
loading: Loading,
3542
});
36-
const Literature$ = Loadable({
37-
loader: () => import('./literature'),
38-
loading: Loading,
39-
});
40-
const Authors$ = Loadable({
41-
loader: () => import('./authors'),
42-
loading: Loading,
43-
});
44-
const Jobs$ = Loadable({
45-
loader: () => import('./jobs'),
46-
loading: Loading,
47-
});
48-
const Conferences$ = Loadable({
49-
loader: () => import('./conferences'),
50-
loading: Loading,
51-
});
52-
const Home$ = Loadable({
53-
loader: () => import('./home'),
54-
loading: Loading,
55-
});
56-
const User$ = Loadable({
57-
loader: () => import('./user'),
58-
loading: Loading,
59-
});
6043
const Submissions$ = Loadable({
6144
loader: () => import('./submissions'),
6245
loading: Loading,
6346
});
64-
const Errors$ = Loadable({
65-
loader: () => import('./errors'),
66-
loading: Loading,
67-
});
6847

6948
function App({ userRoles, dispatch }) {
7049
const [headerHeight, setHeaderHeight] = useState(0);
7150

72-
useEffect(() => {
73-
Loadable.preloadAll();
74-
}, []);
75-
7651
useEffect(
7752
() => {
7853
dispatch(fetchLoggedInUser());
@@ -92,15 +67,15 @@ function App({ userRoles, dispatch }) {
9267
<Header onHeightChange={setHeaderHeight} />
9368
<Layout.Content className="content" style={{ marginTop: headerHeight }}>
9469
<SafeSwitch id="main">
95-
<Route exact path={HOME} component={Home$} />
96-
<Route path={USER} component={User$} />
70+
<Route exact path={HOME} component={Home} />
71+
<Route path={USER} component={User} />
9772
<PrivateRoute path={HOLDINGPEN} component={Holdingpen$} />
98-
<Route path={LITERATURE} component={Literature$} />
99-
<Route path={AUTHORS} component={Authors$} />
100-
<Route path={JOBS} component={Jobs$} />
101-
<Route path={CONFERENCES} component={Conferences$} />
73+
<Route path={LITERATURE} component={Literature} />
74+
<Route path={AUTHORS} component={Authors} />
75+
<Route path={JOBS} component={Jobs} />
76+
<Route path={CONFERENCES} component={Conferences} />
10277
<PrivateRoute path={SUBMISSIONS} component={Submissions$} />
103-
<Route path={ERRORS} component={Errors$} />
78+
<Route path={ERRORS} component={Errors} />
10479
</SafeSwitch>
10580
<UserFeedback />
10681
</Layout.Content>

ui/src/__tests__/App.test.jsx

Lines changed: 13 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ import { Provider } from 'react-redux';
33
import { MemoryRouter } from 'react-router-dom';
44
import { mount } from 'enzyme';
55
import { fromJS, List } from 'immutable';
6+
import Loadable from 'react-loadable';
67

78
import { getStore, getStoreWithState } from '../fixtures/store';
89
import App from '../App';
@@ -63,7 +64,7 @@ describe('App', () => {
6364
expect(store.getActions()).toEqual(expectedActions);
6465
});
6566

66-
it('navigates to Holdingpen when /holdingpen if logged in', () => {
67+
it('navigates to Holdingpen when /holdingpen if logged in', async () => {
6768
const store = getStoreWithState({
6869
user: fromJS({
6970
loggedIn: true,
@@ -79,10 +80,12 @@ describe('App', () => {
7980
</MemoryRouter>
8081
</Provider>
8182
);
83+
await Loadable.preloadAll();
84+
wrapper.update();
8285
expect(wrapper.find(Holdingpen)).toExist();
8386
});
8487

85-
it('does not navigate to Holdingpen when /holdingpen if not logged in', () => {
88+
it('does not navigate to Holdingpen when /holdingpen if not logged in', async () => {
8689
const store = getStoreWithState({
8790
user: fromJS({
8891
loggedIn: false,
@@ -98,6 +101,8 @@ describe('App', () => {
98101
</MemoryRouter>
99102
</Provider>
100103
);
104+
await Loadable.preloadAll();
105+
wrapper.update();
101106
expect(wrapper.find(Holdingpen)).not.toExist();
102107
});
103108

@@ -145,7 +150,7 @@ describe('App', () => {
145150
expect(wrapper.find(Conferences)).toExist();
146151
});
147152

148-
it('navigates to Submissions when /submissions if logged in', () => {
153+
it('navigates to Submissions when /submissions if logged in', async () => {
149154
const store = getStoreWithState({
150155
user: fromJS({
151156
loggedIn: true,
@@ -161,10 +166,12 @@ describe('App', () => {
161166
</MemoryRouter>
162167
</Provider>
163168
);
169+
await Loadable.preloadAll();
170+
wrapper.update();
164171
expect(wrapper.find(Submissions)).toExist();
165172
});
166173

167-
it('navigates to Submissions when /submissions if not logged in', () => {
174+
it('navigates to Submissions when /submissions if not logged in', async () => {
168175
const store = getStoreWithState({
169176
user: fromJS({
170177
loggedIn: false,
@@ -180,6 +187,8 @@ describe('App', () => {
180187
</MemoryRouter>
181188
</Provider>
182189
);
190+
await Loadable.preloadAll();
191+
wrapper.update();
183192
expect(wrapper.find(Submissions)).not.toExist();
184193
});
185194

ui/src/authors/index.jsx

Lines changed: 4 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,26 +1,17 @@
11
import React, { Component } from 'react';
22
import { Route } from 'react-router-dom';
3-
import Loadable from 'react-loadable';
43

54
import { AUTHORS } from '../common/routes';
6-
import Loading from '../common/components/Loading';
75
import './index.scss';
8-
9-
const SearchPage$ = Loadable({
10-
loader: () => import('./containers/SearchPageContainer'),
11-
loading: Loading,
12-
});
13-
const DetailPage$ = Loadable({
14-
loader: () => import('./containers/DetailPageContainer'),
15-
loading: Loading,
16-
});
6+
import SearchPageContainer from './containers/SearchPageContainer';
7+
import DetailPageContainer from './containers/DetailPageContainer';
178

189
class Authors extends Component {
1910
render() {
2011
return (
2112
<div className="__Authors__">
22-
<Route exact path={AUTHORS} component={SearchPage$} />
23-
<Route exact path={`${AUTHORS}/:id`} component={DetailPage$} />
13+
<Route exact path={AUTHORS} component={SearchPageContainer} />
14+
<Route exact path={`${AUTHORS}/:id`} component={DetailPageContainer} />
2415
</div>
2516
);
2617
}
Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
11
.__VerticalDivider__ {
2-
background: $text-color;
3-
margin-left: $padding-md - 1px;
2+
background: $text-color !important;
3+
margin-left: $padding-md - 1px !important;
44
}

ui/src/conferences/index.jsx

Lines changed: 8 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1,25 +1,21 @@
11
import React, { Component } from 'react';
22
import { Route } from 'react-router-dom';
3-
import Loadable from 'react-loadable';
43

54
import { CONFERENCES } from '../common/routes';
6-
import Loading from '../common/components/Loading';
75

8-
const SearchPage$ = Loadable({
9-
loader: () => import('./containers/SearchPageContainer'),
10-
loading: Loading,
11-
});
12-
const DetailPage$ = Loadable({
13-
loader: () => import('./containers/DetailPageContainer'),
14-
loading: Loading,
15-
});
6+
import SearchPageContainer from './containers/SearchPageContainer';
7+
import DetailPageContainer from './containers/DetailPageContainer';
168

179
class Conferences extends Component {
1810
render() {
1911
return (
2012
<div className="w-100">
21-
<Route exact path={CONFERENCES} component={SearchPage$} />
22-
<Route exact path={`${CONFERENCES}/:id`} component={DetailPage$} />
13+
<Route exact path={CONFERENCES} component={SearchPageContainer} />
14+
<Route
15+
exact
16+
path={`${CONFERENCES}/:id`}
17+
component={DetailPageContainer}
18+
/>
2319
</div>
2420
);
2521
}

ui/src/jobs/index.jsx

Lines changed: 4 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,26 +1,17 @@
11
import React, { Component } from 'react';
22
import { Route } from 'react-router-dom';
3-
import Loadable from 'react-loadable';
43

54
import { JOBS } from '../common/routes';
6-
import Loading from '../common/components/Loading';
75
import './index.scss';
8-
9-
const SearchPage$ = Loadable({
10-
loader: () => import('./containers/SearchPageContainer'),
11-
loading: Loading,
12-
});
13-
const DetailPage$ = Loadable({
14-
loader: () => import('./containers/DetailPageContainer'),
15-
loading: Loading,
16-
});
6+
import SearchPageContainer from './containers/SearchPageContainer';
7+
import DetailPageContainer from './containers/DetailPageContainer';
178

189
class Jobs extends Component {
1910
render() {
2011
return (
2112
<div className="__Jobs__">
22-
<Route exact path={JOBS} component={SearchPage$} />
23-
<Route exact path={`${JOBS}/:id`} component={DetailPage$} />
13+
<Route exact path={JOBS} component={SearchPageContainer} />
14+
<Route exact path={`${JOBS}/:id`} component={DetailPageContainer} />
2415
</div>
2516
);
2617
}

ui/src/literature/index.jsx

Lines changed: 8 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,26 +1,21 @@
11
import React, { Component } from 'react';
22
import { Route } from 'react-router-dom';
3-
import Loadable from 'react-loadable';
43

5-
import Loading from '../common/components/Loading';
64
import './index.scss';
75
import { LITERATURE } from '../common/routes';
8-
9-
const SearchPage$ = Loadable({
10-
loader: () => import('./containers/SearchPage'),
11-
loading: Loading,
12-
});
13-
const DetailPage$ = Loadable({
14-
loader: () => import('./containers/DetailPageContainer'),
15-
loading: Loading,
16-
});
6+
import SearchPage from './containers/SearchPage';
7+
import DetailPageContainer from './containers/DetailPageContainer';
178

189
class Literature extends Component {
1910
render() {
2011
return (
2112
<div className="__Literature__">
22-
<Route exact path={LITERATURE} component={SearchPage$} />
23-
<Route exact path={`${LITERATURE}/:id`} component={DetailPage$} />
13+
<Route exact path={LITERATURE} component={SearchPage} />
14+
<Route
15+
exact
16+
path={`${LITERATURE}/:id`}
17+
component={DetailPageContainer}
18+
/>
2419
</div>
2520
);
2621
}

0 commit comments

Comments
 (0)