Eliminate Python page helpers from orders — pure .sx defpages with IO primitives

Orders defpages now fetch data via (service ...) and generate URLs via
(url-for ...) and (route-prefix) directly in .sx. No Python middleman.

- Add url-for, route-prefix IO primitives to shared/sx/primitives_io.py
- Add generic register()/\_\_getattr\_\_ to ServiceRegistry for dynamic services
- Create OrdersPageService with list_page_data/detail_page_data methods
- Rewrite orders.sx defpages to use IO primitives + defcomp calls
- Remove ~320 lines of Python page helpers from orders/sxc/pages/__init__.py
- Convert :data env merge to use kebab-case keys for SX symbol access

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
2026-03-04 01:50:15 +00:00
parent 50b33ab08e
commit 63b895afd8
7 changed files with 240 additions and 335 deletions

View File

@@ -15,6 +15,8 @@ Usage::
"""
from __future__ import annotations
from typing import Any
from shared.contracts.protocols import (
CalendarService,
MarketService,
@@ -36,6 +38,7 @@ class _ServiceRegistry:
self._market: MarketService | None = None
self._cart: CartService | None = None
self._federation: FederationService | None = None
self._extra: dict[str, Any] = {}
# -- calendar -------------------------------------------------------------
@property
@@ -81,10 +84,27 @@ class _ServiceRegistry:
def federation(self, impl: FederationService) -> None:
self._federation = impl
# -- generic registration --------------------------------------------------
def register(self, name: str, impl: Any) -> None:
"""Register a service by name (for services without typed properties)."""
self._extra[name] = impl
def __getattr__(self, name: str) -> Any:
# Fallback to _extra dict for dynamically registered services
try:
extra = object.__getattribute__(self, "_extra")
if name in extra:
return extra[name]
except AttributeError:
pass
raise AttributeError(f"No service registered as: {name}")
# -- introspection --------------------------------------------------------
def has(self, name: str) -> bool:
"""Check whether a domain service is registered."""
return getattr(self, f"_{name}", None) is not None
if getattr(self, f"_{name}", None) is not None:
return True
return name in self._extra
# Module-level singleton — import this everywhere.