4.0 KiB
4.0 KiB
Build Optimization Guide
This guide explains how to optimize the production build for better performance.
Current Issues
- Minify JavaScript: 504 KiB savings possible
- Reduce unused JavaScript: 980 KiB savings possible
- Minify CSS: 24 KiB savings possible
- Reduce unused CSS: 25 KiB savings possible
- Cache Headers: 1,702 KiB not cached (requires server configuration)
React Scripts Build Configuration
React Scripts already minifies JavaScript and CSS in production builds. However, you can optimize further:
1. Environment Variables
Create .env.production (already created) with:
GENERATE_SOURCEMAP=false
INLINE_RUNTIME_CHUNK=false
2. Build Command
Run production build:
npm run build
This will:
- Minify JavaScript (already enabled)
- Minify CSS (already enabled)
- Tree-shake unused code (already enabled)
- Generate source maps (disabled via env var)
Reducing Unused JavaScript
Analyze Bundle Size
Install webpack-bundle-analyzer:
npm install --save-dev webpack-bundle-analyzer
Add to package.json scripts:
"analyze": "npm run build && npx webpack-bundle-analyzer build/static/js/*.js"
Run:
npm run analyze
Common Issues and Solutions
-
Large Dependencies:
framer-motion: 246 KiB - Consider lazy loading animations@mui/material: Multiple chunks - Already code-splitrecharts: Only load when needed
-
Unused Imports:
- Use ESLint rule:
"no-unused-vars": "error" - Run:
npx eslint --ext .ts,.tsx src/ --fix
- Use ESLint rule:
-
Dynamic Imports:
- Already implemented for routes
- Consider lazy loading heavy components like charts
Server-Side Cache Headers
For Express.js (if using)
// Add to your Express server
app.use(express.static('build', {
maxAge: '1y',
immutable: true,
etag: true,
lastModified: true
}));
For Nginx
location /static {
alias /path/to/build/static;
expires 1y;
add_header Cache-Control "public, immutable";
access_log off;
}
For Apache
<IfModule mod_expires.c>
ExpiresActive On
ExpiresByType application/javascript "access plus 1 year"
ExpiresByType text/css "access plus 1 year"
ExpiresByType image/png "access plus 1 year"
ExpiresByType image/jpeg "access plus 1 year"
ExpiresByType image/webp "access plus 1 year"
</IfModule>
Image Optimization
Convert AskAlwrity-min.ico to WebP
- Install sharp or use online tool:
npm install --save-dev sharp
- Create script
scripts/optimize-images.js:
const sharp = require('sharp');
const path = require('path');
sharp('public/AskAlwrity-min.ico')
.resize(60, 60)
.webp({ quality: 80 })
.toFile('public/AskAlwrity-min.webp')
.then(() => console.log('Image optimized!'));
- Update
index.html:
<link rel="icon" href="%PUBLIC_URL%/AskAlwrity-min.webp" />
Performance Budget
Set performance budgets in package.json:
{
"performance": {
"budgets": [
{
"type": "initial",
"maximumWarning": "500kb",
"maximumError": "1mb"
},
{
"type": "anyComponentStyle",
"maximumWarning": "50kb",
"maximumError": "100kb"
}
]
}
}
Monitoring
Lighthouse CI
Add to CI/CD pipeline:
npm install -g @lhci/cli
lhci autorun
Web Vitals
Monitor in production:
import { getCLS, getFID, getFCP, getLCP, getTTFB } from 'web-vitals';
function sendToAnalytics(metric) {
// Send to your analytics service
console.log(metric);
}
getCLS(sendToAnalytics);
getFID(sendToAnalytics);
getFCP(sendToAnalytics);
getLCP(sendToAnalytics);
getTTFB(sendToAnalytics);
Expected Improvements
After implementing all optimizations:
- Performance Score: 28 → 70-80+
- Bundle Size: Reduced by ~1.5MB (unused code + minification)
- Cache Hit Rate: 0% → 90%+ (with proper headers)
- CLS: 0.167 → <0.1 (with layout fixes)
- LCP: Improved by additional 200-300ms