Development Workflow Guide¶
Complete guide for developing, testing, and deploying changes to the Odoo 15 system.
Repository Setup¶
Single Company Setup¶
# You already have this - just use it directly
cd /path/to/odoo15-production
git remote -v # Check your remote
Multi-Company / SaaS Setup¶
# Create a template repo, then clone for each client
git clone git@github.com:yourorg/odoo15-production.git client-abc
cd client-abc
# Customize .env for this client
Git Branching Strategy¶
main (production)
│
├── develop (staging/test)
│ │
│ ├── feature/new-sms-template
│ ├── feature/inventory-report
│ └── bugfix/signature-upload
│
└── hotfix/critical-fix (emergency only)
Branch Types¶
| Branch | Purpose | Merges To |
|---|---|---|
main |
Production code | - |
develop |
Integration testing | main |
feature/* |
New features | develop |
bugfix/* |
Bug fixes | develop |
hotfix/* |
Emergency production fixes | main and develop |
Daily Workflow¶
Starting New Work¶
# 1. Always start from develop
git checkout develop
git pull origin develop
# 2. Create feature branch
git checkout -b feature/add-customer-field
# 3. Make your changes
# ... edit files ...
# 4. Test locally
docker compose restart odoo
# Test in browser at localhost:8016
# 5. Commit changes
git add .
git commit -m "feat(signature): Add customer phone field to FSM order"
# 6. Push branch
git push origin feature/add-customer-field
Merging Changes¶
# Option A: Pull Request (recommended for teams)
# Create PR on GitHub, get review, merge via web UI
# Option B: Local merge (solo developer)
git checkout develop
git merge feature/add-customer-field
git push origin develop
# When ready for production
git checkout main
git merge develop
git push origin main
Module Development¶
Creating a New Module¶
# 1. Create module structure
mkdir -p extra-addons/odoo/my_new_module/{models,views,security}
# 2. Create manifest
cat > extra-addons/odoo/my_new_module/__manifest__.py << 'EOF'
{
'name': 'My New Module',
'version': '15.0.1.0.0',
'category': 'Sales',
'summary': 'Description here',
'description': """
My New Module
=============
Detailed description of what this module does.
""",
'author': 'Your Company',
'depends': ['base', 'sale'],
'data': [
'security/ir.model.access.csv',
'views/my_views.xml',
],
'installable': True,
'auto_install': False,
'license': 'LGPL-3',
}
EOF
# 3. Create __init__.py files
echo "from . import models" > extra-addons/odoo/my_new_module/__init__.py
echo "from . import my_model" > extra-addons/odoo/my_new_module/models/__init__.py
# 4. Create model
cat > extra-addons/odoo/my_new_module/models/my_model.py << 'EOF'
from odoo import models, fields, api
class MyModel(models.Model):
_name = 'my.model'
_description = 'My Model'
name = fields.Char('Name', required=True)
description = fields.Text('Description')
EOF
# 5. Create security file
cat > extra-addons/odoo/my_new_module/security/ir.model.access.csv << 'EOF'
id,name,model_id:id,group_id:id,perm_read,perm_write,perm_create,perm_unlink
access_my_model,my.model,model_my_model,base.group_user,1,1,1,1
EOF
# 6. Restart Odoo to detect new module
docker compose restart odoo
# 7. Install module
docker compose exec odoo odoo -i my_new_module --stop-after-init -d odoo_test
Editing Existing Modules¶
# 1. Create branch
git checkout -b bugfix/fix-sms-sending
# 2. Edit files
nano extra-addons/odoo/justcall_sms/models/justcall_sms.py
# 3. Bump version in manifest
nano extra-addons/odoo/justcall_sms/__manifest__.py
# Change version: '15.0.2.0.0' -> '15.0.2.0.1'
# 4. Update module in Odoo
docker compose exec odoo odoo -u justcall_sms --stop-after-init -d odoo_test
# 5. Test your changes
docker compose restart odoo
# 6. Commit
git add .
git commit -m "fix(justcall): Fix SMS sending for international numbers"
Module Commands Reference¶
# Install module
docker compose exec odoo odoo -i MODULE_NAME --stop-after-init -d DATABASE
# Update module
docker compose exec odoo odoo -u MODULE_NAME --stop-after-init -d DATABASE
# Update multiple modules
docker compose exec odoo odoo -u module1,module2,module3 --stop-after-init -d DATABASE
# Update ALL modules (slow, use sparingly)
docker compose exec odoo odoo -u all --stop-after-init -d DATABASE
# Install with dependencies
docker compose exec odoo odoo -i base,sale,MODULE_NAME --stop-after-init -d DATABASE
Documentation Updates¶
When to Update Docs¶
| Change Type | Documentation Action |
|---|---|
| New module created | Create docs/content/modules/new-module.md |
| New feature added | Update relevant module doc |
| API endpoint added | Update docs/content/api/openapi.md |
| Config option added | Update docs/content/getting-started/configuration.md |
| New script created | Update docs/content/operations/ |
How to Update Documentation¶
# 1. Edit markdown files
nano docs/content/modules/justcall-sms.md
# 2. If adding new page, update navigation
nano docs/mkdocs.yml
# Add your page to the nav: section
# 3. Rebuild docs container
docker compose build docs
# 4. Restart docs service
docker compose up -d docs
# 5. Verify in browser
# Open http://localhost:8080
# 6. Check for warnings in build output
docker compose logs docs | grep -i warning
# 7. Commit documentation with code
git add docs/
git commit -m "docs(justcall): Add new template configuration section"
Documentation Structure¶
docs/content/
├── index.md # Homepage
├── getting-started/ # Installation & setup
│ ├── installation.md
│ ├── configuration.md
│ └── quickstart.md
├── modules/ # Module documentation
│ ├── justcall-sms.md
│ ├── service-signature.md
│ └── ...
├── pwa/ # PWA documentation
├── api/ # API reference
├── operations/ # DevOps guides
└── development/ # Developer guides (you are here)
Complete Development Cycle Example¶
Scenario: Add a "Technician Notes" field to FSM orders
# === STEP 1: Create Branch ===
git checkout develop
git pull origin develop
git checkout -b feature/fsm-technician-notes
# === STEP 2: Edit Model ===
nano extra-addons/odoo/jdx_field_service_automation/models/fsm_order.py
Add the field:
# === STEP 3: Edit View ===
nano extra-addons/odoo/jdx_field_service_automation/views/fsm_order_extended.xml
Add to form view:
# === STEP 4: Update Module Version ===
nano extra-addons/odoo/jdx_field_service_automation/__manifest__.py
# Change: 'version': '15.0.0.1', (increment last number)
# === STEP 5: Update Module in Odoo ===
docker compose exec odoo odoo -u jdx_field_service_automation --stop-after-init -d odoo_test
docker compose restart odoo
# === STEP 6: Test in Browser ===
# Open http://localhost:8016
# Navigate to Field Service > Orders
# Verify new field appears
# === STEP 7: Update Documentation ===
nano docs/content/modules/fsm-extensions.md
# Add section about new field
# === STEP 8: Rebuild Docs ===
docker compose build docs
docker compose up -d docs
# === STEP 9: Commit Everything ===
git add .
git commit -m "feat(fsm): Add technician notes field to FSM orders
- Added technician_notes text field to fsm.order model
- Added field to form view
- Updated documentation"
# === STEP 10: Push & Merge ===
git push origin feature/fsm-technician-notes
git checkout develop
git merge feature/fsm-technician-notes
git push origin develop
Deployment Scripts¶
Two scripts simplify the deployment process:
| Script | Location | Purpose |
|---|---|---|
local_deploy.sh |
Your dev machine | Commit and push to GitHub |
production_deploy.sh |
Production server | Pull, build, update, restart |
Quick Usage¶
# === ON YOUR LOCAL MACHINE ===
./local_deploy.sh "feat(justcall): Add MMS support"
# === ON PRODUCTION SERVER ===
./production_deploy.sh update
Common Commands¶
# Local deployment
./local_deploy.sh "your commit message"
# Production - quick update (most common)
./production_deploy.sh update
# Production - update specific module
./production_deploy.sh update-module justcall_sms
# Production - rebuild containers
./production_deploy.sh rebuild-all
./production_deploy.sh rebuild-pwa
./production_deploy.sh rebuild-docs
# Production - service management
./production_deploy.sh status
./production_deploy.sh logs odoo
./production_deploy.sh restart
For complete command reference, see Deployment Scripts Reference.
Production Deployment (Manual Method)¶
If you prefer manual deployment without scripts:
# On production server
ssh user@production-server
cd /opt/odoo15-production
# 1. Backup first!
./scripts/backup.sh full
# 2. Pull latest code
git checkout main
git pull origin main
# 3. Rebuild containers if Dockerfile changed
docker compose build
# 4. Update Odoo modules
docker compose exec odoo odoo -u all --stop-after-init -d odoo_production
# 5. Restart all services
docker compose down
docker compose up -d
# 6. Verify deployment
./scripts/health-check.sh
# 7. Check logs for errors
docker compose logs --tail=50 odoo
Hotfix Deployment (Emergency)¶
# 1. Create hotfix branch from main
git checkout main
git checkout -b hotfix/critical-fix
# 2. Make fix
# ... edit files ...
# 3. Commit
git commit -m "hotfix: Fix critical issue"
# 4. Merge to main immediately
git checkout main
git merge hotfix/critical-fix
git push origin main
# 5. Deploy to production
# (follow standard deployment steps)
# 6. Also merge to develop
git checkout develop
git merge hotfix/critical-fix
git push origin develop
Quick Reference Commands¶
Daily Operations¶
docker compose ps # Check container status
docker compose logs -f odoo # Watch Odoo logs (Ctrl+C to exit)
docker compose logs -f --tail=100 # Last 100 lines, follow
docker compose restart odoo # Restart Odoo
docker compose restart pwa # Restart PWA
docker compose up -d # Start all services
docker compose down # Stop all services
Module Management¶
# Install module
docker compose exec odoo odoo -i MODULE --stop-after-init -d DATABASE
# Update module
docker compose exec odoo odoo -u MODULE --stop-after-init -d DATABASE
# Update all modules
docker compose exec odoo odoo -u all --stop-after-init -d DATABASE
# List installed modules
docker compose exec db psql -U odoo -d odoo_test -c "SELECT name, state FROM ir_module_module WHERE state='installed' ORDER BY name;"
Backup & Restore¶
./scripts/backup.sh full # Full backup (DB + filestore)
./scripts/backup.sh db # Database only
./scripts/restore.sh backup.sql.gz # Restore database
./scripts/health-check.sh # Check all services
Git Commands¶
git status # Check uncommitted changes
git diff # See what changed
git log --oneline -10 # Last 10 commits
git branch -a # List all branches
git stash # Temporarily save changes
git stash pop # Restore stashed changes
Documentation¶
docker compose build docs # Rebuild docs
docker compose up -d docs # Restart docs
docker compose logs docs # Check for build errors
Commit Message Format¶
Use conventional commits format:
Types¶
| Type | Description |
|---|---|
feat |
New feature |
fix |
Bug fix |
docs |
Documentation only |
style |
Formatting, no code change |
refactor |
Code restructuring |
test |
Adding tests |
chore |
Maintenance tasks |
Examples¶
feat(justcall): Add MMS support for outgoing messages
fix(signature): Fix S3 upload timeout for large files
docs(api): Update authentication examples
refactor(pwa): Simplify job list rendering
Best Practices Checklist¶
| Practice | Description |
|---|---|
| Never commit to main directly | Always use feature branches |
| Test before merging | Run on test environment first |
| Update docs with code | Same commit for code + docs |
| Bump version numbers | Update __manifest__.py version |
| Write clear commit messages | type(scope): description format |
| Backup before major changes | ./scripts/backup.sh full |
| Check build warnings | Review docker compose build output |
| Review your diff | git diff before committing |
| Keep branches short-lived | Merge within 1-2 days |
| Delete merged branches | git branch -d feature/done |
Troubleshooting¶
Module Won't Install¶
# Check Odoo logs
docker compose logs odoo | tail -50
# Common fixes:
# 1. Missing dependency - install required module first
# 2. Syntax error - check Python files
# 3. XML error - validate XML files
Changes Not Appearing¶
# 1. Did you update the module?
docker compose exec odoo odoo -u MODULE --stop-after-init -d DATABASE
# 2. Did you restart Odoo?
docker compose restart odoo
# 3. Clear browser cache
# Ctrl+Shift+R or Cmd+Shift+R