Reorganize scenario testing.

* This moves all scenarios in scenarios directory.
* factorized code between two scenarios in utils.py
* remove unused tempest-heat-plugin

Change-Id: Ifd2e1ad1453484e6af4ae09dedb6e96d96f42b52
This commit is contained in:
Mehdi Abaakouk 2018-09-03 11:50:49 +02:00
parent b35146e1a4
commit b64d2b073f
18 changed files with 239 additions and 298 deletions

View File

@ -10,7 +10,6 @@
- openstack/ceilometer
- openstack/panko
- openstack/telemetry-tempest-plugin
- openstack/heat-tempest-plugin
- openstack/heat
# following are required when DEVSTACK_GATE_HEAT, which this
# job turns on

View File

@ -43,8 +43,6 @@ function generate_telemetry_report(){
openstack stack show integration_test
echo "* Alarm list:"
aodh alarm list
echo "* Event list:"
ceilometer event-list -q 'event_type=string::compute.instance.create.end'
echo "* Nova instance list:"
openstack server list --all-projects
@ -64,6 +62,16 @@ function generate_telemetry_report(){
echo "* Unprocessed measures:"
for key in $(redis-cli --scan --pattern 'incoming*'); do echo -n "$key length = " && redis-cli llen $key; done
echo "* locale:"
locale
echo
echo "* tempest locale:"
sudo -H -u tempest locale
echo
echo "* tempest tox locale:"
sudo -H -u tempest tox -evenv-tempest -- locale
echo
set -e
set -x
}
@ -83,14 +91,14 @@ function generate_reports_and_maybe_exit() {
sudo chown -R tempest:stack $BASE/new/tempest
sudo chown -R tempest:stack $BASE/data/tempest
cd $BASE/new/tempest
sudo -H -u tempest tox -evenv-tempest -- pip install /opt/stack/new/heat-tempest-plugin /opt/stack/new/telemetry-tempest-plugin
sudo -H -u tempest tox -evenv-tempest -- pip install /opt/stack/new/telemetry-tempest-plugin
echo "Checking installed Tempest plugins:"
sudo -H -u tempest tox -evenv-tempest -- tempest list-plugins
set +e
sudo -H -u tempest OS_TEST_TIMEOUT=$TEMPEST_OS_TEST_TIMEOUT tox -evenv-tempest -- tempest run -r telemetry_tempest_plugin --concurrency=$TEMPEST_CONCURRENCY
EXIT_CODE=$?
set -e
export_subunit_data "all-plugin"
export_subunit_data "venv-tempest"
generate_reports_and_maybe_exit $EXIT_CODE
exit $EXIT_CODE

View File

@ -35,7 +35,7 @@
export DEVSTACK_GATE_EXERCISES=0
export DEVSTACK_GATE_INSTALL_TESTONLY=1
export DEVSTACK_GATE_TEMPEST_NOTESTS=1
export PROJECTS="openstack/ceilometer openstack/aodh openstack/panko openstack/telemetry-tempest-plugin openstack/heat openstack/heat-tempest-plugin"
export PROJECTS="openstack/ceilometer openstack/aodh openstack/panko openstack/telemetry-tempest-plugin openstack/heat"
export DEVSTACK_LOCAL_CONFIG+=$'\n'"enable_plugin panko git://git.openstack.org/openstack/panko"
export DEVSTACK_LOCAL_CONFIG+=$'\n'"enable_plugin ceilometer git://git.openstack.org/openstack/ceilometer"
export DEVSTACK_LOCAL_CONFIG+=$'\n'"enable_plugin aodh git://git.openstack.org/openstack/aodh"

View File

@ -1,111 +0,0 @@
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
from __future__ import absolute_import
import os
import unittest
from gabbi import runner
from gabbi import suitemaker
from gabbi import utils
import six.moves.urllib.parse as urlparse
from tempest import config
import tempest.test
CONF = config.CONF
TEST_DIR = os.path.join(os.path.dirname(__file__), '..',
'functional_live', 'gabbits')
class GnocchiGabbiTest(tempest.test.BaseTestCase):
credentials = ['admin']
TIMEOUT_SCALING_FACTOR = 5
@classmethod
def skip_checks(cls):
super(GnocchiGabbiTest, cls).skip_checks()
if not CONF.service_available.gnocchi:
raise cls.skipException("Gnocchi support is required")
def _do_test(self, filename):
token = self.os_admin.auth_provider.get_token()
url = self.os_admin.auth_provider.base_url(
{'service': CONF.metric.catalog_type,
'endpoint_type': CONF.metric.endpoint_type,
'region': CONF.identity.region})
parsed_url = urlparse.urlsplit(url)
prefix = parsed_url.path.rstrip('/') # turn it into a prefix
if parsed_url.scheme == 'https':
port = 443
require_ssl = True
else:
port = 80
require_ssl = False
host = parsed_url.hostname
if parsed_url.port:
port = parsed_url.port
os.environ["GNOCCHI_SERVICE_TOKEN"] = token
os.environ["GNOCCHI_AUTHORIZATION"] = "not used"
with open(os.path.join(TEST_DIR, filename)) as f:
suite_dict = utils.load_yaml(f)
suite_dict.setdefault('defaults', {})['ssl'] = require_ssl
test_suite = suitemaker.test_suite_from_dict(
loader=unittest.defaultTestLoader,
test_base_name="gabbi",
suite_dict=suite_dict,
test_directory=TEST_DIR,
host=host, port=port,
fixture_module=None,
intercept=None,
prefix=prefix,
handlers=runner.initialize_handlers([]),
test_loader_name="tempest")
# NOTE(sileht): We hide stdout/stderr and reraise the failure
# manually, tempest will print it itself.
with open(os.devnull, 'w') as stream:
result = unittest.TextTestRunner(
stream=stream, verbosity=0, failfast=True,
).run(test_suite)
if not result.wasSuccessful():
failures = (result.errors + result.failures +
result.unexpectedSuccesses)
if failures:
test, bt = failures[0]
name = test.test_data.get('name', test.id())
msg = 'From test "%s" :\n%s' % (name, bt)
self.fail(msg)
self.assertTrue(result.wasSuccessful())
def test_maker(name, filename):
def test(self):
self._do_test(filename)
test.__name__ = name
return test
# Create one scenario per yaml file
for filename in os.listdir(TEST_DIR):
if not filename.endswith('.yaml'):
continue
name = "test_%s" % filename[:-5].lower().replace("-", "_")
setattr(GnocchiGabbiTest, name,
test_maker(name, filename))

View File

@ -1,40 +0,0 @@
#
# Copyright 2015 Red Hat. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
"""A test module to exercise the Gnocchi API with gabbi."""
import os
from gabbi import driver
TESTS_DIR = 'gabbits-live'
def load_tests(loader, tests, pattern):
"""Provide a TestSuite to the discovery process."""
NEEDED_ENV = ["AODH_SERVICE_URL", "GNOCCHI_SERVICE_URL",
"HEAT_SERVICE_URL", "NOVA_SERVICE_URL", "PANKO_SERVICE_URL",
"GLANCE_IMAGE_NAME", "ADMIN_TOKEN"]
for env_variable in NEEDED_ENV:
if not os.getenv(env_variable):
if os.getenv("GABBI_LIVE_FAIL_IF_NO_TEST"):
raise RuntimeError('%s is not set' % env_variable)
else:
return
test_dir = os.path.join(os.path.dirname(__file__), TESTS_DIR)
return driver.build_tests(test_dir, loader, host="localhost", port=8041)

View File

@ -10,12 +10,12 @@ defaults:
tests:
- name: check /
GET: /
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/
# Fail to create archive policy
- name: wrong archive policy content type
desc: attempt to create archive policy with invalid content-type
POST: /v1/archive_policy
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy
request_headers:
content-type: text/plain
status: 415
@ -24,14 +24,14 @@ tests:
- name: wrong method
desc: attempt to create archive policy with 'PUT' method
PUT: /v1/archive_policy
PUT: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy
request_headers:
content-type: application/json
status: 405
- name: invalid authZ
desc: x-auth-token is invalid
POST: /v1/archive_policy
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy
request_headers:
content-type: application/json
x-auth-token: 'hello'
@ -44,7 +44,7 @@ tests:
- name: bad archive policy body
desc: archive policy contains invalid key 'cowsay'
POST: /v1/archive_policy
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy
request_headers:
content-type: application/json
data:
@ -55,7 +55,7 @@ tests:
- name: missing definition
desc: archive policy is missing 'definition' keyword
POST: /v1/archive_policy
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy
request_headers:
content-type: application/json
data:
@ -66,7 +66,7 @@ tests:
- name: empty definition
desc: empty definition for archive policy
POST: /v1/archive_policy
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy
request_headers:
content-type: application/json
data:
@ -78,7 +78,7 @@ tests:
- name: wrong value definition
desc: invalid type of 'definition' key
POST: /v1/archive_policy
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy
request_headers:
content-type: application/json
data:
@ -90,7 +90,7 @@ tests:
- name: useless definition
desc: invalid archive policy definition
POST: /v1/archive_policy
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy
request_headers:
content-type: application/json
data:
@ -107,7 +107,7 @@ tests:
- name: create archive policy
desc: create archve policy 'gabbilive' for live tests
POST: /v1/archive_policy
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy
request_headers:
content-type: application/json
data:
@ -134,7 +134,7 @@ tests:
desc: retrieve archive policy 'gabbilive' and asster its values
GET: $LOCATION
response_headers:
content-type: /application/json/
content-type: $ENVIRON['GNOCCHI_SERVICE_URL']/application/json/
response_json_paths:
$.name: gabbilive
$.back_window: 0
@ -152,7 +152,7 @@ tests:
- name: get wrong accept
desc: invalid 'accept' header
GET: /v1/archive_policy/medium
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy/medium
request_headers:
accept: text/plain
status: 406
@ -161,19 +161,19 @@ tests:
- name: post single archive
desc: unexpected 'POST' request to archive policy
POST: /v1/archive_policy/gabbilive
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy/gabbilive
status: 405
- name: put single archive
desc: unexpected 'PUT' request to archive policy
PUT: /v1/archive_policy/gabbilive
PUT: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy/gabbilive
status: 405
# Duplicated archive policy names ain't allowed
- name: create duplicate archive policy
desc: create archve policy 'gabbilive' for live tests
POST: /v1/archive_policy
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy
request_headers:
content-type: application/json
data:
@ -188,7 +188,7 @@ tests:
# Create a unicode named policy
- name: post unicode policy name
POST: /v1/archive_policy
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy
request_headers:
content-type: application/json
data:
@ -208,21 +208,21 @@ tests:
name: ✔éñ☃
- name: delete unicode archive policy
DELETE: /v1/archive_policy/%E2%9C%94%C3%A9%C3%B1%E2%98%83
DELETE: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy/%E2%9C%94%C3%A9%C3%B1%E2%98%83
status: 204
# It really is gone
- name: confirm delete
desc: assert deleted unicode policy is not available
GET: /v1/archive_policy/%E2%9C%94%C3%A9%C3%B1%E2%98%83
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy/%E2%9C%94%C3%A9%C3%B1%E2%98%83
status: 404
# Fail to delete one that does not exist
- name: delete missing archive
desc: delete non-existent archive policy
DELETE: /v1/archive_policy/grandiose
DELETE: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy/grandiose
status: 404
response_strings:
- Archive policy grandiose does not exist
@ -230,7 +230,7 @@ tests:
# Attempt to create illogical policies
- name: create illogical policy
POST: /v1/archive_policy
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy
request_headers:
content-type: application/json
data:
@ -244,7 +244,7 @@ tests:
- timespan ≠ granularity × points
- name: create identical granularities policy
POST: /v1/archive_policy
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy
request_headers:
content-type: application/json
data:
@ -260,7 +260,7 @@ tests:
- name: policy invalid unit
desc: invalid unit for archive policy 'timespan' key
POST: /v1/archive_policy
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy
request_headers:
content-type: application/json
data:
@ -275,7 +275,7 @@ tests:
#
- name: create archive policy rule1
POST: /v1/archive_policy_rule
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy_rule
request_headers:
content-type: application/json
data:
@ -289,7 +289,7 @@ tests:
$.name: gabbilive_rule
- name: create invalid archive policy rule
POST: /v1/archive_policy_rule
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy_rule
request_headers:
content-type: application/json
data:
@ -298,7 +298,7 @@ tests:
status: 400
- name: missing auth archive policy rule
POST: /v1/archive_policy_rule
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy_rule
request_headers:
content-type: application/json
x-auth-token: 'hello'
@ -310,7 +310,7 @@ tests:
status: 401
- name: wrong archive policy rule content type
POST: /v1/archive_policy_rule
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy_rule
request_headers:
content-type: text/plain
status: 415
@ -318,7 +318,7 @@ tests:
- Unsupported Media Type
- name: bad archive policy rule body
POST: /v1/archive_policy_rule
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy_rule
request_headers:
content-type: application/json
data:
@ -330,7 +330,7 @@ tests:
# get an archive policy rules
- name: get all archive policy rules
GET: /v1/archive_policy_rule
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy_rule
status: 200
response_json_paths:
$[\name][0].name: "gabbilive_rule"
@ -338,12 +338,12 @@ tests:
$[\name][0].archive_policy_name: "gabbilive"
- name: get unknown archive policy rule
GET: /v1/archive_policy_rule/foo
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy_rule/foo
status: 404
- name: get archive policy rule
GET: /v1/archive_policy_rule/gabbilive_rule
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy_rule/gabbilive_rule
status: 200
response_json_paths:
$.metric_pattern: "live.*"
@ -352,7 +352,7 @@ tests:
- name: delete archive policy in use
desc: fails due to https://bugs.launchpad.net/gnocchi/+bug/1569781
DELETE: /v1/archive_policy/gabbilive
DELETE: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy/gabbilive
status: 400
#
@ -361,11 +361,11 @@ tests:
- name: get all metrics
GET: /v1/metric
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/metric
status: 200
- name: create metric with name and rule
POST: /v1/metric
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/metric
request_headers:
content-type: application/json
data:
@ -376,17 +376,17 @@ tests:
$.name: live.io.rate
- name: assert metric is present in listing
GET: /v1/metric?id=$HISTORY['create metric with name and rule'].$RESPONSE['$.id']
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/metric?id=$HISTORY['create metric with name and rule'].$RESPONSE['$.id']
response_json_paths:
$.`len`: 1
- name: assert metric is the only one with this policy
GET: /v1/metric?archive_policy_name=gabbilive
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/metric?archive_policy_name=gabbilive
response_json_paths:
$.`len`: 1
- name: delete metric
DELETE: /v1/metric/$HISTORY['create metric with name and rule'].$RESPONSE['$.id']
DELETE: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/metric/$HISTORY['create metric with name and rule'].$RESPONSE['$.id']
status: 204
- name: assert metric is expunged
@ -398,7 +398,7 @@ tests:
$.`len`: 0
- name: create metric with name and policy
POST: /v1/metric
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/metric
request_headers:
content-type: application/json
data:
@ -416,15 +416,15 @@ tests:
$.archive_policy.name: gabbilive
- name: delete the metric
DELETE: /v1/metric/$RESPONSE['$.id']
DELETE: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/metric/$RESPONSE['$.id']
status: 204
- name: ensure the metric is delete
GET: /v1/metric/$HISTORY['get valid metric id'].$RESPONSE['$.id']
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/metric/$HISTORY['get valid metric id'].$RESPONSE['$.id']
status: 404
- name: create metric bad archive policy
POST: /v1/metric
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/metric
request_headers:
content-type: application/json
data:
@ -434,7 +434,7 @@ tests:
- Archive policy 2e2675aa-105e-4664-a30d-c407e6a0ea7f does not exist
- name: create metric bad content-type
POST: /v1/metric
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/metric
request_headers:
content-type: plain/text
data: '{"archive_policy_name": "cookies"}'
@ -446,11 +446,11 @@ tests:
#
- name: delete archive policy rule
DELETE: /v1/archive_policy_rule/gabbilive_rule
DELETE: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy_rule/gabbilive_rule
status: 204
- name: confirm delete archive policy rule
DELETE: /v1/archive_policy_rule/gabbilive_rule
DELETE: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy_rule/gabbilive_rule
status: 404
@ -459,24 +459,24 @@ tests:
#
- name: root of resource
GET: /v1/resource
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource
response_json_paths:
$.generic: $SCHEME://$NETLOC/v1/resource/generic
- name: typo of resource
GET: /v1/resoue
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resoue
status: 404
- name: typo of resource extra
GET: /v1/resource/foobar
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/foobar
status: 404
- name: generic resource
GET: /v1/resource/generic
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/generic
status: 200
- name: post resource type
POST: /v1/resource_type
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource_type
request_headers:
content-type: application/json
data:
@ -492,7 +492,7 @@ tests:
location: $SCHEME://$NETLOC/v1/resource_type/myresource
- name: add an attribute
PATCH: /v1/resource_type/myresource
PATCH: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource_type/myresource
request_headers:
content-type: application/json-patch+json
data:
@ -506,7 +506,7 @@ tests:
$.attributes.[*].`len`: 2
- name: remove an attribute
PATCH: /v1/resource_type/myresource
PATCH: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource_type/myresource
request_headers:
content-type: application/json-patch+json
data:
@ -522,7 +522,7 @@ tests:
desc: Expect 406 on bad accept type
request_headers:
accept: text/plain
GET: /v1/resource/myresource
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/myresource
status: 406
response_strings:
- 406 Not Acceptable
@ -531,11 +531,11 @@ tests:
desc: failover accept media type appropriately
request_headers:
accept: text/plain, application/json; q=0.8
GET: /v1/resource/myresource
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/myresource
status: 200
- name: post myresource resource
POST: /v1/resource/myresource
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/myresource
request_headers:
content-type: application/json
data:
@ -563,14 +563,14 @@ tests:
$.display_name: "myvm"
- name: get vcpus metric
GET: /v1/metric/$HISTORY['get myresource resource'].$RESPONSE['$.metrics.vcpus']
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/metric/$HISTORY['get myresource resource'].$RESPONSE['$.metrics.vcpus']
status: 200
response_json_paths:
$.name: vcpus
$.resource.id: 2ae35573-7f9f-4bb1-aae8-dad8dff5706e
- name: search for myresource resource via user_id
POST: /v1/search/resource/myresource
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/search/resource/myresource
request_headers:
content-type: application/json
data:
@ -583,7 +583,7 @@ tests:
$..display_name: myvm
- name: search for myresource resource via user_id and 'generic' type
POST: /v1/search/resource/generic
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/search/resource/generic
request_headers:
content-type: application/json
data:
@ -593,7 +593,7 @@ tests:
- '"user_id": "126204ef-989a-46fd-999b-ee45c8108f31"'
- name: search for myresource resource via user_id and project_id
POST: /v1/search/resource/generic
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/search/resource/generic
request_headers:
content-type: application/json
data:
@ -606,7 +606,7 @@ tests:
- '"id": "2ae35573-7f9f-4bb1-aae8-dad8dff5706e"'
- name: patch myresource resource
PATCH: /v1/resource/myresource/2ae35573-7f9f-4bb1-aae8-dad8dff5706e
PATCH: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/myresource/2ae35573-7f9f-4bb1-aae8-dad8dff5706e
request_headers:
content-type: application/json
data:
@ -616,7 +616,7 @@ tests:
display_name: myvm2
- name: post some measures to the metric on myresource
POST: /v1/resource/myresource/2ae35573-7f9f-4bb1-aae8-dad8dff5706e/metric/vcpus/measures
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/myresource/2ae35573-7f9f-4bb1-aae8-dad8dff5706e/metric/vcpus/measures
request_headers:
content-type: application/json
data:
@ -627,7 +627,7 @@ tests:
status: 202
- name: get myresource measures with poll
GET: /v1/resource/myresource/2ae35573-7f9f-4bb1-aae8-dad8dff5706e/metric/vcpus/measures
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/myresource/2ae35573-7f9f-4bb1-aae8-dad8dff5706e/metric/vcpus/measures
# wait up to 60 seconds before policy is deleted
poll:
count: 60
@ -637,7 +637,7 @@ tests:
$[1][2]: 2
- name: post some more measures to the metric on myresource
POST: /v1/resource/myresource/2ae35573-7f9f-4bb1-aae8-dad8dff5706e/metric/vcpus/measures
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/myresource/2ae35573-7f9f-4bb1-aae8-dad8dff5706e/metric/vcpus/measures
request_headers:
content-type: application/json
data:
@ -648,7 +648,7 @@ tests:
status: 202
- name: get myresource measures with refresh
GET: /v1/resource/myresource/2ae35573-7f9f-4bb1-aae8-dad8dff5706e/metric/vcpus/measures?refresh=true
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/myresource/2ae35573-7f9f-4bb1-aae8-dad8dff5706e/metric/vcpus/measures?refresh=true
response_json_paths:
$[0][2]: 2
$[1][2]: 4
@ -662,15 +662,15 @@ tests:
#
- name: typo of search
POST: /v1/search/notexists
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/search/notexists
status: 404
- name: typo of search in resource
POST: /v1/search/resource/foobar
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/search/resource/foobar
status: 404
- name: search with invalid uuid
POST: /v1/search/resource/generic
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/search/resource/generic
request_headers:
content-type: application/json
data:
@ -681,7 +681,7 @@ tests:
$.`len`: 0
- name: assert vcpus metric exists in listing
GET: /v1/metric?id=$HISTORY['get myresource resource'].$RESPONSE['$.metrics.vcpus']
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/metric?id=$HISTORY['get myresource resource'].$RESPONSE['$.metrics.vcpus']
poll:
count: 360
delay: 1
@ -689,12 +689,12 @@ tests:
$.`len`: 1
- name: delete myresource resource
DELETE: /v1/resource/myresource/2ae35573-7f9f-4bb1-aae8-dad8dff5706e
DELETE: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/myresource/2ae35573-7f9f-4bb1-aae8-dad8dff5706e
status: 204
# assert resource is really deleted
- name: assert resource resource is deleted
GET: /v1/resource/myresource/2ae35573-7f9f-4bb1-aae8-dad8dff5706e
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/myresource/2ae35573-7f9f-4bb1-aae8-dad8dff5706e
status: 404
- name: assert vcpus metric is really expurged
@ -706,7 +706,7 @@ tests:
$.`len`: 0
- name: post myresource resource no data
POST: /v1/resource/myresource
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/myresource
request_headers:
content-type: application/json
status: 400
@ -722,7 +722,7 @@ tests:
$.`len`: 0
- name: delete single archive policy cleanup
DELETE: /v1/archive_policy/gabbilive
DELETE: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy/gabbilive
poll:
count: 360
delay: 1
@ -731,9 +731,9 @@ tests:
# It really is gone
- name: delete our resource type
DELETE: /v1/resource_type/myresource
DELETE: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource_type/myresource
status: 204
- name: confirm delete of cleanup
GET: /v1/archive_policy/gabbilive
GET: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/archive_policy/gabbilive
status: 404

View File

@ -27,7 +27,7 @@ tests:
#
- name: create new resource type 'instance-like'
POST: /v1/resource_type
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource_type
status: 201
request_headers:
content-type: application/json
@ -51,7 +51,7 @@ tests:
required: False
- name: create new resource type 'image-like'
POST: /v1/resource_type
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource_type
status: 201
request_headers:
content-type: application/json
@ -72,7 +72,7 @@ tests:
# Setup test resources
#
- name: helper. create instance-like resource-1
POST: /v1/resource/instance-like
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/instance-like
request_headers:
content-type: application/json
data:
@ -86,7 +86,7 @@ tests:
status: 201
- name: helper. create instance-like resource-2
POST: /v1/resource/instance-like
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/instance-like
request_headers:
content-type: application/json
data:
@ -100,7 +100,7 @@ tests:
status: 201
- name: helper. create instance-like resource-3
POST: /v1/resource/instance-like
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/instance-like
request_headers:
content-type: application/json
data:
@ -114,7 +114,7 @@ tests:
status: 201
- name: helper. create image-like resource-1
POST: /v1/resource/image-like
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/image-like
request_headers:
content-type: application/json
data:
@ -132,7 +132,7 @@ tests:
- name: search for all resources with a specific user_id
desc: search through all resource types
POST: /v1/search/resource/generic
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/search/resource/generic
request_headers:
content-type: application/json
data:
@ -149,7 +149,7 @@ tests:
- name: search for all resources of instance-like type create by specific user_id
desc: all instances created by a specified user
POST: /v1/search/resource/generic
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/search/resource/generic
request_headers:
content-type: application/json
data:
@ -174,7 +174,7 @@ tests:
- name: search for all resources with a specific project_id
desc: search for all resources in a specific project
POST: /v1/search/resource/generic
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/search/resource/generic
request_headers:
content-type: application/json
data:
@ -186,7 +186,7 @@ tests:
- name: search for intances on a specific compute using "like" keyword
desc: search for vms hosted on a specific compute node
POST: /v1/search/resource/instance-like
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/search/resource/instance-like
request_headers:
content-type: application/json
data:
@ -204,7 +204,7 @@ tests:
- name: search for instances using complex search with "like" keyword and user_id
desc: search for vms of specified user hosted on a specific compute node
POST: /v1/search/resource/instance-like
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/search/resource/instance-like
request_headers:
content-type: application/json
data:
@ -222,7 +222,7 @@ tests:
- name: search for resources of instance-like or image-like type with specific user_id
desc: search for all image-like or instance-like resources created by a specific user
POST: /v1/search/resource/generic
POST: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/search/resource/generic
request_headers:
content-type: application/json
data:
@ -250,26 +250,26 @@ tests:
#
- name: helper. delete instance-like resource-1
DELETE: /v1/resource/instance-like/a64ca14f-bc7c-45b0-aa85-42cd2179e1e2
DELETE: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/instance-like/a64ca14f-bc7c-45b0-aa85-42cd2179e1e2
status: 204
- name: helper. delete instance-like resource-2
DELETE: /v1/resource/instance-like/7ccccfa0-92ce-4225-80ca-3ac9cb122d6a
DELETE: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/instance-like/7ccccfa0-92ce-4225-80ca-3ac9cb122d6a
status: 204
- name: helper. delete instance-like resource-3
DELETE: /v1/resource/instance-like/c442a47c-eb33-46ce-9665-f3aa0bef54e7
DELETE: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/instance-like/c442a47c-eb33-46ce-9665-f3aa0bef54e7
status: 204
- name: helper. delete image-like resource
DELETE: /v1/resource/image-like/7ab2f7ae-7af5-4469-bdc8-3c0f6dfab75d
DELETE: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource/image-like/7ab2f7ae-7af5-4469-bdc8-3c0f6dfab75d
status: 204
- name: helper. delete resource-type instance-like
DELETE: /v1/resource_type/instance-like
DELETE: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource_type/instance-like
status: 204
- name: helper. delete resource-type image-like
DELETE: /v1/resource_type/image-like
DELETE: $ENVIRON['GNOCCHI_SERVICE_URL']/v1/resource_type/image-like
status: 204

View File

@ -0,0 +1,52 @@
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
from __future__ import absolute_import
import os
from tempest import config
import tempest.test
from telemetry_tempest_plugin.scenario import utils
CONF = config.CONF
TEST_DIR = os.path.join(os.path.dirname(__file__), 'gnocchi_gabbits')
class GnocchiGabbiTest(tempest.test.BaseTestCase):
credentials = ['admin']
TIMEOUT_SCALING_FACTOR = 5
@classmethod
def skip_checks(cls):
super(GnocchiGabbiTest, cls).skip_checks()
if not CONF.service_available.gnocchi:
raise cls.skipException("Gnocchi support is required")
def _prep_test(self, filename):
token = self.os_admin.auth_provider.get_token()
url = self.os_admin.auth_provider.base_url(
{'service': CONF.metric.catalog_type,
'endpoint_type': CONF.metric.endpoint_type,
'region': CONF.identity.region})
os.environ.update({
"GNOCCHI_SERVICE_URL": url,
"GNOCCHI_SERVICE_TOKEN": token,
"GNOCCHI_AUTHORIZATION": "not used",
})
utils.generate_tests(GnocchiGabbiTest, TEST_DIR)

View File

@ -11,16 +11,14 @@
# under the License.
import os
import unittest
from gabbi import runner
from gabbi import suitemaker
from gabbi import utils
from tempest import config
from tempest.scenario import manager
TEST_DIR = os.path.join(os.path.dirname(__file__), '..',
'integration', 'gabbi', 'gabbits-live')
from telemetry_tempest_plugin.scenario import utils
TEST_DIR = os.path.join(os.path.dirname(__file__),
'telemetry_integration_gabbits')
class TestTelemetryIntegration(manager.ScenarioTest):
@ -75,7 +73,7 @@ class TestTelemetryIntegration(manager.ScenarioTest):
opt_section.catalog_type)
return endpoints[0]['endpoints'][0][endpoint_type]
def _do_test(self, filename):
def _prep_test(self, filename):
admin_auth = self.os_admin.auth_provider.get_auth()
auth = self.os_primary.auth_provider.get_auth()
networks = self.os_primary.networks_client.list_networks(
@ -96,48 +94,5 @@ class TestTelemetryIntegration(manager.ScenarioTest):
"NEUTRON_NETWORK": networks[0].get('id'),
})
with open(os.path.join(TEST_DIR, filename)) as f:
test_suite = suitemaker.test_suite_from_dict(
loader=unittest.defaultTestLoader,
test_base_name="gabbi",
suite_dict=utils.load_yaml(f),
test_directory=TEST_DIR,
host="example.com", port=None,
fixture_module=None,
intercept=None,
handlers=runner.initialize_handlers([]),
test_loader_name="tempest")
# NOTE(sileht): We hide stdout/stderr and reraise the failure
# manually, tempest will print it itself.
with open(os.devnull, 'w') as stream:
result = unittest.TextTestRunner(
stream=stream, verbosity=0, failfast=True,
).run(test_suite)
if not result.wasSuccessful():
failures = (result.errors + result.failures +
result.unexpectedSuccesses)
if failures:
test, bt = failures[0]
name = test.test_data.get('name', test.id())
msg = 'From test "%s" :\n%s' % (name, bt)
self.fail(msg)
self.assertTrue(result.wasSuccessful())
def test_maker(name, filename):
def test(self):
self._do_test(filename)
test.__name__ = name
return test
# Create one scenario per yaml file
for filename in os.listdir(TEST_DIR):
if not filename.endswith('.yaml'):
continue
name = "test_%s" % filename[:-5].lower().replace("-", "_")
setattr(TestTelemetryIntegration, name,
test_maker(name, filename))
utils.generate_tests(TestTelemetryIntegration, TEST_DIR)

