diff options
Diffstat (limited to 'nova/tests/unit/api/openstack/compute/schemas')
23 files changed, 270 insertions, 0 deletions
diff --git a/nova/tests/unit/api/openstack/compute/schemas/__init__.py b/nova/tests/unit/api/openstack/compute/schemas/__init__.py new file mode 100644 index 0000000000..e69de29bb2 --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/__init__.py diff --git a/nova/tests/unit/api/openstack/compute/schemas/test_schemas.py b/nova/tests/unit/api/openstack/compute/schemas/test_schemas.py new file mode 100644 index 0000000000..c6ce82057e --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/test_schemas.py @@ -0,0 +1,106 @@ +# Copyright 2012 OpenStack Foundation +# 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. + +import glob +import os + +import lxml.etree + +from nova import test + +SCHEMAS = "nova/api/openstack/compute/schemas" + + +class RelaxNGSchemaTestCase(test.NoDBTestCase): + """various validation tasks for the RelaxNG schemas + + lxml.etree has no built-in way to validate an entire namespace + (i.e., multiple RelaxNG schema files defining elements in the same + namespace), so we define a few tests that should hopefully reduce + the risk of an inconsistent namespace + """ + + def _load_schema(self, schemafile): + return lxml.etree.RelaxNG(lxml.etree.parse(schemafile)) + + def _load_test_cases(self, path): + """load test cases from the given path.""" + rv = dict(valid=[], invalid=[]) + path = os.path.join(os.path.dirname(__file__), path) + for ctype in rv.keys(): + for cfile in glob.glob(os.path.join(path, ctype, "*.xml")): + rv[ctype].append(lxml.etree.parse(cfile)) + return rv + + def _validate_schema(self, schemafile): + """validate a single RelaxNG schema file.""" + try: + self._load_schema(schemafile) + except lxml.etree.RelaxNGParseError as err: + self.fail("%s is not a valid RelaxNG schema: %s" % + (schemafile, err)) + + def _api_versions(self): + """get a list of API versions.""" + return [''] + [os.path.basename(v) + for v in glob.glob(os.path.join(SCHEMAS, "v*"))] + + def _schema_files(self, api_version): + return glob.glob(os.path.join(SCHEMAS, api_version, "*.rng")) + + def test_schema_validity(self): + for api_version in self._api_versions(): + for schema in self._schema_files(api_version): + self._validate_schema(schema) + + def test_schema_duplicate_elements(self): + for api_version in self._api_versions(): + elements = dict() + duplicates = dict() + for schemafile in self._schema_files(api_version): + schema = lxml.etree.parse(schemafile) + fname = os.path.basename(schemafile) + if schema.getroot().tag != "element": + # we don't do any sort of validation on grammars + # yet + continue + el_name = schema.getroot().get("name") + if el_name in elements: + duplicates.setdefault(el_name, + [elements[el_name]]).append(fname) + else: + elements[el_name] = fname + self.assertEqual(len(duplicates), 0, + "Duplicate element definitions found: %s" % + "; ".join("%s in %s" % dup + for dup in duplicates.items())) + + def test_schema_explicit_cases(self): + cases = {'v1.1/flavors.rng': self._load_test_cases("v1.1/flavors"), + 'v1.1/images.rng': self._load_test_cases("v1.1/images"), + 'v1.1/servers.rng': self._load_test_cases("v1.1/servers")} + + for schemafile, caselists in cases.items(): + schema = self._load_schema(os.path.join(SCHEMAS, schemafile)) + for case in caselists['valid']: + self.assertTrue(schema.validate(case), + "Schema validation failed against %s: %s\n%s" % + (schemafile, schema.error_log, case)) + + for case in caselists['invalid']: + self.assertFalse( + schema.validate(case), + "Schema validation succeeded unexpectedly against %s: %s" + "\n%s" % (schemafile, schema.error_log, case)) diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/invalid/mixed.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/invalid/mixed.xml new file mode 100644 index 0000000000..df4368bf41 --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/invalid/mixed.xml @@ -0,0 +1,8 @@ +<?xml version="1.0" encoding="utf-8"?> +<flavors xmlns="http://docs.openstack.org/compute/api/v1.1"> + <!-- you cannot mix flavor references (i.e., with only name and id) + and specifications (with all attributes) in the same document + --> + <flavor name="foo" id="foo"/> + <flavor name="bar" id="bar" ram="bar" disk="bar" vcpus="bar"/> +</flavors> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/invalid/partial.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/invalid/partial.xml new file mode 100644 index 0000000000..3343a7be59 --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/invalid/partial.xml @@ -0,0 +1,5 @@ +<?xml version="1.0" encoding="utf-8"?> +<flavors xmlns="http://docs.openstack.org/compute/api/v1.1"> + <!-- this flavor is only partially specified --> + <flavor name="foo"/> +</flavors> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/invalid/partial2.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/invalid/partial2.xml new file mode 100644 index 0000000000..f67c5a82fe --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/invalid/partial2.xml @@ -0,0 +1,6 @@ +<?xml version="1.0" encoding="utf-8"?> +<flavors xmlns="http://docs.openstack.org/compute/api/v1.1"> + <!-- a flavor can either have *only* name and id, or needs to also + have disk and vcpus in addition to ram --> + <flavor name="foo" id="foo" ram="foo"/> +</flavors> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/valid/empty.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/valid/empty.xml new file mode 100644 index 0000000000..36aa3936e7 --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/valid/empty.xml @@ -0,0 +1,2 @@ +<?xml version="1.0" encoding="utf-8"?> +<flavors xmlns="http://docs.openstack.org/compute/api/v1.1"/> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/valid/full.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/valid/full.xml new file mode 100644 index 0000000000..59eafc8608 --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/valid/full.xml @@ -0,0 +1,4 @@ +<?xml version="1.0" encoding="utf-8"?> +<flavors xmlns="http://docs.openstack.org/compute/api/v1.1"> + <flavor name="foo" id="foo" ram="foo" disk="foo" vcpus="foo"/> +</flavors> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/valid/refs.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/valid/refs.xml new file mode 100644 index 0000000000..751b626258 --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/flavors/valid/refs.xml @@ -0,0 +1,5 @@ +<?xml version="1.0" encoding="utf-8"?> +<flavors xmlns="http://docs.openstack.org/compute/api/v1.1"> + <flavor name="foo" id="foo"/> + <flavor name="bar" id="bar"/> +</flavors> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/invalid/mixed.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/invalid/mixed.xml new file mode 100644 index 0000000000..8f7bf208ae --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/invalid/mixed.xml @@ -0,0 +1,9 @@ +<?xml version="1.0" encoding="utf-8"?> +<images xmlns="http://docs.openstack.org/compute/api/v1.1"> + <!-- cannot mix refs and specs in the same document --> + <image name="foo" id="foo"/> + <image name="bar" id="bar" updated="1401991486" created="1401991486" + status="foo"> + <metadata/> + </image> +</images> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/invalid/no-metadata.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/invalid/no-metadata.xml new file mode 100644 index 0000000000..435294e27c --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/invalid/no-metadata.xml @@ -0,0 +1,6 @@ +<?xml version="1.0" encoding="utf-8"?> +<images xmlns="http://docs.openstack.org/compute/api/v1.1"> + <!-- image specs require a metadata child --> + <image name="foo" id="foo" updated="1401991486" created="1401991486" + status="foo"/> +</images> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/invalid/partial.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/invalid/partial.xml new file mode 100644 index 0000000000..5637cce787 --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/invalid/partial.xml @@ -0,0 +1,5 @@ +<?xml version="1.0" encoding="utf-8"?> +<images xmlns="http://docs.openstack.org/compute/api/v1.1"> + <!-- image refs require id --> + <image name="foo"/> +</images> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/invalid/partial2.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/invalid/partial2.xml new file mode 100644 index 0000000000..db5e974621 --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/invalid/partial2.xml @@ -0,0 +1,7 @@ +<?xml version="1.0" encoding="utf-8"?> +<images xmlns="http://docs.openstack.org/compute/api/v1.1"> + <!-- an image must be either a ref, with *only* name and id attrs, + or fully specified, with name, id, updated, created, status, + and a metadata child --> + <image name="foo" id="foo" updated="foo"/> +</images> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/valid/empty.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/valid/empty.xml new file mode 100644 index 0000000000..05e0b8241c --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/valid/empty.xml @@ -0,0 +1,2 @@ +<?xml version="1.0" encoding="utf-8"?> +<images xmlns="http://docs.openstack.org/compute/api/v1.1"/> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/valid/full.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/valid/full.xml new file mode 100644 index 0000000000..4f148db625 --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/valid/full.xml @@ -0,0 +1,14 @@ +<?xml version="1.0" encoding="utf-8"?> +<images xmlns="http://docs.openstack.org/compute/api/v1.1"> + <image name="foo" id="foo" updated="1401991486" created="1401991486" + status="foo"> + <metadata/> + </image> + <image name="bar" id="bar" updated="1401991486" created="1401991486" + status="bar" progress="bar" minDisk="100" minRam="100"> + <server id="bar"/> + <metadata> + <meta key="baz">baz</meta> + </metadata> + </image> +</images> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/valid/refs.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/valid/refs.xml new file mode 100644 index 0000000000..1dfedd2c77 --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/images/valid/refs.xml @@ -0,0 +1,5 @@ +<?xml version="1.0" encoding="utf-8"?> +<images xmlns="http://docs.openstack.org/compute/api/v1.1"> + <image name="foo" id="foo"/> + <image name="bar" id="bar"/> +</images> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/invalid/mixed.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/invalid/mixed.xml new file mode 100644 index 0000000000..c941472beb --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/invalid/mixed.xml @@ -0,0 +1,18 @@ +<?xml version="1.0" encoding="utf-8"?> +<servers xmlns="http://docs.openstack.org/compute/api/v1.1" + xmlns:atom="http://www.w3.org/2005/Atom"> + <!-- you cannot mix server refs and specs in the same document --> + <server name="foo" id="foo"/> + <server name="foo" userId="foo" tenantId="foo" id="foo" updated="1401991486" + created="1401991486" hostId="foo" accessIPv4="1.2.3.4" + accessIPv6="::1" status="foo"> + <image id="foo"> + <atom:link href="/compute/api/v1.1/image/foo"/> + </image> + <flavor id="foo"> + <atom:link href="/compute/api/v1.1/flavor/foo"/> + </flavor> + <metadata/> + <addresses/> + </server> +</servers> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/invalid/partial.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/invalid/partial.xml new file mode 100644 index 0000000000..721ce84327 --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/invalid/partial.xml @@ -0,0 +1,5 @@ +<?xml version="1.0" encoding="utf-8"?> +<servers xmlns="http://docs.openstack.org/compute/api/v1.1"> + <!-- server refs require the id attr --> + <server name="foo"/> +</servers> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/invalid/partial2.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/invalid/partial2.xml new file mode 100644 index 0000000000..474b3a084e --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/invalid/partial2.xml @@ -0,0 +1,6 @@ +<?xml version="1.0" encoding="utf-8"?> +<servers xmlns="http://docs.openstack.org/compute/api/v1.1"> + <!-- server tags must either be refs, with *only* name and id, or + full specifications, with loads more detail --> + <server name="foo" id="foo" updated="foo"/> +</servers> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/invalid/partial3.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/invalid/partial3.xml new file mode 100644 index 0000000000..6455fe899a --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/invalid/partial3.xml @@ -0,0 +1,7 @@ +<?xml version="1.0" encoding="utf-8"?> +<servers xmlns="http://docs.openstack.org/compute/api/v1.1"> + <!-- the server specification requires a number of children --> + <server name="foo" userId="foo" tenantId="foo" id="foo" updated="1401991486" + created="1401991486" hostId="foo" accessIPv4="1.2.3.4" + accessIPv6="::1" status="foo"/> +</servers> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/valid/detailed.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/valid/detailed.xml new file mode 100644 index 0000000000..97f5ee44e6 --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/valid/detailed.xml @@ -0,0 +1,27 @@ +<?xml version="1.0" encoding="utf-8"?> +<servers xmlns="http://docs.openstack.org/compute/api/v1.1" + xmlns:atom="http://www.w3.org/2005/Atom"> + <server name="bar" userId="bar" tenantId="bar" id="bar" updated="1401991486" + created="1401991486" hostId="bar" accessIPv4="1.2.3.4" + accessIPv6="::1" status="bar" progress="10" adminPass="bar"> + <image id="foo"> + <atom:link href="/compute/api/v1.1/image/foo"/> + </image> + <flavor id="foo"> + <atom:link href="/compute/api/v1.1/flavor/foo"/> + </flavor> + <fault code="1" created="1401991486"> + <message>fault</message> + <details>fault</details> + </fault> + <metadata> + <meta key="bar">bar</meta> + </metadata> + <addresses> + <network id="bar"/> + <network id="baz"> + <ip version="4" addr="1.2.3.4"/> + </network> + </addresses> + </server> +</servers> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/valid/empty.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/valid/empty.xml new file mode 100644 index 0000000000..b2f3666245 --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/valid/empty.xml @@ -0,0 +1,2 @@ +<?xml version="1.0" encoding="utf-8"?> +<servers xmlns="http://docs.openstack.org/compute/api/v1.1"/> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/valid/full.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/valid/full.xml new file mode 100644 index 0000000000..fbd6202a76 --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/valid/full.xml @@ -0,0 +1,16 @@ +<?xml version="1.0" encoding="utf-8"?> +<servers xmlns="http://docs.openstack.org/compute/api/v1.1" + xmlns:atom="http://www.w3.org/2005/Atom"> + <server name="foo" userId="foo" tenantId="foo" id="foo" updated="1401991486" + created="1401991486" hostId="foo" accessIPv4="1.2.3.4" + accessIPv6="::1" status="foo"> + <image id="foo"> + <atom:link href="/compute/api/v1.1/image/foo"/> + </image> + <flavor id="foo"> + <atom:link href="/compute/api/v1.1/flavor/foo"/> + </flavor> + <metadata/> + <addresses/> + </server> +</servers> diff --git a/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/valid/refs.xml b/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/valid/refs.xml new file mode 100644 index 0000000000..e1212e985f --- /dev/null +++ b/nova/tests/unit/api/openstack/compute/schemas/v1.1/servers/valid/refs.xml @@ -0,0 +1,5 @@ +<?xml version="1.0" encoding="utf-8"?> +<servers xmlns="http://docs.openstack.org/compute/api/v1.1"> + <server name="foo" id="foo"/> + <server name="bar" id="bar"/> +</servers> |