Files
coracle-rust/book/plan/addresses.md
T
2026-04-17 16:43:56 -07:00

2.6 KiB

Plan: Addresses

Overview

This chapter introduces the Address struct — a stable reference to a replaceable or addressable event. Where an event ID is a hash of a specific version, an address is the triple (kind, pubkey, identifier) that names the slot a mutable event occupies.

Prerequisites

Reader has already covered: keys (PublicKey, bech32), tags (Tags, d-tag access via tags.value("d")), events (Event struct), kinds (kind ranges, is_addressable, is_replaceable).

Structure

1. Motivation (prose only)

  • Event IDs are hashes of content — they change when the content changes
  • For replaceable/addressable events, you need a stable reference
  • An address is kind:pubkey:identifier — it names the slot, not the version

2. The module

  • Register pub mod addresses; in lib.rs
  • Import dependencies: keys::PublicKey, tags::Tag, events::Event, kinds, bech32, std::fmt, std::str::FromStr

3. Error type

  • AddressError enum: InvalidFormat, InvalidBech32, WrongPrefix, InvalidKey, FieldMissing(&'static str), TlvError

4. The Address struct

  • Fields: kind: u16, pubkey: PublicKey, identifier: String
  • Constructor: Address::new(kind, pubkey, identifier)
  • from_event(event) -> Option<Self> — returns None for non-replaceable/non-addressable events. Uses tags.value("d").unwrap_or("").to_string() for identifier.
  • to_tag(relay_hint: Option<&str>) -> Tag — produces an a tag

5. Display / FromStr (kind:pubkey:identifier format)

  • Display: write!(f, "{}:{}:{}", self.kind, self.pubkey, self.identifier)
  • FromStr: split on :, take first two segments, join remainder as identifier (handles colons in d-tags)

6. NIP-19 naddr encoding

  • Introduce TLV format: type(1 byte) + length(1 byte) + value(N bytes)
  • Constants: SPECIAL=0, RELAY=1, AUTHOR=2, KIND=3
  • to_naddr() -> String — encode as bech32 with "naddr" prefix
  • from_naddr(s: &str) -> Result<(Self, Vec<String>), AddressError> — returns address + relay hints
    • TLV decode: while loop consuming bytes
    • SPECIAL=identifier (UTF-8), RELAY=URL string, AUTHOR=32-byte pubkey, KIND=u32 big-endian

7. What's next

  • Brief pointer to proof of work or filters chapter

Code placement

  • All code in coracle-lib/src/addresses.rs
  • Module registered in coracle-lib/src/lib.rs

Tests needed

  • Address::new basic construction
  • from_event for addressable event (returns Some)
  • from_event for regular event (returns None)
  • from_event for replaceable event (returns Some, empty identifier)
  • Display round-trip through FromStr
  • to_naddr / from_naddr round-trip
  • FromStr with identifier containing colons
  • to_tag produces correct a tag format