snnlab
API referencesnnlab.lang

snnlab.lang.core

Complete declared API of the core module, with signatures, data fields, validation and source.

Back to lang reference

Authoring objects are mutable until compilation. Signal shapes use explicit axis names such as time and batch. Projection weights use uS; neuron and synapse factories produce data specifications, not running models. Factory keyword arguments are serialized into the specification and validated when the graph is compiled. Use the compiler and graph executor capability checks before assuming a specification is executable.

The signatures, defaults, fields, docstrings and implementation excerpts below are generated from the Python source. Annotations are shown as declared; unannotated means the source supplies no type annotation. These pages document callable surfaces, including legacy support utilities, without promising backend support for every declaration.

SymbolKind
Quantityclass
Unitclass
SignalLikeclass
Specclass
COBA_LIFfunction
LIFfunction
LeakyIntegratorfunction
AMPAfunction
GABAfunction
Modulatoryfunction
Normalfunction
LowerClampedNormalfunction
SignedNormalfunction
Uniformfunction
Zerosfunction
Constantfunction
NonNegativefunction
Signalclass
ParameterRefclass
Populationclass
Projectionclass
Componentclass
Networkclass

Quantity

View source

Class decorators: dataclass(frozen=True).

Dataclass constructor parameters. Factory defaults are shown as field declarations; omit these arguments to create fresh values per instance:

Quantity(value: float, unit: str)

Declared fields, including fields inherited from local data classes:

FieldAnnotationDefaultMeaning
valuefloatrequiredStored member of this data contract; see the class docstring and serialization methods.
unitstrrequiredDeclared physical unit; projection weights use uS.

Quantity.json

View source

def Quantity.json(self) -> dict[str, Any]

Return annotation: dict[str, Any].

Return expressions (branch-dependent; names refer to the linked implementation):

{'value': self.value, 'unit': self.unit}
Implementation
def json(self) -> dict[str, Any]:
        return {"value": self.value, "unit": self.unit}
Complete class implementation
class Quantity:
    value: float
    unit: str

    def json(self) -> dict[str, Any]:
        return {"value": self.value, "unit": self.unit}

Unit

View source

Constructor:

Unit(self, symbol: str)
ParameterAnnotationDefaultMeaning
symbolstrrequiredDefined by the constructor implementation below.

Instance members assigned by the constructor (expressions are evaluated when constructed):

MemberAnnotationInitial expression
symbolunannotatedsymbol

Unit.rmul

View source

def Unit.__rmul__(self, value: float) -> Quantity
ParameterAnnotationDefaultMeaning
valuefloatrequiredDefined by the source contract and implementation below.

Return annotation: Quantity.

Return expressions (branch-dependent; names refer to the linked implementation):

Quantity(float(value), self.symbol)
Implementation
def __rmul__(self, value: float) -> Quantity:
        return Quantity(float(value), self.symbol)
Complete class implementation
class Unit:
    def __init__(self, symbol: str):
        self.symbol = symbol

    def __rmul__(self, value: float) -> Quantity:
        return Quantity(float(value), self.symbol)

SignalLike

View source

Bases: Protocol. Inherited third-party framework APIs follow their owning library.

Declared fields, including fields inherited from local data classes:

FieldAnnotationDefaultMeaning
idstrrequiredStable identifier in the relevant graph or data contract.
Complete class implementation
class SignalLike(Protocol):
    id: str

Spec

View source

Class decorators: dataclass(frozen=True).

Dataclass constructor parameters. Factory defaults are shown as field declarations; omit these arguments to create fresh values per instance:

Spec(kind: str, values: dict[str, Any] = field(default_factory=dict))

Declared fields, including fields inherited from local data classes:

FieldAnnotationDefaultMeaning
kindstrrequiredStored member of this data contract; see the class docstring and serialization methods.
valuesdict[str, Any]field(default_factory=dict)Stored member of this data contract; see the class docstring and serialization methods.

Spec.json

View source

def Spec.json(self) -> dict[str, Any]

Return annotation: dict[str, Any].

Return expressions (branch-dependent; names refer to the linked implementation):

{'kind': self.kind, **{k: _value(v) for k, v in sorted(self.values.items())}}
Implementation
def json(self) -> dict[str, Any]:
        return {
            "kind": self.kind,
            **{k: _value(v) for k, v in sorted(self.values.items())},
        }
Complete class implementation
class Spec:
    kind: str
    values: dict[str, Any] = field(default_factory=dict)

    def json(self) -> dict[str, Any]:
        return {
            "kind": self.kind,
            **{k: _value(v) for k, v in sorted(self.values.items())},
        }

COBA_LIF

View source

def COBA_LIF(**values: Any) -> Spec

Create a coba_lif neuron specification. Graph execution requires tau_mem as a time Quantity, for example 20 * ms. Other supported fields include capacitance_nf, leak_us, resting_mv, threshold_mv, reset_mv, refractory_steps, voltage_grad_dampen and initial_voltage_mv. Numerical nF, uS and mV fields use the units named. See plan_graph and GraphExecutor for the current lowering contract.

ParameterAnnotationDefaultMeaning
**valuesAnyvariadicDefined by the source contract and implementation below.

Return annotation: Spec.

Return expressions (branch-dependent; names refer to the linked implementation):

Spec('coba_lif', values)
Implementation
def COBA_LIF(**values: Any) -> Spec:
    return Spec("coba_lif", values)

