What Is OpenUpgrade?
OpenUpgrade is an OCA (Odoo Community Association) project that provides migration scripts for upgrading between Odoo versions. It handles: database schema changes, data transformations, renamed fields/models, and removed features. It is the standard tool for Community Edition migrations.
When to Use OpenUpgrade
- Migrating Odoo Community Edition (free)
- Single version jumps (e.g., 17 → 18, 18 → 19)
- When you cannot use Odoo.sh (Enterprise only)
- When you want full control over the migration process
Prerequisites
- Working Odoo installation of the target version
- Full database backup of the source version
- Source code of both versions
- Git and Python environment
- Test server (never migrate directly on production)
Step 1: Backup Source Database
# Full backup — CRITICAL: do this first!
pg_dump -U odoo -Fc source_db > /backups/pre_migration_$(date +%Y%m%d).dump
# Also backup filestore
tar -czf /backups/filestore_$(date +%Y%m%d).tar.gz \
/var/lib/odoo/.local/share/Odoo/filestore/source_db/
# Verify backup
pg_restore -l /backups/pre_migration_$(date +%Y%m%d).dump | head -5Step 2: Clone OpenUpgrade
# Clone OpenUpgrade for the TARGET version
git clone https://github.com/OCA/OpenUpgrade.git --branch 19.0 /opt/openupgrade
# Install dependencies
cd /opt/openupgrade
pip install -r requirements.txt
pip install openupgradelib # Helper libraryStep 3: Restore Source Database on Test Server
# Create test database
createdb -U odoo migration_test
# Restore source backup
pg_restore -U odoo -d migration_test /backups/pre_migration.dump
# Copy filestore
cp -r /var/lib/odoo/.local/share/Odoo/filestore/source_db/ \
/var/lib/odoo/.local/share/Odoo/filestore/migration_test/Step 4: Run OpenUpgrade
# Run the migration
python /opt/openupgrade/odoo-bin \
-d migration_test \
--update all \
--stop-after-init \
--load=base,web,openupgrade_framework \
--addons-path=/opt/openupgrade/addons,/opt/odoo/custom-addons \
--logfile=/var/log/odoo/migration.log
# This can take 10 minutes to several hours depending on database sizeStep 5: Check Migration Log
# Look for errors
grep -i "error\|warning\|failed" /var/log/odoo/migration.log | head -50
# Look for OpenUpgrade-specific messages
grep "openupgrade" /var/log/odoo/migration.log | tail -20
# Common warnings (usually safe to ignore):
# "Field X is not found" — renamed in new version
# "Table X does not exist" — removed in new version
# Real errors to fix:
# "FATAL" — migration script failed
# "IntegrityError" — data constraint violated
# "AttributeError" — missing method in custom moduleStep 6: Verify Data Integrity
# Compare record counts
SELECT 'res_partner' as model, count(*) FROM res_partner
UNION ALL
SELECT 'sale_order', count(*) FROM sale_order
UNION ALL
SELECT 'account_move', count(*) FROM account_move
UNION ALL
SELECT 'product_product', count(*) FROM product_product
UNION ALL
SELECT 'stock_move', count(*) FROM stock_move;
# Compare against source database counts
# Any significant difference needs investigation
# Check financial totals
SELECT SUM(amount_total) FROM account_move WHERE move_type = 'out_invoice';
# Should match source databaseStep 7: Migrate Custom Modules
# Custom modules need manual adaptation:
# 1. Update __manifest__.py version
'version': '19.0.1.0.0',
# 2. Fix breaking changes (varies by version)
# Common changes 18 → 19:
# - _sql_constraints → models.Constraint
# - →
# - attrs dict → direct attributes
# 3. Install adapted module
python odoo-bin -d migration_test -i custom_module --stop-after-init
# 4. Run custom module tests
python odoo-bin -d migration_test --test-tags /custom_module --stop-after-initStep 8: Functional Testing
Test every critical business process:
- Login as different user roles
- Create and confirm a sale order
- Create and post an invoice
- Process a payment
- Run bank reconciliation
- Check inventory operations
- Generate PDF reports
- Send an email from Odoo
- Check all dashboards and KPIs
- Verify all cron jobs run correctly
Step 9: Production Migration
# Only after thorough testing:
# 1. Announce maintenance window
# 2. Stop production Odoo
systemctl stop odoo
# 3. Final backup
pg_dump -U odoo -Fc production > /backups/final_pre_migration.dump
# 4. Run migration on production database
python /opt/openupgrade/odoo-bin \
-d production \
--update all \
--stop-after-init \
--load=base,web,openupgrade_framework
# 5. Start new version Odoo
systemctl start odoo
# 6. Verify health check
curl -f http://localhost:8069/web/health
# 7. Monitor closely for 24-48 hoursRollback Plan
# If migration fails:
systemctl stop odoo
# Restore pre-migration backup
dropdb -U odoo production
createdb -U odoo production
pg_restore -U odoo -d production /backups/final_pre_migration.dump
# Restore filestore
rm -rf /var/lib/odoo/.local/share/Odoo/filestore/production/
tar -xzf /backups/filestore_pre_migration.tar.gz -C /
# Start OLD version Odoo
systemctl start odooMulti-Version Jumps
# OpenUpgrade supports ONE version at a time:
# 15 → 16 → 17 → 18 → 19
# Each step requires running OpenUpgrade for that target version
# For large jumps (14 → 19), consider:
# Option A: Sequential migration (5 steps, most reliable)
# Option B: Fresh install + data migration (import key data only)
# Option C: Hybrid (migrate to intermediate version, then fresh + import)DeployMonkey
DeployMonkey simplifies Odoo migrations. Deploy a test instance of the new version, use the AI agent to identify custom module changes needed, run the migration on staging, and verify before touching production.