diff options
-rw-r--r-- | api/actions/result.py | 55 | ||||
-rw-r--r-- | api/actions/test.py | 8 | ||||
-rw-r--r-- | api/conf.py | 8 | ||||
-rw-r--r-- | api/server.py | 8 | ||||
-rw-r--r-- | api/urls.py | 11 | ||||
-rw-r--r-- | api/utils/common.py | 31 | ||||
-rw-r--r-- | api/utils/daemonthread.py | 8 | ||||
-rw-r--r-- | api/utils/influx.py | 18 | ||||
-rw-r--r-- | api/views.py | 35 | ||||
-rw-r--r-- | docs/release/release-notes.rst | 44 | ||||
-rw-r--r-- | tests/unit/api/actions/test_result.py | 29 | ||||
-rw-r--r-- | tests/unit/api/actions/test_test.py | 8 | ||||
-rw-r--r-- | tests/unit/api/test_views.py | 23 | ||||
-rw-r--r-- | tests/unit/api/utils/test_common.py | 38 | ||||
-rw-r--r-- | tests/unit/api/utils/test_daemonthread.py | 8 | ||||
-rw-r--r-- | tests/unit/api/utils/test_influx.py | 22 |
16 files changed, 328 insertions, 26 deletions
diff --git a/api/actions/result.py b/api/actions/result.py new file mode 100644 index 000000000..9f606d2cb --- /dev/null +++ b/api/actions/result.py @@ -0,0 +1,55 @@ +############################################################################## +# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others. +# +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## +import logging + +from api.utils import influx as influx_utils +from api.utils import common as common_utils +from api import conf + +logger = logging.getLogger(__name__) + + +def getResult(args): + try: + measurement = args['measurement'] + task_id = args['task_id'] + except KeyError: + message = 'measurement and task_id must be needed' + return common_utils.error_handler(message) + + measurement = conf.TEST_CASE_PRE + measurement + + query_sql = "select * from $table where task_id='$task_id'" + param = {'table': 'tasklist', 'task_id': task_id} + data = common_utils.translate_to_str(influx_utils.query(query_sql, param)) + + def _unfinished(): + return common_utils.result_handler(0, []) + + def _finished(): + param = {'table': measurement, 'task_id': task_id} + data = common_utils.translate_to_str(influx_utils.query(query_sql, + param)) + + return common_utils.result_handler(1, data) + + def _error(): + return common_utils.result_handler(2, data[0]['error']) + + try: + status = data[0]['status'] + + switcher = { + 0: _unfinished, + 1: _finished, + 2: _error + } + return switcher.get(status, lambda: 'nothing')() + except IndexError: + return common_utils.error_handler('no such task') diff --git a/api/actions/test.py b/api/actions/test.py index 0de70bb71..b1dc212c2 100644 --- a/api/actions/test.py +++ b/api/actions/test.py @@ -1,3 +1,11 @@ +############################################################################## +# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others. +# +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## import uuid import json import os diff --git a/api/conf.py b/api/conf.py index b5553f452..e1da4aba0 100644 --- a/api/conf.py +++ b/api/conf.py @@ -1,3 +1,11 @@ +############################################################################## +# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others. +# +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## from pyroute2 import IPDB diff --git a/api/server.py b/api/server.py index d0e4d30a2..1cbe1725d 100644 --- a/api/server.py +++ b/api/server.py @@ -1,3 +1,11 @@ +############################################################################## +# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others. +# +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## import logging from flask import Flask diff --git a/api/urls.py b/api/urls.py index 9fa0bc935..2a9e72a76 100644 --- a/api/urls.py +++ b/api/urls.py @@ -1,7 +1,16 @@ +############################################################################## +# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others. +# +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## from api import views from api.utils.common import Url urlpatterns = [ - Url('/yardstick/test/action', views.Test, 'test') + Url('/yardstick/test/action', views.Test, 'test'), + Url('/yardstick/result/action', views.Result, 'result') ] diff --git a/api/utils/common.py b/api/utils/common.py index 9d7998abd..04a6fe0d6 100644 --- a/api/utils/common.py +++ b/api/utils/common.py @@ -1,8 +1,20 @@ +############################################################################## +# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others. +# +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## import collections +import logging +import json from api.utils.daemonthread import DaemonThread from yardstick.cmd.cli import YardstickCLI +logger = logging.getLogger(__name__) + def translate_to_str(object): if isinstance(object, collections.Mapping): @@ -20,7 +32,7 @@ def get_command_list(command_list, opts, args): command_list.extend(('--{}'.format(k) for k in opts if 'task-args' != k)) - task_args = opts.get('task_args', '') + task_args = opts.get('task-args', '') if task_args: command_list.extend(['--task-args', task_args]) @@ -32,6 +44,23 @@ def exec_command_task(command_list, task_id): # pragma: no cover daemonthread.start() +def error_handler(message): + logger.debug(message) + result = { + 'status': 'error', + 'message': message + } + return json.dumps(result) + + +def result_handler(status, data): + result = { + 'status': status, + 'result': data + } + return json.dumps(result) + + class Url(object): def __init__(self, url, resource, endpoint): diff --git a/api/utils/daemonthread.py b/api/utils/daemonthread.py index 77a0f6ab7..47c0b9108 100644 --- a/api/utils/daemonthread.py +++ b/api/utils/daemonthread.py @@ -1,3 +1,11 @@ +############################################################################## +# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others. +# +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## import threading import os import datetime diff --git a/api/utils/influx.py b/api/utils/influx.py index 1d56c95fd..9366ed3e9 100644 --- a/api/utils/influx.py +++ b/api/utils/influx.py @@ -1,3 +1,11 @@ +############################################################################## +# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others. +# +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## import logging from urlparse import urlsplit @@ -53,3 +61,13 @@ def write_data_tasklist(task_id, timestamp, status, error=''): field = {'status': status, 'error': error} tags = {'task_id': task_id} _write_data('tasklist', field, timestamp, tags) + + +def query(query_sql): + try: + client = get_data_db_client() + logger.debug('Start to query: %s', query_sql) + return list(client.query(query_sql).get_points()) + except RuntimeError: + logger.error('dispatcher is not influxdb') + raise diff --git a/api/views.py b/api/views.py index 883091222..e78389f5a 100644 --- a/api/views.py +++ b/api/views.py @@ -1,4 +1,11 @@ -import json +############################################################################## +# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others. +# +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## import logging from flask import request @@ -6,7 +13,7 @@ from flask_restful import Resource from api.utils import common as common_utils from api.actions import test as test_action -from api import conf +from api.actions import result as result_action logger = logging.getLogger(__name__) @@ -17,13 +24,19 @@ class Test(Resource): args = common_utils.translate_to_str(request.json.get('args', {})) logger.debug('Input args is: action: %s, args: %s', action, args) - if action not in conf.TEST_ACTION: - logger.error('Wrong action') - result = { - 'status': 'error', - 'message': 'wrong action' - } - return json.dumps(result) + try: + return getattr(test_action, action)(args) + except AttributeError: + return common_utils.error_handler('Wrong action') - method = getattr(test_action, action) - return method(args) + +class Result(Resource): + def get(self): + args = common_utils.translate_to_str(request.args) + action = args.get('action', '') + logger.debug('Input args is: action: %s, args: %s', action, args) + + try: + return getattr(result_action, action)(args) + except AttributeError: + return common_utils.error_handler('Wrong action') diff --git a/docs/release/release-notes.rst b/docs/release/release-notes.rst index 72f263c2d..8df0776df 100644 --- a/docs/release/release-notes.rst +++ b/docs/release/release-notes.rst @@ -38,7 +38,10 @@ Version History | *Date* | *Version* | *Comment* | | | | | +----------------+--------------------+---------------------------------+ -| Oct 27nd, 2016 | 2.0 | Yardstick for Colorado release | +| Dec 5th, 2016 | 3.0 | Yardstick for Colorado release | +| | | | ++----------------+--------------------+---------------------------------+ +| Oct 27th, 2016 | 2.0 | Yardstick for Colorado release | | | | | +----------------+--------------------+---------------------------------+ | Aug 22nd, 2016 | 1.0 | Yardstick for Colorado release | @@ -132,19 +135,19 @@ Release Data | **Project** | Yardstick | | | | +--------------------------------------+--------------------------------------+ -| **Repo/tag** | yardstick/colorado.2.0 | +| **Repo/tag** | yardstick/colorado.3.0 | | | | +--------------------------------------+--------------------------------------+ -| **Yardstick Docker image tag** | colorado.2.0 | +| **Yardstick Docker image tag** | colorado.3.0 | | | | +--------------------------------------+--------------------------------------+ | **Release designation** | Colorado | | | | +--------------------------------------+--------------------------------------+ -| **Release date** | October 27 2016 | +| **Release date** | December 5th, 2016 | | | | +--------------------------------------+--------------------------------------+ -| **Purpose of the delivery** | OPNFV Colorado release 2.0 | +| **Purpose of the delivery** | OPNFV Colorado release 3.0 | | | | +--------------------------------------+--------------------------------------+ @@ -163,22 +166,22 @@ Documents Software Deliverables --------------------- -**Yardstick framework source code <colorado.2.0>** +**Yardstick framework source code <colorado.3.0>** +--------------------------------------+--------------------------------------+ | **Project** | Yardstick | | | | +--------------------------------------+--------------------------------------+ -| **Repo/tag** | yardstick/colorado.2.0 | +| **Repo/tag** | yardstick/colorado.3.0 | | | | +--------------------------------------+--------------------------------------+ -| **Yardstick Docker image tag** | colorado.2.0 | +| **Yardstick Docker image tag** | colorado.3.0 | | | | +--------------------------------------+--------------------------------------+ | **Release designation** | Colorado | | | | +--------------------------------------+--------------------------------------+ -| **Release date** | October 27th, 2016 | +| **Release date** | December 5th, 2016 | | | | +--------------------------------------+--------------------------------------+ | **Purpose of the delivery** | OPNFV Colorado release | @@ -502,7 +505,7 @@ Feature additions Scenario Matrix =============== -For Colorado 2.0, Yardstick was tested on the following scenarios: +For Colorado 3.0, Yardstick was tested on the following scenarios: +-------------------------+---------+---------+---------+---------+ | Scenario | Apex | Compass | Fuel | Joid | @@ -585,6 +588,21 @@ Known Issues/Faults Corrected Faults ---------------- +Colorado.3.0: + ++----------------------------+------------------------------------------------+ +| **JIRA REFERENCE** | **SLOGAN** | +| | | ++----------------------------+------------------------------------------------+ +| JIRA: YARDSTICK-239 | Define process for working with Yardstick | +| | Grafana dashboard. | +| | | ++----------------------------+------------------------------------------------+ +| JIRA: YARDSTICK-373 | Add os-odl_l2-fdio-ha scenario support. | +| | | ++----------------------------+------------------------------------------------+ + + Colorado.2.0: +----------------------------+------------------------------------------------+ @@ -621,7 +639,7 @@ Colorado.2.0: +----------------------------+------------------------------------------------+ -Colorado 2.0 known restrictions/issues +Colorado 3.0 known restrictions/issues ================================== +-----------+-----------+----------------------------------------------+ | Installer | Scenario | Issue | @@ -656,6 +674,8 @@ Useful links - Yardstick IRC chanel: #opnfv-yardstick +.. _`YARDSTICK-239` : https://jira.opnfv.org/browse/YARDSTICK-239 + .. _`YARDSTICK-325` : https://jira.opnfv.org/browse/YARDSTICK-325 .. _`YARDSTICK-358` : https://jira.opnfv.org/browse/YARDSTICK-358 @@ -669,3 +689,5 @@ Useful links .. _`YARDSTICK-371` : https://jira.opnfv.org/browse/YARDSTICK-371 .. _`YARDSTICK-372` : https://jira.opnfv.org/browse/YARDSTICK-372 + +.. _`YARDSTICK-373` : https://jira.opnfv.org/browse/YARDSTICK-373 diff --git a/tests/unit/api/actions/test_result.py b/tests/unit/api/actions/test_result.py new file mode 100644 index 000000000..168631905 --- /dev/null +++ b/tests/unit/api/actions/test_result.py @@ -0,0 +1,29 @@ +############################################################################## +# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others. +# +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## +import unittest +import json + +from api.actions import result + + +class GetResultTestCase(unittest.TestCase): + + def test_getResult_with_no_taskid_arg(self): + args = {} + output = json.loads(result.getResult(args)) + + self.assertEqual('error', output['status']) + + +def main(): + unittest.main() + + +if __name__ == '__main__': + main() diff --git a/tests/unit/api/actions/test_test.py b/tests/unit/api/actions/test_test.py index 158062ff4..7ebe9fc24 100644 --- a/tests/unit/api/actions/test_test.py +++ b/tests/unit/api/actions/test_test.py @@ -1,3 +1,11 @@ +############################################################################## +# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others. +# +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## import unittest import json diff --git a/tests/unit/api/test_views.py b/tests/unit/api/test_views.py index 650ed569c..e57ec08a4 100644 --- a/tests/unit/api/test_views.py +++ b/tests/unit/api/test_views.py @@ -1,21 +1,42 @@ +############################################################################## +# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others. +# +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## import unittest import mock import json from api.views import Test +from api.views import Result class TestTestCase(unittest.TestCase): @mock.patch('api.views.request') def test_post(self, mock_request): - mock_request.json.get.side_effect = ['runTestSuite', {}] + mock_request.json.get.side_effect = ['hello', {}] result = json.loads(Test().post()) self.assertEqual('error', result['status']) +class ResultTestCase(unittest.TestCase): + + @mock.patch('api.views.request') + def test_get(self, mock_request): + mock_request.args.get.return_value = 'hello' + + print Result().get() + result = json.loads(Result().get()) + + self.assertEqual('error', result['status']) + + def main(): unittest.main() diff --git a/tests/unit/api/utils/test_common.py b/tests/unit/api/utils/test_common.py index 5d858a32c..9e050c714 100644 --- a/tests/unit/api/utils/test_common.py +++ b/tests/unit/api/utils/test_common.py @@ -1,4 +1,13 @@ +############################################################################## +# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others. +# +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## import unittest +import json from api.utils import common @@ -49,6 +58,35 @@ class GetCommandListTestCase(unittest.TestCase): self.assertEqual(result_list, output_list) +class ErrorHandlerTestCase(unittest.TestCase): + + def test_error_handler(self): + message = 'hello world' + output_dict = json.loads(common.error_handler(message)) + + result = { + 'status': 'error', + 'message': message + } + + self.assertEqual(result, output_dict) + + +class ResultHandlerTestCase(unittest.TestCase): + + def test_result_handler(self): + status = 1 + data = ['hello world'] + output_dict = json.loads(common.result_handler(status, data)) + + result = { + 'status': status, + 'result': data + } + + self.assertEqual(result, output_dict) + + def main(): unittest.main() diff --git a/tests/unit/api/utils/test_daemonthread.py b/tests/unit/api/utils/test_daemonthread.py index 918f1f506..f07f0fede 100644 --- a/tests/unit/api/utils/test_daemonthread.py +++ b/tests/unit/api/utils/test_daemonthread.py @@ -1,3 +1,11 @@ +############################################################################## +# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others. +# +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## import unittest import mock diff --git a/tests/unit/api/utils/test_influx.py b/tests/unit/api/utils/test_influx.py index 5f1e2c36f..0852da2dd 100644 --- a/tests/unit/api/utils/test_influx.py +++ b/tests/unit/api/utils/test_influx.py @@ -1,3 +1,11 @@ +############################################################################## +# Copyright (c) 2016 Huawei Technologies Co.,Ltd and others. +# +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## import unittest import mock import uuid @@ -13,7 +21,7 @@ class GetDataDbClientTestCase(unittest.TestCase): mock_parser.ConfigParser().get.return_value = 'file' try: influx.get_data_db_client() - except Exception, e: + except Exception as e: self.assertIsInstance(e, RuntimeError) @@ -54,6 +62,18 @@ class WriteDataTasklistTestCase(unittest.TestCase): mock_write_data.assert_called_with('tasklist', field, timestamp, tags) +class QueryTestCase(unittest.TestCase): + + @mock.patch('api.utils.influx.ConfigParser') + def test_query_dispatcher_not_influxdb(self, mock_parser): + mock_parser.ConfigParser().get.return_value = 'file' + try: + sql = 'select * form tasklist' + influx.query(sql) + except Exception as e: + self.assertIsInstance(e, RuntimeError) + + def main(): unittest.main() |