Component Base Class

class tabascal.components.Component[source]

Base class for all tabascal components

build_constants() Dict[str, Any][source]

Return arrays that do not change during the forward pass.

Returns a dict of array_name -> array_value. These will be stored in constants as “_c/<ClassName>/array_name” by Model.__init__.

abstractmethod build_forward() Callable[source]

Build the forward computation function

build_set_params() Callable[source]

Build parameter sampling function (optional)

require_double(config: Any) None[source]

Raise if this requires_double component is run in single precision.

Some components only work in double precision: the SGP4/phase trajectory components (differentiable orbits). Those set requires_double = True and call this at the top of setup so they fail with a clear message under single precision instead of producing silently-wrong fp32 results. Driven by the requires_double flag so it stays in sync with the run-time preflight.

abstractmethod setup(tab_config: Any) None[source]

Initialize component with configuration

validate_state(state: Dict[str, Any]) None[source]

Raise if a declared required input is not yet in the model state.

Only the keys of state are meaningful here: this runs at assembly time, where the values are placeholders for keys the model supplies itself. Called for each component in turn by validate_component_order().

exception tabascal.components.ComponentOrderError[source]

model.components is incomplete or in the wrong dependency order.

exception tabascal.components.MissingStateInput(component: str, key: str, message: str)[source]

A component declares a required input that is not in the model state.

Carries the component and key so the caller can say why it is missing – see validate_component_order().

tabascal.components.component_outputs(component) List[str][source]

The state keys a component writes.

state_outputs is what Model actually merges into the state, so it wins once setup has run. Before that – or for a component checked without an observation to set it up against – the class-level output_shapes declaration is the same list.

tabascal.components.component_ref(component) str[source]

The "module:Class" string a component is written as in a config.

tabascal.components.in_tree_components() Dict[str, type][source]

Every concrete component shipped with tabascal, keyed by config reference.

The keys are the "module:Class" strings model.components is written in, so they can be quoted straight back at the user. Abstract bases are left out – they cannot be listed in a config.

tabascal.components.is_class(obj: Any) bool[source]

Whether obj really is a class, on every supported Python.

isinstance(obj, type) is not enough to guard an issubclass call. Up to Python 3.10 a PEP 585 alias such as np.ndarray[Any, np.dtype[Any]] proxies __class__ to its origin, so it passes that check and then makes issubclass raise TypeError: issubclass() arg 1 must be a class. CPython removed the proxy in 3.11 (gh-88912), which is why the module scan below only ever broke on the 3.10 floor – and it scans real module namespaces, where numpy.typing.NDArray was exactly such an alias.

type(obj) is never proxied, so asking whether the real metaclass is a metaclass is stable across versions.

tabascal.components.state_key_producers() Dict[str, List[str]][source]

Map each state key to the in-tree components that write it.

tabascal.components.validate_component_order(components: Sequence[Any], initial_state_keys: Iterable[str] = ()) None[source]

Check a model.components list against the components’ declarations.

Walks the list in order, tracking which state keys exist by the time each component runs – initial_state_keys plus the outputs of everything before it – and raises ComponentOrderError on the first component whose required_inputs are not all there. Runs on constructed components whether or not they have been set up, so the whole list is checked before any of it is traced; without it a missing or mis-ordered component surfaced only as a KeyError on a state key from inside the JIT-ed forward pass.