tests on root and khatru working.

This commit is contained in:
fiatjaf
2025-04-17 20:30:44 -03:00
parent 1c56906506
commit 32efaa7c58
13 changed files with 56 additions and 74 deletions

View File

@@ -13,9 +13,9 @@ func TestCount(t *testing.T) {
rl := mustRelayConnect(t, RELAY) rl := mustRelayConnect(t, RELAY)
defer rl.Close() defer rl.Close()
count, _, err := rl.Count(context.Background(), Filters{ count, _, err := rl.Count(context.Background(), Filter{
{Kinds: []uint16{KindFollowList}, Tags: TagMap{"p": []string{"3bf0c63fcb93463407af97a5e5ee64fa883d107ef9e558472c4eb9aaaefa459d"}}}, Kinds: []uint16{KindFollowList}, Tags: TagMap{"p": []string{"3bf0c63fcb93463407af97a5e5ee64fa883d107ef9e558472c4eb9aaaefa459d"}},
}) }, SubscriptionOptions{})
assert.NoError(t, err) assert.NoError(t, err)
assert.Greater(t, count, int64(0)) assert.Greater(t, count, uint32(0))
} }

View File

@@ -202,7 +202,7 @@ func (v CountEnvelope) MarshalJSON() ([]byte, error) {
w := jwriter.Writer{NoEscapeHTML: true} w := jwriter.Writer{NoEscapeHTML: true}
w.RawString(`["COUNT","`) w.RawString(`["COUNT","`)
w.RawString(v.SubscriptionID) w.RawString(v.SubscriptionID)
w.RawString(`"`) w.RawString(`",`)
if v.Count != nil { if v.Count != nil {
w.RawString(`{"count":`) w.RawString(`{"count":`)
w.RawString(strconv.FormatUint(uint64(*v.Count), 10)) w.RawString(strconv.FormatUint(uint64(*v.Count), 10))

View File

@@ -12,9 +12,9 @@ func TestEOSEMadness(t *testing.T) {
rl := mustRelayConnect(t, RELAY) rl := mustRelayConnect(t, RELAY)
defer rl.Close() defer rl.Close()
sub, err := rl.Subscribe(context.Background(), Filters{ sub, err := rl.Subscribe(context.Background(), Filter{
{Kinds: []uint16{KindTextNote}, Limit: 2}, Kinds: []uint16{KindTextNote}, Limit: 2,
}) }, SubscriptionOptions{})
assert.NoError(t, err) assert.NoError(t, err)
timeout := time.After(3 * time.Second) timeout := time.After(3 * time.Second)

View File

@@ -94,7 +94,7 @@ func TestIDCheck(t *testing.T) {
require.False(t, evt.CheckID()) require.False(t, evt.CheckID())
evt.Sign(GeneratePrivateKey()) evt.Sign(Generate())
require.True(t, evt.CheckID()) require.True(t, evt.CheckID())
evt.Content += "!" evt.Content += "!"
@@ -108,7 +108,7 @@ func BenchmarkIDCheck(b *testing.B) {
Content: fmt.Sprintf("hello"), Content: fmt.Sprintf("hello"),
Tags: Tags{}, Tags: Tags{},
} }
evt.Sign(GeneratePrivateKey()) evt.Sign(Generate())
b.Run("naïve", func(b *testing.B) { b.Run("naïve", func(b *testing.B) {
for b.Loop() { for b.Loop() {

View File

@@ -78,7 +78,7 @@ func TestFilterMatchingLive(t *testing.T) {
json.Unmarshal([]byte(`{"kinds":[1],"authors":["a8171781fd9e90ede3ea44ddca5d3abf828fe8eedeb0f3abb0dd3e563562e1fc","1d80e5588de010d137a67c42b03717595f5f510e73e42cfc48f31bae91844d59","ed4ca520e9929dfe9efdadf4011b53d30afd0678a09aa026927e60e7a45d9244"],"since":1677033299}`), &filter) json.Unmarshal([]byte(`{"kinds":[1],"authors":["a8171781fd9e90ede3ea44ddca5d3abf828fe8eedeb0f3abb0dd3e563562e1fc","1d80e5588de010d137a67c42b03717595f5f510e73e42cfc48f31bae91844d59","ed4ca520e9929dfe9efdadf4011b53d30afd0678a09aa026927e60e7a45d9244"],"since":1677033299}`), &filter)
json.Unmarshal([]byte(`{"id":"5a127c9c931f392f6afc7fdb74e8be01c34035314735a6b97d2cf360d13cfb94","pubkey":"1d80e5588de010d137a67c42b03717595f5f510e73e42cfc48f31bae91844d59","created_at":1677033299,"kind":1,"tags":[["t","japan"]],"content":"If you like my art,I'd appreciate a coin or two!!\nZap is welcome!! Thanks.\n\n\n#japan #bitcoin #art #bananaart\nhttps://void.cat/d/CgM1bzDgHUCtiNNwfX9ajY.webp","sig":"828497508487ca1e374f6b4f2bba7487bc09fccd5cc0d1baa82846a944f8c5766918abf5878a580f1e6615de91f5b57a32e34c42ee2747c983aaf47dbf2a0255"}`), &event) json.Unmarshal([]byte(`{"id":"5a127c9c931f392f6afc7fdb74e8be01c34035314735a6b97d2cf360d13cfb94","pubkey":"1d80e5588de010d137a67c42b03717595f5f510e73e42cfc48f31bae91844d59","created_at":1677033299,"kind":1,"tags":[["t","japan"]],"content":"If you like my art,I'd appreciate a coin or two!!\nZap is welcome!! Thanks.\n\n\n#japan #bitcoin #art #bananaart\nhttps://void.cat/d/CgM1bzDgHUCtiNNwfX9ajY.webp","sig":"828497508487ca1e374f6b4f2bba7487bc09fccd5cc0d1baa82846a944f8c5766918abf5878a580f1e6615de91f5b57a32e34c42ee2747c983aaf47dbf2a0255"}`), &event)
assert.True(t, filter.Matches(&event), "live filter should match") assert.True(t, filter.Matches(event), "live filter should match")
} }
func TestFilterEquality(t *testing.T) { func TestFilterEquality(t *testing.T) {
@@ -120,13 +120,13 @@ func TestFilterClone(t *testing.T) {
Kinds: []uint16{0, 1, 2, 3, 4, 5, 6, 7, 8, 9}, Kinds: []uint16{0, 1, 2, 3, 4, 5, 6, 7, 8, 9},
Tags: TagMap{"letter": {"a", "b"}, "fruit": {"banana"}}, Tags: TagMap{"letter": {"a", "b"}, "fruit": {"banana"}},
Since: &ts, Since: &ts,
IDs: []ID{IDFromHex("9894b4b5cb5166d23ee8899a4151cf0c66aec00bde101982a13b8e8ceb972df9")}, IDs: []ID{MustIDFromHex("9894b4b5cb5166d23ee8899a4151cf0c66aec00bde101982a13b8e8ceb972df9")},
} }
clone := flt.Clone() clone := flt.Clone()
assert.True(t, FilterEqual(flt, clone), "clone is not equal:\n %v !=\n %v", flt, clone) assert.True(t, FilterEqual(flt, clone), "clone is not equal:\n %v !=\n %v", flt, clone)
clone1 := flt.Clone() clone1 := flt.Clone()
clone1.IDs = append(clone1.IDs, IDFromHex("88f0c63fcb93463407af97a5e5ee64fa883d107ef9e558472c4eb9aaaefa459d")) clone1.IDs = append(clone1.IDs, MustIDFromHex("88f0c63fcb93463407af97a5e5ee64fa883d107ef9e558472c4eb9aaaefa459d"))
assert.False(t, FilterEqual(flt, clone1), "modifying the clone ids should cause it to not be equal anymore") assert.False(t, FilterEqual(flt, clone1), "modifying the clone ids should cause it to not be equal anymore")
clone2 := flt.Clone() clone2 := flt.Clone()

View File

@@ -28,22 +28,22 @@ func TestIsLower(t *testing.T) {
func TestIDExtract(t *testing.T) { func TestIDExtract(t *testing.T) {
{ {
data := `{"kind":1,"id":"6b5988e9471fa340880a40df815befc69c901420facfb670acd8308012088f16","pubkey":"67ada8e344532cbf82f0e702472e24c7896e0e1c96235eacbaaa4b8616052171","created_at":1736909072,"tags":[["e","cfdf18b78527455097515545be4ccbe17e9b88f64539a566c632e405e2c0d08a","","root"],["e","f1ec9c301383be082f1860f7e24e49164d855bfab67f8e5c3ed17f6f3f867cca","","reply"],["p","1afe0c74e3d7784eba93a5e3fa554a6eeb01928d12739ae8ba4832786808e36d"],["p","8aa642e26e65072139e10db59646a89aa7538a59965aab3ed89191d71967d6c3"],["p","f4d89779148ccd245c8d50914a284fd62d97cb0fb68b797a70f24a172b522db9"],["p","18905d0a5d623ab81a98ba98c582bd5f57f2506c6b808905fc599d5a0b229b08"],["p","9a0e2043afaa056a12b8bbe77ac4c3185c0e2bc46b12aac158689144323c0e3c"],["p","45f195cffcb8c9724efc248f0507a2fb65b579dfabe7cd35398598163cab7627"]],"content":"🫡","sig":"d21aaf43963b07a3cb5f85ac8809c2b2e4dd3269195f4d810e1b7650895178fe01cf685ab3ee93f193cdde1f8d17419ff05332c6e3fc7429bbbe3d70016b8638"}` data := `{"kind":1,"id":"6b5988e9471fa340880a40df815befc69c901420facfb670acd8308012088f16","pubkey":"67ada8e344532cbf82f0e702472e24c7896e0e1c96235eacbaaa4b8616052171","created_at":1736909072,"tags":[["e","cfdf18b78527455097515545be4ccbe17e9b88f64539a566c632e405e2c0d08a","","root"],["e","f1ec9c301383be082f1860f7e24e49164d855bfab67f8e5c3ed17f6f3f867cca","","reply"],["p","1afe0c74e3d7784eba93a5e3fa554a6eeb01928d12739ae8ba4832786808e36d"],["p","8aa642e26e65072139e10db59646a89aa7538a59965aab3ed89191d71967d6c3"],["p","f4d89779148ccd245c8d50914a284fd62d97cb0fb68b797a70f24a172b522db9"],["p","18905d0a5d623ab81a98ba98c582bd5f57f2506c6b808905fc599d5a0b229b08"],["p","9a0e2043afaa056a12b8bbe77ac4c3185c0e2bc46b12aac158689144323c0e3c"],["p","45f195cffcb8c9724efc248f0507a2fb65b579dfabe7cd35398598163cab7627"]],"content":"🫡","sig":"d21aaf43963b07a3cb5f85ac8809c2b2e4dd3269195f4d810e1b7650895178fe01cf685ab3ee93f193cdde1f8d17419ff05332c6e3fc7429bbbe3d70016b8638"}`
require.Equal(t, "6b5988e9471fa340880a40df815befc69c901420facfb670acd8308012088f16", extractEventID(data)) require.Equal(t, MustIDFromHex("6b5988e9471fa340880a40df815befc69c901420facfb670acd8308012088f16"), extractEventID(data))
} }
{ {
data := `{"kind":1,"pubkey":"67ada8e344532cbf82f0e702472e24c7896e0e1c96235eacbaaa4b8616052171","created_at":1736909072,"tags":[["e","cfdf18b78527455097515545be4ccbe17e9b88f64539a566c632e405e2c0d08a","","root"],["e","f1ec9c301383be082f1860f7e24e49164d855bfab67f8e5c3ed17f6f3f867cca","","reply"],["p","1afe0c74e3d7784eba93a5e3fa554a6eeb01928d12739ae8ba4832786808e36d"],["p","8aa642e26e65072139e10db59646a89aa7538a59965aab3ed89191d71967d6c3"],["p","f4d89779148ccd245c8d50914a284fd62d97cb0fb68b797a70f24a172b522db9"],["p","18905d0a5d623ab81a98ba98c582bd5f57f2506c6b808905fc599d5a0b229b08"],["p","9a0e2043afaa056a12b8bbe77ac4c3185c0e2bc46b12aac158689144323c0e3c"],["p","45f195cffcb8c9724efc248f0507a2fb65b579dfabe7cd35398598163cab7627"]],"content":"🫡","sig":"d21aaf43963b07a3cb5f85ac8809c2b2e4dd3269195f4d810e1b7650895178fe01cf685ab3ee93f193cdde1f8d17419ff05332c6e3fc7429bbbe3d70016b8638","id": "6b5988e9471fa340880a40df815befc69c901420facfb670acd8308012088f16" }` data := `{"kind":1,"pubkey":"67ada8e344532cbf82f0e702472e24c7896e0e1c96235eacbaaa4b8616052171","created_at":1736909072,"tags":[["e","cfdf18b78527455097515545be4ccbe17e9b88f64539a566c632e405e2c0d08a","","root"],["e","f1ec9c301383be082f1860f7e24e49164d855bfab67f8e5c3ed17f6f3f867cca","","reply"],["p","1afe0c74e3d7784eba93a5e3fa554a6eeb01928d12739ae8ba4832786808e36d"],["p","8aa642e26e65072139e10db59646a89aa7538a59965aab3ed89191d71967d6c3"],["p","f4d89779148ccd245c8d50914a284fd62d97cb0fb68b797a70f24a172b522db9"],["p","18905d0a5d623ab81a98ba98c582bd5f57f2506c6b808905fc599d5a0b229b08"],["p","9a0e2043afaa056a12b8bbe77ac4c3185c0e2bc46b12aac158689144323c0e3c"],["p","45f195cffcb8c9724efc248f0507a2fb65b579dfabe7cd35398598163cab7627"]],"content":"🫡","sig":"d21aaf43963b07a3cb5f85ac8809c2b2e4dd3269195f4d810e1b7650895178fe01cf685ab3ee93f193cdde1f8d17419ff05332c6e3fc7429bbbe3d70016b8638","id": "6b5988e9471fa340880a40df815befc69c901420facfb670acd8308012088f16" }`
require.Equal(t, "6b5988e9471fa340880a40df815befc69c901420facfb670acd8308012088f16", extractEventID(data)) require.Equal(t, MustIDFromHex("6b5988e9471fa340880a40df815befc69c901420facfb670acd8308012088f16"), extractEventID(data))
} }
} }
func TestPubKeyExtract(t *testing.T) { func TestPubKeyExtract(t *testing.T) {
{ {
data := `{"kind":1,"id":"6b5988e9471fa340880a40df815befc69c901420facfb670acd8308012088f16","pubkey":"67ada8e344532cbf82f0e702472e24c7896e0e1c96235eacbaaa4b8616052171","created_at":1736909072,"tags":[["e","cfdf18b78527455097515545be4ccbe17e9b88f64539a566c632e405e2c0d08a","","root"],["e","f1ec9c301383be082f1860f7e24e49164d855bfab67f8e5c3ed17f6f3f867cca","","reply"],["p","1afe0c74e3d7784eba93a5e3fa554a6eeb01928d12739ae8ba4832786808e36d"],["p","8aa642e26e65072139e10db59646a89aa7538a59965aab3ed89191d71967d6c3"],["p","f4d89779148ccd245c8d50914a284fd62d97cb0fb68b797a70f24a172b522db9"],["p","18905d0a5d623ab81a98ba98c582bd5f57f2506c6b808905fc599d5a0b229b08"],["p","9a0e2043afaa056a12b8bbe77ac4c3185c0e2bc46b12aac158689144323c0e3c"],["p","45f195cffcb8c9724efc248f0507a2fb65b579dfabe7cd35398598163cab7627"]],"content":"🫡","sig":"d21aaf43963b07a3cb5f85ac8809c2b2e4dd3269195f4d810e1b7650895178fe01cf685ab3ee93f193cdde1f8d17419ff05332c6e3fc7429bbbe3d70016b8638"}` data := `{"kind":1,"id":"6b5988e9471fa340880a40df815befc69c901420facfb670acd8308012088f16","pubkey":"67ada8e344532cbf82f0e702472e24c7896e0e1c96235eacbaaa4b8616052171","created_at":1736909072,"tags":[["e","cfdf18b78527455097515545be4ccbe17e9b88f64539a566c632e405e2c0d08a","","root"],["e","f1ec9c301383be082f1860f7e24e49164d855bfab67f8e5c3ed17f6f3f867cca","","reply"],["p","1afe0c74e3d7784eba93a5e3fa554a6eeb01928d12739ae8ba4832786808e36d"],["p","8aa642e26e65072139e10db59646a89aa7538a59965aab3ed89191d71967d6c3"],["p","f4d89779148ccd245c8d50914a284fd62d97cb0fb68b797a70f24a172b522db9"],["p","18905d0a5d623ab81a98ba98c582bd5f57f2506c6b808905fc599d5a0b229b08"],["p","9a0e2043afaa056a12b8bbe77ac4c3185c0e2bc46b12aac158689144323c0e3c"],["p","45f195cffcb8c9724efc248f0507a2fb65b579dfabe7cd35398598163cab7627"]],"content":"🫡","sig":"d21aaf43963b07a3cb5f85ac8809c2b2e4dd3269195f4d810e1b7650895178fe01cf685ab3ee93f193cdde1f8d17419ff05332c6e3fc7429bbbe3d70016b8638"}`
require.Equal(t, "67ada8e344532cbf82f0e702472e24c7896e0e1c96235eacbaaa4b8616052171", extractEventPubKey(data)) require.Equal(t, MustPubKeyFromHex("67ada8e344532cbf82f0e702472e24c7896e0e1c96235eacbaaa4b8616052171"), extractEventPubKey(data))
} }
{ {
data := `{"kind":1,"pubkey":"67ada8e344532cbf82f0e702472e24c7896e0e1c96235eacbaaa4b8616052171","created_at":1736909072,"tags":[["e","cfdf18b78527455097515545be4ccbe17e9b88f64539a566c632e405e2c0d08a","","root"],["e","f1ec9c301383be082f1860f7e24e49164d855bfab67f8e5c3ed17f6f3f867cca","","reply"],["p","1afe0c74e3d7784eba93a5e3fa554a6eeb01928d12739ae8ba4832786808e36d"],["p","8aa642e26e65072139e10db59646a89aa7538a59965aab3ed89191d71967d6c3"],["p","f4d89779148ccd245c8d50914a284fd62d97cb0fb68b797a70f24a172b522db9"],["p","18905d0a5d623ab81a98ba98c582bd5f57f2506c6b808905fc599d5a0b229b08"],["p","9a0e2043afaa056a12b8bbe77ac4c3185c0e2bc46b12aac158689144323c0e3c"],["p","45f195cffcb8c9724efc248f0507a2fb65b579dfabe7cd35398598163cab7627"]],"content":"🫡","sig":"d21aaf43963b07a3cb5f85ac8809c2b2e4dd3269195f4d810e1b7650895178fe01cf685ab3ee93f193cdde1f8d17419ff05332c6e3fc7429bbbe3d70016b8638","id": "6b5988e9471fa340880a40df815befc69c901420facfb670acd8308012088f16" }` data := `{"kind":1,"pubkey":"67ada8e344532cbf82f0e702472e24c7896e0e1c96235eacbaaa4b8616052171","created_at":1736909072,"tags":[["e","cfdf18b78527455097515545be4ccbe17e9b88f64539a566c632e405e2c0d08a","","root"],["e","f1ec9c301383be082f1860f7e24e49164d855bfab67f8e5c3ed17f6f3f867cca","","reply"],["p","1afe0c74e3d7784eba93a5e3fa554a6eeb01928d12739ae8ba4832786808e36d"],["p","8aa642e26e65072139e10db59646a89aa7538a59965aab3ed89191d71967d6c3"],["p","f4d89779148ccd245c8d50914a284fd62d97cb0fb68b797a70f24a172b522db9"],["p","18905d0a5d623ab81a98ba98c582bd5f57f2506c6b808905fc599d5a0b229b08"],["p","9a0e2043afaa056a12b8bbe77ac4c3185c0e2bc46b12aac158689144323c0e3c"],["p","45f195cffcb8c9724efc248f0507a2fb65b579dfabe7cd35398598163cab7627"]],"content":"🫡","sig":"d21aaf43963b07a3cb5f85ac8809c2b2e4dd3269195f4d810e1b7650895178fe01cf685ab3ee93f193cdde1f8d17419ff05332c6e3fc7429bbbe3d70016b8638","id": "6b5988e9471fa340880a40df815befc69c901420facfb670acd8308012088f16" }`
require.Equal(t, "67ada8e344532cbf82f0e702472e24c7896e0e1c96235eacbaaa4b8616052171", extractEventPubKey(data)) require.Equal(t, MustPubKeyFromHex("67ada8e344532cbf82f0e702472e24c7896e0e1c96235eacbaaa4b8616052171"), extractEventPubKey(data))
} }
} }

View File

@@ -45,6 +45,7 @@ func (rl *Relay) handleNormal(ctx context.Context, evt nostr.Event) (skipBroadca
} else { } else {
// otherwise it's a replaceable // otherwise it's a replaceable
if nil != rl.ReplaceEvent { if nil != rl.ReplaceEvent {
fmt.Print("\nREPLACING .", evt.CreatedAt, "\n\n")
if err := rl.ReplaceEvent(ctx, evt); err != nil { if err := rl.ReplaceEvent(ctx, evt); err != nil {
switch err { switch err {
case eventstore.ErrDupEvent: case eventstore.ErrDupEvent:

View File

@@ -53,7 +53,7 @@ func (rl *Relay) ServeHTTP(w http.ResponseWriter, r *http.Request) {
} }
func (rl *Relay) HandleWebsocket(w http.ResponseWriter, r *http.Request) { func (rl *Relay) HandleWebsocket(w http.ResponseWriter, r *http.Request) {
if rl.RejectConnection == nil { if nil != rl.RejectConnection {
if rl.RejectConnection(r) { if rl.RejectConnection(r) {
w.WriteHeader(429) // Too many requests w.WriteHeader(429) // Too many requests
return return
@@ -92,7 +92,7 @@ func (rl *Relay) HandleWebsocket(w http.ResponseWriter, r *http.Request) {
) )
kill := func() { kill := func() {
if rl.OnDisconnect == nil { if nil != rl.OnDisconnect {
rl.OnDisconnect(ctx) rl.OnDisconnect(ctx)
} }
@@ -114,7 +114,7 @@ func (rl *Relay) HandleWebsocket(w http.ResponseWriter, r *http.Request) {
return nil return nil
}) })
if rl.OnConnect == nil { if nil != rl.OnConnect {
rl.OnConnect(ctx) rl.OnConnect(ctx)
} }

View File

@@ -183,7 +183,7 @@ func TestBasicRelayFunctionality(t *testing.T) {
// create newer event that should replace the first // create newer event that should replace the first
evt2 := createEvent(sk1, 0, `{"name":"newer"}`, nil) evt2 := createEvent(sk1, 0, `{"name":"newer"}`, nil)
evt2.CreatedAt = 2000 // Newer timestamp evt2.CreatedAt = 2004 // Newer timestamp
evt2.Sign(sk1) evt2.Sign(sk1)
err = client1.Publish(ctx, evt2) err = client1.Publish(ctx, evt2)
if err != nil { if err != nil {
@@ -213,8 +213,8 @@ func TestBasicRelayFunctionality(t *testing.T) {
var receivedEvents []nostr.Event var receivedEvents []nostr.Event
for { for {
select { select {
case env := <-sub.Events: case evt := <-sub.Events:
receivedEvents = append(receivedEvents, env) receivedEvents = append(receivedEvents, evt)
case <-sub.EndOfStoredEvents: case <-sub.EndOfStoredEvents:
if len(receivedEvents) != 1 { if len(receivedEvents) != 1 {
t.Errorf("expected exactly 1 event, got %d", len(receivedEvents)) t.Errorf("expected exactly 1 event, got %d", len(receivedEvents))

View File

@@ -32,7 +32,6 @@ func (rl *Relay) handleRequest(ctx context.Context, id string, eose *sync.WaitGr
for event := range rl.QueryStored(ctx, filter) { for event := range rl.QueryStored(ctx, filter) {
ws.WriteJSON(nostr.EventEnvelope{SubscriptionID: &id, Event: event}) ws.WriteJSON(nostr.EventEnvelope{SubscriptionID: &id, Event: event})
} }
eose.Done()
} }
return nil return nil

View File

@@ -13,7 +13,6 @@ import (
"testing" "testing"
"time" "time"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require" "github.com/stretchr/testify/require"
"golang.org/x/net/websocket" "golang.org/x/net/websocket"
) )
@@ -29,7 +28,7 @@ func TestPublish(t *testing.T) {
PubKey: pub, PubKey: pub,
} }
err := textNote.Sign(priv) err := textNote.Sign(priv)
assert.NoError(t, err) require.NoError(t, err)
// fake relay server // fake relay server
var mu sync.Mutex // guards published to satisfy go test -race var mu sync.Mutex // guards published to satisfy go test -race
@@ -41,24 +40,24 @@ func TestPublish(t *testing.T) {
// verify the client sent exactly the textNote // verify the client sent exactly the textNote
var raw []stdjson.RawMessage var raw []stdjson.RawMessage
err := websocket.JSON.Receive(conn, &raw) err := websocket.JSON.Receive(conn, &raw)
assert.NoError(t, err) require.NoError(t, err)
event := parseEventMessage(t, raw) event := parseEventMessage(t, raw)
assert.True(t, bytes.Equal(event.Serialize(), textNote.Serialize())) require.True(t, bytes.Equal(event.Serialize(), textNote.Serialize()))
// send back an ok nip-20 command result // send back an ok nip-20 command result
res := []any{"OK", textNote.ID, true, ""} res := []any{"OK", textNote.ID, true, ""}
err = websocket.JSON.Send(conn, res) err = websocket.JSON.Send(conn, res)
assert.NoError(t, err) require.NoError(t, err)
}) })
defer ws.Close() defer ws.Close()
// connect a client and send the text note // connect a client and send the text note
rl := mustRelayConnect(t, ws.URL) rl := mustRelayConnect(t, ws.URL)
err = rl.Publish(context.Background(), textNote) err = rl.Publish(context.Background(), textNote)
assert.NoError(t, err) require.NoError(t, err)
assert.True(t, published, "fake relay server saw no event") require.True(t, published, "fake relay server saw no event")
} }
func TestPublishBlocked(t *testing.T) { func TestPublishBlocked(t *testing.T) {
@@ -71,7 +70,7 @@ func TestPublishBlocked(t *testing.T) {
// discard received message; not interested // discard received message; not interested
var raw []stdjson.RawMessage var raw []stdjson.RawMessage
err := websocket.JSON.Receive(conn, &raw) err := websocket.JSON.Receive(conn, &raw)
assert.NoError(t, err) require.NoError(t, err)
// send back a not ok nip-20 command result // send back a not ok nip-20 command result
res := []any{"OK", textNote.ID.String(), false, "blocked"} res := []any{"OK", textNote.ID.String(), false, "blocked"}
@@ -82,7 +81,7 @@ func TestPublishBlocked(t *testing.T) {
// connect a client and send a text note // connect a client and send a text note
rl := mustRelayConnect(t, ws.URL) rl := mustRelayConnect(t, ws.URL)
err := rl.Publish(context.Background(), textNote) err := rl.Publish(context.Background(), textNote)
assert.Error(t, err) require.Error(t, err)
} }
func TestPublishWriteFailed(t *testing.T) { func TestPublishWriteFailed(t *testing.T) {
@@ -102,7 +101,7 @@ func TestPublishWriteFailed(t *testing.T) {
// Force brief period of time so that publish always fails on closed socket. // Force brief period of time so that publish always fails on closed socket.
time.Sleep(1 * time.Millisecond) time.Sleep(1 * time.Millisecond)
err := rl.Publish(context.Background(), textNote) err := rl.Publish(context.Background(), textNote)
assert.Error(t, err) require.Error(t, err)
} }
func TestConnectContext(t *testing.T) { func TestConnectContext(t *testing.T) {
@@ -120,45 +119,28 @@ func TestConnectContext(t *testing.T) {
// relay client // relay client
ctx, cancel := context.WithTimeout(context.Background(), 3*time.Second) ctx, cancel := context.WithTimeout(context.Background(), 3*time.Second)
defer cancel() defer cancel()
r, err := RelayConnect(ctx, ws.URL) r, err := RelayConnect(ctx, ws.URL, RelayOptions{})
assert.NoError(t, err) require.NoError(t, err)
defer r.Close() defer r.Close()
mu.Lock() mu.Lock()
defer mu.Unlock() defer mu.Unlock()
assert.True(t, connected, "fake relay server saw no client connect") require.True(t, connected, "fake relay server saw no client connect")
} }
func TestConnectContextCanceled(t *testing.T) { func TestConnectContextCanceled(t *testing.T) {
// fake relay server // fake relay server
ws := newWebsocketServer(discardingHandler) ws := newWebsocketServer(func(conn *websocket.Conn) {
io.ReadAll(conn) // discard all input
})
defer ws.Close() defer ws.Close()
// relay client // relay client
ctx, cancel := context.WithCancel(context.Background()) ctx, cancel := context.WithCancel(context.Background())
cancel() // make ctx expired cancel() // make ctx expired
_, err := RelayConnect(ctx, ws.URL) _, err := RelayConnect(ctx, ws.URL, RelayOptions{})
assert.ErrorIs(t, err, context.Canceled) require.ErrorIs(t, err, context.Canceled)
}
func TestConnectWithOrigin(t *testing.T) {
// fake relay server
// default handler requires origin golang.org/x/net/websocket
ws := httptest.NewServer(websocket.Handler(discardingHandler))
defer ws.Close()
// relay client
r := NewRelay(context.Background(), NormalizeURL(ws.URL),
WithRequestHeader(http.Header{"origin": {"https://example.com"}}))
ctx, cancel := context.WithTimeout(context.Background(), 3*time.Second)
defer cancel()
err := r.Connect(ctx)
assert.NoError(t, err)
}
func discardingHandler(conn *websocket.Conn) {
io.ReadAll(conn) // discard all input
} }
func newWebsocketServer(handler func(*websocket.Conn)) *httptest.Server { func newWebsocketServer(handler func(*websocket.Conn)) *httptest.Server {
@@ -178,7 +160,7 @@ var anyOriginHandshake = func(conf *websocket.Config, r *http.Request) error {
func makeKeyPair(t *testing.T) (priv, pub [32]byte) { func makeKeyPair(t *testing.T) (priv, pub [32]byte) {
t.Helper() t.Helper()
privkey := GeneratePrivateKey() privkey := Generate()
pubkey := GetPublicKey(privkey) pubkey := GetPublicKey(privkey)
return privkey, pubkey return privkey, pubkey
@@ -187,7 +169,7 @@ func makeKeyPair(t *testing.T) (priv, pub [32]byte) {
func mustRelayConnect(t *testing.T, url string) *Relay { func mustRelayConnect(t *testing.T, url string) *Relay {
t.Helper() t.Helper()
rl, err := RelayConnect(context.Background(), url) rl, err := RelayConnect(context.Background(), url, RelayOptions{})
require.NoError(t, err) require.NoError(t, err)
return rl return rl
@@ -196,14 +178,14 @@ func mustRelayConnect(t *testing.T, url string) *Relay {
func parseEventMessage(t *testing.T, raw []stdjson.RawMessage) Event { func parseEventMessage(t *testing.T, raw []stdjson.RawMessage) Event {
t.Helper() t.Helper()
assert.Condition(t, func() (success bool) { require.Condition(t, func() (success bool) {
return len(raw) >= 2 return len(raw) >= 2
}) })
var typ string var typ string
err := json.Unmarshal(raw[0], &typ) err := json.Unmarshal(raw[0], &typ)
assert.NoError(t, err) require.NoError(t, err)
assert.Equal(t, "EVENT", typ) require.Equal(t, "EVENT", typ)
var event Event var event Event
err = json.Unmarshal(raw[1], &event) err = json.Unmarshal(raw[1], &event)
@@ -215,23 +197,23 @@ func parseEventMessage(t *testing.T, raw []stdjson.RawMessage) Event {
func parseSubscriptionMessage(t *testing.T, raw []stdjson.RawMessage) (subid string, filters []Filter) { func parseSubscriptionMessage(t *testing.T, raw []stdjson.RawMessage) (subid string, filters []Filter) {
t.Helper() t.Helper()
assert.Greater(t, len(raw), 3) require.Greater(t, len(raw), 3)
var typ string var typ string
err := json.Unmarshal(raw[0], &typ) err := json.Unmarshal(raw[0], &typ)
assert.NoError(t, err) require.NoError(t, err)
assert.Equal(t, "REQ", typ) require.Equal(t, "REQ", typ)
var id string var id string
err = json.Unmarshal(raw[1], &id) err = json.Unmarshal(raw[1], &id)
assert.NoError(t, err) require.NoError(t, err)
var ff []Filter var ff []Filter
for _, b := range raw[2:] { for _, b := range raw[2:] {
var f Filter var f Filter
err := json.Unmarshal(b, &f) err := json.Unmarshal(b, &f)
assert.NoError(t, err) require.NoError(t, err)
ff = append(ff, f) ff = append(ff, f)
} }
return id, ff return id, ff

View File

@@ -17,7 +17,7 @@ func TestSubscribeBasic(t *testing.T) {
rl := mustRelayConnect(t, RELAY) rl := mustRelayConnect(t, RELAY)
defer rl.Close() defer rl.Close()
sub, err := rl.Subscribe(context.Background(), Filters{{Kinds: []uint16{KindTextNote}, Limit: 2}}) sub, err := rl.Subscribe(context.Background(), Filter{Kinds: []uint16{KindTextNote}, Limit: 2}, SubscriptionOptions{})
assert.NoError(t, err) assert.NoError(t, err)
timeout := time.After(5 * time.Second) timeout := time.After(5 * time.Second)
@@ -51,21 +51,21 @@ func TestNestedSubscriptions(t *testing.T) {
n := atomic.Uint32{} n := atomic.Uint32{}
// fetch 2 replies to a note // fetch 2 replies to a note
sub, err := rl.Subscribe(context.Background(), Filters{{Kinds: []uint16{KindTextNote}, Tags: TagMap{"e": []string{"0e34a74f8547e3b95d52a2543719b109fd0312aba144e2ef95cba043f42fe8c5"}}, Limit: 3}}) sub, err := rl.Subscribe(context.Background(), Filter{Kinds: []uint16{KindTextNote}, Tags: TagMap{"e": []string{"0e34a74f8547e3b95d52a2543719b109fd0312aba144e2ef95cba043f42fe8c5"}}, Limit: 3}, SubscriptionOptions{})
assert.NoError(t, err) assert.NoError(t, err)
for { for {
select { select {
case event := <-sub.Events: case event := <-sub.Events:
// now fetch author of this // now fetch author of this
sub, err := rl.Subscribe(context.Background(), Filters{{Kinds: []uint16{KindProfileMetadata}, Authors: []PubKey{event.PubKey}, Limit: 1}}) sub, err := rl.Subscribe(context.Background(), Filter{Kinds: []uint16{KindProfileMetadata}, Authors: []PubKey{event.PubKey}, Limit: 1}, SubscriptionOptions{})
assert.NoError(t, err) assert.NoError(t, err)
for { for {
select { select {
case <-sub.Events: case <-sub.Events:
// do another subscription here in "sync" mode, just so we're sure things are not blocking // do another subscription here in "sync" mode, just so we're sure things are not blocking
rl.QuerySync(context.Background(), Filter{Limit: 1}) rl.QueryEvents(Filter{Limit: 1})
n.Add(1) n.Add(1)
if n.Load() == 3 { if n.Load() == 3 {

View File

@@ -21,7 +21,7 @@ func TestTagHelpers(t *testing.T) {
assert.Equal(t, "ffffff", tags.FindLast("e")[1], "failed to get last") assert.Equal(t, "ffffff", tags.FindLast("e")[1], "failed to get last")
assert.Equal(t, 2, len(slices.Collect(tags.FindAll("e"))), "failed to get all") assert.Equal(t, 2, len(slices.Collect(tags.FindAll("e"))), "failed to get all")
c := make(Tags, 0, 2) c := make(Tags, 0, 2)
for _, tag := range tags.All([]string{"e", ""}) { for tag := range tags.FindAll("e") {
c = append(c, tag) c = append(c, tag)
} }
} }