- Add comprehensive Training Leads system for HVAC trainers * New /trainer/training-leads/ page with tabular contact submission display * HVAC_Training_Leads class with AJAX status updates and filtering * Empty state messaging and profile sharing CTA * Database integration with existing contact forms system - Restructure trainer navigation menu for better UX * Rename "Customize" to "Profile" with logical groupings * Move "Logout" under "Profile" submenu * Change "Personal Profile" to "Trainer Profile" * Add "Training Leads" under Profile section * Update help menu to show only question mark icon positioned far right - Enhance documentation system * Fix /trainer/documentation/ page styling and navigation integration * Update content to reflect current platform features * Add Training Leads documentation and navigation guide * Implement proper WordPress template structure - Update user management * Change joe@upskillhvac.com display name to "Joe Medosch" * Assign Joe as author of measureQuick headquarters venue * Assign Joe as author of measureQuick and Upskill HVAC organizers 🤖 Generated with [Claude Code](https://claude.ai/code) Co-Authored-By: Claude <noreply@anthropic.com>
		
			
				
	
	
		
			386 lines
		
	
	
		
			No EOL
		
	
	
		
			12 KiB
		
	
	
	
		
			Bash
		
	
	
		
			Executable file
		
	
	
	
	
			
		
		
	
	
			386 lines
		
	
	
		
			No EOL
		
	
	
		
			12 KiB
		
	
	
	
		
			Bash
		
	
	
		
			Executable file
		
	
	
	
	
| #!/bin/bash
 | |
| 
 | |
| # Production Pre-Deployment Cleanup Script
 | |
| # Removes all test data from staging before pushing to production
 | |
| # This ensures no test accounts, events, or data make it to the live site
 | |
| 
 | |
| source .env
 | |
| 
 | |
| echo "========================================="
 | |
| echo "🧹 PRODUCTION PRE-DEPLOYMENT CLEANUP"
 | |
| echo "========================================="
 | |
| echo "Target: $UPSKILL_STAGING_IP"
 | |
| echo "This will remove ALL test data from staging"
 | |
| echo "before pushing to production."
 | |
| echo ""
 | |
| 
 | |
| # Confirm cleanup action
 | |
| echo "⚠️  WARNING: This will permanently delete:"
 | |
| echo "   • Test user accounts (test_trainer, JoeMedosch@gmail.com)"
 | |
| echo "   • Test events and all associated data"
 | |
| echo "   • Test attendees and check-in records"
 | |
| echo "   • Test certificates and certificate files"
 | |
| echo "   • Test venues and organizers"
 | |
| echo "   • Test tickets and orders"
 | |
| echo ""
 | |
| 
 | |
| read -p "Are you sure you want to proceed? (yes/no): " confirm
 | |
| if [ "$confirm" != "yes" ]; then
 | |
|     echo "Cleanup cancelled."
 | |
|     exit 1
 | |
| fi
 | |
| 
 | |
| echo ""
 | |
| echo "🚀 Starting test data cleanup..."
 | |
| 
 | |
| # Upload and execute comprehensive cleanup PHP script
 | |
| sshpass -p "$UPSKILL_STAGING_PASS" scp -o StrictHostKeyChecking=no /dev/stdin $UPSKILL_STAGING_SSH_USER@$UPSKILL_STAGING_IP:tmp/cleanup-test-data.php << 'PHPEOF'
 | |
| <?php
 | |
| /**
 | |
|  * Production Pre-Deployment Test Data Cleanup
 | |
|  * 
 | |
|  * Removes all test data including:
 | |
|  * - Test user accounts
 | |
|  * - Test events and associated data
 | |
|  * - Test certificates and files
 | |
|  * - Test attendees and orders
 | |
|  */
 | |
| 
 | |
| require_once('wp-load.php');
 | |
| 
 | |
| echo "=== Starting Production Pre-Deployment Cleanup ===\n\n";
 | |
| 
 | |
| // Initialize counters
 | |
| $deleted_users = 0;
 | |
| $deleted_events = 0;
 | |
| $deleted_attendees = 0;
 | |
| $deleted_certificates = 0;
 | |
| $deleted_venues = 0;
 | |
| $deleted_organizers = 0;
 | |
| $deleted_tickets = 0;
 | |
| $deleted_files = 0;
 | |
| 
 | |
| // 1. REMOVE TEST USER ACCOUNTS
 | |
| echo "🗑️  Removing test user accounts...\n";
 | |
| 
 | |
| $test_users = [
 | |
|     'test_trainer',
 | |
|     'joemedosch',
 | |
|     'JoeMedosch@gmail.com'  // search by email
 | |
| ];
 | |
| 
 | |
| foreach ($test_users as $identifier) {
 | |
|     // Try to find user by login first, then by email
 | |
|     $user = get_user_by('login', $identifier);
 | |
|     if (!$user) {
 | |
|         $user = get_user_by('email', $identifier);
 | |
|     }
 | |
|     
 | |
|     if ($user) {
 | |
|         echo "  - Removing user: {$user->user_login} ({$user->user_email})\n";
 | |
|         
 | |
|         // Remove user and reassign their content to admin (ID 1)
 | |
|         $admin_user = get_user_by('ID', 1);
 | |
|         if ($admin_user) {
 | |
|             wp_delete_user($user->ID, 1); // Reassign to admin
 | |
|         } else {
 | |
|             wp_delete_user($user->ID); // Delete without reassignment
 | |
|         }
 | |
|         $deleted_users++;
 | |
|     }
 | |
| }
 | |
| 
 | |
| // Remove HVAC roles from joe@measurequick.com if they exist
 | |
| $joe_mq = get_user_by('email', 'joe@measurequick.com');
 | |
| if ($joe_mq) {
 | |
|     echo "  - Removing HVAC roles from joe@measurequick.com\n";
 | |
|     $user = new WP_User($joe_mq->ID);
 | |
|     $user->remove_role('hvac_trainer');
 | |
|     $user->remove_role('hvac_master_trainer');
 | |
| }
 | |
| 
 | |
| echo "✅ Removed {$deleted_users} test user accounts\n\n";
 | |
| 
 | |
| // 2. REMOVE TEST EVENTS AND ASSOCIATED DATA
 | |
| echo "🗑️  Removing test events and associated data...\n";
 | |
| 
 | |
| // Get all events that might be test events (look for common test patterns)
 | |
| $test_event_patterns = [
 | |
|     'HVAC System Diagnostics',
 | |
|     'Commercial Refrigeration',
 | |
|     'Energy Efficient HVAC',
 | |
|     'Advanced HVAC Troubleshooting',
 | |
|     'HVAC Energy Efficiency Workshop',
 | |
|     'Commercial Refrigeration Systems',
 | |
|     'Residential HVAC Installation Best Practices',
 | |
|     'HVAC Controls and Automation'
 | |
| ];
 | |
| 
 | |
| $all_events = get_posts([
 | |
|     'post_type' => 'tribe_events',
 | |
|     'post_status' => 'any',
 | |
|     'posts_per_page' => -1,
 | |
|     'meta_query' => [
 | |
|         'relation' => 'OR',
 | |
|         [
 | |
|             'key' => '_eventbrite_event_id',
 | |
|             'compare' => 'NOT EXISTS'
 | |
|         ],
 | |
|         [
 | |
|             'key' => '_eventbrite_event_id',
 | |
|             'value' => '',
 | |
|             'compare' => '='
 | |
|         ]
 | |
|     ]
 | |
| ]);
 | |
| 
 | |
| foreach ($all_events as $event) {
 | |
|     $is_test_event = false;
 | |
|     
 | |
|     // Check if event title matches test patterns
 | |
|     foreach ($test_event_patterns as $pattern) {
 | |
|         if (stripos($event->post_title, $pattern) !== false) {
 | |
|             $is_test_event = true;
 | |
|             break;
 | |
|         }
 | |
|     }
 | |
|     
 | |
|     // Also check if event was created recently (within last 6 months) and has test-like characteristics
 | |
|     $event_date = strtotime($event->post_date);
 | |
|     $six_months_ago = strtotime('-6 months');
 | |
|     
 | |
|     if ($event_date > $six_months_ago) {
 | |
|         // Check for test-like content
 | |
|         $test_indicators = ['test', 'training center', 'example', 'dummy', 'sample'];
 | |
|         $event_content = strtolower($event->post_title . ' ' . $event->post_content);
 | |
|         
 | |
|         foreach ($test_indicators as $indicator) {
 | |
|             if (strpos($event_content, $indicator) !== false) {
 | |
|                 $is_test_event = true;
 | |
|                 break;
 | |
|             }
 | |
|         }
 | |
|     }
 | |
|     
 | |
|     if ($is_test_event) {
 | |
|         $event_id = $event->ID;
 | |
|         echo "  - Removing event: {$event->post_title} (ID: {$event_id})\n";
 | |
|         
 | |
|         // Get associated attendees first
 | |
|         $attendees = get_posts([
 | |
|             'post_type' => 'tribe_tpp_attendees',
 | |
|             'meta_query' => [
 | |
|                 [
 | |
|                     'key' => '_tribe_tpp_event',
 | |
|                     'value' => $event_id
 | |
|                 ]
 | |
|             ],
 | |
|             'posts_per_page' => -1
 | |
|         ]);
 | |
|         
 | |
|         // Remove attendees
 | |
|         foreach ($attendees as $attendee) {
 | |
|             wp_delete_post($attendee->ID, true);
 | |
|             $deleted_attendees++;
 | |
|         }
 | |
|         
 | |
|         // Get associated tickets
 | |
|         $tickets = get_posts([
 | |
|             'post_type' => 'tribe_tpp_tickets',
 | |
|             'meta_query' => [
 | |
|                 [
 | |
|                     'key' => '_tribe_tpp_for_event',
 | |
|                     'value' => $event_id
 | |
|                 ]
 | |
|             ],
 | |
|             'posts_per_page' => -1
 | |
|         ]);
 | |
|         
 | |
|         // Remove tickets
 | |
|         foreach ($tickets as $ticket) {
 | |
|             wp_delete_post($ticket->ID, true);
 | |
|             $deleted_tickets++;
 | |
|         }
 | |
|         
 | |
|         // Get venue ID before deleting event
 | |
|         $venue_id = get_post_meta($event_id, '_EventVenueID', true);
 | |
|         
 | |
|         // Remove the event
 | |
|         wp_delete_post($event_id, true);
 | |
|         $deleted_events++;
 | |
|         
 | |
|         // Remove associated venue if it looks like a test venue
 | |
|         if ($venue_id) {
 | |
|             $venue = get_post($venue_id);
 | |
|             if ($venue && $venue->post_type === 'tribe_venue') {
 | |
|                 $test_venue_indicators = ['training center', 'test', 'example', 'demo'];
 | |
|                 $venue_content = strtolower($venue->post_title . ' ' . $venue->post_content);
 | |
|                 
 | |
|                 $is_test_venue = false;
 | |
|                 foreach ($test_venue_indicators as $indicator) {
 | |
|                     if (strpos($venue_content, $indicator) !== false) {
 | |
|                         $is_test_venue = true;
 | |
|                         break;
 | |
|                     }
 | |
|                 }
 | |
|                 
 | |
|                 if ($is_test_venue) {
 | |
|                     wp_delete_post($venue_id, true);
 | |
|                     $deleted_venues++;
 | |
|                 }
 | |
|             }
 | |
|         }
 | |
|     }
 | |
| }
 | |
| 
 | |
| echo "✅ Removed {$deleted_events} test events, {$deleted_attendees} attendees, {$deleted_tickets} tickets, {$deleted_venues} venues\n\n";
 | |
| 
 | |
| // 3. REMOVE TEST CERTIFICATES AND FILES
 | |
| echo "🗑️  Removing test certificates and files...\n";
 | |
| 
 | |
| if (class_exists('HVAC_Certificate_Manager')) {
 | |
|     global $wpdb;
 | |
|     $certificate_table = $wpdb->prefix . 'hvac_certificates';
 | |
|     
 | |
|     // Get all certificates
 | |
|     $certificates = $wpdb->get_results("SELECT * FROM {$certificate_table}");
 | |
|     
 | |
|     foreach ($certificates as $certificate) {
 | |
|         $should_delete = false;
 | |
|         
 | |
|         // Check if associated event was deleted (event doesn't exist anymore)
 | |
|         $event_exists = get_post($certificate->event_id);
 | |
|         if (!$event_exists) {
 | |
|             $should_delete = true;
 | |
|         }
 | |
|         
 | |
|         // Check if certificate file looks like test data
 | |
|         if (strpos($certificate->file_path, 'test') !== false || 
 | |
|             strpos($certificate->file_path, 'example') !== false ||
 | |
|             strpos($certificate->file_path, 'demo') !== false) {
 | |
|             $should_delete = true;
 | |
|         }
 | |
|         
 | |
|         if ($should_delete) {
 | |
|             // Remove certificate file
 | |
|             $upload_dir = wp_upload_dir();
 | |
|             $full_file_path = $upload_dir['basedir'] . '/' . $certificate->file_path;
 | |
|             
 | |
|             if (file_exists($full_file_path)) {
 | |
|                 unlink($full_file_path);
 | |
|                 $deleted_files++;
 | |
|             }
 | |
|             
 | |
|             // Remove certificate record
 | |
|             $wpdb->delete($certificate_table, ['id' => $certificate->id]);
 | |
|             $deleted_certificates++;
 | |
|         }
 | |
|     }
 | |
| }
 | |
| 
 | |
| echo "✅ Removed {$deleted_certificates} test certificates and {$deleted_files} certificate files\n\n";
 | |
| 
 | |
| // 4. REMOVE TEST ORGANIZERS
 | |
| echo "🗑️  Removing test organizers...\n";
 | |
| 
 | |
| $organizers = get_posts([
 | |
|     'post_type' => 'tribe_organizer',
 | |
|     'post_status' => 'any',
 | |
|     'posts_per_page' => -1
 | |
| ]);
 | |
| 
 | |
| foreach ($organizers as $organizer) {
 | |
|     $test_organizer_indicators = ['test', 'example', 'demo', 'training', 'sample'];
 | |
|     $organizer_content = strtolower($organizer->post_title . ' ' . $organizer->post_content);
 | |
|     
 | |
|     $is_test_organizer = false;
 | |
|     foreach ($test_organizer_indicators as $indicator) {
 | |
|         if (strpos($organizer_content, $indicator) !== false) {
 | |
|             $is_test_organizer = true;
 | |
|             break;
 | |
|         }
 | |
|     }
 | |
|     
 | |
|     // Be more conservative - only remove organizers with clear test indicators
 | |
|     // Don't automatically remove based on creation date for organizers
 | |
|     // Many legitimate training organizations may have been added recently
 | |
|     
 | |
|     if ($is_test_organizer) {
 | |
|         wp_delete_post($organizer->ID, true);
 | |
|         $deleted_organizers++;
 | |
|     }
 | |
| }
 | |
| 
 | |
| echo "✅ Removed {$deleted_organizers} test organizers\n\n";
 | |
| 
 | |
| // 5. CLEAN UP ORPHANED META DATA
 | |
| echo "🗑️  Cleaning up orphaned meta data...\n";
 | |
| 
 | |
| // Clean up post meta for deleted posts
 | |
| $wpdb->query("DELETE pm FROM {$wpdb->postmeta} pm LEFT JOIN {$wpdb->posts} p ON pm.post_id = p.ID WHERE p.ID IS NULL");
 | |
| 
 | |
| // Clean up user meta for deleted users  
 | |
| $wpdb->query("DELETE um FROM {$wpdb->usermeta} um LEFT JOIN {$wpdb->users} u ON um.user_id = u.ID WHERE u.ID IS NULL");
 | |
| 
 | |
| echo "✅ Cleaned up orphaned meta data\n\n";
 | |
| 
 | |
| // 6. FINAL CLEANUP
 | |
| echo "🗑️  Final cleanup tasks...\n";
 | |
| 
 | |
| // Clear any caches
 | |
| if (function_exists('wp_cache_flush')) {
 | |
|     wp_cache_flush();
 | |
| }
 | |
| 
 | |
| // Clear object cache
 | |
| if (function_exists('wp_cache_delete_group')) {
 | |
|     wp_cache_delete_group('posts');
 | |
|     wp_cache_delete_group('users');
 | |
| }
 | |
| 
 | |
| // Clear transients related to events
 | |
| $wpdb->query("DELETE FROM {$wpdb->options} WHERE option_name LIKE '_transient_tribe_events_%'");
 | |
| $wpdb->query("DELETE FROM {$wpdb->options} WHERE option_name LIKE '_transient_timeout_tribe_events_%'");
 | |
| 
 | |
| echo "✅ Final cleanup completed\n\n";
 | |
| 
 | |
| // SUMMARY
 | |
| echo "========================================\n";
 | |
| echo "🎉 CLEANUP SUMMARY\n";
 | |
| echo "========================================\n";
 | |
| echo "Users removed: {$deleted_users}\n";
 | |
| echo "Events removed: {$deleted_events}\n";
 | |
| echo "Attendees removed: {$deleted_attendees}\n";
 | |
| echo "Tickets removed: {$deleted_tickets}\n";
 | |
| echo "Venues removed: {$deleted_venues}\n";
 | |
| echo "Organizers removed: {$deleted_organizers}\n";
 | |
| echo "Certificates removed: {$deleted_certificates}\n";
 | |
| echo "Certificate files removed: {$deleted_files}\n";
 | |
| echo "========================================\n";
 | |
| echo "✅ Production cleanup completed successfully!\n";
 | |
| echo "Staging is now clean and ready for production deployment.\n";
 | |
| ?>
 | |
| PHPEOF
 | |
| 
 | |
| # Execute the cleanup script on the server
 | |
| echo "Executing cleanup script on staging server..."
 | |
| sshpass -p "$UPSKILL_STAGING_PASS" ssh -o StrictHostKeyChecking=no $UPSKILL_STAGING_SSH_USER@$UPSKILL_STAGING_IP "cd $UPSKILL_STAGING_PATH && php ../tmp/cleanup-test-data.php && rm ../tmp/cleanup-test-data.php"
 | |
| 
 | |
| echo ""
 | |
| echo "========================================="
 | |
| echo "✅ PRODUCTION CLEANUP COMPLETED!"
 | |
| echo "========================================="
 | |
| echo ""
 | |
| echo "The staging environment has been cleaned of all test data:"
 | |
| echo "• Test user accounts removed"
 | |
| echo "• Test events and associated data removed"
 | |
| echo "• Test certificates and files removed"
 | |
| echo "• Orphaned data cleaned up"
 | |
| echo "• Caches cleared"
 | |
| echo ""
 | |
| echo "🚀 Staging is now ready for production deployment!"
 | |
| echo ""
 | |
| echo "Next steps:"
 | |
| echo "1. Verify cleanup was successful"
 | |
| echo "2. Run final tests on staging"
 | |
| echo "3. Deploy to production when ready" |