blob: 2a5ebc1a023365fab07875b51d60c0ea8d472545 [file] [log] [blame]
Matteo Scandolo769a5a42018-05-31 16:43:39 -07001# Copyright 2017-present Open Networking Foundation
2#
3# Licensed under the Apache License, Version 2.0 (the "License");
4# you may not use this file except in compliance with the License.
5# You may obtain a copy of the License at
6#
7# http://www.apache.org/licenses/LICENSE-2.0
8#
9# Unless required by applicable law or agreed to in writing, software
10# distributed under the License is distributed on an "AS IS" BASIS,
11# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12# See the License for the specific language governing permissions and
13# limitations under the License.
14
15import unittest
16
17import functools
18from mock import patch, call, Mock, PropertyMock
19import requests_mock
20import multistructlog
21from multistructlog import create_logger
22
23import os, sys
24
Matteo Scandolo769a5a42018-05-31 16:43:39 -070025test_path=os.path.abspath(os.path.dirname(os.path.realpath(__file__)))
Matteo Scandolo769a5a42018-05-31 16:43:39 -070026
27def match_json(desired, req):
28 if desired!=req.json():
29 raise Exception("Got request %s, but body is not matching" % req.url)
30 return False
31 return True
32
33class TestSyncRoutes(unittest.TestCase):
34
35 def setUp(self):
36
37 self.sys_path_save = sys.path
Matteo Scandolo769a5a42018-05-31 16:43:39 -070038
39 # Setting up the config module
40 from xosconfig import Config
41 config = os.path.join(test_path, "../test_config.yaml")
42 Config.clear()
43 Config.init(config, "synchronizer-config-schema.yaml")
44 # END Setting up the config module
45
Scott Baker81389db2019-02-04 15:13:38 -080046 from xossynchronizer.mock_modelaccessor_build import mock_modelaccessor_config
47 mock_modelaccessor_config(test_path, [("vrouter", "vrouter.xproto")])
48
49 import xossynchronizer.modelaccessor
50 import mock_modelaccessor
51 reload(mock_modelaccessor) # in case nose2 loaded it in a previous test
52 reload(xossynchronizer.modelaccessor) # in case nose2 loaded it in a previous test
Matteo Scandolo769a5a42018-05-31 16:43:39 -070053
54 from sync_routes import SyncRoutes, model_accessor
55
Scott Baker81389db2019-02-04 15:13:38 -080056 self.model_accessor = model_accessor
57
Matteo Scandolo769a5a42018-05-31 16:43:39 -070058 # import all class names to globals
59 for (k, v) in model_accessor.all_model_classes.items():
60 globals()[k] = v
61
Matteo Scandolo769a5a42018-05-31 16:43:39 -070062 self.sync_step = SyncRoutes
63 self.sync_step.log = Mock()
64
Matteo Scandolo769a5a42018-05-31 16:43:39 -070065 # mock onos-fabric
66 onos_fabric = Mock()
67 onos_fabric.name = "onos-fabric"
68 onos_fabric.rest_hostname = "onos-fabric"
69 onos_fabric.rest_port = "8181"
70 onos_fabric.rest_username = "onos"
71 onos_fabric.rest_password = "rocks"
72
73 onos_fabric_base = Mock()
74 onos_fabric_base.leaf_model = onos_fabric
75
76 self.fabric = Mock()
77 self.fabric.name = "fabric"
Matteo Scandolo181140e2018-08-30 15:17:09 -070078 self.fabric.provider_services = [onos_fabric_base]
Matteo Scandolo769a5a42018-05-31 16:43:39 -070079
80 self.vrouter = Mock()
81 self.vrouter.name = "vrouter"
Matteo Scandolo181140e2018-08-30 15:17:09 -070082 self.vrouter.provider_services = [self.fabric]
Matteo Scandolo769a5a42018-05-31 16:43:39 -070083
84 # create a mock VRouterStaticRoute instance
85 self.o = Mock()
86 self.o.id = 1
87 self.o.vrouter.owner = self.vrouter
88 self.o.tologdict.return_value = {}
89
Matteo Scandolo769a5a42018-05-31 16:43:39 -070090 def tearDown(self):
91 self.o = None
92 sys.path = self.sys_path_save
93
94 @requests_mock.Mocker()
Luca Prete9fae28c2018-11-01 10:59:52 -070095 def test_sync_route_ipv4(self, m):
Matteo Scandolo769a5a42018-05-31 16:43:39 -070096
Matteo Scandolo769a5a42018-05-31 16:43:39 -070097 self.o.prefix = "0.0.0.0/0"
Luca Prete9fae28c2018-11-01 10:59:52 -070098 self.o.next_hop = "192.168.0.254"
Matteo Scandolo769a5a42018-05-31 16:43:39 -070099
100 expected_conf = {
101 "prefix": self.o.prefix,
102 "nextHop": self.o.next_hop
103 }
104
105 m.post("http://onos-fabric:8181/onos/routeservice/routes",
106 status_code=204,
107 additional_matcher=functools.partial(match_json, expected_conf))
108
Scott Baker81389db2019-02-04 15:13:38 -0800109 self.sync_step(model_accessor = self.model_accessor).sync_record(self.o)
Matteo Scandolo769a5a42018-05-31 16:43:39 -0700110
111 self.assertTrue(m.called)
112
113 @requests_mock.Mocker()
Luca Prete9fae28c2018-11-01 10:59:52 -0700114 def test_sync_route_ipv6(self, m):
Matteo Scandolo769a5a42018-05-31 16:43:39 -0700115
Luca Prete9fae28c2018-11-01 10:59:52 -0700116 self.o.prefix = "::/0"
117 self.o.next_hop = "2001:db8:abcd:0012::0/64"
118
119 expected_conf = {
120 "prefix": self.o.prefix,
121 "nextHop": self.o.next_hop
122 }
123
124 m.post("http://onos-fabric:8181/onos/routeservice/routes",
125 status_code=204,
126 additional_matcher=functools.partial(match_json, expected_conf))
127
Scott Baker81389db2019-02-04 15:13:38 -0800128 self.sync_step(model_accessor = self.model_accessor).sync_record(self.o)
Luca Prete9fae28c2018-11-01 10:59:52 -0700129
130 self.assertTrue(m.called)
131
132 @requests_mock.Mocker()
133 def test_delete_route_ipv4(self, m):
134
Matteo Scandolo769a5a42018-05-31 16:43:39 -0700135 self.o.prefix = "0.0.0.0/0"
Luca Prete9fae28c2018-11-01 10:59:52 -0700136 self.o.next_hop = "192.168.0.254"
Matteo Scandolo769a5a42018-05-31 16:43:39 -0700137
138 expected_conf = {
139 "prefix": self.o.prefix,
140 "nextHop": self.o.next_hop
141 }
142
143 m.delete("http://onos-fabric:8181/onos/routeservice/routes",
144 status_code=204,
145 additional_matcher=functools.partial(match_json, expected_conf))
146
Scott Baker81389db2019-02-04 15:13:38 -0800147 self.sync_step(model_accessor = self.model_accessor).delete_record(self.o)
Matteo Scandolo769a5a42018-05-31 16:43:39 -0700148
Luca Prete9fae28c2018-11-01 10:59:52 -0700149 self.assertTrue(m.called)
150
151 @requests_mock.Mocker()
152 def test_delete_route_ipv6(self, m):
153
154 self.o.prefix = "::/0"
155 self.o.next_hop = "2001:db8:abcd:0012::0/64"
156
157 expected_conf = {
158 "prefix": self.o.prefix,
159 "nextHop": self.o.next_hop
160 }
161
162 m.delete("http://onos-fabric:8181/onos/routeservice/routes",
163 status_code=204,
164 additional_matcher=functools.partial(match_json, expected_conf))
165
Scott Baker81389db2019-02-04 15:13:38 -0800166 self.sync_step(model_accessor = self.model_accessor).delete_record(self.o)
Luca Prete9fae28c2018-11-01 10:59:52 -0700167
168 self.assertTrue(m.called)