LIF

View source

def LIF(**values: Any) -> Spec

Create a lif neuron specification. This authoring factory is distinct from COBA_LIF; the current graph executor advertises coba_lif and leaky_integrator, so this specification is not automatically graph-executable.

ParameterAnnotationDefaultMeaning
**valuesAnyvariadicDefined by the source contract and implementation below.

Return annotation: Spec.

Return expressions (branch-dependent; names refer to the linked implementation):

Spec('lif', values)
Implementation
def LIF(**values: Any) -> Spec:
    return Spec("lif", values)

LeakyIntegrator

View source

def LeakyIntegrator(**values: Any) -> Spec

Create a leaky_integrator specification. MeanVoltage uses tau, soft_reset_threshold, surrogate_slope and initial_voltage. The authoring factory is shared by the readout population and its projection; these fields describe the serialized contract rather than executing dynamics at construction time.

ParameterAnnotationDefaultMeaning
**valuesAnyvariadicDefined by the source contract and implementation below.

Return annotation: Spec.

Return expressions (branch-dependent; names refer to the linked implementation):

Spec('leaky_integrator', values)
Implementation
def LeakyIntegrator(**values: Any) -> Spec:
    return Spec("leaky_integrator", values)

AMPA

View source

def AMPA(**values: Any) -> Spec

Create an ampa synapse specification. Set tau using a time Quantity, for example 2 * ms. Connect to an excitatory population port; weights are non-negative conductances when a NonNegative constraint is declared.

ParameterAnnotationDefaultMeaning
**valuesAnyvariadicDefined by the source contract and implementation below.

Return annotation: Spec.

Return expressions (branch-dependent; names refer to the linked implementation):

Spec('ampa', values)
Implementation
def AMPA(**values: Any) -> Spec:
    return Spec("ampa", values)

GABA

View source

def GABA(**values: Any) -> Spec

Create a gaba synapse specification. Set tau using a time Quantity, for example 9 * ms. Connect to an inhibitory port; inhibitory polarity is represented by that port and synapse rather than by a negative conductance.

ParameterAnnotationDefaultMeaning
**valuesAnyvariadicDefined by the source contract and implementation below.

Return annotation: Spec.

Return expressions (branch-dependent; names refer to the linked implementation):

Spec('gaba', values)
Implementation
def GABA(**values: Any) -> Spec:
    return Spec("gaba", values)

Modulatory

View source

def Modulatory(**values: Any) -> Spec

Create a modulatory synapse specification. This is supported by authoring but is outside the current graph executor's advertised synapse vocabulary.

ParameterAnnotationDefaultMeaning
**valuesAnyvariadicDefined by the source contract and implementation below.

Return annotation: Spec.

Return expressions (branch-dependent; names refer to the linked implementation):

Spec('modulatory', values)
Implementation
def Modulatory(**values: Any) -> Spec:
    return Spec("modulatory", values)

Normal

View source

def Normal(mean: float, std: float) -> Spec

Source docstring:

Compatibility name for the collection's lower-clamped normal law.
ParameterAnnotationDefaultMeaning
meanfloatrequiredParent distribution mean.
stdfloatrequiredParent distribution standard deviation.

Return annotation: Spec.

Return expressions (branch-dependent; names refer to the linked implementation):

LowerClampedNormal(mean, std)
Implementation
def Normal(mean: float, std: float) -> Spec:
    """Compatibility name for the collection's lower-clamped normal law."""
    return LowerClampedNormal(mean, std)

LowerClampedNormal

View source

def LowerClampedNormal(mean: float, std: float, *, initial_zero_fraction: float=0.0, zeroing: str='bernoulli') -> Spec

Declare Gaussian draws clamped below at zero. mean and std describe the parent Gaussian, not the realised clamped moments. initial_zero_fraction adds initial sparsity; zeroing selects bernoulli or exact_k behavior. Graph projection initialization additionally applies its fan-in convention.

ParameterAnnotationDefaultMeaning
meanfloatrequiredParent distribution mean.
stdfloatrequiredParent distribution standard deviation.
initial_zero_fractionfloat0.0Fraction of additional zeroed weights at initialization.
zeroingstr'bernoulli'Initialization zeroing strategy: bernoulli or exact_k.

Return annotation: Spec.

Return expressions (branch-dependent; names refer to the linked implementation):

Spec('lower_clamped_normal', {'mean': mean, 'std': std, 'initial_zero_fraction': initial_zero_fraction, 'zeroing': zeroing})
Implementation
def LowerClampedNormal(
    mean: float,
    std: float,
    *,
    initial_zero_fraction: float = 0.0,
    zeroing: str = "bernoulli",
) -> Spec:
    return Spec(
        "lower_clamped_normal",
        {
            "mean": mean,
            "std": std,
            "initial_zero_fraction": initial_zero_fraction,
            "zeroing": zeroing,
        },
    )

SignedNormal

View source

def SignedNormal(mean: float, std: float) -> Spec

Declare an unclamped signed Gaussian initializer with parent mean and standard deviation. A separately declared parameter constraint may still project values at execution time.

ParameterAnnotationDefaultMeaning
meanfloatrequiredParent distribution mean.
stdfloatrequiredParent distribution standard deviation.

Return annotation: Spec.

Return expressions (branch-dependent; names refer to the linked implementation):

