Merge from OSM SO master
[osm/SO.git] / rwlaunchpad / plugins / rwpkgmgr / test / utest_filesystem_proxy_dts.py
1 #!/usr/bin/env python3
2
3 #
4 # Copyright 2016 RIFT.IO Inc
5 #
6 # Licensed under the Apache License, Version 2.0 (the "License");
7 # you may not use this file except in compliance with the License.
8 # You may obtain a copy of the License at
9 #
10 # http://www.apache.org/licenses/LICENSE-2.0
11 #
12 # Unless required by applicable law or agreed to in writing, software
13 # distributed under the License is distributed on an "AS IS" BASIS,
14 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 # See the License for the specific language governing permissions and
16 # limitations under the License.
17 #
18
19 import asyncio
20 import argparse
21 import logging
22 import os
23 import shutil
24 import stat
25 import sys
26 import unittest
27 import uuid
28 import xmlrunner
29
30 import gi
31 gi.require_version('RwDts', '1.0')
32 gi.require_version('RwPkgMgmtYang', '1.0')
33 from gi.repository import (
34 RwDts as rwdts,
35 RwPkgMgmtYang,
36 )
37 from rift.tasklets.rwpkgmgr.proxy import filesystem
38
39 import rift.tasklets.rwpkgmgr.publisher as pkg_publisher
40 import rift.tasklets.rwpkgmgr.rpc as rpc
41 import rift.test.dts
42 from rift.mano.utils.project import ManoProject, DEFAULT_PROJECT
43
44 TEST_STRING = "foobar"
45
46
47 class MockPublisher(object):
48 def __init__(self, uid):
49 self.assert_uid = uid
50
51 @asyncio.coroutine
52 def register_downloader(self, *args):
53 return self.assert_uid
54
55
56 class MockProject(ManoProject):
57 def __init__(self, log, uid=None):
58 super().__init__(log, name=DEFAULT_PROJECT)
59 self.job_handler = MockPublisher(uid)
60
61
62 class MockTasklet:
63 def __init__(self, log, uid=None):
64 self.log = log
65 self.projects = {}
66 project = MockProject(self.log,
67 uid=uid)
68 project.publisher = None
69 self.projects[project.name] = project
70
71
72 class TestCase(rift.test.dts.AbstractDTSTest):
73 @classmethod
74 def configure_schema(cls):
75 return RwPkgMgmtYang.get_schema()
76
77 @classmethod
78 def configure_timeout(cls):
79 return 240
80
81 def configure_test(self, loop, test_id):
82 self.log.debug("STARTING - %s", test_id)
83 self.tinfo = self.new_tinfo(str(test_id))
84 self.dts = rift.tasklets.DTS(self.tinfo, self.schema, self.loop)
85
86 def tearDown(self):
87 super().tearDown()
88
89 def create_mock_package(self):
90 uid = str(uuid.uuid4())
91 path = os.path.join(
92 os.getenv('RIFT_ARTIFACTS'),
93 "launchpad/packages/vnfd",
94 uid)
95
96 package_path = os.path.join(path, "pong_vnfd")
97
98 os.makedirs(package_path)
99 open(os.path.join(path, "pong_vnfd.xml"), "wb").close()
100 open(os.path.join(path, "logo.png"), "wb").close()
101
102 return uid, path
103
104 @rift.test.dts.async_test
105 def test_endpoint_discovery(self):
106 """
107 Verifies the following:
108 The endpoint RPC returns a URL
109 """
110 proxy = filesystem.FileSystemProxy(self.loop, self.log)
111 endpoint = rpc.EndpointDiscoveryRpcHandler(self.log, self.dts, self.loop, proxy)
112 yield from endpoint.register()
113
114 ip = RwPkgMgmtYang.YangInput_RwPkgMgmt_GetPackageEndpoint.from_dict({
115 "package_type": "VNFD",
116 "package_id": "BLAHID",
117 "project_name": DEFAULT_PROJECT})
118
119 rpc_out = yield from self.dts.query_rpc(
120 "I,/get-package-endpoint",
121 rwdts.XactFlag.TRACE,
122 ip)
123
124 for itr in rpc_out:
125 result = yield from itr
126 assert result.result.endpoint == 'https://127.0.0.1:4567/api/package/vnfd/BLAHID'
127
128 @rift.test.dts.async_test
129 def test_schema_rpc(self):
130 """
131 Verifies the following:
132 The schema RPC return the schema structure
133 """
134 proxy = filesystem.FileSystemProxy(self.loop, self.log)
135 endpoint = rpc.SchemaRpcHandler(self.log, self.dts, self.loop, proxy)
136 yield from endpoint.register()
137
138 ip = RwPkgMgmtYang.YangInput_RwPkgMgmt_GetPackageSchema.from_dict({
139 "package_type": "VNFD",
140 "project_name": DEFAULT_PROJECT})
141
142 rpc_out = yield from self.dts.query_rpc(
143 "I,/get-package-schema",
144 rwdts.XactFlag.TRACE,
145 ip)
146
147 for itr in rpc_out:
148 result = yield from itr
149 assert "charms" in result.result.schema
150
151 @rift.test.dts.async_test
152 def test_file_proxy_rpc(self):
153 """
154 1. The file RPC returns a valid UUID thro' DTS
155 """
156 assert_uid = str(uuid.uuid4())
157
158 uid, path = self.create_mock_package()
159
160 proxy = filesystem.FileSystemProxy(self.loop, self.log)
161 endpoint = rpc.PackageOperationsRpcHandler(
162 self.log,
163 self.dts,
164 self.loop,
165 proxy,
166 MockTasklet(self.log, uid=assert_uid))
167 yield from endpoint.register()
168
169 ip = RwPkgMgmtYang.YangInput_RwPkgMgmt_PackageFileAdd.from_dict({
170 "package_type": "VNFD",
171 "package_id": uid,
172 "external_url": "https://raw.githubusercontent.com/RIFTIO/RIFT.ware/master/rift-shell",
173 "package_path": "script/rift-shell",
174 "project_name": DEFAULT_PROJECT})
175
176 rpc_out = yield from self.dts.query_rpc(
177 "I,/rw-pkg-mgmt:package-file-add",
178 rwdts.XactFlag.TRACE,
179 ip)
180
181 for itr in rpc_out:
182 result = yield from itr
183 assert result.result.task_id == assert_uid
184
185 shutil.rmtree(path)
186
187 @rift.test.dts.async_test
188 def test_file_add_workflow(self):
189 """
190 Integration test:
191 1. Verify the end to end flow of package ADD (NO MOCKS)
192 """
193 uid, path = self.create_mock_package()
194
195 proxy = filesystem.FileSystemProxy(self.loop, self.log)
196 tasklet = MockTasklet(self.log, uid=uid)
197 project = tasklet.projects[DEFAULT_PROJECT]
198 publisher = pkg_publisher.DownloadStatusPublisher(self.log, self.dts, self.loop, project)
199 project.job_handler = publisher
200 endpoint = rpc.PackageOperationsRpcHandler(
201 self.log,
202 self.dts,
203 self.loop,
204 proxy,
205 tasklet)
206
207 yield from publisher.register()
208 yield from endpoint.register()
209
210 ip = RwPkgMgmtYang.YangInput_RwPkgMgmt_PackageFileAdd.from_dict({
211 "package_type": "VNFD",
212 "package_id": uid,
213 "external_url": "https://raw.githubusercontent.com/RIFTIO/RIFT.ware/master/rift-shell",
214 "package_path": "icons/rift-shell",
215 "project_name": DEFAULT_PROJECT})
216
217 rpc_out = yield from self.dts.query_rpc(
218 "I,/rw-pkg-mgmt:package-file-add",
219 rwdts.XactFlag.TRACE,
220 ip)
221
222 yield from asyncio.sleep(5, loop=self.loop)
223 filepath = os.path.join(path, ip.package_path)
224 self.log.debug("Filepath: {}".format(filepath))
225 assert os.path.isfile(filepath)
226 mode = oct(os.stat(filepath)[stat.ST_MODE])
227 assert str(mode) == "0o100664"
228
229 shutil.rmtree(path)
230
231
232 @rift.test.dts.async_test
233 def test_file_delete_workflow(self):
234 """
235 Integration test:
236 1. Verify the end to end flow of package ADD (NO MOCKS)
237 """
238 uid, path = self.create_mock_package()
239
240 proxy = filesystem.FileSystemProxy(self.loop, self.log)
241 endpoint = rpc.PackageDeleteOperationsRpcHandler(
242 self.log,
243 self.dts,
244 self.loop,
245 proxy)
246
247 yield from endpoint.register()
248
249 ip = RwPkgMgmtYang.YangInput_RwPkgMgmt_PackageFileDelete.from_dict({
250 "package_type": "VNFD",
251 "package_id": uid,
252 "package_path": "logo.png",
253 "project_name": DEFAULT_PROJECT})
254
255 assert os.path.isfile(os.path.join(path, ip.package_path))
256
257 rpc_out = yield from self.dts.query_rpc(
258 "I,/rw-pkg-mgmt:package-file-delete",
259 rwdts.XactFlag.TRACE,
260 ip)
261
262 yield from asyncio.sleep(5, loop=self.loop)
263 assert not os.path.isfile(os.path.join(path, ip.package_path))
264
265 shutil.rmtree(path)
266
267 def main():
268 runner = xmlrunner.XMLTestRunner(output=os.environ["RIFT_MODULE_TEST"])
269
270 parser = argparse.ArgumentParser()
271 parser.add_argument('-v', '--verbose', action='store_true')
272 parser.add_argument('-n', '--no-runner', action='store_true')
273 args, unittest_args = parser.parse_known_args()
274 if args.no_runner:
275 runner = None
276
277 logging.basicConfig(format='TEST %(message)s')
278 logging.getLogger().setLevel(logging.DEBUG)
279
280
281 unittest.main(testRunner=runner, argv=[sys.argv[0]] + unittest_args)
282
283 if __name__ == '__main__':
284 main()