Namespace Changes (g2p.* → spp.*)
Contents
Namespace Changes (g2p.* → spp.*)#
This guide is for developers migrating code from the g2p.* namespace to spp.* namespace in OpenSPP V2.
Overview#
OpenSPP V2 renames all g2p.* modules and models to spp.* for clarity and ownership:
Module names:
g2p_*→spp_*Model names:
g2p.*→spp.*XML IDs:
g2p_*→spp_*
This change affects all G2P-derived modules in the OpenSPP codebase.
Module Name Changes#
Core Registry Modules#
V1 Module |
V2 Module |
Notes |
|---|---|---|
|
|
Consolidated from 4 modules |
|
|
Merged into base |
|
|
Merged into base |
|
|
Merged into base |
Program Modules#
V1 Module |
V2 Module |
Notes |
|---|---|---|
|
|
Renamed |
|
|
Namespace change only |
|
|
Namespace change only |
|
|
Namespace change only |
Payment & Banking Modules#
V1 Module |
V2 Module |
Notes |
|---|---|---|
|
|
Renamed |
|
|
Namespace change only |
|
|
Namespace change only |
Security & Credentials#
V1 Module |
V2 Module |
Notes |
|---|---|---|
|
|
Namespace change only |
|
|
Renamed for clarity |
|
|
Renamed |
Other Modules#
V1 Module |
V2 Module |
Notes |
|---|---|---|
|
|
Namespace change only |
Update Module Dependencies#
In __manifest__.py#
# Before (V1)
{
'name': 'Custom Farmer Module',
'version': '17.0.1.0.0',
'depends': [
'g2p_registry_base',
'g2p_registry_individual',
'g2p_programs',
'g2p_bank',
],
}
# After (V2)
{
'name': 'Custom Farmer Module',
'version': '19.0.1.0.0', # Note Odoo version change
'depends': [
'spp_registry_base', # Individual/group merged in
'spp_programs_base', # Note: _base suffix
'spp_banking', # Note: different name
],
}
Consolidated Modules#
Several registry modules were consolidated. Update dependencies:
# Before (V1) - Multiple dependencies
'depends': [
'g2p_registry_base',
'g2p_registry_individual',
'g2p_registry_group',
]
# After (V2) - Single dependency
'depends': [
'spp_registry_base', # Contains all registry functionality
]
Update Import Statements#
Python Imports#
No changes needed for Python imports - models are referenced by string name:
# Both V1 and V2 use the same pattern
self.env['spp.program'] # Model string changes, not imports
XML External IDs#
Update all external ID references:
# Before (V1)
<field name="ref" eval="ref('g2p_registry_base.group_g2p_admin')" />
<field name="model_id" ref="g2p_programs.model_g2p_program" />
# After (V2)
<field name="ref" eval="ref('spp_registry_base.group_spp_admin')" />
<field name="model_id" ref="spp_programs_base.model_spp_program" />
Update Model References#
In Python Code#
# Before (V1)
registrant = self.env['g2p.registrant'].search([])
program = self.env['g2p.program'].browse(program_id)
entitlement = self.env['g2p.entitlement'].create(vals)
# After (V2)
registrant = self.env['spp.registrant'].search([])
program = self.env['spp.program'].browse(program_id)
entitlement = self.env['spp.entitlement'].create(vals)
In XML Views#
<!-- Before (V1) -->
<record id="view_g2p_program_form" model="ir.ui.view">
<field name="model">g2p.program</field>
<field name="arch" type="xml">
<form>
<!-- form content -->
</form>
</field>
</record>
<!-- After (V2) -->
<record id="view_spp_program_form" model="ir.ui.view">
<field name="model">spp.program</field>
<field name="arch" type="xml">
<form>
<!-- form content -->
</form>
</field>
</record>
In Security Rules#
# Before (V1) - ir.model.access.csv
id,name,model_id:id,group_id:id,perm_read,perm_write,perm_create,perm_unlink
access_g2p_program_user,access_g2p_program_user,model_g2p_program,group_g2p_user,1,0,0,0
# After (V2) - ir.model.access.csv
id,name,model_id:id,group_id:id,perm_read,perm_write,perm_create,perm_unlink
access_spp_program_user,access_spp_program_user,model_spp_program,group_spp_user,1,0,0,0
Automated Migration Script#
Use this script to update module dependencies:
#!/usr/bin/env python3
"""
Update module dependencies from g2p to spp
Usage: python update_manifest.py /path/to/module
"""
import ast
import sys
from pathlib import Path
# Module renames (comprehensive list)
MODULE_RENAMES = {
'g2p_registry_base': 'spp_registry_base',
'g2p_registry_individual': 'spp_registry_base',
'g2p_registry_group': 'spp_registry_base',
'g2p_registry_membership': 'spp_registry_base',
'g2p_programs': 'spp_programs_base',
'g2p_bank': 'spp_banking',
'g2p_encryption': 'spp_encryption',
'g2p_openid_vci': 'spp_credentials',
'g2p_openid_vci_rest_api': 'spp_credentials_rest_api',
'g2p_payment_interop_layer': 'spp_payment_interop_layer',
'g2p_payment_phee': 'spp_payment_phee',
'g2p_program_assessment': 'spp_program_assessment',
'g2p_program_approval': 'spp_program_approval',
'g2p_program_cycleless': 'spp_program_cycleless',
'g2p_entitlement_in_kind': 'spp_entitlement_in_kind',
}
def update_manifest(manifest_path):
"""Update __manifest__.py with new module names"""
content = manifest_path.read_text()
# Simple string replacement
for old, new in MODULE_RENAMES.items():
content = content.replace(f"'{old}'", f"'{new}'")
content = content.replace(f'"{old}"', f'"{new}"')
manifest_path.write_text(content)
print(f"✓ Updated {manifest_path}")
def main():
if len(sys.argv) != 2:
print("Usage: python update_manifest.py /path/to/module")
sys.exit(1)
module_path = Path(sys.argv[1])
manifest_path = module_path / '__manifest__.py'
if not manifest_path.exists():
print(f"Error: {manifest_path} not found")
sys.exit(1)
update_manifest(manifest_path)
if __name__ == "__main__":
main()
Search and Replace Patterns#
For Module Names in __manifest__.py#
# In your custom module directory
sed -i "s/'g2p_registry_base'/'spp_registry_base'/g" __manifest__.py
sed -i "s/'g2p_programs'/'spp_programs_base'/g" __manifest__.py
sed -i "s/'g2p_bank'/'spp_banking'/g" __manifest__.py
For Model Names in Python Files#
# Replace in all Python files
find . -name "*.py" -exec sed -i 's/g2p\.registrant/spp.registrant/g' {} \;
find . -name "*.py" -exec sed -i 's/g2p\.program/spp.program/g' {} \;
find . -name "*.py" -exec sed -i 's/g2p\.entitlement/spp.entitlement/g' {} \;
For XML IDs in XML Files#
# Replace in all XML files
find . -name "*.xml" -exec sed -i 's/g2p_registry_base\./spp_registry_base./g' {} \;
find . -name "*.xml" -exec sed -i 's/g2p_programs\./spp_programs_base./g' {} \;
Testing After Migration#
After updating namespace references, verify:
# tests/test_namespace_migration.py
from odoo.tests import TransactionCase
class TestNamespaceMigration(TransactionCase):
def test_models_exist(self):
"""Verify all spp.* models are accessible"""
# Test your commonly used models
self.assertTrue(self.env['spp.registrant'])
self.assertTrue(self.env['spp.program'])
def test_external_ids_work(self):
"""Verify external IDs resolve correctly"""
group = self.env.ref('spp_registry_base.group_spp_admin')
self.assertTrue(group.exists())
def test_module_installed(self):
"""Verify dependencies are installed"""
module = self.env['ir.module.module'].search([
('name', '=', 'spp_registry_base'),
('state', '=', 'installed')
])
self.assertTrue(module.exists())
Common Migration Issues#
Issue: Module Not Found#
ModuleNotFoundError: No module named 'g2p_registry_base'
Solution: Update dependency in __manifest__.py from g2p_* to spp_*
Issue: Model Does Not Exist#
ValueError: Model 'g2p.program' does not exist
Solution: Update model string from g2p.* to spp.* in your code
Issue: External ID Not Found#
ValueError: External ID not found: g2p_registry_base.group_g2p_admin
Solution: Update external ID reference from g2p_*.* to spp_*.*
See Also#
Model and Field Renames - Complete list of model renames
Breaking Changes - Odoo 19 compatibility issues
openspp.org