1
1
package main
2
2
3
3
import (
4
+ "crypto/rand"
5
+ "encoding/binary"
4
6
"fmt"
5
7
event_rpc "github.com/docker/infrakit/pkg/rpc/event"
6
8
rpc_server "github.com/docker/infrakit/pkg/rpc/server"
9
+ "github.com/docker/infrakit/pkg/spi/application"
7
10
"github.com/docker/infrakit/pkg/spi/event"
8
11
testing_event "github.com/docker/infrakit/pkg/testing/event"
9
12
"github.com/docker/infrakit/pkg/types"
10
13
MQTT "github.com/eclipse/paho.mqtt.golang"
11
14
"github.com/stretchr/testify/require"
12
15
"io/ioutil"
13
16
"path/filepath"
17
+ "strconv"
14
18
"testing"
15
19
"time"
16
20
)
17
21
18
- var MQTTTESTSERVER string = "tcp://test.mosquitto.org:1883"
22
+ var MQTTTESTSERVER = "tcp://iot.eclipse.org:1883"
23
+ var EVENTNUM = 5
24
+
25
+ func TestUnitUpdate (t * testing.T ) {
26
+ socketPath := tempSocket ()
27
+ stub := func () interface {} { return nil }
28
+ m := map [string ]interface {}{}
29
+ types .Put (types .PathFromString ("test/instance1" ), stub , m )
30
+ types .Put (types .PathFromString ("test/instance2" ), stub , m )
31
+ plugin := & testing_event.Plugin {
32
+ Publisher : (* testing_event .Publisher )(nil ),
33
+ DoList : func (topic types.Path ) ([]string , error ) {
34
+ return types .List (topic , m ), nil
35
+ },
36
+ }
37
+ var impl rpc_server.VersionedInterface = event_rpc .PluginServerWithTypes (
38
+ map [string ]event.Plugin {
39
+ "test" : plugin ,
40
+ })
41
+ server , err := rpc_server .StartPluginAtPath (socketPath , impl )
42
+ require .NoError (t , err )
43
+ defer server .Stop ()
44
+
45
+ //Test ADD operation
46
+ require .NoError (t , err )
47
+ e := NewEventRepeater (socketPath , "" , "stderr" , false ).(* eventRepeater )
48
+ mes := & application.Message {
49
+ Op : application .ADD ,
50
+ Resource : "event" ,
51
+ Data : types .AnyString ("[{\" sourcetopic\" :\" test/instance1\" ,\" sinktopic\" :\" test/sink/instance1\" },{\" sourcetopic\" :\" test/instance2\" ,\" sinktopic\" :\" test/sink/instance2\" }]" ),
52
+ }
53
+ err = e .Update (mes )
54
+ require .NoError (t , err )
55
+ require .Equal (t , 2 , len (e .Events ))
56
+ require .Equal (t , "test/sink/instance1" , e .Events ["test/instance1" ].SinkTopic )
57
+ require .Equal (t , "test/sink/instance2" , e .Events ["test/instance2" ].SinkTopic )
58
+
59
+ //Test DELETE operation
60
+ mes = & application.Message {
61
+ Op : application .DELETE ,
62
+ Resource : "event" ,
63
+ Data : types .AnyString ("[{\" sourcetopic\" :\" test/instance2\" ,\" sinktopic\" :\" \" }]" ),
64
+ }
65
+ err = e .Update (mes )
66
+ require .NoError (t , err )
67
+ require .Equal (t , 1 , len (e .Events ))
68
+ require .Equal (t , "test/sink/instance1" , e .Events ["test/instance1" ].SinkTopic )
69
+ _ , ok := e .Events ["test/instance2" ]
70
+ require .Equal (t , false , ok )
71
+
72
+ //Test UPDATE operation
73
+ mes = & application.Message {
74
+ Op : application .UPDATE ,
75
+ Resource : "event" ,
76
+ Data : types .AnyString ("[{\" sourcetopic\" :\" test/instance1\" ,\" sinktopic\" :\" test/event/instance1\" }]" ),
77
+ }
78
+ err = e .Update (mes )
79
+ require .NoError (t , err )
80
+ require .Equal (t , "test/event/instance1" , e .Events ["test/instance1" ].SinkTopic )
81
+ }
19
82
20
83
func tempSocket () string {
21
84
dir , err := ioutil .TempDir ("" , "infrakit-test-" )
@@ -24,24 +87,37 @@ func tempSocket() string {
24
87
}
25
88
return filepath .Join (dir , "app-impl-test" )
26
89
}
27
- func runEvent (startPub chan struct {}) (* string , rpc_server.Stoppable , error ) {
90
+ func runEvent (startPub chan struct {}, tPrefix string ) (string , rpc_server.Stoppable , error ) {
28
91
socketPath := tempSocket ()
29
- events := 5
30
92
publishChan0 := make (chan chan <- * event.Event )
31
93
go func () {
32
94
publish := <- publishChan0
33
95
defer close (publish )
34
96
<- startPub
35
97
// here we have the channel and ready to go
36
- for i := 0 ; i < events ; i ++ {
98
+ for i := 0 ; i < EVENTNUM ; i ++ {
37
99
<- time .After (50 * time .Millisecond )
38
- fmt .Printf ("publish event%d\n " , i )
39
100
publish <- event.Event {
40
101
Topic : types .PathFromString ("instance/create" ),
41
102
ID : fmt .Sprintf ("host-%d" , i ),
42
103
}.Init ().WithDataMust ([]int {1 , 2 }).Now ()
43
104
}
44
105
}()
106
+ publishChan1 := make (chan chan <- * event.Event )
107
+ go func () {
108
+ publish := <- publishChan1
109
+ defer close (publish )
110
+ <- startPub
111
+ // here we have the channel and ready to go
112
+ for i := 0 ; i < EVENTNUM ; i ++ {
113
+ <- time .After (50 * time .Millisecond )
114
+ publish <- event.Event {
115
+ Topic : types .PathFromString ("instance/create" ),
116
+ ID : fmt .Sprintf ("disk-%d" , i ),
117
+ }.Init ().WithDataMust ([]string {"foo" , "bar" }).Now ()
118
+ }
119
+ }()
120
+
45
121
m := map [string ]interface {}{}
46
122
types .Put (types .PathFromString ("instance/create" ), "instance-create" , m )
47
123
plugin0 := & testing_event.Plugin {
@@ -55,61 +131,145 @@ func runEvent(startPub chan struct{}) (*string, rpc_server.Stoppable, error) {
55
131
},
56
132
},
57
133
}
134
+ plugin1 := & testing_event.Plugin {
135
+ DoList : func (topic types.Path ) ([]string , error ) {
136
+ return types .List (topic , m ), nil
137
+ },
138
+ Publisher : & testing_event.Publisher {
139
+ DoPublishOn : func (c chan <- * event.Event ) {
140
+ publishChan1 <- c
141
+ close (publishChan1 )
142
+ },
143
+ },
144
+ }
58
145
var impl rpc_server.VersionedInterface = event_rpc .PluginServerWithTypes (
59
146
map [string ]event.Plugin {
60
- "iktest" : plugin0 ,
147
+ tPrefix + "-compute" : plugin0 ,
148
+ tPrefix + "-storage" : plugin1 ,
61
149
})
62
150
server , err := rpc_server .StartPluginAtPath (socketPath , impl )
63
151
if err != nil {
64
- return nil , nil , err
152
+ return "" , nil , err
65
153
}
66
- return & socketPath , server , nil
154
+ return socketPath , server , nil
67
155
}
68
156
69
- func runSub (msgch chan MQTT.Message ) (MQTT.Client , error ) {
157
+ func runSub (msgch chan MQTT.Message , tPrefix string ) (MQTT.Client , error ) {
70
158
opts := MQTT .NewClientOptions ().AddBroker (MQTTTESTSERVER )
71
159
client := MQTT .NewClient (opts )
72
160
if token := client .Connect (); token .Wait () && token .Error () != nil {
73
161
return nil , token .Error ()
74
162
}
75
163
subToken := client .Subscribe (
76
- "iktest /instance/create" ,
164
+ tPrefix + " /instance/create" ,
77
165
0 ,
78
166
func (client MQTT.Client , msg MQTT.Message ) {
79
167
msgch <- msg
80
168
})
81
- fmt .Printf ("mqtt substart" )
82
169
if subToken .Wait () && subToken .Error () != nil {
83
170
return nil , subToken .Error ()
84
171
}
85
172
return client , nil
86
173
}
87
174
88
- func TestIntegration (t * testing.T ) {
175
+ func TestIntegrationAllowAll (t * testing.T ) {
176
+ var n uint64
177
+ binary .Read (rand .Reader , binary .LittleEndian , & n )
178
+ randString := strconv .FormatUint (n , 36 )
179
+ topicPrefix := "ifktest-" + randString
89
180
startPub := make (chan struct {})
90
- socketPath , erpcsrv , err := runEvent (startPub )
181
+ socketPath , erpcsrv , err := runEvent (startPub , topicPrefix )
91
182
defer erpcsrv .Stop ()
92
183
require .NoError (t , err )
93
- mqsubch := make (chan MQTT.Message )
94
- mqttClient , err := runSub (mqsubch )
184
+ mqsubch0 := make (chan MQTT.Message )
185
+ mqttClient0 , err := runSub (mqsubch0 , topicPrefix + "-compute" )
186
+ require .NoError (t , err )
187
+ mqsubch1 := make (chan MQTT.Message )
188
+ mqttClient1 , err := runSub (mqsubch1 , topicPrefix + "-storage" )
95
189
require .NoError (t , err )
96
- defer mqttClient .Disconnect (250 )
97
- app := NewEventRepeater (* socketPath , MQTTTESTSERVER , "mqtt" , true )
190
+ defer mqttClient0 .Disconnect (250 )
191
+ defer mqttClient1 .Disconnect (250 )
192
+ app := NewEventRepeater (socketPath , MQTTTESTSERVER , "mqtt" , true )
98
193
defer app .(* eventRepeater ).Stop ()
99
194
close (startPub )
100
- var subEvent int = 0
195
+ var subEvent0 int
196
+ var subEvent1 int
101
197
loop:
102
198
for {
103
199
select {
104
200
case <- time .After (500 * time .Millisecond ):
105
201
break loop
106
- case sub := <- mqsubch :
107
- subany := types .AnyBytes (sub .Payload ())
202
+ case sub0 := <- mqsubch0 :
203
+ subany := types .AnyBytes (sub0 .Payload ())
204
+ subevent := event.Event {}
205
+ err := subany .Decode (& subevent )
206
+ require .NoError (t , err )
207
+ require .Equal (t , fmt .Sprintf ("host-%d" , subEvent0 ), subevent .ID )
208
+ subEvent0 ++
209
+ case sub1 := <- mqsubch1 :
210
+ subany := types .AnyBytes (sub1 .Payload ())
211
+ subevent := event.Event {}
212
+ err := subany .Decode (& subevent )
213
+ require .NoError (t , err )
214
+ require .Equal (t , fmt .Sprintf ("disk-%d" , subEvent1 ), subevent .ID )
215
+ subEvent1 ++
216
+
217
+ }
218
+ }
219
+ require .Equal (t , EVENTNUM , subEvent0 )
220
+ require .Equal (t , EVENTNUM , subEvent1 )
221
+ }
222
+
223
+ func TestIntegrationDenyAll (t * testing.T ) {
224
+ var n uint64
225
+ binary .Read (rand .Reader , binary .LittleEndian , & n )
226
+ randString := strconv .FormatUint (n , 36 )
227
+ topicPrefix := "ifktest-" + randString
228
+ startPub := make (chan struct {})
229
+ socketPath , erpcsrv , err := runEvent (startPub , topicPrefix )
230
+ defer erpcsrv .Stop ()
231
+ require .NoError (t , err )
232
+ mqsubch0 := make (chan MQTT.Message )
233
+ mqttClient0 , err := runSub (mqsubch0 , topicPrefix + "-compute" )
234
+ require .NoError (t , err )
235
+ mqsubch1 := make (chan MQTT.Message )
236
+ mqttClient1 , err := runSub (mqsubch1 , topicPrefix + "-storage" )
237
+ require .NoError (t , err )
238
+ defer mqttClient0 .Disconnect (250 )
239
+ defer mqttClient1 .Disconnect (250 )
240
+ app := NewEventRepeater (socketPath , MQTTTESTSERVER , "mqtt" , false )
241
+ defer app .(* eventRepeater ).Stop ()
242
+ m := & application.Message {
243
+ Op : application .ADD ,
244
+ Resource : "event" ,
245
+ Data : types .AnyString ("[{\" sourcetopic\" :\" " + topicPrefix + "-compute/instance/create\" ,\" sinktopic\" :\" \" }]" ),
246
+ }
247
+ err = app .Update (m )
248
+ require .NoError (t , err )
249
+ close (startPub )
250
+ var subEvent0 int
251
+ var subEvent1 int
252
+ loop:
253
+ for {
254
+ select {
255
+ case <- time .After (500 * time .Millisecond ):
256
+ break loop
257
+ case sub0 := <- mqsubch0 :
258
+ subany := types .AnyBytes (sub0 .Payload ())
259
+ subevent := event.Event {}
260
+ err := subany .Decode (& subevent )
261
+ require .NoError (t , err )
262
+ require .Equal (t , fmt .Sprintf ("host-%d" , subEvent0 ), subevent .ID )
263
+ subEvent0 ++
264
+ case sub1 := <- mqsubch1 :
265
+ subany := types .AnyBytes (sub1 .Payload ())
108
266
subevent := event.Event {}
109
267
err := subany .Decode (& subevent )
110
268
require .NoError (t , err )
111
- require .Equal (t , subevent . ID , fmt .Sprintf ("host -%d" , subEvent ) )
112
- subEvent ++
269
+ require .Equal (t , fmt .Sprintf ("disk -%d" , subEvent1 ), subevent . ID )
270
+ subEvent1 ++
113
271
}
114
272
}
273
+ require .Equal (t , EVENTNUM , subEvent0 )
274
+ require .Equal (t , 0 , subEvent1 )
115
275
}
0 commit comments