summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDavanum Srinivas <davanum@gmail.com>2012-10-22 17:53:30 -0400
committerGerrit Code Review <review@openstack.org>2012-10-26 02:06:44 +0000
commit10caf4b48fa67b160e6024a801efbda292d44ebf (patch)
tree8e66afd49d629b06e0f6e5c472fbe0e4423e0d53
parentf1e5fbf92af1fb1e1c2f0634870159e7bac19cfd (diff)
downloadnova-10caf4b48fa67b160e6024a801efbda292d44ebf.tar.gz
nova-10caf4b48fa67b160e6024a801efbda292d44ebf.tar.xz
nova-10caf4b48fa67b160e6024a801efbda292d44ebf.zip
Fix Broken XML Namespace Handling
nodeName is set to ns2:metadata and not just metadata when namespaces are specified using first example in the defect. Explicitly check namespaces where necessary and use localName instead of nodeName. Ensure that scheduler_hints are picked up from the correct namespace fix lines too long from pep8 Fixes bug 887191 Change-Id: I5db2b575d24f6b1b358489e309af7e6ace2950fd
-rw-r--r--nova/api/openstack/compute/servers.py10
-rw-r--r--nova/api/openstack/wsgi.py13
-rw-r--r--nova/tests/api/openstack/compute/test_servers.py51
3 files changed, 65 insertions, 9 deletions
diff --git a/nova/api/openstack/compute/servers.py b/nova/api/openstack/compute/servers.py
index 9c182f3a5..ba88d72e7 100644
--- a/nova/api/openstack/compute/servers.py
+++ b/nova/api/openstack/compute/servers.py
@@ -241,13 +241,9 @@ class CommonDeserializer(wsgi.MetadataXMLDeserializer):
def _extract_scheduler_hints(self, server_node):
"""Marshal the scheduler hints attribute of a parsed request"""
- node = self.find_first_child_named(server_node,
- "OS-SCH-HNT:scheduler_hints")
- # NOTE(vish): Support the os: prefix because it is what we use
- # for json, even though OS-SCH-HNT: is more correct
- if not node:
- node = self.find_first_child_named(server_node,
- "os:scheduler_hints")
+ node = self.find_first_child_named_in_namespace(server_node,
+ "http://docs.openstack.org/compute/ext/scheduler-hints/api/v2",
+ "scheduler_hints")
if node:
scheduler_hints = {}
for child in self.extract_elements(node):
diff --git a/nova/api/openstack/wsgi.py b/nova/api/openstack/wsgi.py
index a7a3823e9..bfe0ec599 100644
--- a/nova/api/openstack/wsgi.py
+++ b/nova/api/openstack/wsgi.py
@@ -244,17 +244,26 @@ class XMLDeserializer(TextDeserializer):
listnames)
return result
+ def find_first_child_named_in_namespace(self, parent, namespace, name):
+ """Search a nodes children for the first child with a given name"""
+ for node in parent.childNodes:
+ if (node.localName == name and
+ node.namespaceURI and
+ node.namespaceURI == namespace):
+ return node
+ return None
+
def find_first_child_named(self, parent, name):
"""Search a nodes children for the first child with a given name"""
for node in parent.childNodes:
- if node.nodeName == name:
+ if node.localName == name:
return node
return None
def find_children_named(self, parent, name):
"""Return all of a nodes children who have the given name"""
for node in parent.childNodes:
- if node.nodeName == name:
+ if node.localName == name:
yield node
def extract_text(self, node):
diff --git a/nova/tests/api/openstack/compute/test_servers.py b/nova/tests/api/openstack/compute/test_servers.py
index 0a35fb36a..afa181ee3 100644
--- a/nova/tests/api/openstack/compute/test_servers.py
+++ b/nova/tests/api/openstack/compute/test_servers.py
@@ -3030,6 +3030,57 @@ class TestServerCreateRequestXMLDeserializer(test.TestCase):
}
self.assertEquals(request['body'], expected)
+ def test_request_with_alternate_namespace_prefix(self):
+ serial_request = """
+<ns2:server xmlns:ns2="http://docs.openstack.org/compute/api/v2"
+ name="new-server-test"
+ imageRef="1"
+ flavorRef="2">
+ <ns2:metadata><ns2:meta key="hello">world</ns2:meta></ns2:metadata>
+ </ns2:server>
+ """
+ request = self.deserializer.deserialize(serial_request)
+ expected = {
+ "server": {
+ "name": "new-server-test",
+ "imageRef": "1",
+ "flavorRef": "2",
+ 'metadata': {"hello": "world"},
+ },
+ }
+ self.assertEquals(request['body'], expected)
+
+ def test_request_with_scheduler_hints_and_alternate_namespace_prefix(self):
+ serial_request = """
+<ns2:server xmlns:ns2="http://docs.openstack.org/compute/api/v2"
+ name="new-server-test"
+ imageRef="1"
+ flavorRef="2">
+ <ns2:metadata><ns2:meta key="hello">world</ns2:meta></ns2:metadata>
+ <os:scheduler_hints
+ xmlns:os="http://docs.openstack.org/compute/ext/scheduler-hints/api/v2">
+ <hypervisor>xen</hypervisor>
+ <near>eb999657-dd6b-464e-8713-95c532ac3b18</near>
+ </os:scheduler_hints>
+ </ns2:server>
+ """
+ request = self.deserializer.deserialize(serial_request)
+ expected = {
+ "server": {
+ 'OS-SCH-HNT:scheduler_hints': {
+ 'hypervisor': ['xen'],
+ 'near': ['eb999657-dd6b-464e-8713-95c532ac3b18']
+ },
+ "name": "new-server-test",
+ "imageRef": "1",
+ "flavorRef": "2",
+ "metadata": {
+ "hello": "world"
+ }
+ }
+ }
+ self.assertEquals(request['body'], expected)
+
def test_access_ipv4(self):
serial_request = """
<server xmlns="http://docs.openstack.org/compute/api/v2"