forked from ortuman/jackal
-
Notifications
You must be signed in to change notification settings - Fork 0
/
roster.go
136 lines (121 loc) · 4.15 KB
/
roster.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
/*
* Copyright (c) 2018 Miguel Ángel Ortuño.
* See the LICENSE file for more information.
*/
package badgerdb
import (
"github.com/dgraph-io/badger"
"github.com/ortuman/jackal/model/rostermodel"
)
// InsertOrUpdateRosterItem inserts a new roster item entity into storage,
// or updates it in case it's been previously inserted.
func (b *Storage) InsertOrUpdateRosterItem(ri *rostermodel.Item) (rostermodel.Version, error) {
if err := b.db.Update(func(tx *badger.Txn) error {
return b.insertOrUpdate(ri, b.rosterItemKey(ri.Username, ri.JID), tx)
}); err != nil {
return rostermodel.Version{}, err
}
return b.updateRosterVer(ri.Username, false)
}
// DeleteRosterItem deletes a roster item entity from storage.
func (b *Storage) DeleteRosterItem(user, contact string) (rostermodel.Version, error) {
if err := b.db.Update(func(tx *badger.Txn) error {
return b.delete(b.rosterItemKey(user, contact), tx)
}); err != nil {
return rostermodel.Version{}, err
}
return b.updateRosterVer(user, true)
}
// FetchRosterItems retrieves from storage all roster item entities
// associated to a given user.
func (b *Storage) FetchRosterItems(user string) ([]rostermodel.Item, rostermodel.Version, error) {
var ris []rostermodel.Item
if err := b.fetchAll(&ris, []byte("rosterItems:"+user)); err != nil {
return nil, rostermodel.Version{}, err
}
ver, err := b.fetchRosterVer(user)
return ris, ver, err
}
// FetchRosterItem retrieves from storage a roster item entity.
func (b *Storage) FetchRosterItem(user, contact string) (*rostermodel.Item, error) {
var ri rostermodel.Item
err := b.fetch(&ri, b.rosterItemKey(user, contact))
switch err {
case nil:
return &ri, nil
case errBadgerDBEntityNotFound:
return nil, nil
default:
return nil, err
}
}
// InsertOrUpdateRosterNotification inserts a new roster notification entity
// into storage, or updates it in case it's been previously inserted.
func (b *Storage) InsertOrUpdateRosterNotification(rn *rostermodel.Notification) error {
return b.db.Update(func(tx *badger.Txn) error {
return b.insertOrUpdate(rn, b.rosterNotificationKey(rn.Contact, rn.JID), tx)
})
}
// DeleteRosterNotification deletes a roster notification entity from storage.
func (b *Storage) DeleteRosterNotification(contact, jid string) error {
return b.db.Update(func(tx *badger.Txn) error {
return b.delete(b.rosterNotificationKey(contact, jid), tx)
})
}
// FetchRosterNotification retrieves from storage a roster notification entity.
func (b *Storage) FetchRosterNotification(contact string, jid string) (*rostermodel.Notification, error) {
var rn rostermodel.Notification
err := b.fetch(&rn, b.rosterNotificationKey(contact, jid))
switch err {
case nil:
return &rn, nil
case errBadgerDBEntityNotFound:
return nil, nil
default:
return nil, err
}
}
// FetchRosterNotifications retrieves from storage all roster notifications
// associated to a given user.
func (b *Storage) FetchRosterNotifications(contact string) ([]rostermodel.Notification, error) {
var rns []rostermodel.Notification
if err := b.fetchAll(&rns, []byte("rosterNotifications:"+contact)); err != nil {
return nil, err
}
return rns, nil
}
func (b *Storage) updateRosterVer(username string, isDeletion bool) (rostermodel.Version, error) {
v, err := b.fetchRosterVer(username)
if err != nil {
return rostermodel.Version{}, err
}
v.Ver++
if isDeletion {
v.DeletionVer = v.Ver
}
if err := b.db.Update(func(tx *badger.Txn) error {
return b.insertOrUpdate(&v, b.rosterVersionKey(username), tx)
}); err != nil {
return rostermodel.Version{}, err
}
return v, nil
}
func (b *Storage) fetchRosterVer(username string) (rostermodel.Version, error) {
var ver rostermodel.Version
err := b.fetch(&ver, b.rosterVersionKey(username))
switch err {
case nil, errBadgerDBEntityNotFound:
return ver, nil
default:
return ver, err
}
}
func (b *Storage) rosterItemKey(user, contact string) []byte {
return []byte("rosterItems:" + user + ":" + contact)
}
func (b *Storage) rosterVersionKey(username string) []byte {
return []byte("rosterVersions:" + username)
}
func (b *Storage) rosterNotificationKey(contact, jid string) []byte {
return []byte("rosterNotifications:" + contact + ":" + jid)
}