View File

@ -0,0 +1,78 @@
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
from __future__ import absolute_import
import os
import unittest
from gabbi import runner
from gabbi import suitemaker
from gabbi import utils
from oslo_log import log as logging
LOG = logging.getLogger(__name__)
def run_test(test_class_instance, test_dir, filename):
d = utils.load_yaml(yaml_file=os.path.join(test_dir, filename))
test_suite = suitemaker.test_suite_from_dict(
loader=unittest.defaultTestLoader,
test_base_name="gabbi",
suite_dict=d,
test_directory=test_dir,
host='example.com', port=None,
fixture_module=None,
intercept=None,
handlers=runner.initialize_handlers([]),
test_loader_name="tempest")
# NOTE(sileht): We hide stdout/stderr and reraise the failure
# manually, tempest will print it ittest_class.
with open(os.devnull, 'w') as stream:
result = unittest.TextTestRunner(
stream=stream, verbosity=0, failfast=True,
).run(test_suite)
return
if not result.wasSuccessful():
failures = (result.errors + result.failures +
result.unexpectedSuccesses)
if failures:
test, bt = failures[0]
name = test.test_data.get('name', test.id())
msg = 'From test "%s" :\n%s' % (name, bt)
test_class_instance.fail(msg)
test_class_instance.assertTrue(result.wasSuccessful())
def test_maker(test_dir, filename, name):
def test(self):
self._prep_test(filename)
run_test(self, test_dir, filename)
test.__name__ = name
return test
def generate_tests(test_class, test_dir):
# Create one scenario per yaml file
filenames = os.listdir(test_dir)
if not filenames:
raise RuntimeError("%s is empty" % test_dir)
for filename in filenames:
if not filename.endswith('.yaml'):
continue
name = "test_%s" % filename[:-5].lower().replace("-", "_")
setattr(test_class, name,
test_maker(test_dir, filename, name))