protocol

package
v0.5.1 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jul 17, 2026 License: MIT Imports: 5 Imported by: 0

Documentation

Overview

Package protocol defines the canonical libp2p wire contract: the stream protocol identifiers, the GossipSub topic names, and the framed message structs that travel over them.

Every identifier is pinned to a single protocol version (1.0.0). A node only speaks to peers that dial the exact same string, so the version is the wire compatibility boundary — bump it deliberately, never per-stream.

The package is transport-agnostic: it owns the names and the bytes, never a host.Host. The auth/receipt/pubsub helpers under pkg/p2p take a caller-built host and register handlers for these identifiers.

Index

Constants

View Source
const (
	// ProtocolAuth carries the nonce-challenge authentication handshake: the
	// server sends an AuthChallenge, the peer returns a signed AuthResponse.
	ProtocolAuth = "/ynp/auth/1.0.0"

	// ProtocolBurnReceipt carries a signed BurnReceipt — the attestation that
	// the L1 execute() of a finalized withdrawal landed — and a ReceiptAck.
	ProtocolBurnReceipt = "/ynp/burnreceipt/1.0.0"

	// ProtocolMintReceipt carries a signed MintReceipt — the attestation that
	// an L1 deposit confirmed — and a ReceiptAck.
	ProtocolMintReceipt = "/ynp/mintreceipt/1.0.0"
)

Stream protocol identifiers. Each names a libp2p request/response or one-shot stream; the body is a cborx envelope (auth) or frame (receipt) of the typed payload. Only the identifiers a shared SDK consumer drives are exported here; the cluster-internal streams (transfer, heartbeat, identify, …) stay in the node that owns them.

TODO(sdk): revisit whether other streams belong here. The rule today is "move a channel iff a consumer of the SDK could legitimately speak it" — so only the three shared custody↔clearnet streams (auth, burn/mint receipt) moved, and the ~14 cluster-internal streams (transfer, swap, shardsync, heartbeat, identify, peerexchange, signature, …) stayed in node.go. If a future consumer needs to dial one of those (and its wire body is extracted to the SDK), promote its identifier here and pin the version.

View Source
const (
	// TopicBlocks fans out sealed *core.Block values.
	TopicBlocks = "/clearnet/blocks.v1"

	// TopicTransfers fans out a batched []core.Event of non-pool events.
	TopicTransfers = "/clearnet/transfers.v1"

	// TopicWithdrawals fans out *core.FinalizedWithdrawal notifications.
	TopicWithdrawals = "/clearnet/withdrawals.v1"

	// TopicChallenges fans out fraud-challenge submissions.
	TopicChallenges = "/clearnet/challenges.v1"
)

GossipSub topic names. The topic name encodes the payload type; a subscriber dispatches on the topic and decodes the body as the cborx envelope of that payload directly (no inner message wrapper).

Variables

This section is empty.

Functions

func PoolTopic

func PoolTopic(anchor [32]byte) string

PoolTopic returns the canonical GossipSub topic for a pool anchor. Format: /clearnet/pool/<anchor-hex>.v1. The payload is a batched []core.Event of pool events (Swap, LiquidityAdded/Removed, Repeg, PoolCreated).

func PoolTopicHex

func PoolTopicHex(anchorHex string) string

PoolTopicHex is the string-anchor variant for call sites that already carry the anchor as hex (no 0x prefix, lowercase, 64 chars).

Types

type AuthChallenge

type AuthChallenge struct {
	Nonce [32]byte
}

AuthChallenge is sent by the server (entry node) to a connecting peer at the start of the auth handshake: 32 random bytes scoped to a single attempt.

Wire encoding: cborx V1 envelope wrapping a 1-tuple (Nonce [32]byte).

func (*AuthChallenge) MarshalCBOR

func (t *AuthChallenge) MarshalCBOR(w io.Writer) error

MarshalCBOR writes AuthChallenge as a 1-element CBOR array.

func (*AuthChallenge) UnmarshalCBOR

func (t *AuthChallenge) UnmarshalCBOR(r io.Reader) error

UnmarshalCBOR reads AuthChallenge from a 1-element CBOR array.

type AuthResponse

type AuthResponse struct {
	Signature []byte
	Address   string
}

AuthResponse is the peer's reply after signing the nonce.

Wire encoding: cborx V1 envelope wrapping a 2-tuple (Signature []byte, Address string). Operator auth sets Address and signs keccak256(Nonce) with the operator secp256k1 key (raw v=0/1 form). Passive auth leaves Address empty and signs a domain-separated nonce with the libp2p identity key; the Address field is then carried empty.

func (*AuthResponse) MarshalCBOR

func (t *AuthResponse) MarshalCBOR(w io.Writer) error

MarshalCBOR writes AuthResponse as a 2-element CBOR array.

func (*AuthResponse) UnmarshalCBOR

func (t *AuthResponse) UnmarshalCBOR(r io.Reader) error

UnmarshalCBOR reads AuthResponse from a 2-element CBOR array.

type ReceiptAck

type ReceiptAck struct {
	Accepted bool
	Reason   string
}

ReceiptAck is the server's response to a burn/mint receipt submission.

Accepted is true when the server persisted the receipt or recognized it as a duplicate of an already-persisted one (the receipt path is idempotent on the natural keys the clearing layer de-dupes by, so retries are safe). Reason carries a short diagnostic when Accepted is false; empty otherwise.

Wire encoding: cborx V1 frame wrapping a 2-tuple (Accepted bool, Reason string).

func (*ReceiptAck) MarshalCBOR

func (t *ReceiptAck) MarshalCBOR(w io.Writer) error

MarshalCBOR writes ReceiptAck as a 2-element CBOR array.

func (*ReceiptAck) UnmarshalCBOR

func (t *ReceiptAck) UnmarshalCBOR(r io.Reader) error

UnmarshalCBOR reads ReceiptAck from a 2-element CBOR array.

type Registrar

type Registrar interface {
	// Register installs the server's stream handlers on h. The caller owns h
	// and its lifecycle; Register only attaches handlers.
	Register(h host.Host)
}

Registrar is implemented by every p2p server: it installs that server's stream handlers on a caller-owned host. Keeping the contract here lets the wiring layer treat auth/receipt/… servers uniformly — register a slice of Registrars against one host without knowing their concrete types.

GossipSub helpers (publish/subscribe over topics) deliberately do NOT implement Registrar: they register no stream handlers, which is the line between a stream protocol and a broadcast topic.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL