This repository has been archived by the owner on Jul 16, 2019. It is now read-only.
-
-
Notifications
You must be signed in to change notification settings - Fork 0
/
feeddb.go
98 lines (75 loc) · 1.83 KB
/
feeddb.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
package main
import (
"sort"
"sync"
"time"
"github.com/SlyMarbo/rss"
"github.com/pkg/errors"
log "github.com/sirupsen/logrus"
)
type feedInfo struct {
DisplayName string `yaml:"display_name"`
ProfileURL string `yaml:"profile_url"`
FeedURL string `yaml:"feed_url"`
}
type feedDBEntry struct {
Items []*rss.Item
LastUpdated time.Time
Info feedInfo
}
type feedDB struct {
feeds map[string]feedDBEntry
lock sync.RWMutex
}
func newFeedDB(feedConfig map[string]feedInfo) *feedDB {
f := &feedDB{
feeds: make(map[string]feedDBEntry),
}
for feedName, info := range feedConfig {
f.feeds[feedName] = feedDBEntry{
Info: info,
}
// Initialize database at startup
if _, err := f.Update(feedName); err != nil {
log.WithField("feed_name", feedName).WithError(err).Error("Unable to refresh feed")
}
}
return f
}
func (f *feedDB) entriesByFeedName(name string) []*rss.Item {
f.lock.RLock()
defer f.lock.RUnlock()
if e, ok := f.feeds[name]; ok {
return e.Items
}
return nil
}
func (f *feedDB) infoByFeedName(name string) *feedInfo {
f.lock.RLock()
defer f.lock.RUnlock()
if e, ok := f.feeds[name]; ok {
return &e.Info
}
return nil
}
func (f *feedDB) Update(feedName string) (bool, error) {
f.lock.RLock()
fe := f.feeds[feedName]
f.lock.RUnlock()
if len(fe.Items) > 0 && fe.LastUpdated.Add(cfg.FeedPollInterval).After(time.Now()) {
// Don't poll more often than requested
return false, nil
}
feed, err := rss.Fetch(fe.Info.FeedURL)
if err != nil {
return false, errors.Wrap(err, "Unable to retrieve feed")
}
// Reverse sort (newest to oldest): swapped i, j
sort.Slice(feed.Items, func(j, i int) bool { return feed.Items[i].Date.Before(feed.Items[j].Date) })
fe.Items = feed.Items
fe.LastUpdated = time.Now()
f.lock.Lock()
f.feeds[feedName] = fe
f.lock.Unlock()
return true, nil
}