Introduces a widget system where domains register UI fragments into named slots (container_nav, container_card, account_page, account_link). Host apps iterate widgets generically without naming any domain. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
50 lines
1.4 KiB
Python
50 lines
1.4 KiB
Python
"""Widget descriptors for cross-domain UI composition.
|
|
|
|
Each widget type describes a UI fragment that one domain contributes to
|
|
another domain's page. Host apps iterate widgets generically — they never
|
|
name the contributing domain.
|
|
"""
|
|
from __future__ import annotations
|
|
|
|
from dataclasses import dataclass
|
|
from typing import Callable
|
|
|
|
|
|
@dataclass(frozen=True, slots=True)
|
|
class NavWidget:
|
|
"""Renders nav items on a container page (entries, calendars, markets)."""
|
|
domain: str
|
|
order: int
|
|
context_fn: Callable # async (session, *, container_type, container_id, **kw) -> dict
|
|
template: str
|
|
|
|
|
|
@dataclass(frozen=True, slots=True)
|
|
class CardWidget:
|
|
"""Decorates content cards in listings with domain data."""
|
|
domain: str
|
|
order: int
|
|
batch_fn: Callable # async (session, post_ids) -> dict[int, list]
|
|
context_key: str # key injected into each post dict
|
|
template: str
|
|
|
|
|
|
@dataclass(frozen=True, slots=True)
|
|
class AccountPageWidget:
|
|
"""Sub-page under /auth/<slug>/."""
|
|
domain: str
|
|
slug: str
|
|
label: str
|
|
order: int
|
|
context_fn: Callable # async (session, *, user_id, **kw) -> dict
|
|
template: str
|
|
|
|
|
|
@dataclass(frozen=True, slots=True)
|
|
class AccountNavLink:
|
|
"""Nav link on account page (internal or external)."""
|
|
label: str
|
|
order: int
|
|
href_fn: Callable # () -> str
|
|
external: bool = False
|