Spec('signed_normal', {'mean': mean, 'std': std})
Implementation
def SignedNormal(mean: float, std: float) -> Spec:
    return Spec("signed_normal", {"mean": mean, "std": std})

Uniform

View source

def Uniform(low: float, high: float) -> Spec

Declare a uniform initializer with lower and upper bounds low and high.

ParameterAnnotationDefaultMeaning
lowfloatrequiredDefined by the source contract and implementation below.
highfloatrequiredDefined by the source contract and implementation below.

Return annotation: Spec.

Return expressions (branch-dependent; names refer to the linked implementation):

Spec('uniform', {'low': low, 'high': high})
Implementation
def Uniform(low: float, high: float) -> Spec:
    return Spec("uniform", {"low": low, "high": high})

Zeros

View source

def Zeros() -> Spec

Declare an initializer that fills the parameter with zero.

Return annotation: Spec.

Return expressions (branch-dependent; names refer to the linked implementation):

Spec('zeros')
Implementation
def Zeros() -> Spec:
    return Spec("zeros")

Constant

View source

def Constant(value: float) -> Spec

Declare an initializer that fills the parameter with value.

ParameterAnnotationDefaultMeaning
valuefloatrequiredDefined by the source contract and implementation below.

Return annotation: Spec.

Return expressions (branch-dependent; names refer to the linked implementation):

Spec('constant', {'value': value})
Implementation
def Constant(value: float) -> Spec:
    return Spec("constant", {"value": value})

NonNegative

View source

def NonNegative() -> Spec

Declare a non_negative parameter constraint. Graph initialization and optimizer updates apply the non-negative projection where supported.

Return annotation: Spec.

Return expressions (branch-dependent; names refer to the linked implementation):

Spec('non_negative')
Implementation
def NonNegative() -> Spec:
    return Spec("non_negative")

Signal

View source

Class decorators: dataclass(frozen=True).

Dataclass constructor parameters. Factory defaults are shown as field declarations; omit these arguments to create fresh values per instance:

Signal(network: 'Network', id: str, shape: Shape, unit: str, signal_type: str, owner: str, port: str)

Declared fields, including fields inherited from local data classes:

FieldAnnotationDefaultMeaning
network'Network'requiredMutable authoring Network.
idstrrequiredStable identifier in the relevant graph or data contract.
shapeShaperequiredExplicit dimensions/axes or layout shape, as required by the containing contract.
unitstrrequiredDeclared physical unit; projection weights use uS.
signal_typestrrequiredDeclared signal vocabulary, for example spikes or continuous.
ownerstrrequiredStored member of this data contract; see the class docstring and serialization methods.
portstrrequiredStored member of this data contract; see the class docstring and serialization methods.

Signal.json_ref

View source

def Signal.json_ref(self) -> str

Return annotation: str.

Return expressions (branch-dependent; names refer to the linked implementation):

self.id
Implementation
def json_ref(self) -> str:
        return self.id
Complete class implementation
class Signal:
    network: "Network" = field(compare=False, repr=False)
    id: str
    shape: Shape
    unit: str
    signal_type: str
    owner: str
    port: str

    def json_ref(self) -> str:
        return self.id

ParameterRef

View source

Class decorators: dataclass(frozen=True).

Dataclass constructor parameters. Factory defaults are shown as field declarations; omit these arguments to create fresh values per instance:

ParameterRef(network: 'Network', id: str)

Declared fields, including fields inherited from local data classes:

FieldAnnotationDefaultMeaning
network'Network'requiredMutable authoring Network.
idstrrequiredStable identifier in the relevant graph or data contract.
Complete class implementation
class ParameterRef:
    network: "Network" = field(compare=False, repr=False)
    id: str

Population

View source

Class decorators: dataclass.

Dataclass constructor parameters. Factory defaults are shown as field declarations; omit these arguments to create fresh values per instance:

Population(network: 'Network', id: str, size: int, neuron: Spec, spiking: bool, group: str | None)

Declared fields, including fields inherited from local data classes:

FieldAnnotationDefaultMeaning
network'Network'requiredMutable authoring Network.
idstrrequiredStable identifier in the relevant graph or data contract.
sizeintrequiredStored member of this data contract; see the class docstring and serialization methods.
neuronSpecrequiredStored member of this data contract; see the class docstring and serialization methods.
spikingboolrequiredStored member of this data contract; see the class docstring and serialization methods.
groupstr | NonerequiredStored member of this data contract; see the class docstring and serialization methods.

Population.spikes

View source

Decorators: property.

def Population.spikes(self) -> Signal

Return annotation: Signal.

Return expressions (branch-dependent; names refer to the linked implementation):

self.network._signal(f'{self.id}.spikes')

Explicit exceptions in this implementation; called helpers may raise additional errors:

Explicit exception expression
AttributeError(f'{self.id!r} is non-spiking and has no spikes port')
Implementation
def spikes(self) -> Signal:
        if not self.spiking:
            raise AttributeError(f"{self.id!r} is non-spiking and has no spikes port")
        return self.network._signal(f"{self.id}.spikes")

Population.voltage

View source

Decorators: property.

def Population.voltage(self) -> Signal

Return annotation: Signal.

Return expressions (branch-dependent; names refer to the linked implementation):

self.network._signal(f'{self.id}.voltage')
Implementation
def voltage(self) -> Signal:
        return self.network._signal(f"{self.id}.voltage")

Population.excitatory

View source

Decorators: property.

def Population.excitatory(self) -> str

