Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit d7f6321

Browse files
authored
feat: Add code splitting to reduce bundle size (#1285)
This splits our pages to use separate JavaScript bundles. It initially splits the terminal, which reduces our primary bundle size by ~400KB. We should do this for all pages, but that can come in a future change. This leaves the loading page empty for now, which I think is fine. None of our pages are large enough that the blank screen temporarily would be concerning.
1 parent f911c8a commit d7f6321

File tree

4 files changed

+98
-89
lines changed

4 files changed

+98
-89
lines changed

site/src/AppRouter.tsx

Lines changed: 89 additions & 86 deletions
Original file line numberDiff line numberDiff line change
@@ -17,133 +17,136 @@ import { SettingsPage } from "./pages/SettingsPage/SettingsPage"
1717
import { CreateWorkspacePage } from "./pages/TemplatesPages/OrganizationPage/TemplatePage/CreateWorkspacePage"
1818
import { TemplatePage } from "./pages/TemplatesPages/OrganizationPage/TemplatePage/TemplatePage"
1919
import { TemplatesPage } from "./pages/TemplatesPages/TemplatesPage"
20-
import { TerminalPage } from "./pages/TerminalPage/TerminalPage"
2120
import { CreateUserPage } from "./pages/UsersPage/CreateUserPage/CreateUserPage"
2221
import { UsersPage } from "./pages/UsersPage/UsersPage"
2322
import { WorkspacePage } from "./pages/WorkspacesPage/WorkspacesPage"
2423

25-
export const AppRouter: React.FC = () => (
26-
<Routes>
27-
<Route path="/">
28-
<Route
29-
index
30-
element={
31-
<RequireAuth>
32-
<IndexPage />
33-
</RequireAuth>
34-
}
35-
/>
36-
37-
<Route path="login" element={<LoginPage />} />
38-
<Route path="healthz" element={<HealthzPage />} />
39-
<Route
40-
path="cli-auth"
41-
element={
42-
<RequireAuth>
43-
<CliAuthenticationPage />
44-
</RequireAuth>
45-
}
46-
/>
24+
const TerminalPage = React.lazy(() => import("./pages/TerminalPage/TerminalPage"))
4725

48-
<Route path="templates">
26+
export const AppRouter: React.FC = () => (
27+
<React.Suspense fallback={<></>}>
28+
<Routes>
29+
<Route path="/">
4930
<Route
5031
index
5132
element={
52-
<AuthAndFrame>
53-
<TemplatesPage />
54-
</AuthAndFrame>
33+
<RequireAuth>
34+
<IndexPage />
35+
</RequireAuth>
36+
}
37+
/>
38+
39+
<Route path="login" element={<LoginPage />} />
40+
<Route path="healthz" element={<HealthzPage />} />
41+
<Route
42+
path="cli-auth"
43+
element={
44+
<RequireAuth>
45+
<CliAuthenticationPage />
46+
</RequireAuth>
5547
}
5648
/>
57-
<Route path=":organization/:template">
49+
50+
<Route path="templates">
51+
<Route
52+
index
53+
element={
54+
<AuthAndFrame>
55+
<TemplatesPage />
56+
</AuthAndFrame>
57+
}
58+
/>
59+
<Route path=":organization/:template">
60+
<Route
61+
index
62+
element={
63+
<AuthAndFrame>
64+
<TemplatePage />
65+
</AuthAndFrame>
66+
}
67+
/>
68+
<Route
69+
path="create"
70+
element={
71+
<RequireAuth>
72+
<CreateWorkspacePage />
73+
</RequireAuth>
74+
}
75+
/>
76+
</Route>
77+
</Route>
78+
79+
<Route path="workspaces">
80+
<Route
81+
path=":workspace"
82+
element={
83+
<AuthAndFrame>
84+
<WorkspacePage />
85+
</AuthAndFrame>
86+
}
87+
/>
88+
</Route>
89+
90+
<Route path="users">
5891
<Route
5992
index
6093
element={
6194
<AuthAndFrame>
62-
<TemplatePage />
95+
<UsersPage />
6396
</AuthAndFrame>
6497
}
6598
/>
6699
<Route
67100
path="create"
68101
element={
69102
<RequireAuth>
70-
<CreateWorkspacePage />
103+
<CreateUserPage />
71104
</RequireAuth>
72105
}
73106
/>
74107
</Route>
75-
</Route>
76-
77-
<Route path="workspaces">
78108
<Route
79-
path=":workspace"
109+
path="orgs"
80110
element={
81111
<AuthAndFrame>
82-
<WorkspacePage />
112+
<OrgsPage />
83113
</AuthAndFrame>
84114
}
85115
/>
86-
</Route>
87-
88-
<Route path="users">
89116
<Route
90-
index
117+
path="settings"
91118
element={
92119
<AuthAndFrame>
93-
<UsersPage />
120+
<SettingsPage />
94121
</AuthAndFrame>
95122
}
96123
/>
97-
<Route
98-
path="create"
99-
element={
100-
<RequireAuth>
101-
<CreateUserPage />
102-
</RequireAuth>
103-
}
104-
/>
105-
</Route>
106-
<Route
107-
path="orgs"
108-
element={
109-
<AuthAndFrame>
110-
<OrgsPage />
111-
</AuthAndFrame>
112-
}
113-
/>
114-
<Route
115-
path="settings"
116-
element={
117-
<AuthAndFrame>
118-
<SettingsPage />
119-
</AuthAndFrame>
120-
}
121-
/>
122124

123-
<Route path="preferences" element={<PreferencesLayout />}>
124-
<Route path="account" element={<AccountPage />} />
125-
<Route path="security" element={<SecurityPage />} />
126-
<Route path="ssh-keys" element={<SSHKeysPage />} />
127-
<Route path="linked-accounts" element={<LinkedAccountsPage />} />
128-
</Route>
125+
<Route path="preferences" element={<PreferencesLayout />}>
126+
<Route path="account" element={<AccountPage />} />
127+
<Route path="security" element={<SecurityPage />} />
128+
<Route path="ssh-keys" element={<SSHKeysPage />} />
129+
<Route path="linked-accounts" element={<LinkedAccountsPage />} />
130+
</Route>
129131

130-
<Route path=":username">
131-
<Route path=":workspace">
132-
<Route
133-
path="terminal"
134-
element={
135-
<RequireAuth>
136-
<TerminalPage />
137-
</RequireAuth>
138-
}
139-
/>
132+
<Route path=":username">
133+
<Route path=":workspace">
134+
<Route
135+
path="terminal"
136+
element={
137+
<RequireAuth>
138+
<TerminalPage />
139+
</RequireAuth>
140+
}
141+
/>
142+
</Route>
140143
</Route>
141-
</Route>
142144

143-
{/* Using path="*"" means "match anything", so this route
145+
{/* Using path="*"" means "match anything", so this route
144146
acts like a catch-all for URLs that we don't have explicit
145147
routes for. */}
146-
<Route path="*" element={<NotFoundPage />} />
147-
</Route>
148-
</Routes>
148+
<Route path="*" element={<NotFoundPage />} />
149+
</Route>
150+
</Routes>
151+
</React.Suspense>
149152
)

site/src/pages/TerminalPage/TerminalPage.test.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ import { TextDecoder, TextEncoder } from "util"
88
import { ReconnectingPTYRequest } from "../../api/types"
99
import { history, MockWorkspaceAgent, render } from "../../testHelpers"
1010
import { server } from "../../testHelpers/server"
11-
import { Language, TerminalPage } from "./TerminalPage"
11+
import TerminalPage, { Language } from "./TerminalPage"
1212

1313
Object.defineProperty(window, "matchMedia", {
1414
writable: true,

site/src/pages/TerminalPage/TerminalPage.tsx

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@ export const Language = {
1717
websocketErrorMessagePrefix: "WebSocket failed: ",
1818
}
1919

20-
export const TerminalPage: React.FC<{
20+
const TerminalPage: React.FC<{
2121
readonly renderer?: XTerm.RendererType
2222
}> = ({ renderer }) => {
2323
const location = useLocation()
@@ -200,6 +200,8 @@ export const TerminalPage: React.FC<{
200200
)
201201
}
202202

203+
export default TerminalPage
204+
203205
const useStyles = makeStyles(() => ({
204206
overlay: {
205207
position: "absolute",

site/tsconfig.prod.json

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,8 @@
11
{
22
"extends": "./tsconfig.json",
3-
"exclude": ["node_modules", "_jest", "**/*.stories.tsx", "**/*.test.tsx"]
3+
"exclude": ["node_modules", "_jest", "**/*.stories.tsx", "**/*.test.tsx"],
4+
"compilerOptions": {
5+
// https://github.com/webpack/webpack/issues/5703#issuecomment-357512412
6+
"module": "esnext"
7+
}
48
}

0 commit comments

Comments
 (0)