Austin JDX Backup & Restore¶
Production backup and restore procedures specific to austinjdx.com.
Production Environment¶
| Component | Value |
|---|---|
| RDS Host | db.austinjdx.com |
| RDS Port | 5432 |
| Database User | austinjdx |
| Database Name | production |
| PostgreSQL Version | 15.14 |
| Filestore Path | /var/lib/odoo/.local/share/Odoo/filestore/production |
pg_dump vs psql¶
Critical: Use pg_dump, NOT psql
psql is for running queries. It will NOT create a valid backup.
Backup Commands¶
Basic Backup¶
With Compression (Recommended)¶
pg_dump -h db.austinjdx.com -p 5432 -U austinjdx -d production | gzip > backup-$(date +%Y%m%d).sql.gz
Fastest - Parallel Custom Format¶
pg_dump -h db.austinjdx.com -p 5432 -U austinjdx -d production -Fc -j 4 -f backup-$(date +%Y%m%d).dump
For Cross-Environment Restore (Production → Docker)¶
Use --no-owner to avoid role errors when restoring to Docker:
pg_dump -h db.austinjdx.com -p 5432 -U austinjdx -d production --no-owner --no-acl | gzip > backup-noowner-$(date +%Y%m%d).sql.gz
Without --no-owner, you'll see:
Filestore Backup¶
sudo tar -czvf filestore-$(date +%Y%m%d).tar.gz -C /var/lib/odoo/.local/share/Odoo/filestore production
Download to Local Machine¶
If you have SSH configured with an alias (e.g., ssh austinjdx), you can use the same alias with scp.
Create Backup on Production Server¶
# SSH to production and create database backup
ssh austinjdx "pg_dump -h db.austinjdx.com -p 5432 -U austinjdx -d production --no-owner --no-acl | gzip > /home/ubuntu/backup-$(date +%Y%m%d).sql.gz"
# Filestore backup (run on production server)
ssh austinjdx "sudo tar -czvf /home/ubuntu/filestore-$(date +%Y%m%d).tar.gz -C /var/lib/odoo/.local/share/Odoo/filestore production"
Download Files¶
# List available backups
ssh austinjdx "ls -lh /home/ubuntu/*.gz"
# Download database backup
scp austinjdx:/home/ubuntu/backup-$(date +%Y%m%d).sql.gz .
# Download filestore (typically 500-700MB)
scp austinjdx:/home/ubuntu/filestore-$(date +%Y%m%d).tar.gz .
One-Step Database Dump (Alternative)¶
Stream directly to local machine without storing on server:
ssh austinjdx "pg_dump -h db.austinjdx.com -p 5432 -U austinjdx -d production --no-owner --no-acl" | gzip > backup-$(date +%Y%m%d).sql.gz
Restore to Docker¶
Step 1: Stop Odoo¶
Step 2: Drop and Recreate Database¶
docker compose exec db psql -U odoo -d postgres -c "DROP DATABASE IF EXISTS odoo_test;"
docker compose exec db psql -U odoo -d postgres -c "CREATE DATABASE odoo_test OWNER odoo;"
Step 3: Restore Backup¶
# From compressed file
gunzip -c backup-noowner-$(date +%Y%m%d).sql.gz | docker compose exec -T db psql -U odoo -d odoo_test
# From uncompressed file
cat backup.sql | docker compose exec -T db psql -U odoo -d odoo_test
Step 4: Restore Filestore¶
# Remove old filestore
sudo rm -rf odoo-data/filestore/odoo_test
# Extract production filestore
sudo tar -xzvf /path/to/filestore-YYYYMMDD.tar.gz -C odoo-data/filestore/
# Rename to match database name
sudo mv odoo-data/filestore/production odoo-data/filestore/odoo_test
# Fix permissions (101 is the odoo user inside container)
sudo chown -R 101:101 odoo-data/filestore/odoo_test
Step 5: Start Odoo¶
Auto Backup Module¶
Production uses the auto_backup Odoo module which requires paramiko.
Error After Restore¶
Fix¶
# Add to odoo/requirements.txt
echo "paramiko>=3.0.0" >> odoo/requirements.txt
# Rebuild and restart
docker compose build odoo
docker compose up -d odoo
The paramiko dependency is already included in odoo/requirements.txt:
Module Schema Sync¶
When restoring production to Docker, schema mismatches occur if modules differ between environments.
Common Errors¶
psycopg2.errors.UndefinedColumn: column res_company.sale_order_prefix does not exist
psycopg2.errors.UndefinedTable: relation "helpdesk_ticket_assign_wizard" does not exist
ERROR: Some modules are not loaded: ['sync_google_contact']
Fix: Upgrade Modules¶
Step 1: Upgrade stock module first (required for jdx_core_data):
Step 2: Then upgrade custom modules:
docker compose run --rm odoo odoo -d odoo_test \
-u bi_product_dimension,jdx_sale_order_photos,jdx_service_signature,jdx_field_service_automation,helpdesk,restapi \
--stop-after-init
docker compose start odoo
stock.route Error
If you see KeyError: 'stock.route' when installing modules, upgrade the stock module first:
Uninstall Missing Modules¶
If a module exists in database but not in addons (e.g., sync_google_contact):
docker compose exec db psql -U odoo -d odoo_test -c "
UPDATE ir_module_module SET state = 'uninstalled' WHERE name = 'sync_google_contact';
DELETE FROM ir_model_data WHERE module = 'sync_google_contact';
"
Clean Up Invalid Views¶
After removing modules, orphaned views cause 500 errors:
Field "middle_name" does not exist in model "res.partner"
Field "module_google_contacts" does not exist in model "res.config.settings"
Fix:
docker compose exec db psql -U odoo -d odoo_test -c "
DELETE FROM ir_ui_view
WHERE arch_db LIKE '%middle_name%'
OR arch_db LIKE '%module_google_contacts%'
OR arch_db LIKE '%remove_token%';
"
Clean Up Orphaned Models¶
If you see warnings like Model google.contacts is declared but cannot be loaded:
docker compose exec db psql -U odoo -d odoo_test -c "
DELETE FROM ir_model WHERE model IN ('google.contacts', 'google.details', 'google.groups');
DELETE FROM ir_model_fields WHERE model IN ('google.contacts', 'google.details', 'google.groups');
"
Troubleshooting Checklist¶
500 Error After Restore¶
-
Check logs:
-
Look for:
UndefinedColumn,UndefinedTable, missing module errors
Missing Column Errors¶
Option A: Run module upgrade (recommended)
Option B: Manually add column
docker compose exec db psql -U odoo -d odoo_test -c "
ALTER TABLE res_company ADD COLUMN IF NOT EXISTS sale_order_prefix VARCHAR(10);
ALTER TABLE res_company ADD COLUMN IF NOT EXISTS sale_order_next_number INTEGER DEFAULT 1;
"
Missing Module Errors¶
Uninstall from database:
docker compose exec db psql -U odoo -d odoo_test -c "
UPDATE ir_module_module SET state = 'uninstalled' WHERE name = 'module_name';
DELETE FROM ir_model_data WHERE module = 'module_name';
"
Transaction Errors (InFailedSqlTransaction)¶
If persists, check earlier log entries for root cause.
PostgreSQL Version Check¶
| Environment | Version |
|---|---|
| Production RDS | 15.14 |
| Docker | 15.15 |
Both use PostgreSQL 15.x - fully compatible.
# Check Production
psql -h db.austinjdx.com -p 5432 -U austinjdx -d production -c "SELECT version();"
# Check Docker
docker compose exec db psql -U odoo -d postgres -c "SELECT version();"
Quick Reference¶
Full Backup & Restore to Docker¶
# 1. Backup from production (--no-owner avoids role errors on restore)
ssh austinjdx "pg_dump -h db.austinjdx.com -p 5432 -U austinjdx -d production --no-owner --no-acl | gzip > /home/ubuntu/backup.sql.gz"
ssh austinjdx "sudo tar -czvf /home/ubuntu/filestore.tar.gz -C /var/lib/odoo/.local/share/Odoo/filestore production"
# 2. Download to local
scp austinjdx:/home/ubuntu/backup.sql.gz .
scp austinjdx:/home/ubuntu/filestore.tar.gz .
# 3. Stop Odoo
docker compose stop odoo
# 4. Recreate database
docker compose exec db psql -U odoo -d postgres -c "DROP DATABASE IF EXISTS odoo_test;"
docker compose exec db psql -U odoo -d postgres -c "CREATE DATABASE odoo_test OWNER odoo;"
# 5. Restore database
gunzip -c backup.sql.gz | docker compose exec -T db psql -U odoo -d odoo_test
# 6. Restore filestore
sudo rm -rf odoo-data/filestore/odoo_test
sudo tar -xzvf filestore.tar.gz -C odoo-data/filestore/
sudo mv odoo-data/filestore/production odoo-data/filestore/odoo_test
sudo chown -R 101:101 odoo-data/filestore/odoo_test
# 7. Uninstall missing sync_google_contact module
docker compose exec db psql -U odoo -d odoo_test -c "
UPDATE ir_module_module SET state = 'uninstalled' WHERE name = 'sync_google_contact';
DELETE FROM ir_model_data WHERE module = 'sync_google_contact';
"
# 8. Upgrade purchase and stock modules
docker compose run --rm odoo odoo -d odoo_test -u purchase,stock --stop-after-init
# 9. Upgrade custom modules (includes restapi binary fix)
docker compose run --rm odoo odoo -d odoo_test -u bi_product_dimension,jdx_sale_order_photos,jdx_service_signature,jdx_field_service_automation,helpdesk,restapi --stop-after-init
# 10. Clean up invalid views from removed modules
docker compose exec db psql -U odoo -d odoo_test -c "
DELETE FROM ir_ui_view
WHERE arch_db LIKE '%middle_name%'
OR arch_db LIKE '%module_google_contacts%'
OR arch_db LIKE '%remove_token%';
"
# 11. Clear assets cache
docker compose exec db psql -U odoo -d odoo_test -c "DELETE FROM ir_attachment WHERE url LIKE '/web/assets/%';"
# 12. Start Odoo
docker compose start odoo
# 13. Test (clear browser cache first)
curl -s http://localhost:8016/web/login -o /dev/null -w "%{http_code}"
# Should return: 200
REST API Binary Fix
Step 9 upgrades the restapi module which includes a fix for binary attachment handling. Without this, creating attachments with images via REST API fails with UTF-8 decode errors. See Troubleshooting > REST API Issues for details.
View Conflict Fixed
The purchase_stock view conflict (Element '<xpath expr="//div[@t-elif='o.date_order']">' cannot be located) is now permanently fixed.
The bi_product_dimension module was restructured to use position="attributes" with display:none instead of position="replace". This preserves the original DOM structure that purchase_stock needs. No need to delete views manually - just upgrade purchase,stock together.