Return annotation: str.

Return expressions (branch-dependent; names refer to the linked implementation):

f'{self.id}.excitatory'
Implementation
def excitatory(self) -> str:
        return f"{self.id}.excitatory"

Population.inhibitory

View source

Decorators: property.

def Population.inhibitory(self) -> str

Return annotation: str.

Return expressions (branch-dependent; names refer to the linked implementation):

f'{self.id}.inhibitory'
Implementation
def inhibitory(self) -> str:
        return f"{self.id}.inhibitory"

Population.modulatory

View source

Decorators: property.

def Population.modulatory(self) -> str

Return annotation: str.

Return expressions (branch-dependent; names refer to the linked implementation):

f'{self.id}.modulatory'
Implementation
def modulatory(self) -> str:
        return f"{self.id}.modulatory"
Complete class implementation
class Population:
    network: "Network" = field(repr=False)
    id: str
    size: int
    neuron: Spec
    spiking: bool
    group: str | None

    @property
    def spikes(self) -> Signal:
        if not self.spiking:
            raise AttributeError(f"{self.id!r} is non-spiking and has no spikes port")
        return self.network._signal(f"{self.id}.spikes")

    @property
    def voltage(self) -> Signal:
        return self.network._signal(f"{self.id}.voltage")

    @property
    def excitatory(self) -> str:
        return f"{self.id}.excitatory"

    @property
    def inhibitory(self) -> str:
        return f"{self.id}.inhibitory"

    @property
    def modulatory(self) -> str:
        return f"{self.id}.modulatory"

Projection

View source

Class decorators: dataclass.

Dataclass constructor parameters. Factory defaults are shown as field declarations; omit these arguments to create fresh values per instance:

Projection(network: 'Network', id: str, source: str, target: str, synapse: Spec, connection: str, delay: Quantity | None, parameter_ids: tuple[str, ...], group: str | None, enabled: bool)

Declared fields, including fields inherited from local data classes:

FieldAnnotationDefaultMeaning
network'Network'requiredMutable authoring Network.
idstrrequiredStable identifier in the relevant graph or data contract.
sourcestrrequiredStored member of this data contract; see the class docstring and serialization methods.
targetstrrequiredStored member of this data contract; see the class docstring and serialization methods.
synapseSpecrequiredSerialized synapse specification.
connectionstrrequiredDeclared connection kind, for example feedforward, recurrent or feedback.
delayQuantity | NonerequiredPhysical projection delay; graph execution requires integral timestep alignment.
parameter_idstuple[str, ...]requiredStored member of this data contract; see the class docstring and serialization methods.
groupstr | NonerequiredStored member of this data contract; see the class docstring and serialization methods.
enabledboolrequiredWhether an authored projection contributes conductance during execution.

Projection.weight

View source

Decorators: property.

def Projection.weight(self) -> ParameterRef

Return annotation: ParameterRef.

Return expressions (branch-dependent; names refer to the linked implementation):

ParameterRef(self.network, self.parameter_ids[0])
Implementation
def weight(self) -> ParameterRef:
        return ParameterRef(self.network, self.parameter_ids[0])
Complete class implementation
class Projection:
    network: "Network" = field(repr=False)
    id: str
    source: str
    target: str
    synapse: Spec
    connection: str
    delay: Quantity | None
    parameter_ids: tuple[str, ...]
    group: str | None
    enabled: bool

    @property
    def weight(self) -> ParameterRef:
        return ParameterRef(self.network, self.parameter_ids[0])

Component

View source

Class decorators: dataclass.

Dataclass constructor parameters. Factory defaults are shown as field declarations; omit these arguments to create fresh values per instance:

Component(name: str, members: list[str] = field(default_factory=list), parent: str | None = None)

Declared fields, including fields inherited from local data classes:

FieldAnnotationDefaultMeaning
namestrrequiredName used to identify the authored or rendered object.
memberslist[str]field(default_factory=list)Stored member of this data contract; see the class docstring and serialization methods.
parentstr | NoneNoneStored member of this data contract; see the class docstring and serialization methods.
Complete class implementation
class Component:
    name: str
    members: list[str] = field(default_factory=list)
    parent: str | None = None

Network

View source

Source docstring:

Mutable Python authoring surface; compilation produces immutable data.

Constructor:

Network(self, name: str, *, dt: Quantity=0.1 * ms)
ParameterAnnotationDefaultMeaning
namestrrequiredName used to identify the authored or rendered object.
dtQuantity0.1 * msTimestep; authoring uses a Quantity and legacy simulation uses milliseconds.

Instance members assigned by the constructor (expressions are evaluated when constructed):

MemberAnnotationInitial expression
nameunannotatedname
dtunannotateddt
inputslist[dict[str, Any]][]
populationslist[dict[str, Any]][]
projectionslist[dict[str, Any]][]
operationslist[dict[str, Any]][]
parameterslist[dict[str, Any]][]
constantslist[dict[str, Any]][]
outputslist[dict[str, Any]][]
observableslist[dict[str, Any]][]
assetslist[dict[str, Any]][]
groupsdict[str, Component]{}

Network.current_group

View source

Decorators: property.

def Network.current_group(self) -> str | None

Return annotation: str \| None.

Return expressions (branch-dependent; names refer to the linked implementation):

self._group_stack[-1] if self._group_stack else None
Implementation
def current_group(self) -> str | None:
        return self._group_stack[-1] if self._group_stack else None

