🗑️ Deprecate deploy-pokedex.js in favor of deploy.sh and update environment variable validation messages

This commit is contained in:
2026-01-30 11:29:28 -05:00
parent fee8fe2551
commit 84f1fcb42a
3 changed files with 51 additions and 36 deletions

View File

@@ -1,23 +1,23 @@
/** /**
* DEPRECATED: Use deploy.sh instead * DEPRECATED: Use deploy.sh instead
* *
* This utility is being phased out in favor of the comprehensive deploy.sh script * This utility is being phased out in favor of the comprehensive deploy.sh script
* located at code/websites/pokedex.online/deploy.sh * located at code/websites/pokedex.online/deploy.sh
* *
* Migration guide: * Migration guide:
* Old: node code/utils/deploy-pokedex.js --target internal * Old: node code/utils/deploy-pokedex.js --target internal
* New: cd code/websites/pokedex.online && ./deploy.sh --target production * New: cd code/websites/pokedex.online && ./deploy.sh --target production
* *
* Old: node code/utils/deploy-pokedex.js --target local * Old: node code/utils/deploy-pokedex.js --target local
* New: cd code/websites/pokedex.online && ./deploy.sh --target local * New: cd code/websites/pokedex.online && ./deploy.sh --target local
* *
* The new deploy.sh provides: * The new deploy.sh provides:
* - Environment-specific builds using Vite modes * - Environment-specific builds using Vite modes
* - Automatic build verification * - Automatic build verification
* - Pre-deployment validation * - Pre-deployment validation
* - Integrated testing * - Integrated testing
* - Better error handling * - Better error handling
* *
* This file will be removed in a future update. * This file will be removed in a future update.
*/ */

View File

