Skip to content

relay

relay

Validated Nostr relay URL with network type detection.

Parses, normalizes, and validates WebSocket relay URLs (ws:// or wss://), automatically detecting the NetworkType (clearnet, Tor, I2P, Lokinet) and enforcing the correct scheme for each network. Local and private IP addresses are rejected.

See Also

bigbrotr.models.constants: Defines the NetworkType enum used for classification. bigbrotr.models.event_relay: Links a Relay to an Event via the event_relay junction table. bigbrotr.models.relay_metadata: Links a Relay to a Metadata record via the relay_metadata junction table. bigbrotr.utils.transport: Uses Relay URLs for WebSocket connectivity checks.

Classes

RelayDbParams

Bases: NamedTuple

Positional parameters for the relay database insert procedure.

Produced by Relay.to_db_params() and consumed by the relay_insert stored procedure in PostgreSQL.

Attributes:

  • url (str) –

    Fully normalized WebSocket URL including scheme.

  • network (str) –

    Network type string (e.g., "clearnet", "tor").

  • discovered_at (int) –

    Unix timestamp when the relay was first discovered.

See Also

Relay: The model that produces these parameters. Relay.from_db_params(): Reconstructs a Relay from these parameters.

Relay dataclass

Relay(
    raw_url: str,
    discovered_at: int = (lambda: int(time()))(),
)

Immutable representation of a Nostr relay.

Validates and normalizes a WebSocket URL on construction, detecting the NetworkType from the hostname. The scheme is enforced per network:

  • clearnet -- wss:// (TLS required on the public internet)
  • tor / i2p / loki -- ws:// (encryption handled by the overlay)

Attributes:

  • url (str) –

    Fully normalized URL including scheme.

  • network (NetworkType) –

    Detected NetworkType enum value.

  • scheme (str) –

    URL scheme (ws or wss).

  • host (str) –

    Hostname or IP address (brackets stripped for IPv6).

  • port (int | None) –

    Explicit port number, or None when using the default.

  • path (str | None) –

    URL path component, or None.

  • discovered_at (int) –

    Unix timestamp when the relay was first discovered.

Raises:

  • ValueError

    If the URL is malformed, uses an unsupported scheme, resolves to a local/private address, or contains null bytes.

Examples:

relay = Relay("wss://relay.damus.io")
relay.url       # 'wss://relay.damus.io'
relay.network   # NetworkType.CLEARNET
relay.scheme    # 'wss'
relay.to_db_params()
# RelayDbParams(url='wss://relay.damus.io', network='clearnet', ...)

Overlay networks automatically use ws://:

tor_relay = Relay("wss://abc123.onion")
tor_relay.scheme    # 'ws'
tor_relay.network   # NetworkType.TOR
Note

from_db_params() always re-parses the URL through __post_init__, re-detecting the network type rather than trusting the stored network value. This is by design for safety -- it guarantees that a Relay instance is always fully validated, even when reconstructed from the database.

Computed fields are set via object.__setattr__ in __post_init__ because the dataclass is frozen. This is the standard workaround and is safe because it runs during __init__ before the instance is exposed.

See Also

NetworkType: Enum of supported network types. RelayDbParams: Database parameter container produced by to_db_params(). RelayMetadata: Junction linking a relay to a Metadata record. EventRelay: Junction linking a relay to an Event.

Functions
to_db_params
to_db_params() -> RelayDbParams

Return cached positional parameters for the database insert procedure.

The result is computed once during construction and cached for the lifetime of the (frozen) instance, avoiding repeated network name conversions.

Returns:

Source code in src/bigbrotr/models/relay.py
def to_db_params(self) -> RelayDbParams:
    """Return cached positional parameters for the database insert procedure.

    The result is computed once during construction and cached for the
    lifetime of the (frozen) instance, avoiding repeated network name
    conversions.

    Returns:
        [RelayDbParams][bigbrotr.models.relay.RelayDbParams] with the
        normalized URL, network name, and discovery timestamp.
    """
    return self._db_params
from_db_params classmethod
from_db_params(params: RelayDbParams) -> Relay

Reconstruct a Relay from database parameters.

The URL is re-parsed and re-validated through __post_init__; the network field in params is not used directly because it is recomputed from the URL.

Parameters:

Returns:

Note

The re-parsing behavior is intentional -- it guarantees that every Relay instance is fully validated regardless of origin, at the cost of a small overhead on reconstruction.

Source code in src/bigbrotr/models/relay.py
@classmethod
def from_db_params(cls, params: RelayDbParams) -> Relay:
    """Reconstruct a [Relay][bigbrotr.models.relay.Relay] from database parameters.

    The URL is re-parsed and re-validated through ``__post_init__``; the
    ``network`` field in *params* is **not** used directly because it is
    recomputed from the URL.

    Args:
        params: Database row values previously produced by
            [to_db_params()][bigbrotr.models.relay.Relay.to_db_params].

    Returns:
        A new [Relay][bigbrotr.models.relay.Relay] instance.

    Note:
        The re-parsing behavior is intentional -- it guarantees that every
        Relay instance is fully validated regardless of origin, at the cost
        of a small overhead on reconstruction.
    """
    return cls(params.url, params.discovered_at)

Functions