Coveralls logob
Coveralls logo
  • Home
  • Features
  • Pricing
  • Docs
  • Sign In

weaveworks / weave / #3760

22 Sep 2015 - 13:52 coverage increased (+0.3%) to 77.586%
#3760

Pull #1449

circleci

Eac6f57e46837c7b0d0bacac4288d0b9?size=18&default=identiconpaulbellamy
Removing confusing variable from getDNSDomain, just return "" when disabled
Pull Request #1449: Override sneaky /start HostConfig params

44 of 70 new or added lines in 3 files covered. (62.86%)

3 existing lines in 1 file now uncovered.

5317 of 6853 relevant lines covered (77.59%)

126843.01 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

91.09
/router/gossip.go
1
package router
2

3
import (
4
        "fmt"
5
)
6

7
type GossipData interface {
8
        Encode() [][]byte
9
        Merge(GossipData)
10
}
11

12
type Gossip interface {
13
        // specific message from one peer to another
14
        // intermediate peers relay it using unicast topology.
15
        GossipUnicast(dstPeerName PeerName, msg []byte) error
16
        // send gossip to every peer, relayed using broadcast topology.
17
        GossipBroadcast(update GossipData) error
18
}
19

20
type Gossiper interface {
21
        OnGossipUnicast(sender PeerName, msg []byte) error
22
        // merge received data into state and return a representation of
23
        // the received data, for further propagation
24
        OnGossipBroadcast(sender PeerName, update []byte) (GossipData, error)
25
        // return state of everything we know; gets called periodically
26
        Gossip() GossipData
27
        // merge received data into state and return "everything new I've
28
        // just learnt", or nil if nothing in the received data was new
29
        OnGossip(update []byte) (GossipData, error)
30
}
31

32
// Accumulates GossipData that needs to be sent to one destination,
33
// and sends it when possible.
34
type GossipSender struct {
35
        send func(GossipData)
36
        cell chan GossipData
37
        // for testing
38
        sent    bool
39
        flushch chan chan bool
40
}
41

42
func NewGossipSender(send func(GossipData)) *GossipSender {
318×
43
        cell := make(chan GossipData, 1)
318×
44
        flushch := make(chan chan bool)
318×
45
        sender := &GossipSender{
318×
46
                send:    send,
318×
47
                cell:    cell,
318×
48
                flushch: flushch,
318×
49
        }
318×
50
        go sender.run()
318×
51
        return sender
318×
52
}
318×
53

54
func (sender *GossipSender) run() {
318×
55
        for {
1,563×
56
                select {
1,563×
57
                case pending := <-sender.cell:
910×
58
                        if pending == nil { // receive zero value when chan is closed
5×
59
                                return
5×
60
                        }
5×
61
                        sender.send(pending)
905×
62
                        sender.sent = true
905×
63
                case ch := <-sender.flushch:
340×
64
                        // send anything pending, then reply back whether we sent
340×
65
                        // anything since previous flush
340×
66
                        select {
340×
UNCOV
67
                        case pending := <-sender.cell:
!
UNCOV
68
                                sender.send(pending)
!
UNCOV
69
                                sender.sent = true
!
70
                        default:
340×
71
                        }
72
                        ch <- sender.sent
340×
73
                        sender.sent = false
340×
74
                }
75
        }
76
}
77

78
func (sender *GossipSender) Send(data GossipData) {
931×
79
        // NB: this must not be invoked concurrently
931×
80
        select {
931×
81
        case pending := <-sender.cell:
26×
82
                pending.Merge(data)
26×
83
                sender.cell <- pending
26×
84
        default:
905×
85
                sender.cell <- data
905×
86
        }
87
}
88

89
func (sender *GossipSender) Stop() {
5×
90
        close(sender.cell)
5×
91
}
5×
92

93
type GossipChannels map[string]*GossipChannel
94

95
func (router *Router) NewGossip(channelName string, g Gossiper) Gossip {
173×
96
        channel := NewGossipChannel(channelName, router.Ourself, router.Routes, g)
173×
97
        router.gossipLock.Lock()
173×
98
        defer router.gossipLock.Unlock()
173×
99
        if _, found := router.gossipChannels[channelName]; found {
!
100
                checkFatal(fmt.Errorf("[gossip] duplicate channel %s", channelName))
!
101
        }
!
102
        router.gossipChannels[channelName] = channel
173×
103
        return channel
173×
104
}
105

106
func (router *Router) gossipChannel(channelName string) *GossipChannel {
495×
107
        router.gossipLock.RLock()
495×
108
        channel, found := router.gossipChannels[channelName]
495×
109
        router.gossipLock.RUnlock()
495×
110
        if found {
491×
111
                return channel
491×
112
        }
491×
113
        router.gossipLock.Lock()
4×
114
        defer router.gossipLock.Unlock()
4×
115
        if channel, found = router.gossipChannels[channelName]; found {
!
116
                return channel
!
117
        }
!
118
        channel = NewGossipChannel(channelName, router.Ourself, router.Routes, &surrogateGossiper)
4×
119
        channel.log("created surrogate channel")
4×
120
        router.gossipChannels[channelName] = channel
4×
121
        return channel
4×
122
}
123

124
func (router *Router) gossipChannelSet() map[*GossipChannel]struct{} {
139×
125
        channels := make(map[*GossipChannel]struct{})
139×
126
        router.gossipLock.RLock()
139×
127
        defer router.gossipLock.RUnlock()
139×
128
        for _, channel := range router.gossipChannels {
243×
129
                channels[channel] = void
243×
130
        }
243×
131
        return channels
139×
132
}
133

134
func (router *Router) SendAllGossip() {
10×
135
        for channel := range router.gossipChannelSet() {
26×
136
                if gossip := channel.gossiper.Gossip(); gossip != nil {
26×
137
                        channel.Send(router.Ourself.Name, gossip)
26×
138
                }
26×
139
        }
140
}
141

142
func (router *Router) SendAllGossipDown(conn Connection) {
47×
143
        for channel := range router.gossipChannelSet() {
120×
144
                if gossip := channel.gossiper.Gossip(); gossip != nil {
117×
145
                        channel.SendDown(conn, channel.gossiper.Gossip())
117×
146
                }
117×
147
        }
148
}
149

150
// for testing
151

152
func (router *Router) sendPendingGossip() bool {
82×
153
        sentSomething := false
82×
154
        for channel := range router.gossipChannelSet() {
97×
155
                channel.Lock()
97×
156
                for _, sender := range channel.senders {
118×
157
                        sentSomething = sender.flush() || sentSomething
118×
158
                }
118×
159
                for _, sender := range channel.broadcasters {
222×
160
                        sentSomething = sender.flush() || sentSomething
222×
161
                }
222×
162
                channel.Unlock()
97×
163
        }
164
        return sentSomething
82×
165
}
166

167
func (sender *GossipSender) flush() bool {
340×
168
        ch := make(chan bool)
340×
169
        sender.flushch <- ch
340×
170
        return <-ch
340×
171
}
340×
Troubleshooting · Open an Issue · Sales · Support · ENTERPRISE · CAREERS · STATUS
BLOG · TWITTER · Legal & Privacy · Supported CI Services · What's a CI service? · Automated Testing

© 2022 Coveralls, Inc