Network.input

View source

def Network.input(self, name: str, *, shape: Shape, signal_type: str, unit: str='1') -> Signal

Register an input and return its Signal. A spike input conventionally uses shape=(time, batch, channels), signal_type=spikes and unit=spike. Input names are graph ids; concrete tensors and input recipes are supplied at execution time.

ParameterAnnotationDefaultMeaning
namestrrequiredName used to identify the authored or rendered object.
shapeShaperequiredExplicit dimensions/axes or layout shape, as required by the containing contract.
signal_typestrrequiredDeclared signal vocabulary, for example spikes or continuous.
unitstr'1'Declared physical unit; projection weights use uS.

Return annotation: Signal.

Return expressions (branch-dependent; names refer to the linked implementation):

signal
Implementation
def input(
        self, name: str, *, shape: Shape, signal_type: str, unit: str = "1"
    ) -> Signal:
        self._claim(name)
        signal = Signal(
            self, f"{name}.value", tuple(shape), unit, signal_type, name, "value"
        )
        self._signals[signal.id] = signal
        self.inputs.append(
            {"id": name, "shape": list(shape), "signal_type": signal_type, "unit": unit}
        )
        return signal

Network.population

View source

def Network.population(self, name: str, *, size: int, neuron: Spec, spiking: bool=True) -> Population

Register a population and its voltage port, and optionally its spikes port. Return a Population handle. size must be positive; neuron is a serialized Spec. Non-spiking populations have no usable spikes property.

ParameterAnnotationDefaultMeaning
namestrrequiredName used to identify the authored or rendered object.
sizeintrequiredDefined by the source contract and implementation below.
neuronSpecrequiredDefined by the source contract and implementation below.
spikingboolTrueDefined by the source contract and implementation below.

Return annotation: Population.

Return expressions (branch-dependent; names refer to the linked implementation):

Population(self, name, size, neuron, spiking, group)

Explicit exceptions in this implementation; called helpers may raise additional errors:

Explicit exception expression
ValueError('population size must be positive')
Implementation
def population(
        self, name: str, *, size: int, neuron: Spec, spiking: bool = True
    ) -> Population:
        self._claim(name)
        if size <= 0:
            raise ValueError("population size must be positive")
        group = self.current_group
        self.populations.append(
            {
                "id": name,
                "size": size,
                "neuron": neuron.json(),
                "spiking": spiking,
                "group": group,
            }
        )
        if spiking:
            self._signals[f"{name}.spikes"] = Signal(
                self,
                f"{name}.spikes",
                ("time", "batch", size),
                "spike",
                "spikes",
                name,
                "spikes",
            )
        self._signals[f"{name}.voltage"] = Signal(
            self,
            f"{name}.voltage",
            ("time", "batch", size),
            "mV",
            "voltage",
            name,
            "voltage",
        )
        return Population(self, name, size, neuron, spiking, group)

Network.parameter

View source

def Network.parameter(self, name: str, *, shape: Shape, initializer: Spec, unit: str='1', constraint: Spec | None=None) -> ParameterRef

Register a named parameter with explicit shape, initializer, unit and optional constraint. Return a ParameterRef for sharing that parameter in authored projections or operations.

ParameterAnnotationDefaultMeaning
namestrrequiredName used to identify the authored or rendered object.
shapeShaperequiredExplicit dimensions/axes or layout shape, as required by the containing contract.
initializerSpecrequiredSerialized parameter initialization law.
unitstr'1'Declared physical unit; projection weights use uS.
constraintSpec | NoneNoneParameter constraint or Graphviz layout constraint, as annotated.

Return annotation: ParameterRef.

Return expressions (branch-dependent; names refer to the linked implementation):

ParameterRef(self, name)
Implementation
def parameter(
        self,
        name: str,
        *,
        shape: Shape,
        initializer: Spec,
        unit: str = "1",
        constraint: Spec | None = None,
    ) -> ParameterRef:
        self._claim(name)
        self.parameters.append(
            {
                "id": name,
                "shape": list(shape),
                "unit": unit,
                "initializer": initializer.json(),
                "constraint": constraint.json() if constraint else None,
                "group": self.current_group,
            }
        )
        return ParameterRef(self, name)

Network.constant

View source

def Network.constant(self, name: str, value: Any, *, unit: str='1') -> str

Register a named serialized value with a unit, and return its id.

ParameterAnnotationDefaultMeaning
namestrrequiredName used to identify the authored or rendered object.
valueAnyrequiredDefined by the source contract and implementation below.
unitstr'1'Declared physical unit; projection weights use uS.

Return annotation: str.

Return expressions (branch-dependent; names refer to the linked implementation):

name
Implementation
def constant(self, name: str, value: Any, *, unit: str = "1") -> str:
        self._claim(name)
        self.constants.append({"id": name, "value": _value(value), "unit": unit})
        return name

Network.connect

View source

def Network.connect(self, source: Signal, target: str, *, name: str, synapse: Spec, weight: Spec | ParameterRef=Constant(1.0), constraint: Spec | None=None, connection: str='feedforward', delay: Quantity | None=None, enabled: bool=True) -> Projection

Register a projection to a population port. A new weight specification creates a parameter with authored shape (target size, source channels) and unit uS. A ParameterRef reuses a named parameter. enabled=False retains topology and parameter identity but contributes no runtime conductance. Delay and backend capability checks occur during validation/planning.

