fix(fusion_clock): planning port defers when planning ORM not loaded during -u

fusion_clock doesn't depend on planning, so planning's models load AFTER it
during -u and the port saw no data. Now detect planning tables via SQL,
defer (no marker) when the ORM isn't loaded, and finish the port from the
deploy odoo-shell step (full registry). Marker now owned by the method.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
gsinghpal
2026-06-04 21:28:34 -04:00
parent 498963e83a
commit 1630a2025f
3 changed files with 43 additions and 17 deletions

View File

@@ -620,17 +620,38 @@ class FusionClockSchedule(models.Model):
@api.model
def _fclk_port_planning_data(self):
"""Port Odoo Planning data (roles, employee roles, slots) into the
native models. Safe no-op when planning is not installed. Returns a
dict of counts. Called by the 19.0.5.0.0 migration and by tests."""
native models. Idempotent (marker-guarded). Returns a dict of counts.
Because fusion_clock does NOT depend on planning, during a `-u` planning
may load AFTER us, so its ORM models aren't available in the migration's
registry. When that happens we set ``deferred`` and do nothing; the
deploy then runs this again from `odoo shell`, where the whole registry
(planning included) is loaded. Called by the 19.0.5.0.0 migration, the
deploy shell step, and tests."""
import pytz
counts = {'roles': 0, 'employees': 0, 'slots': 0, 'skipped': 0}
counts = {'roles': 0, 'employees': 0, 'slots': 0, 'skipped': 0, 'deferred': False}
env = self.env
has_roles = 'planning.role' in env
has_slots = 'planning.slot' in env
if not has_roles and not has_slots:
ICP = env['ir.config_parameter'].sudo()
if ICP.get_param('fusion_clock.planning_migrated'):
return counts
# Do the planning tables exist at all? (raw SQL — independent of whether
# planning's ORM models are loaded in this registry.)
env.cr.execute(
"SELECT to_regclass('public.planning_role'), to_regclass('public.planning_slot')")
role_tbl, slot_tbl = env.cr.fetchone()
if not role_tbl and not slot_tbl:
ICP.set_param('fusion_clock.planning_migrated', '1') # Community / fresh
return counts
# Tables exist but the ORM models may not be loaded yet -> defer.
if 'planning.slot' not in env or 'planning.role' not in env:
counts['deferred'] = True
return counts
has_roles = bool(role_tbl)
has_slots = bool(slot_tbl)
Role = env['fusion.clock.role'].sudo()
role_map = {}
if has_roles:
@@ -692,6 +713,8 @@ class FusionClockSchedule(models.Model):
except Exception as exc:
counts['skipped'] += 1
_logger.warning("Fusion Clock: skip planning.slot %s (%s).", slot.id, exc)
ICP.set_param('fusion_clock.planning_migrated', '1')
return counts