Introduced `lol.Tracer` for function entry/exit logging across various packages. This improves traceability and debugging of function executions while preserving existing behavior. Removed unused files `doc.go` and `nothing.go` to clean up the repository.
160 lines
3.8 KiB
Go
160 lines
3.8 KiB
Go
// Package eventid is a codec for managing nostr event Ids (hash of the
|
|
// canonical form of a nostr event).
|
|
package eventid
|
|
|
|
import (
|
|
"lukechampine.com/frand"
|
|
|
|
"realy.lol/chk"
|
|
"realy.lol/errorf"
|
|
"realy.lol/hex"
|
|
"realy.lol/log"
|
|
"realy.lol/lol"
|
|
"realy.lol/sha256"
|
|
)
|
|
|
|
const Len = sha256.Size
|
|
|
|
// T is the SHA256 hash in hexadecimal of the canonical form of an event as
|
|
// produced by the output of T.ToCanonical().Bytes().
|
|
type T [Len]byte
|
|
|
|
// New creates a new eventid.T. This is actually more wordy than simply creating a &T{} via
|
|
// slice literal.
|
|
func New() (ei *T) { return &T{} }
|
|
|
|
// NewWith creates an eventid.T out of bytes or string but assumes it is binary
|
|
// and that it is the right length. The result is either truncated or padded automatically by
|
|
// the use of the "copy" operation.
|
|
func NewWith[V string | []byte](s V) (ei *T) {
|
|
lol.Tracer("New", s)
|
|
defer func() { lol.Tracer("end New", ei) }()
|
|
id := T{}
|
|
copy(id[:], s)
|
|
ei = &id
|
|
return
|
|
}
|
|
|
|
// Set the value of an eventid.T with checking of the length before copying it.
|
|
func (ei *T) Set(b []byte) (err error) {
|
|
lol.Tracer("Set", b)
|
|
defer func() { lol.Tracer("end Set", err) }()
|
|
if ei == nil {
|
|
err = errorf.E("event id is nil")
|
|
return
|
|
}
|
|
if len(b) != Len {
|
|
err = errorf.E("Id bytes incorrect size, got %d require %d",
|
|
len(b), Len)
|
|
return
|
|
}
|
|
copy(ei[:], b)
|
|
return
|
|
}
|
|
|
|
// NewFromBytes creates a new eventid.T from the raw event Id hash.
|
|
func NewFromBytes(b []byte) (ei *T, err error) {
|
|
lol.Tracer("NewFromBytes", b)
|
|
defer func() { lol.Tracer("end NewFromBytes", ei, err) }()
|
|
ei = New()
|
|
if err = ei.Set(b); chk.E(err) {
|
|
return
|
|
}
|
|
return
|
|
}
|
|
|
|
// String renders an eventid.T as a string.
|
|
func (ei *T) String() string {
|
|
if ei == nil {
|
|
return ""
|
|
}
|
|
return hex.Enc(ei[:])
|
|
}
|
|
|
|
// ByteString renders an eventid.T as bytes in ASCII hex.
|
|
func (ei *T) ByteString(src []byte) (b []byte) {
|
|
lol.Tracer("ByteString", src)
|
|
defer func() { lol.Tracer("end ByteString", b) }()
|
|
b = hex.EncAppend(src, ei[:])
|
|
return
|
|
}
|
|
|
|
// Bytes returns the raw bytes of the eventid.T.
|
|
func (ei *T) Bytes() (b []byte) { return ei[:] }
|
|
|
|
// Len returns the length of the eventid.T.
|
|
func (ei *T) Len() int {
|
|
if ei == nil {
|
|
log.W.Ln("nil event id")
|
|
return 0
|
|
}
|
|
return len(ei)
|
|
}
|
|
|
|
// Equal tests whether another eventid.T is the same.
|
|
func (ei *T) Equal(ei2 *T) (eq bool) {
|
|
if ei == nil || ei2 == nil {
|
|
log.W.Ln("can't compare to nil event id")
|
|
return
|
|
}
|
|
return *ei == *ei2
|
|
}
|
|
|
|
// Marshal renders the eventid.T into JSON.
|
|
func (ei *T) Marshal(dst []byte) (b []byte) {
|
|
lol.Tracer("Marshal", dst)
|
|
defer func() { lol.Tracer("end Marshal", b) }()
|
|
b = dst
|
|
b = make([]byte, 0, 2*Len+2)
|
|
b = append(b, '"')
|
|
hex.EncAppend(b, ei[:])
|
|
b = append(b, '"')
|
|
return
|
|
}
|
|
|
|
// Unmarshal decodes a JSON encoded eventid.T.
|
|
func (ei *T) Unmarshal(b []byte) (rem []byte, err error) {
|
|
lol.Tracer("Unmarshal", b)
|
|
defer func() { lol.Tracer("end Unmarshal", rem, err) }()
|
|
// trim off the quotes.
|
|
b = b[1 : 2*Len+1]
|
|
if len(b) != 2*Len {
|
|
err = errorf.E("event Id hex incorrect size, got %d require %d",
|
|
len(b), 2*Len)
|
|
log.E.Ln(string(b))
|
|
return
|
|
}
|
|
var bb []byte
|
|
if bb, err = hex.Dec(string(b)); chk.E(err) {
|
|
return
|
|
}
|
|
copy(ei[:], bb)
|
|
return
|
|
}
|
|
|
|
// NewFromString inspects a string and ensures it is a valid, 64 character long
|
|
// hexadecimal string, returns the string coerced to the type.
|
|
func NewFromString(s string) (ei *T, err error) {
|
|
lol.Tracer("NewFromString", s)
|
|
defer func() { lol.Tracer("end NewFromString", ei, err) }()
|
|
if len(s) != 2*Len {
|
|
return nil, errorf.E("event Id hex wrong size, got %d require %d",
|
|
len(s), 2*Len)
|
|
}
|
|
ei = &T{}
|
|
b := make([]byte, 0, Len)
|
|
b, err = hex.DecAppend(b, []byte(s))
|
|
copy(ei[:], b)
|
|
return
|
|
}
|
|
|
|
// Gen creates a fake pseudorandom generated event Id for tests.
|
|
func Gen() (ei *T) {
|
|
lol.Tracer("Gen")
|
|
defer func() { lol.Tracer("end Gen", ei) }()
|
|
b := frand.Bytes(Len)
|
|
ei = &T{}
|
|
copy(ei[:], b)
|
|
return
|
|
}
|