ParameterAnnotationDefaultMeaning
sourceSignalrequiredDefined by the source contract and implementation below.
targetstrrequiredDefined by the source contract and implementation below.
namestrrequiredName used to identify the authored or rendered object.
synapseSpecrequiredSerialized synapse specification.
weightSpec | ParameterRefConstant(1.0)Defined by the source contract and implementation below.
constraintSpec | NoneNoneParameter constraint or Graphviz layout constraint, as annotated.
connectionstr'feedforward'Declared connection kind, for example feedforward, recurrent or feedback.
delayQuantity | NoneNonePhysical projection delay; graph execution requires integral timestep alignment.
enabledboolTrueWhether an authored projection contributes conductance during execution.

Return annotation: Projection.

Return expressions (branch-dependent; names refer to the linked implementation):

Projection(self, name, source.id, target, synapse, connection, delay, (parameter_id,), self.current_group, enabled)

Explicit exceptions in this implementation; called helpers may raise additional errors:

Explicit exception expression
ValueError('source belongs to another network')
ValueError(f'invalid target port: {target}')
ValueError(f'invalid connection kind: {connection}')
TypeError('projection enabled must be boolean')
Implementation
def connect(
        self,
        source: Signal,
        target: str,
        *,
        name: str,
        synapse: Spec,
        weight: Spec | ParameterRef = Constant(1.0),
        constraint: Spec | None = None,
        connection: str = "feedforward",
        delay: Quantity | None = None,
        enabled: bool = True,
    ) -> Projection:
        self._claim(name)
        target_pop, _, target_port = target.partition(".")
        populations = {p["id"]: p for p in self.populations}
        if source.network is not self:
            raise ValueError("source belongs to another network")
        if target_pop not in populations or target_port not in {
            "excitatory",
            "inhibitory",
            "modulatory",
        }:
            raise ValueError(f"invalid target port: {target}")
        if connection not in {"feedforward", "recurrent", "feedback", "modulatory"}:
            raise ValueError(f"invalid connection kind: {connection}")
        if not isinstance(enabled, bool):
            raise TypeError("projection enabled must be boolean")
        if isinstance(weight, ParameterRef):
            parameter_id = weight.id
        else:
            parameter_id = f"{name}.weight"
            self.parameters.append(
                {
                    "id": parameter_id,
                    "shape": [populations[target_pop]["size"], source.shape[-1]],
                    "unit": "uS",
                    "initializer": weight.json(),
                    "constraint": constraint.json() if constraint else None,
                    "group": self.current_group,
                }
            )
        row = {
            "id": name,
            "source": source.id,
            "target": target,
            "synapse": synapse.json(),
            "connection": connection,
            "polarity": target_port,
            "delay": _value(delay),
            "parameters": [parameter_id],
            "group": self.current_group,
        }
        if not enabled:
            row["enabled"] = False
        self.projections.append(row)
        return Projection(
            self,
            name,
            source.id,
            target,
            synapse,
            connection,
            delay,
            (parameter_id,),
            self.current_group,
            enabled,
        )

Network.operation

View source

def Network.operation(self, kind: str, sources: Signal | Sequence[Signal], *, name: str, shape: Shape, unit: str, signal_type: str='continuous', parameters: Sequence[ParameterRef]=(), **config: Any) -> Signal

Register an operation with explicit inputs, output shape, units and parameter references. Return its output Signal. Extra keyword arguments become the operation config; the executor accepts only its advertised operation vocabulary.

ParameterAnnotationDefaultMeaning
kindstrrequiredDefined by the source contract and implementation below.
sourcesSignal | Sequence[Signal]requiredDefined by the source contract and implementation below.
namestrrequiredName used to identify the authored or rendered object.
shapeShaperequiredExplicit dimensions/axes or layout shape, as required by the containing contract.
unitstrrequiredDeclared physical unit; projection weights use uS.
signal_typestr'continuous'Declared signal vocabulary, for example spikes or continuous.
parametersSequence[ParameterRef]()Defined by the source contract and implementation below.
**configAnyvariadicDefined by the source contract and implementation below.

Return annotation: Signal.

Return expressions (branch-dependent; names refer to the linked implementation):

signal

Explicit exceptions in this implementation; called helpers may raise additional errors:

Explicit exception expression
ValueError('operation source belongs to another network')
Implementation
def operation(
        self,
        kind: str,
        sources: Signal | Sequence[Signal],
        *,
        name: str,
        shape: Shape,
        unit: str,
        signal_type: str = "continuous",
        parameters: Sequence[ParameterRef] = (),
        **config: Any,
    ) -> Signal:
        self._claim(name)
        source_list = [sources] if isinstance(sources, Signal) else list(sources)
        if any(s.network is not self for s in source_list):
            raise ValueError("operation source belongs to another network")
        signal = Signal(
            self, f"{name}.value", tuple(shape), unit, signal_type, name, "value"
        )
        self._signals[signal.id] = signal
        self.operations.append(
            {
                "id": name,
                "kind": kind,
                "sources": [s.id for s in source_list],
                "shape": list(shape),
                "unit": unit,
                "signal_type": signal_type,
                "parameters": [p.id for p in parameters],
                "config": {k: _value(v) for k, v in sorted(config.items())},
                "group": self.current_group,
            }
        )
        return signal

Network.output

View source

def Network.output(self, name: str, signal: SignalLike) -> SignalLike

