blob: 17627dca23b948e4bfdefcf899c5af8fb38192a2 [file] [log] [blame]
khenaidooab1f7bd2019-11-14 14:00:27 -05001/*
2 * Copyright 2019-present Open Networking Foundation
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
Kent Hagerman2b216042020-04-03 18:28:56 -040016package remote
khenaidooab1f7bd2019-11-14 14:00:27 -050017
18import (
19 "context"
20 "crypto/rand"
khenaidoo442e7c72020-03-10 16:13:48 -040021 "github.com/golang/protobuf/ptypes"
22 any2 "github.com/golang/protobuf/ptypes/any"
khenaidooab1f7bd2019-11-14 14:00:27 -050023 cm "github.com/opencord/voltha-go/rw_core/mocks"
serkant.uluderya2ae470f2020-01-21 11:13:09 -080024 com "github.com/opencord/voltha-lib-go/v3/pkg/adapters/common"
25 "github.com/opencord/voltha-lib-go/v3/pkg/kafka"
26 "github.com/opencord/voltha-lib-go/v3/pkg/log"
Matteo Scandolod525ae32020-04-02 17:27:29 -070027 mock_kafka "github.com/opencord/voltha-lib-go/v3/pkg/mocks/kafka"
khenaidoo442e7c72020-03-10 16:13:48 -040028 ic "github.com/opencord/voltha-protos/v3/go/inter_container"
serkant.uluderya2ae470f2020-01-21 11:13:09 -080029 of "github.com/opencord/voltha-protos/v3/go/openflow_13"
30 "github.com/opencord/voltha-protos/v3/go/voltha"
khenaidooab1f7bd2019-11-14 14:00:27 -050031 "github.com/stretchr/testify/assert"
32 "google.golang.org/grpc/codes"
33 "google.golang.org/grpc/status"
khenaidoo442e7c72020-03-10 16:13:48 -040034 "strings"
35 "testing"
36 "time"
khenaidooab1f7bd2019-11-14 14:00:27 -050037)
38
39const (
40 coreName = "rw_core"
41 adapterName = "adapter_mock"
npujar1d86a522019-11-14 17:11:16 +053042 coreInstanceID = "1000"
khenaidooab1f7bd2019-11-14 14:00:27 -050043)
44
45var (
npujar467fe752020-01-16 20:17:45 +053046 coreKafkaICProxy kafka.InterContainerProxy
47 adapterKafkaICProxy kafka.InterContainerProxy
khenaidooab1f7bd2019-11-14 14:00:27 -050048 kc kafka.Client
49 adapterReqHandler *com.RequestHandlerProxy
50 adapter *cm.Adapter
51)
52
53func init() {
npujar1d86a522019-11-14 17:11:16 +053054 if _, err := log.SetDefaultLogger(log.JSON, 0, log.Fields{"instanceId": coreInstanceID}); err != nil {
khenaidooab1f7bd2019-11-14 14:00:27 -050055 log.With(log.Fields{"error": err}).Fatal("Cannot setup logging")
56 }
57 // Set the log level to Warning
khenaidoo442e7c72020-03-10 16:13:48 -040058 log.SetAllLogLevel(log.WarnLevel)
khenaidooab1f7bd2019-11-14 14:00:27 -050059
60 var err error
61
62 // Create the KV client
Matteo Scandolod525ae32020-04-02 17:27:29 -070063 kc = mock_kafka.NewKafkaClient()
khenaidooab1f7bd2019-11-14 14:00:27 -050064
65 // Setup core inter-container proxy and core request handler
npujar467fe752020-01-16 20:17:45 +053066 coreKafkaICProxy = kafka.NewInterContainerProxy(
khenaidooab1f7bd2019-11-14 14:00:27 -050067 kafka.MsgClient(kc),
npujar467fe752020-01-16 20:17:45 +053068 kafka.DefaultTopic(&kafka.Topic{Name: coreName}))
khenaidoo442e7c72020-03-10 16:13:48 -040069
npujar1d86a522019-11-14 17:11:16 +053070 if err = coreKafkaICProxy.Start(); err != nil {
Girish Kumarf56a4682020-03-20 20:07:46 +000071 logger.Fatalw("Failure-starting-core-kafka-intercontainerProxy", log.Fields{"error": err})
khenaidooab1f7bd2019-11-14 14:00:27 -050072 }
npujar1d86a522019-11-14 17:11:16 +053073 if err = coreKafkaICProxy.SubscribeWithDefaultRequestHandler(kafka.Topic{Name: coreName}, 0); err != nil {
Girish Kumarf56a4682020-03-20 20:07:46 +000074 logger.Fatalw("Failure-subscribing-core-request-handler", log.Fields{"error": err})
khenaidooab1f7bd2019-11-14 14:00:27 -050075 }
76
77 // Setup adapter inter-container proxy and adapter request handler
78 adapterCoreProxy := com.NewCoreProxy(nil, adapterName, coreName)
79 adapter = cm.NewAdapter(adapterCoreProxy)
npujar1d86a522019-11-14 17:11:16 +053080 adapterReqHandler = com.NewRequestHandlerProxy(coreInstanceID, adapter, adapterCoreProxy)
npujar467fe752020-01-16 20:17:45 +053081 adapterKafkaICProxy = kafka.NewInterContainerProxy(
khenaidooab1f7bd2019-11-14 14:00:27 -050082 kafka.MsgClient(kc),
83 kafka.DefaultTopic(&kafka.Topic{Name: adapterName}),
npujar467fe752020-01-16 20:17:45 +053084 kafka.RequestHandlerInterface(adapterReqHandler))
khenaidoo442e7c72020-03-10 16:13:48 -040085
khenaidooab1f7bd2019-11-14 14:00:27 -050086 if err = adapterKafkaICProxy.Start(); err != nil {
Girish Kumarf56a4682020-03-20 20:07:46 +000087 logger.Fatalw("Failure-starting-adapter-kafka-intercontainerProxy", log.Fields{"error": err})
khenaidooab1f7bd2019-11-14 14:00:27 -050088 }
89 if err = adapterKafkaICProxy.SubscribeWithDefaultRequestHandler(kafka.Topic{Name: adapterName}, 0); err != nil {
Girish Kumarf56a4682020-03-20 20:07:46 +000090 logger.Fatalw("Failure-subscribing-adapter-request-handler", log.Fields{"error": err})
khenaidooab1f7bd2019-11-14 14:00:27 -050091 }
92}
93
94func getRandomBytes(size int) (bytes []byte, err error) {
95 bytes = make([]byte, size)
96 _, err = rand.Read(bytes)
97 return
98}
99
100func TestCreateAdapterProxy(t *testing.T) {
Matteo Scandolod525ae32020-04-02 17:27:29 -0700101 ap := NewAdapterProxy(coreKafkaICProxy, coreName, mock_kafka.NewEndpointManager())
khenaidooab1f7bd2019-11-14 14:00:27 -0500102 assert.NotNil(t, ap)
103}
104
khenaidoo442e7c72020-03-10 16:13:48 -0400105func waitForResponse(ctx context.Context, ch chan *kafka.RpcResponse) (*any2.Any, error) {
106 select {
107 case rpcResponse, ok := <-ch:
108 if !ok {
109 return nil, status.Error(codes.Aborted, "channel-closed")
110 } else if rpcResponse.Err != nil {
111 return nil, rpcResponse.Err
112 } else {
113 return rpcResponse.Reply, nil
114 }
115 case <-ctx.Done():
116 return nil, ctx.Err()
117 }
118}
119
khenaidooab1f7bd2019-11-14 14:00:27 -0500120func testSimpleRequests(t *testing.T) {
khenaidoo442e7c72020-03-10 16:13:48 -0400121 type simpleRequest func(context.Context, *voltha.Device) (chan *kafka.RpcResponse, error)
Matteo Scandolod525ae32020-04-02 17:27:29 -0700122 ap := NewAdapterProxy(coreKafkaICProxy, coreName, mock_kafka.NewEndpointManager())
khenaidooab1f7bd2019-11-14 14:00:27 -0500123 simpleRequests := []simpleRequest{
Kent Hagerman2b216042020-04-03 18:28:56 -0400124 ap.AdoptDevice,
125 ap.DisableDevice,
126 ap.RebootDevice,
127 ap.DeleteDevice,
128 ap.ReconcileDevice,
129 ap.ReEnableDevice,
khenaidooab1f7bd2019-11-14 14:00:27 -0500130 }
131 for _, f := range simpleRequests {
khenaidoo442e7c72020-03-10 16:13:48 -0400132 // Success
khenaidooab1f7bd2019-11-14 14:00:27 -0500133 d := &voltha.Device{Id: "deviceId", Adapter: adapterName}
134 ctx, cancel := context.WithTimeout(context.Background(), 1*time.Second)
khenaidoo442e7c72020-03-10 16:13:48 -0400135 rpcResponse, err := f(ctx, d)
khenaidooab1f7bd2019-11-14 14:00:27 -0500136 assert.Nil(t, err)
khenaidoo442e7c72020-03-10 16:13:48 -0400137 _, err = waitForResponse(ctx, rpcResponse)
138 assert.Nil(t, err)
139 cancel()
khenaidooab1f7bd2019-11-14 14:00:27 -0500140
141 // Failure - invalid adapter
khenaidoo442e7c72020-03-10 16:13:48 -0400142 expectedError := "context deadline exceeded"
khenaidooab1f7bd2019-11-14 14:00:27 -0500143 d = &voltha.Device{Id: "deviceId", Adapter: "adapter_mock_1"}
144 ctx, cancel = context.WithTimeout(context.Background(), 20*time.Millisecond)
khenaidoo442e7c72020-03-10 16:13:48 -0400145 rpcResponse, err = f(ctx, d)
146 assert.Nil(t, err)
147 _, err = waitForResponse(ctx, rpcResponse)
khenaidooab1f7bd2019-11-14 14:00:27 -0500148 cancel()
149 assert.NotNil(t, err)
khenaidoo442e7c72020-03-10 16:13:48 -0400150 assert.True(t, strings.Contains(err.Error(), expectedError))
khenaidooab1f7bd2019-11-14 14:00:27 -0500151
khenaidoo442e7c72020-03-10 16:13:48 -0400152 // Failure - timeout
khenaidooab1f7bd2019-11-14 14:00:27 -0500153 d = &voltha.Device{Id: "deviceId", Adapter: adapterName}
154 ctx, cancel = context.WithTimeout(context.Background(), 100*time.Nanosecond)
khenaidoo442e7c72020-03-10 16:13:48 -0400155 rpcResponse, err = f(ctx, d)
156 assert.Nil(t, err)
157 _, err = waitForResponse(ctx, rpcResponse)
khenaidooab1f7bd2019-11-14 14:00:27 -0500158 cancel()
159 assert.NotNil(t, err)
khenaidoo442e7c72020-03-10 16:13:48 -0400160 assert.True(t, strings.Contains(err.Error(), expectedError))
khenaidooab1f7bd2019-11-14 14:00:27 -0500161 }
162}
163
164func testGetSwitchCapabilityFromAdapter(t *testing.T) {
Matteo Scandolod525ae32020-04-02 17:27:29 -0700165 ap := NewAdapterProxy(coreKafkaICProxy, coreName, mock_kafka.NewEndpointManager())
khenaidooab1f7bd2019-11-14 14:00:27 -0500166 d := &voltha.Device{Id: "deviceId", Adapter: adapterName}
167 ctx, cancel := context.WithTimeout(context.Background(), 3*time.Second)
khenaidoo442e7c72020-03-10 16:13:48 -0400168 defer cancel()
Kent Hagerman2b216042020-04-03 18:28:56 -0400169 rpcResponse, err := ap.GetOfpDeviceInfo(ctx, d)
khenaidoo442e7c72020-03-10 16:13:48 -0400170 assert.Nil(t, err)
171 response, err := waitForResponse(ctx, rpcResponse)
172 assert.Nil(t, err)
173 switchCap := &ic.SwitchCapability{}
174 err = ptypes.UnmarshalAny(response, switchCap)
khenaidooab1f7bd2019-11-14 14:00:27 -0500175 assert.Nil(t, err)
176 assert.NotNil(t, switchCap)
177 expectedCap, _ := adapter.Get_ofp_device_info(d)
178 assert.Equal(t, switchCap.String(), expectedCap.String())
179}
180
181func testGetPortInfoFromAdapter(t *testing.T) {
Matteo Scandolod525ae32020-04-02 17:27:29 -0700182 ap := NewAdapterProxy(coreKafkaICProxy, coreName, mock_kafka.NewEndpointManager())
khenaidooab1f7bd2019-11-14 14:00:27 -0500183 d := &voltha.Device{Id: "deviceId", Adapter: adapterName}
184 ctx, cancel := context.WithTimeout(context.Background(), 3*time.Second)
khenaidoo442e7c72020-03-10 16:13:48 -0400185 defer cancel()
khenaidooab1f7bd2019-11-14 14:00:27 -0500186 portNo := uint32(1)
Kent Hagerman2b216042020-04-03 18:28:56 -0400187 rpcResponse, err := ap.GetOfpPortInfo(ctx, d, portNo)
khenaidooab1f7bd2019-11-14 14:00:27 -0500188 assert.Nil(t, err)
khenaidoo442e7c72020-03-10 16:13:48 -0400189 response, err := waitForResponse(ctx, rpcResponse)
190 assert.Nil(t, err)
191 portCap := &ic.PortCapability{}
192 err = ptypes.UnmarshalAny(response, portCap)
193 assert.Nil(t, err)
194 assert.NotNil(t, portCap)
khenaidooab1f7bd2019-11-14 14:00:27 -0500195 expectedPortInfo, _ := adapter.Get_ofp_port_info(d, int64(portNo))
khenaidoo442e7c72020-03-10 16:13:48 -0400196 assert.Equal(t, portCap.String(), expectedPortInfo.String())
khenaidooab1f7bd2019-11-14 14:00:27 -0500197}
198
199func testPacketOut(t *testing.T) {
Matteo Scandolod525ae32020-04-02 17:27:29 -0700200 ap := NewAdapterProxy(coreKafkaICProxy, coreName, mock_kafka.NewEndpointManager())
khenaidooab1f7bd2019-11-14 14:00:27 -0500201 d := &voltha.Device{Id: "deviceId", Adapter: adapterName}
202 outPort := uint32(1)
203 packet, err := getRandomBytes(50)
204 assert.Nil(t, err)
khenaidoo442e7c72020-03-10 16:13:48 -0400205 ctx, cancel := context.WithTimeout(context.Background(), 1*time.Second)
206 defer cancel()
Kent Hagerman2b216042020-04-03 18:28:56 -0400207 rpcResponse, err := ap.PacketOut(ctx, adapterName, d.Id, outPort, &of.OfpPacketOut{Data: packet})
khenaidoo442e7c72020-03-10 16:13:48 -0400208 assert.Nil(t, err)
209 _, err = waitForResponse(ctx, rpcResponse)
khenaidooab1f7bd2019-11-14 14:00:27 -0500210 assert.Nil(t, err)
211}
212
213func testFlowUpdates(t *testing.T) {
Matteo Scandolod525ae32020-04-02 17:27:29 -0700214 ap := NewAdapterProxy(coreKafkaICProxy, coreName, mock_kafka.NewEndpointManager())
khenaidooab1f7bd2019-11-14 14:00:27 -0500215 d := &voltha.Device{Id: "deviceId", Adapter: adapterName}
Kent Hagerman2b216042020-04-03 18:28:56 -0400216 _, err := ap.UpdateFlowsBulk(context.Background(), d, &voltha.Flows{}, &voltha.FlowGroups{}, &voltha.FlowMetadata{})
khenaidooab1f7bd2019-11-14 14:00:27 -0500217 assert.Nil(t, err)
218 flowChanges := &voltha.FlowChanges{ToAdd: &voltha.Flows{Items: nil}, ToRemove: &voltha.Flows{Items: nil}}
219 groupChanges := &voltha.FlowGroupChanges{ToAdd: &voltha.FlowGroups{Items: nil}, ToRemove: &voltha.FlowGroups{Items: nil}, ToUpdate: &voltha.FlowGroups{Items: nil}}
khenaidoo442e7c72020-03-10 16:13:48 -0400220 ctx, cancel := context.WithTimeout(context.Background(), 1*time.Second)
221 defer cancel()
Kent Hagerman2b216042020-04-03 18:28:56 -0400222 rpcResponse, err := ap.UpdateFlowsIncremental(ctx, d, flowChanges, groupChanges, &voltha.FlowMetadata{})
khenaidoo442e7c72020-03-10 16:13:48 -0400223 assert.Nil(t, err)
224 _, err = waitForResponse(ctx, rpcResponse)
khenaidooab1f7bd2019-11-14 14:00:27 -0500225 assert.Nil(t, err)
226}
227
228func testPmUpdates(t *testing.T) {
Matteo Scandolod525ae32020-04-02 17:27:29 -0700229 ap := NewAdapterProxy(coreKafkaICProxy, coreName, mock_kafka.NewEndpointManager())
khenaidooab1f7bd2019-11-14 14:00:27 -0500230 d := &voltha.Device{Id: "deviceId", Adapter: adapterName}
231 ctx, cancel := context.WithTimeout(context.Background(), 3*time.Second)
khenaidoo442e7c72020-03-10 16:13:48 -0400232 defer cancel()
Kent Hagerman2b216042020-04-03 18:28:56 -0400233 rpcResponse, err := ap.UpdatePmConfigs(ctx, d, &voltha.PmConfigs{})
khenaidoo442e7c72020-03-10 16:13:48 -0400234 assert.Nil(t, err)
235 _, err = waitForResponse(ctx, rpcResponse)
khenaidooab1f7bd2019-11-14 14:00:27 -0500236 assert.Nil(t, err)
237}
238
Matteo Scandolod525ae32020-04-02 17:27:29 -0700239func TestSuiteAdapterProxy(t *testing.T) {
khenaidooab1f7bd2019-11-14 14:00:27 -0500240 //1. Test the simple requests first
241 testSimpleRequests(t)
242
243 //2. Test get switch capability
244 testGetSwitchCapabilityFromAdapter(t)
245
246 //3. Test get port info
247 testGetPortInfoFromAdapter(t)
248
249 //4. Test PacketOut
250 testPacketOut(t)
251
252 // 5. Test flow updates
253 testFlowUpdates(t)
254
255 //6. Pm configs
256 testPmUpdates(t)
257}