Skip to content

Commit 76abd03

Browse files
committed
nip29: "hidden" and "private" metadata fields.
nostr-protocol/nips#2106
1 parent 5efd8c6 commit 76abd03

File tree

3 files changed

+64
-43
lines changed

3 files changed

+64
-43
lines changed

nip29/group.go

Lines changed: 34 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -42,8 +42,18 @@ type Group struct {
4242
Picture string
4343
About string
4444
Members map[nostr.PubKey][]*Role
45+
46+
// indicates that only members can read group messages
4547
Private bool
46-
Closed bool
48+
49+
// indicates that only members can write messages to the group
50+
Restricted bool
51+
52+
// indicates that relays should hide group metadata from non-members
53+
Hidden bool
54+
55+
// indicates that join requests are ignored unless they include an invite code
56+
Closed bool
4757

4858
Roles []*Role
4959
InviteCodes []string
@@ -56,11 +66,19 @@ type Group struct {
5666

5767
func (group Group) String() string {
5868
maybePrivate := ""
69+
maybeRestricted := ""
70+
maybeHidden := ""
5971
maybeClosed := ""
6072

6173
if group.Private {
6274
maybePrivate = " private"
6375
}
76+
if group.Restricted {
77+
maybeRestricted = " restricted"
78+
}
79+
if group.Hidden {
80+
maybeHidden = " hidden"
81+
}
6482
if group.Closed {
6583
maybeClosed = " closed"
6684
}
@@ -83,10 +101,12 @@ func (group Group) String() string {
83101
i++
84102
}
85103

86-
return fmt.Sprintf(`<Group %s name="%s"%s%s picture="%s" about="%s" members=[%v]>`,
104+
return fmt.Sprintf(`<Group %s name="%s"%s%s%s%s picture="%s" about="%s" members=[%v]>`,
87105
group.Address,
88106
group.Name,
89107
maybePrivate,
108+
maybeRestricted,
109+
maybeHidden,
90110
maybeClosed,
91111
group.Picture,
92112
group.About,
@@ -143,13 +163,15 @@ func (group Group) ToMetadataEvent() nostr.Event {
143163
// status
144164
if group.Private {
145165
evt.Tags = append(evt.Tags, nostr.Tag{"private"})
146-
} else {
147-
evt.Tags = append(evt.Tags, nostr.Tag{"public"})
166+
}
167+
if group.Restricted {
168+
evt.Tags = append(evt.Tags, nostr.Tag{"restricted"})
169+
}
170+
if group.Hidden {
171+
evt.Tags = append(evt.Tags, nostr.Tag{"hidden"})
148172
}
149173
if group.Closed {
150174
evt.Tags = append(evt.Tags, nostr.Tag{"closed"})
151-
} else {
152-
evt.Tags = append(evt.Tags, nostr.Tag{"open"})
153175
}
154176

155177
return evt
@@ -238,6 +260,12 @@ func (group *Group) MergeInMetadataEvent(evt *nostr.Event) error {
238260
if tag := evt.Tags.Find("private"); tag != nil {
239261
group.Private = true
240262
}
263+
if tag := evt.Tags.Find("restricted"); tag != nil {
264+
group.Restricted = true
265+
}
266+
if tag := evt.Tags.Find("hidden"); tag != nil {
267+
group.Hidden = true
268+
}
241269
if tag := evt.Tags.Find("closed"); tag != nil {
242270
group.Closed = true
243271
}

nip29/moderation_actions.go

Lines changed: 18 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -92,20 +92,11 @@ var moderationActionFactories = map[nostr.Kind]func(nostr.Event) (Action, error)
9292
}
9393

9494
y := true
95-
n := false
96-
97-
if evt.Tags.Has("public") {
98-
edit.PrivateValue = &n
99-
ok = true
100-
} else if evt.Tags.Has("private") {
95+
if evt.Tags.Has("private") {
10196
edit.PrivateValue = &y
10297
ok = true
10398
}
104-
105-
if evt.Tags.Has("open") {
106-
edit.ClosedValue = &n
107-
ok = true
108-
} else if evt.Tags.Has("closed") {
99+
if evt.Tags.Has("closed") {
109100
edit.ClosedValue = &y
110101
ok = true
111102
}
@@ -205,12 +196,14 @@ func (a RemoveUser) Apply(group *Group) {
205196
}
206197

207198
type EditMetadata struct {
208-
NameValue *string
209-
PictureValue *string
210-
AboutValue *string
211-
PrivateValue *bool
212-
ClosedValue *bool
213-
When nostr.Timestamp
199+
NameValue *string
200+
PictureValue *string
201+
AboutValue *string
202+
PrivateValue *bool
203+
RestrictedValue *bool
204+
HiddenValue *bool
205+
ClosedValue *bool
206+
When nostr.Timestamp
214207
}
215208

216209
func (_ EditMetadata) Name() string { return "edit-metadata" }
@@ -228,6 +221,12 @@ func (a EditMetadata) Apply(group *Group) {
228221
if a.PrivateValue != nil {
229222
group.Private = *a.PrivateValue
230223
}
224+
if a.RestrictedValue != nil {
225+
group.Restricted = *a.RestrictedValue
226+
}
227+
if a.HiddenValue != nil {
228+
group.Hidden = *a.HiddenValue
229+
}
231230
if a.ClosedValue != nil {
232231
group.Closed = *a.ClosedValue
233232
}
@@ -254,6 +253,8 @@ func (a DeleteGroup) Apply(group *Group) {
254253
group.Members = make(map[nostr.PubKey][]*Role)
255254
group.Closed = true
256255
group.Private = true
256+
group.Restricted = true
257+
group.Hidden = true
257258
group.Name = "[deleted]"
258259
group.About = ""
259260
group.Picture = ""

nip29/nip29_test.go

Lines changed: 12 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ package nip29
33
import (
44
"testing"
55

6+
"fiatjaf.com/nostr"
67
"github.com/stretchr/testify/require"
78
)
89

@@ -31,37 +32,28 @@ func TestGroupEventBackAndForth(t *testing.T) {
3132
require.True(t, hasPrivate, "translation of group1 to metadata event failed: %s", meta1)
3233

3334
group2, _ := NewGroup("groups.com'abc")
34-
group2.Members[ALICE] = []*Role{{Name: "nada"}}
35-
group2.Members[BOB] = []*Role{{Name: "nada"}}
36-
group2.Members[CAROL] = nil
37-
group2.Members[DEREK] = nil
35+
alicePub, _ := nostr.PubKeyFromHex(ALICE)
36+
group2.Members[alicePub] = []*Role{{Name: "nada"}}
3837
admins2 := group2.ToAdminsEvent()
3938

4039
require.Equal(t, "abc", admins2.Tags.GetD(), "translation of group2 to admins event failed")
41-
require.Equal(t, 3, len(admins2.Tags), "translation of group2 to admins event failed")
40+
require.Equal(t, 2, len(admins2.Tags), "translation of group2 to admins event failed")
4241
require.True(t, admins2.Tags.FindWithValue("p", ALICE)[2] == "nada", "translation of group2 to admins event failed")
43-
require.True(t, admins2.Tags.FindWithValue("p", BOB)[2] == "nada", "translation of group2 to admins event failed")
4442

4543
members2 := group2.ToMembersEvent()
46-
require.Equal(t, "abc", members2.Tags.GetD(), "translation of group2 to members2 event failed")
47-
require.Equal(t, 5, len(members2.Tags), "translation of group2 to members2 event failed")
44+
require.Equal(t, 2, len(members2.Tags), "translation of group2 to members2 event failed")
4845
require.NotNil(t, members2.Tags.FindWithValue("p", ALICE), "translation of group2 to members2 event failed")
49-
require.NotNil(t, members2.Tags.FindWithValue("p", BOB), "translation of group2 to members2 event failed")
50-
require.NotNil(t, members2.Tags.FindWithValue("p", CAROL), "translation of group2 to members2 event failed")
51-
require.NotNil(t, members2.Tags.FindWithValue("p", DEREK), "translation of group2 to members2 event failed")
5246

53-
group1.MergeInMembersEvent(members2)
54-
require.Equal(t, 4, len(group1.Members), "merge of members2 into group1 failed")
55-
require.Len(t, group1.Members[ALICE], 0, "merge of members2 into group1 failed")
56-
require.Len(t, group1.Members[DEREK], 0, "merge of members2 into group1 failed")
47+
group1.MergeInMembersEvent(&members2)
48+
require.Equal(t, 1, len(group1.Members), "merge of members2 into group1 failed")
49+
require.Len(t, group1.Members[alicePub], 0, "merge of members2 into group1 failed")
5750

58-
group1.MergeInAdminsEvent(admins2)
59-
require.Equal(t, 4, len(group1.Members), "merge of admins2 into group1 failed")
51+
group1.MergeInAdminsEvent(&admins2)
52+
require.Equal(t, 1, len(group1.Members), "merge of admins2 into group1 failed")
6053

61-
require.Equal(t, "nada", group1.Members[ALICE][0].Name, "merge of admins2 into group1 failed")
62-
require.Len(t, group1.Members[DEREK], 0, "merge of admins2 into group1 failed")
54+
require.Equal(t, "nada", group1.Members[alicePub][0].Name, "merge of admins2 into group1 failed")
6355

64-
group2.MergeInMetadataEvent(meta1)
56+
group2.MergeInMetadataEvent(&meta1)
6557
require.Equal(t, "banana", group2.Name, "merge of meta1 into group2 failed")
6658
require.Equal(t, "abc", group2.Address.ID, "merge of meta1 into group2 failed")
6759
}

0 commit comments

Comments
 (0)