Deploy React Admin UI Bundle
Automates the full React admin UI deployment pipeline. This process has a critical manual step (JS bundle renaming) that has caused production blank pages when forgotten.
The argument passed to this skill (if any) can be "build" (full build + deploy), "copy" (skip build, just copy existing build output), or "check" (verify current state without changing anything). Default is full build + deploy.
The Pipeline
Step 1: Verify Prerequisites
# Check that the admin-ui directory exists and has node_modules ls congressional-hearing-tools/capitol-transcribe/admin-ui/package.json ls congressional-hearing-tools/capitol-transcribe/admin-ui/node_modules/.package-lock.json
If node_modules is missing, run npm install first:
cd congressional-hearing-tools/capitol-transcribe/admin-ui && npm install
Step 2: Build the React App
Skip this step if the user passed "copy" as the argument.
cd congressional-hearing-tools/capitol-transcribe/admin-ui && npm run build
Report build result: success/failure, any warnings. If the build fails, stop and troubleshoot — do NOT proceed with stale build artifacts.
Step 3: Copy Build Output to Static Bundle
# Clear old static bundle (preserve the directory) rm -rf api/static_bundle/static/ # Copy new build output cp -r congressional-hearing-tools/capitol-transcribe/admin-ui/build/static api/static_bundle/static/ cp congressional-hearing-tools/capitol-transcribe/admin-ui/build/index.html api/static_bundle/index.html cp congressional-hearing-tools/capitol-transcribe/admin-ui/build/asset-manifest.json api/static_bundle/asset-manifest.json
Step 4: Rename the JS Bundle (CRITICAL)
This is the step that causes blank pages when forgotten.
The index.html and asset-manifest.json reference main.b3b7498e.js for backwards compatibility. The new build will have a different hash. You MUST rename it.
# Find the new JS bundle (it will have a different hash) ls api/static_bundle/static/js/main.*.js
Rename whatever main.*.js file exists to main.b3b7498e.js:
# Rename the new bundle to the expected filename mv api/static_bundle/static/js/main.*.js api/static_bundle/static/js/main.b3b7498e.js
Also handle the CSS bundle if present — check if index.html references a specific CSS filename and rename accordingly.
Step 5: Verify index.html References
Read api/static_bundle/index.html and confirm:
- •The JS
<script>tag references/admin/capitoltranscribe/static/js/main.b3b7498e.js - •If it references a different hash, update it to
main.b3b7498e.js
Read api/static_bundle/asset-manifest.json and confirm:
- •The
main.jsentry referencesmain.b3b7498e.js - •If it references a different hash, update it
Step 6: Verify the Bundle
# Confirm the renamed file exists ls -la api/static_bundle/static/js/main.b3b7498e.js # Confirm index.html references the right filename grep "main.b3b7498e" api/static_bundle/index.html
Report the final state:
- •JS bundle:
main.b3b7498e.js(size) - •CSS bundle: filename (size)
- •index.html: references verified
Step 7: Stage for Commit
git add api/static_bundle/ git status
Report what files are staged. Do NOT commit automatically — present the staged changes and let the user decide when to commit.
Check Mode
If the user passed "check", skip all build/copy steps and just report:
- •Current JS bundle in
api/static_bundle/static/js/— filename, size, modified date - •Whether
index.htmlreferencesmain.b3b7498e.js - •Whether
asset-manifest.jsonreferencesmain.b3b7498e.js - •Last build date in
congressional-hearing-tools/capitol-transcribe/admin-ui/build/(if it exists) - •Any discrepancies between the admin-ui build output and the static bundle
Troubleshooting
- •Blank admin UI page: Almost always the JS bundle rename was missed. Check the browser console for a 404 on the JS file.
- •Build fails with module errors: Run
npm installin the admin-ui directory. Node modules may be missing or stale. - •Multiple main.*.js files in static bundle: The
rm -rfin Step 3 should prevent this, but if it happens, delete all and re-copy. - •CSS not loading: Same pattern as JS — check if the CSS filename in index.html matches what's in
static/css/.