Register a named output pointing at a signal or readout id, and return the supplied handle unchanged.

ParameterAnnotationDefaultMeaning
namestrrequiredName used to identify the authored or rendered object.
signalSignalLikerequiredDefined by the source contract and implementation below.

Return annotation: SignalLike.

Return expressions (branch-dependent; names refer to the linked implementation):

signal
Implementation
def output(self, name: str, signal: SignalLike) -> SignalLike:
        self._claim(name)
        self.outputs.append({"id": name, "signal": signal.id})
        return signal

Network.expose

View source

def Network.expose(self, *signals: Signal, name: str | None=None) -> None

Register observable signals. A single supplied name is used directly; multiple signals with a name become name_0, name_1 and so on. Without a name, observable ids use each signal's owner and port.

ParameterAnnotationDefaultMeaning
*signalsSignalvariadicDefined by the source contract and implementation below.
namestr | NoneNoneName used to identify the authored or rendered object.

Return annotation: None.

Implementation
def expose(self, *signals: Signal, name: str | None = None) -> None:
        for index, signal in enumerate(signals):
            obs_name = (
                name if name and len(signals) == 1 else f"{signal.owner}_{signal.port}"
            )
            if len(signals) > 1 and name:
                obs_name = f"{name}_{index}"
            self._claim(obs_name)
            self.observables.append({"id": obs_name, "signal": signal.id})

Network.asset

View source

def Network.asset(self, name: str, *, media_type: str, description: str='') -> str

Declare a logical asset and return its id. Pass physical source files in compile(assets=...) so compilation can authenticate and copy them into the bundle.

ParameterAnnotationDefaultMeaning
namestrrequiredName used to identify the authored or rendered object.
media_typestrrequiredDefined by the source contract and implementation below.
descriptionstr''Defined by the source contract and implementation below.

Return annotation: str.

Return expressions (branch-dependent; names refer to the linked implementation):

name
Implementation
def asset(self, name: str, *, media_type: str, description: str = "") -> str:
        self._claim(name)
        self.assets.append(
            {"id": name, "media_type": media_type, "description": description}
        )
        return name

Network.group

View source

Decorators: contextmanager.

def Network.group(self, name: str, *, parent: str | None=None) -> Iterator[Component]

Context manager that assigns newly authored elements to a component group. An optional parent must already exist. The active group is removed from the stack when the context exits.

ParameterAnnotationDefaultMeaning
namestrrequiredName used to identify the authored or rendered object.
parentstr | NoneNoneDefined by the source contract and implementation below.

Return annotation: Iterator[Component].

Explicit exceptions in this implementation; called helpers may raise additional errors:

Explicit exception expression
ValueError(f'unknown parent group: {parent}')
Implementation
def group(self, name: str, *, parent: str | None = None) -> Iterator[Component]:
        self._claim(name)
        if parent and parent not in self.groups:
            raise ValueError(f"unknown parent group: {parent}")
        component = Component(name, parent=parent)
        self.groups[name] = component
        self._group_stack.append(name)
        try:
            yield component
        finally:
            self._group_stack.pop()
