mit einem Klick
wsh-code-splitting
// Code splitting strategies for WSH 2026 — React.lazy, Suspense, splitChunks, and route-based splitting for the CaX app.
// Code splitting strategies for WSH 2026 — React.lazy, Suspense, splitChunks, and route-based splitting for the CaX app.
Crok AI chat rendering optimization — SSE debouncing, ChatMessage memoization, Markdown re-render prevention
DM page and flow optimization — afterSave hook, message rendering, unread count queries for WSH 2026
Home page performance optimization — Post defaultScope, SSR data reduction, lazy media hydration for WSH 2026 CaX app
Lazy loading modal containers and route components to reduce initial bundle size — CrokContainer, NewPostModalContainer
SSE streaming optimization — batching char-by-char events and debouncing React re-renders for Crok AI chat performance
Runs Visual Regression Testing (VRT) locally to prevent disqualification in Web Speed Hackathon. Captures screenshots, compares against baselines, updates snapshots, and validates visual integrity after performance optimizations. Use when optimizing WSH apps, running VRT checks, updating VRT baselines, or investigating VRT failures.
| name | wsh-code-splitting |
| description | Code splitting strategies for WSH 2026 — React.lazy, Suspense, splitChunks, and route-based splitting for the CaX app. |
Splitting the monolithic 108MB bundle into route-based chunks reduces initial load time dramatically. Only the code needed for the current page is loaded upfront.
Use this skill when implementing React.lazy, Suspense, webpack splitChunks, or route-based code splitting.
// Before (AppContainer.tsx)
import { TimelineContainer } from "./TimelineContainer";
import { PostContainer } from "./PostContainer";
// ... all containers imported statically
// After
const TimelineContainer = React.lazy(() => import("./TimelineContainer"));
const PostContainer = React.lazy(() => import("./PostContainer"));
const DirectMessageListContainer = React.lazy(() => import("./DirectMessageListContainer"));
const DirectMessageContainer = React.lazy(() => import("./DirectMessageContainer"));
const SearchContainer = React.lazy(() => import("./SearchContainer"));
const UserProfileContainer = React.lazy(() => import("./UserProfileContainer"));
const TermContainer = React.lazy(() => import("./TermContainer"));
const CrokContainer = React.lazy(() => import("./CrokContainer"));
const NotFoundContainer = React.lazy(() => import("./NotFoundContainer"));
// Wrap Routes with Suspense
<Suspense fallback={<div />}>
<Routes>
<Route element={<TimelineContainer />} path="/" />
...
</Routes>
</Suspense>
Impact: Initial bundle loads only shared code + current route. TBT -40-60%.
// webpack.config.js
optimization: {
splitChunks: {
chunks: "all",
cacheGroups: {
vendor: {
test: /[\\/]node_modules[\\/]/,
name: "vendor",
chunks: "all",
},
},
},
}
Libraries like katex, react-markdown, react-syntax-highlighter should be dynamically imported only when needed.
const ReactMarkdown = React.lazy(() => import("react-markdown"));
| Pitfall | Symptom | Fix |
|---|---|---|
| Missing Suspense boundary | React error: "A component suspended..." | Wrap lazy components in Suspense |
| Suspense fallback too visible | CLS increase from layout shift | Use minimal/invisible fallback |
| Named exports with React.lazy | Build error — lazy requires default export | Use import(...).then(m => ({ default: m.NamedExport })) |
| Change | Visual Impact | Mitigation |
|---|---|---|
| Suspense fallback | Brief flash before content | Use empty div as fallback |
| Chunk loading delay | Content appears later | Prefetch critical chunks |
application/client/src/containers/