Most WHMCS upgrades are uneventful. The ones that aren't are usually preventable. Skipping the prep, running the upgrade on live traffic, not testing modules — these are the three reasons I get called in to "fix WHMCS after an upgrade." The fix is always slower than doing it right the first time.
This is the runbook I use on every WHMCS upgrade, from a 50-customer dev site to a 30,000-customer production deployment.
When to upgrade — and when to wait
WHMCS ships major releases (8.10, 8.11, etc.) every few months and minor patches between them. My policy:
- Security patches: within 7 days of release. No exceptions.
- Minor versions: within 30 days, after I see other hosts upgrade without obvious issues.
- Major versions: after a 60-90 day waiting period. Let other hosting companies find the edge cases first.
- Never on a Friday. Never the day before a public holiday. Schedule for low-traffic hours.
Subscribe to the WHMCS release notes RSS and security alerts. Don't rely on the "Update Available" banner alone — it can lag the actual release.
Step 1 — Pre-upgrade checklist
Run all of these before the upgrade. Each one is cheap; collectively they prevent the bad day.
# 1. Confirm current version
cat /path/to/whmcs/init.php | grep -i 'version'
# OR look at WHMCS Admin → Help → About
# 2. Confirm target version's requirements
# Visit https://docs.whmcs.com/Server_Requirements_Page for the target version
# Match PHP version, MySQL/MariaDB version, extensions
# 3. Take a full backup
mysqldump --single-transaction -u root -p whmcs_db > /backup/whmcs_predupgrade_$(date +%Y%m%d).sql
tar czf /backup/whmcs_files_$(date +%Y%m%d).tar.gz /path/to/whmcs/
# 4. Verify backup integrity
mysql -u root -p -e "CREATE DATABASE whmcs_restore_test;"
mysql -u root -p whmcs_restore_test < /backup/whmcs_preupgrade_*.sql
mysql -u root -p -e "DROP DATABASE whmcs_restore_test;"
# 5. Check disk space
df -h # Confirm 2x the size of WHMCS + DB free
# 6. List installed modules
ls /path/to/whmcs/modules/addons/
ls /path/to/whmcs/modules/servers/
ls /path/to/whmcs/modules/gateways/
ls /path/to/whmcs/modules/registrars/
# Save this list - you'll need to verify each module after the upgrade
Also in WHMCS Admin:
- Utilities → System → System Health Status — confirm everything is green.
- Setup → General Settings → Security — make a note of the encryption hash. If you ever lose this hash, your encrypted data (server passwords, payment credentials) becomes unrecoverable.
- Help → Module & Version Compatibility (if available) — checks installed modules against the target version.
Step 2 — Run the upgrade on staging first
This step is non-negotiable on any install above ~1,000 customers.
Set up staging:
# Clone the files
rsync -av /path/to/production/whmcs/ /path/to/staging/whmcs/
# Clone the database
mysqldump --single-transaction whmcs_prod > /tmp/dump.sql
mysql -e "CREATE DATABASE whmcs_staging;"
mysql whmcs_staging < /tmp/dump.sql
# Update staging's configuration.php with the staging DB name and license key
# (you may need a dev WHMCS license; request one from WHMCS)
# Disable outgoing emails on staging (critical — see EmailPreSend hook in my hooks guide)
# Add a hook in /includes/hooks/staging_email_block.php to short-circuit all sends
Run the upgrade on staging end-to-end. Verify:
- Login works (both admin + client).
- All custom modules load without errors.
- Cron runs cleanly.
- Test order completes end-to-end.
- Test ticket can be opened and replied to.
- Custom theme renders correctly.
- API endpoints respond correctly.
If any of these fail on staging, fix them before touching production.
Step 3 — Execute the production upgrade
Pick a window with the lowest expected traffic. Communicate to customers if the maintenance window is >15 minutes — a banner on the client area is sufficient for short windows.
# 1. Take a fresh backup (yes, again)
mysqldump --single-transaction -u root -p whmcs_db > /backup/whmcs_upgrade_$(date +%Y%m%d%H%M).sql
# 2. Enable maintenance mode (optional but recommended)
# Setup → General Settings → Other → Maintenance Mode: enabled with a message
# 3. Disable WHMCS cron temporarily to prevent overlap with upgrade
# Comment out the cron line in crontab, or rename cron.php briefly
# 4. Download the new WHMCS files from members.whmcs.com (you need an active license)
# Upload to a temp directory
# 5. Run the upgrade
# Method A: Replace files in-place (riskier)
rsync -av --exclude='configuration.php' --exclude='attachments/' --exclude='downloads/' /tmp/new_whmcs/ /path/to/whmcs/
# Method B (preferred): rename existing folder, move new files in, copy critical files over
mv /path/to/whmcs /path/to/whmcs.old
mv /tmp/new_whmcs /path/to/whmcs
cp /path/to/whmcs.old/configuration.php /path/to/whmcs/
rsync -av /path/to/whmcs.old/attachments/ /path/to/whmcs/attachments/
rsync -av /path/to/whmcs.old/downloads/ /path/to/whmcs/downloads/
rsync -av /path/to/whmcs.old/modules/ /path/to/whmcs/modules/ # keep your custom modules!
# 6. Run the database upgrade
# Visit https://yourwhmcs.com/install/upgrade.php in your browser
# Or use the CLI alternative if available
# 7. Re-enable cron
# Uncomment the cron line, or rename cron.php back
# 8. Disable maintenance mode
The upgrade installer runs database migrations. Don't kill the browser tab while it runs — incomplete migrations leave the schema in a half-state. If it hangs for >10 minutes, get into MySQL directly and check what's running (SHOW PROCESSLIST).
Step 4 — Post-upgrade verification
Run the same end-to-end test you ran on staging:
- Admin login works.
- Client login works (impersonate a client).
- System Health Status shows green.
- Cron runs cleanly (force it:
php /path/to/whmcs/crons/cron.php). - Place a tiny test order — pay with a test gateway or your own card; refund after.
- Open a test support ticket.
- Send a test email (Utilities → Send Test Email).
- Check Activity Log for errors / deprecation warnings in the last 10 minutes.
Watch the activity log for the next 30 minutes. Anything unusual (errors that weren't there before, deprecation notices from your custom modules, slow queries) gets attention now while the upgrade is fresh in mind.
Step 5 — How to roll back if needed
If the upgrade fails badly and the fix isn't immediate, rollback:
# 1. Maintenance mode ON (if not already)
# 2. Restore files
mv /path/to/whmcs /path/to/whmcs.broken
mv /path/to/whmcs.old /path/to/whmcs
# 3. Restore database
mysql -u root -p whmcs_db < /backup/whmcs_upgrade_YYYYMMDDHHMM.sql
# 4. Re-enable cron, disable maintenance mode
# 5. Confirm working
You're now back to the pre-upgrade state. Investigate what went wrong on staging; do not re-attempt the upgrade until you understand the failure.
Why I keep the old folder around for at least 7 days post-upgrade: sometimes a customer reports a specific bug a few days later, and you want to diff the relevant files quickly.
The module compatibility problem
Major WHMCS upgrades deprecate or remove APIs. Your custom modules (and marketplace modules) may break. Strategy:
- Inventory all installed modules with their versions before the upgrade (see the
lscommands in step 1). - Check each module's release notes for compatibility with the target WHMCS version.
- Upgrade modules first, then WHMCS. If a module's latest version supports both your current WHMCS and the target — upgrade the module first as a separate change. This isolates failures.
- For abandoned modules (last updated 12+ months ago, no compatibility statement): find a replacement or fork it. Don't upgrade WHMCS hoping the module still works.
Common pitfalls
"Upgrade installer hangs at 'Updating database tables.'" Long-running ALTER TABLE on a big tblmodulelog or tblactivitylog. Wait — it'll complete. Don't interrupt. Schedule the upgrade for off-peak hours so this isn't blocking customers.
"Module Log shows mysterious errors after upgrade." Often deprecation warnings from custom modules. Read them — they tell you exactly which function to update.
"Custom theme broke." Theme inheritance changed in some versions. Re-test against the new six default theme. If you edited six directly (bad), restore your changes from backup.
"License invalid after upgrade." The encryption hash changed or the license check is failing. Check Utilities → System → System Information → Reload License Info. If still broken, log in to members.whmcs.com and reissue the license.
"Performance degraded after upgrade." New WHMCS versions occasionally ship with more aggressive defaults (e.g., extra logging). Tune them down if needed. Also check if OPcache picked up the new files — restart PHP-FPM.
My take — the discipline that prevents incidents
- Schedule upgrades, don't do them spontaneously. A scheduled Saturday morning upgrade beats a Friday afternoon "just upgrade real quick."
- Always run staging first above a certain scale. The cost of a staging environment is much less than one botched upgrade.
- Keep an upgrade log per WHMCS install. Date of each upgrade, version from/to, any issues encountered. The third upgrade of the year you'll forget what you learned the first two times.
- Subscribe to the security mailing list at whmcs.com/security. Security patches don't wait for your scheduled window.
Going further
I run WHMCS upgrades for hosting businesses — staging setup, module compatibility audits, the upgrade itself, and the post-upgrade verification. If you're sitting on an outdated WHMCS and afraid to upgrade, tell me what version you're on and I'll send a quote + plan in 24 hours.