@@ -1,9 +1,9 @@
/** /**
* Build Verification Script * Build Verification Script
* *
* Extracts and validates environment variables embedded in the built bundle. * Extracts and validates environment variables embedded in the built bundle.
* Ensures redirect URIs match the expected deployment target. * Ensures redirect URIs match the expected deployment target.
* *
* Usage: * Usage:
* BUILD_TARGET=docker-local npm run build:verify * BUILD_TARGET=docker-local npm run build:verify
* BUILD_TARGET=production npm run build:verify * BUILD_TARGET=production npm run build:verify
@@ -36,18 +36,20 @@ function log(color, symbol, message) {
function findBuiltAssets() { function findBuiltAssets() {
const distPath = path.resolve(__dirname, '../dist/assets'); const distPath = path.resolve(__dirname, '../dist/assets');
if (!fs.existsSync(distPath)) { if (!fs.existsSync(distPath)) {
throw new Error('dist/assets directory not found. Run build first.'); throw new Error('dist/assets directory not found. Run build first.');
} }
const files = fs.readdirSync(distPath); const files = fs.readdirSync(distPath);
const jsFiles = files.filter(f => f.endsWith('.js') && f.startsWith('index-')); const jsFiles = files.filter(
f => f.endsWith('.js') && f.startsWith('index-')
);
if (jsFiles.length === 0) { if (jsFiles.length === 0) {
throw new Error('No built JavaScript files found in dist/assets/'); throw new Error('No built JavaScript files found in dist/assets/');
} }
return jsFiles.map(f => path.join(distPath, f)); return jsFiles.map(f => path.join(distPath, f));
} }
@@ -59,58 +61,58 @@ function extractRedirectUri(content) {
/redirectUri[\"']?\s*[:=]\s*[\"']([^\"']+oauth\/callback)[\"']/, /redirectUri[\"']?\s*[:=]\s*[\"']([^\"']+oauth\/callback)[\"']/,
/(https?:\/\/[^\"'\s]+\/oauth\/callback)/ /(https?:\/\/[^\"'\s]+\/oauth\/callback)/
]; ];
for (const pattern of patterns) { for (const pattern of patterns) {
const match = content.match(pattern); const match = content.match(pattern);
if (match && match[1]) { if (match && match[1]) {
return match[1]; return match[1];
} }
} }
return null; return null;
} }
function verifyBuild() { function verifyBuild() {
console.log('\n🔍 Build Verification\n'); console.log('\n🔍 Build Verification\n');
// Get target from environment variable // Get target from environment variable
const target = process.env.BUILD_TARGET || 'local'; const target = process.env.BUILD_TARGET || 'local';
if (!EXPECTED_URIS[target]) { if (!EXPECTED_URIS[target]) {
log('red', '❌', `Invalid BUILD_TARGET: ${target}`); log('red', '❌', `Invalid BUILD_TARGET: ${target}`);
log('blue', '', 'Valid targets: docker-local, production'); log('blue', '', 'Valid targets: docker-local, production');
process.exit(1); process.exit(1);
} }
const expectedUri = EXPECTED_URIS[target]; const expectedUri = EXPECTED_URIS[target];
log('blue', '', `Deployment target: ${target}`); log('blue', '', `Deployment target: ${target}`);
log('blue', '', `Expected redirect URI: ${expectedUri}`); log('blue', '', `Expected redirect URI: ${expectedUri}`);
try { try {
// Find built assets // Find built assets
const assetFiles = findBuiltAssets(); const assetFiles = findBuiltAssets();
log('green', '✅', `Found ${assetFiles.length} built asset(s)`); log('green', '✅', `Found ${assetFiles.length} built asset(s)`);
// Search for redirect URI in all assets // Search for redirect URI in all assets
let foundUri = null; let foundUri = null;
for (const assetFile of assetFiles) { for (const assetFile of assetFiles) {
const content = fs.readFileSync(assetFile, 'utf8'); const content = fs.readFileSync(assetFile, 'utf8');
const uri = extractRedirectUri(content); const uri = extractRedirectUri(content);
if (uri) { if (uri) {
foundUri = uri; foundUri = uri;
break; break;
} }
} }
if (!foundUri) { if (!foundUri) {
log('yellow', '⚠', 'Could not find Discord redirect URI in bundle'); log('yellow', '⚠', 'Could not find Discord redirect URI in bundle');
log('blue', '', 'This may be OK if OAuth is not used'); log('blue', '', 'This may be OK if OAuth is not used');
process.exit(0); process.exit(0);
} }
log('blue', '', `Found redirect URI: ${foundUri}`); log('blue', '', `Found redirect URI: ${foundUri}`);
// Validate URI matches expected // Validate URI matches expected
if (foundUri === expectedUri) { if (foundUri === expectedUri) {
log('green', '✅', 'Redirect URI matches expected value!'); log('green', '✅', 'Redirect URI matches expected value!');
@@ -121,13 +123,18 @@ function verifyBuild() {
log('blue', '', `Expected: ${expectedUri}`); log('blue', '', `Expected: ${expectedUri}`);
log('blue', '', `Found: ${foundUri}`); log('blue', '', `Found: ${foundUri}`);
console.log('\n❌ Build verification failed\n'); console.log('\n❌ Build verification failed\n');
console.log('This usually means the wrong .env.{mode} file was used during build.'); console.log(
console.log('Check that you\'re using the correct Vite mode flag:\n'); 'This usually means the wrong .env.{mode} file was used during build.'
console.log(' vite build --mode docker-local (for local Docker deployment)'); );
console.log(' vite build --mode production (for Synology deployment)\n'); console.log("Check that you're using the correct Vite mode flag:\n");
console.log(
' vite build --mode docker-local (for local Docker deployment)'
);
console.log(
' vite build --mode production (for Synology deployment)\n'
);
process.exit(1); process.exit(1);
} }
} catch (error) { } catch (error) {
log('red', '❌', `Verification error: ${error.message}`); log('red', '❌', `Verification error: ${error.message}`);
process.exit(1); process.exit(1);

View File

@@ -35,24 +35,30 @@ const REQUIRED_ENV_VARS = {
description: 'Frontend URL for CORS', description: 'Frontend URL for CORS',
validate: (val, env) => { validate: (val, env) => {
if (!val) return false; if (!val) return false;
// Validate that FRONTEND_URL matches DEPLOYMENT_TARGET (if set) // Validate that FRONTEND_URL matches DEPLOYMENT_TARGET (if set)
const target = env?.DEPLOYMENT_TARGET; const target = env?.DEPLOYMENT_TARGET;
if (!target) return true; // Skip validation if target not set yet if (!target) return true; // Skip validation if target not set yet
if (target === 'dev' && !val.includes('localhost:5173')) { if (target === 'dev' && !val.includes('localhost:5173')) {
console.error('⚠️ FRONTEND_URL should be http://localhost:5173 for dev target'); console.error(
'⚠️ FRONTEND_URL should be http://localhost:5173 for dev target'
);
return false; return false;
} }
if (target === 'docker-local' && !val.includes('localhost:8099')) { if (target === 'docker-local' && !val.includes('localhost:8099')) {
console.error('⚠️ FRONTEND_URL should be http://localhost:8099 for docker-local target'); console.error(
'⚠️ FRONTEND_URL should be http://localhost:8099 for docker-local target'
);
return false; return false;
} }
if (target === 'production' && !val.includes('app.pokedex.online')) { if (target === 'production' && !val.includes('app.pokedex.online')) {
console.error('⚠️ FRONTEND_URL should be https://app.pokedex.online for production target'); console.error(
'⚠️ FRONTEND_URL should be https://app.pokedex.online for production target'
);
return false; return false;
} }
return true; return true;
} }
}, },
@@ -137,7 +143,9 @@ export function validateOrExit(exitOnError = true) {
// Print validation results // Print validation results
console.log('\n🔍 Environment Validation:'); console.log('\n🔍 Environment Validation:');
console.log(` DEPLOYMENT_TARGET: ${process.env.DEPLOYMENT_TARGET || 'not set'}`); console.log(
` DEPLOYMENT_TARGET: ${process.env.DEPLOYMENT_TARGET || 'not set'}`
);
console.log(` NODE_ENV: ${process.env.NODE_ENV || 'not set'}`); console.log(` NODE_ENV: ${process.env.NODE_ENV || 'not set'}`);
console.log(` PORT: ${process.env.PORT || 'not set'}`); console.log(` PORT: ${process.env.PORT || 'not set'}`);
console.log(` FRONTEND_URL: ${process.env.FRONTEND_URL || 'not set'}`); console.log(` FRONTEND_URL: ${process.env.FRONTEND_URL || 'not set'}`);
@@ -180,7 +188,7 @@ export function validateOrExit(exitOnError = true) {
export function getConfig() { export function getConfig() {
const deploymentTarget = process.env.DEPLOYMENT_TARGET || 'dev'; const deploymentTarget = process.env.DEPLOYMENT_TARGET || 'dev';
const frontendUrl = process.env.FRONTEND_URL; const frontendUrl = process.env.FRONTEND_URL;
return { return {
deploymentTarget, deploymentTarget,
nodeEnv: process.env.NODE_ENV || 'development', nodeEnv: process.env.NODE_ENV || 'development',