Complete class implementation
class Network:
    """Mutable Python authoring surface; compilation produces immutable data."""

    def __init__(self, name: str, *, dt: Quantity = 0.1 * ms):
        self.name = name
        self.dt = dt
        self.inputs: list[dict[str, Any]] = []
        self.populations: list[dict[str, Any]] = []
        self.projections: list[dict[str, Any]] = []
        self.operations: list[dict[str, Any]] = []
        self.parameters: list[dict[str, Any]] = []
        self.constants: list[dict[str, Any]] = []
        self.outputs: list[dict[str, Any]] = []
        self.observables: list[dict[str, Any]] = []
        self.assets: list[dict[str, Any]] = []
        self.groups: dict[str, Component] = {}
        self._signals: dict[str, Signal] = {}
        self._names: set[str] = set()
        self._group_stack: list[str] = []

    @property
    def current_group(self) -> str | None:
        return self._group_stack[-1] if self._group_stack else None

    def _claim(self, name: str) -> None:
        if not name or any(c.isspace() for c in name):
            raise ValueError(
                f"name must be non-empty and contain no whitespace: {name!r}"
            )
        if name in self._names:
            raise ValueError(f"duplicate name: {name}")
        self._names.add(name)
        if self.current_group:
            self.groups[self.current_group].members.append(name)

    def _signal(self, signal_id: str) -> Signal:
        return self._signals[signal_id]

    def input(
        self, name: str, *, shape: Shape, signal_type: str, unit: str = "1"
    ) -> Signal:
        self._claim(name)
        signal = Signal(
            self, f"{name}.value", tuple(shape), unit, signal_type, name, "value"
        )
        self._signals[signal.id] = signal
        self.inputs.append(
            {"id": name, "shape": list(shape), "signal_type": signal_type, "unit": unit}
        )
        return signal

    def population(
        self, name: str, *, size: int, neuron: Spec, spiking: bool = True
    ) -> Population:
        self._claim(name)
        if size <= 0:
            raise ValueError("population size must be positive")
        group = self.current_group
        self.populations.append(
            {
                "id": name,
                "size": size,
                "neuron": neuron.json(),
                "spiking": spiking,
                "group": group,
            }
        )
        if spiking:
            self._signals[f"{name}.spikes"] = Signal(
                self,
                f"{name}.spikes",
                ("time", "batch", size),
                "spike",
                "spikes",
                name,
                "spikes",
            )
        self._signals[f"{name}.voltage"] = Signal(
            self,
            f"{name}.voltage",
            ("time", "batch", size),
            "mV",
            "voltage",
            name,
            "voltage",
        )
        return Population(self, name, size, neuron, spiking, group)

    def parameter(
        self,
        name: str,
        *,
        shape: Shape,
        initializer: Spec,
        unit: str = "1",
        constraint: Spec | None = None,
    ) -> ParameterRef:
        self._claim(name)
        self.parameters.append(
            {
                "id": name,
                "shape": list(shape),
                "unit": unit,
                "initializer": initializer.json(),
                "constraint": constraint.json() if constraint else None,
                "group": self.current_group,
            }
        )
        return ParameterRef(self, name)

    def constant(self, name: str, value: Any, *, unit: str = "1") -> str:
        self._claim(name)
        self.constants.append({"id": name, "value": _value(value), "unit": unit})
        return name

    def connect(
        self,
        source: Signal,
        target: str,
        *,
        name: str,
        synapse: Spec,
        weight: Spec | ParameterRef = Constant(1.0),
        constraint: Spec | None = None,
        connection: str = "feedforward",
        delay: Quantity | None = None,
        enabled: bool = True,
    ) -> Projection:
        self._claim(name)
        target_pop, _, target_port = target.partition(".")
        populations = {p["id"]: p for p in self.populations}
        if source.network is not self:
            raise ValueError("source belongs to another network")
        if target_pop not in populations or target_port not in {
            "excitatory",
            "inhibitory",
            "modulatory",
        }:
            raise ValueError(f"invalid target port: {target}")
        if connection not in {"feedforward", "recurrent", "feedback", "modulatory"}:
            raise ValueError(f"invalid connection kind: {connection}")
        if not isinstance(enabled, bool):
            raise TypeError("projection enabled must be boolean")
        if isinstance(weight, ParameterRef):
            parameter_id = weight.id
        else:
            parameter_id = f"{name}.weight"
            self.parameters.append(
                {
                    "id": parameter_id,
                    "shape": [populations[target_pop]["size"], source.shape[-1]],
                    "unit": "uS",
                    "initializer": weight.json(),
                    "constraint": constraint.json() if constraint else None,
                    "group": self.current_group,
                }
            )
        row = {
            "id": name,
            "source": source.id,
            "target": target,
            "synapse": synapse.json(),
            "connection": connection,
            "polarity": target_port,
            "delay": _value(delay),
            "parameters": [parameter_id],
            "group": self.current_group,
        }
        if not enabled:
            row["enabled"] = False
        self.projections.append(row)
        return Projection(
            self,
            name,
            source.id,
            target,
            synapse,
            connection,
            delay,
            (parameter_id,),
            self.current_group,
            enabled,
        )

    def operation(
        self,
        kind: str,
        sources: Signal | Sequence[Signal],
        *,
        name: str,
        shape: Shape,
        unit: str,
        signal_type: str = "continuous",
        parameters: Sequence[ParameterRef] = (),
        **config: Any,
    ) -> Signal:
        self._claim(name)
        source_list = [sources] if isinstance(sources, Signal) else list(sources)
        if any(s.network is not self for s in source_list):
            raise ValueError("operation source belongs to another network")
        signal = Signal(
            self, f"{name}.value", tuple(shape), unit, signal_type, name, "value"
        )
        self._signals[signal.id] = signal
        self.operations.append(
            {
                "id": name,
                "kind": kind,
                "sources": [s.id for s in source_list],
                "shape": list(shape),
                "unit": unit,
                "signal_type": signal_type,
                "parameters": [p.id for p in parameters],
                "config": {k: _value(v) for k, v in sorted(config.items())},
                "group": self.current_group,
            }
        )
        return signal

    def output(self, name: str, signal: SignalLike) -> SignalLike:
        self._claim(name)
        self.outputs.append({"id": name, "signal": signal.id})
        return signal

    def expose(self, *signals: Signal, name: str | None = None) -> None:
        for index, signal in enumerate(signals):
            obs_name = (
                name if name and len(signals) == 1 else f"{signal.owner}_{signal.port}"
            )
            if len(signals) > 1 and name:
                obs_name = f"{name}_{index}"
            self._claim(obs_name)
            self.observables.append({"id": obs_name, "signal": signal.id})

    def asset(self, name: str, *, media_type: str, description: str = "") -> str:
        self._claim(name)
        self.assets.append(
            {"id": name, "media_type": media_type, "description": description}
        )
        return name

    @contextmanager
    def group(self, name: str, *, parent: str | None = None) -> Iterator[Component]:
        self._claim(name)
        if parent and parent not in self.groups:
            raise ValueError(f"unknown parent group: {parent}")
        component = Component(name, parent=parent)
        self.groups[name] = component
        self._group_stack.append(name)
        try:
            yield component
        finally:
            self._group_stack.pop()

Constants and type aliases

Initial source expressions are shown, not evaluated runtime values. Legacy configuration may mutate module defaults.

NameAnnotationInitial expressionSource
Shapeunannotatedtuple[int | str, ...]Source
msunannotatedUnit('ms')Source
mVunannotatedUnit('mV')Source
nSunannotatedUnit('nS')Source
uSunannotatedUnit('uS')Source
HzunannotatedUnit('Hz')Source

On this page