heat API : Move aws api common code into aws/utils.py
Move heat-api AWS common utility functions into a new utils.py, so these functions can be reused by cloudwatch Change-Id: I030d796b1048ffc4e7c40f7c8760121ab2854733 Signed-off-by: Steven Hardy <shardy@redhat.com>
This commit is contained in:
parent
1b6c2dad19
commit
ecc5a408a3
78
heat/api/aws/utils.py
Normal file
78
heat/api/aws/utils.py
Normal file
@ -0,0 +1,78 @@
|
|||||||
|
# vim: tabstop=4 shiftwidth=4 softtabstop=4
|
||||||
|
|
||||||
|
#
|
||||||
|
# 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.
|
||||||
|
|
||||||
|
'''
|
||||||
|
Helper utilities related to the AWS API implementations
|
||||||
|
'''
|
||||||
|
|
||||||
|
import re
|
||||||
|
|
||||||
|
|
||||||
|
def format_response(action, response):
|
||||||
|
"""
|
||||||
|
Format response from engine into API format
|
||||||
|
"""
|
||||||
|
return {'%sResponse' % action: {'%sResult' % action: response}}
|
||||||
|
|
||||||
|
|
||||||
|
def extract_user_params(params):
|
||||||
|
"""
|
||||||
|
Extract a dictionary of user input parameters for the stack
|
||||||
|
|
||||||
|
In the AWS API parameters, each user parameter appears as two key-value
|
||||||
|
pairs with keys of the form below:
|
||||||
|
|
||||||
|
Parameters.member.1.ParameterKey
|
||||||
|
Parameters.member.1.ParameterValue
|
||||||
|
|
||||||
|
We reformat this into a normal dict here to match the heat
|
||||||
|
engine API expected format
|
||||||
|
|
||||||
|
Note this implemented outside of "create" as it will also be
|
||||||
|
used by update (and EstimateTemplateCost if appropriate..)
|
||||||
|
"""
|
||||||
|
# Define the AWS key format to extract
|
||||||
|
PARAM_KEYS = (
|
||||||
|
PARAM_USER_KEY_re,
|
||||||
|
PARAM_USER_VALUE_fmt,
|
||||||
|
) = (
|
||||||
|
re.compile(r'Parameters\.member\.(.*?)\.ParameterKey$'),
|
||||||
|
'Parameters.member.%s.ParameterValue',
|
||||||
|
)
|
||||||
|
|
||||||
|
def get_param_pairs():
|
||||||
|
for k in params:
|
||||||
|
keymatch = PARAM_USER_KEY_re.match(k)
|
||||||
|
if keymatch:
|
||||||
|
key = params[k]
|
||||||
|
v = PARAM_USER_VALUE_fmt % keymatch.group(1)
|
||||||
|
try:
|
||||||
|
value = params[v]
|
||||||
|
except KeyError:
|
||||||
|
logger.error('Could not apply parameter %s' % key)
|
||||||
|
|
||||||
|
yield (key, value)
|
||||||
|
|
||||||
|
return dict(get_param_pairs())
|
||||||
|
|
||||||
|
|
||||||
|
def reformat_dict_keys(keymap={}, inputdict={}):
|
||||||
|
'''
|
||||||
|
Utility function for mapping one dict format to another
|
||||||
|
'''
|
||||||
|
result = {}
|
||||||
|
for key in keymap:
|
||||||
|
result[keymap[key]] = inputdict[key]
|
||||||
|
return result
|
@ -21,10 +21,10 @@ import json
|
|||||||
import os
|
import os
|
||||||
import socket
|
import socket
|
||||||
import sys
|
import sys
|
||||||
import re
|
|
||||||
import urlparse
|
import urlparse
|
||||||
import webob
|
import webob
|
||||||
from heat.api.aws import exception
|
from heat.api.aws import exception
|
||||||
|
from heat.api.aws import utils as api_utils
|
||||||
from heat.common import wsgi
|
from heat.common import wsgi
|
||||||
from heat.common import config
|
from heat.common import config
|
||||||
from heat.common import context
|
from heat.common import context
|
||||||
@ -62,63 +62,6 @@ class StackController(object):
|
|||||||
str(resp['StackId'])])
|
str(resp['StackId'])])
|
||||||
return resp
|
return resp
|
||||||
|
|
||||||
def _format_response(self, action, response):
|
|
||||||
"""
|
|
||||||
Format response from engine into API format
|
|
||||||
"""
|
|
||||||
return {'%sResponse' % action: {'%sResult' % action: response}}
|
|
||||||
|
|
||||||
@staticmethod
|
|
||||||
def _extract_user_params(params):
|
|
||||||
"""
|
|
||||||
Extract a dictionary of user input parameters for the stack
|
|
||||||
|
|
||||||
In the AWS API parameters, each user parameter appears as two key-value
|
|
||||||
pairs with keys of the form below:
|
|
||||||
|
|
||||||
Parameters.member.1.ParameterKey
|
|
||||||
Parameters.member.1.ParameterValue
|
|
||||||
|
|
||||||
We reformat this into a normal dict here to match the heat
|
|
||||||
engine API expected format
|
|
||||||
|
|
||||||
Note this implemented outside of "create" as it will also be
|
|
||||||
used by update (and EstimateTemplateCost if appropriate..)
|
|
||||||
"""
|
|
||||||
# Define the AWS key format to extract
|
|
||||||
PARAM_KEYS = (
|
|
||||||
PARAM_USER_KEY_re,
|
|
||||||
PARAM_USER_VALUE_fmt,
|
|
||||||
) = (
|
|
||||||
re.compile(r'Parameters\.member\.(.*?)\.ParameterKey$'),
|
|
||||||
'Parameters.member.%s.ParameterValue',
|
|
||||||
)
|
|
||||||
|
|
||||||
def get_param_pairs():
|
|
||||||
for k in params:
|
|
||||||
keymatch = PARAM_USER_KEY_re.match(k)
|
|
||||||
if keymatch:
|
|
||||||
key = params[k]
|
|
||||||
v = PARAM_USER_VALUE_fmt % keymatch.group(1)
|
|
||||||
try:
|
|
||||||
value = params[v]
|
|
||||||
except KeyError:
|
|
||||||
logger.error('Could not apply parameter %s' % key)
|
|
||||||
|
|
||||||
yield (key, value)
|
|
||||||
|
|
||||||
return dict(get_param_pairs())
|
|
||||||
|
|
||||||
@staticmethod
|
|
||||||
def _reformat_dict_keys(keymap={}, inputdict={}):
|
|
||||||
'''
|
|
||||||
Utility function for mapping one dict format to another
|
|
||||||
'''
|
|
||||||
result = {}
|
|
||||||
for key in keymap:
|
|
||||||
result[keymap[key]] = inputdict[key]
|
|
||||||
return result
|
|
||||||
|
|
||||||
def list(self, req):
|
def list(self, req):
|
||||||
"""
|
"""
|
||||||
Implements ListStacks API action
|
Implements ListStacks API action
|
||||||
@ -140,7 +83,7 @@ class StackController(object):
|
|||||||
engine_api.STACK_TMPL_DESCRIPTION: 'TemplateDescription',
|
engine_api.STACK_TMPL_DESCRIPTION: 'TemplateDescription',
|
||||||
}
|
}
|
||||||
|
|
||||||
result = self._reformat_dict_keys(keymap, s)
|
result = api_utils.reformat_dict_keys(keymap, s)
|
||||||
|
|
||||||
# AWS docs indicate DeletionTime is ommitted for current stacks
|
# AWS docs indicate DeletionTime is ommitted for current stacks
|
||||||
# This is still TODO in the engine, we don't keep data for
|
# This is still TODO in the engine, we don't keep data for
|
||||||
@ -165,7 +108,7 @@ class StackController(object):
|
|||||||
res = {'StackSummaries': [format_stack_summary(s)
|
res = {'StackSummaries': [format_stack_summary(s)
|
||||||
for s in stack_list['stacks']]}
|
for s in stack_list['stacks']]}
|
||||||
|
|
||||||
return self._format_response('ListStacks', res)
|
return api_utils.format_response('ListStacks', res)
|
||||||
|
|
||||||
def describe(self, req):
|
def describe(self, req):
|
||||||
"""
|
"""
|
||||||
@ -179,7 +122,7 @@ class StackController(object):
|
|||||||
engine_api.OUTPUT_VALUE: 'OutputValue',
|
engine_api.OUTPUT_VALUE: 'OutputValue',
|
||||||
}
|
}
|
||||||
|
|
||||||
return self._reformat_dict_keys(keymap, o)
|
return api_utils.reformat_dict_keys(keymap, o)
|
||||||
|
|
||||||
def format_stack(s):
|
def format_stack(s):
|
||||||
"""
|
"""
|
||||||
@ -200,7 +143,7 @@ class StackController(object):
|
|||||||
engine_api.STACK_TIMEOUT: 'TimeoutInMinutes',
|
engine_api.STACK_TIMEOUT: 'TimeoutInMinutes',
|
||||||
}
|
}
|
||||||
|
|
||||||
result = self._reformat_dict_keys(keymap, s)
|
result = api_utils.reformat_dict_keys(keymap, s)
|
||||||
|
|
||||||
# Reformat outputs, these are handled separately as they are
|
# Reformat outputs, these are handled separately as they are
|
||||||
# only present in the engine output for a completely created
|
# only present in the engine output for a completely created
|
||||||
@ -239,7 +182,7 @@ class StackController(object):
|
|||||||
|
|
||||||
res = {'Stacks': [format_stack(s) for s in stack_list['stacks']]}
|
res = {'Stacks': [format_stack(s) for s in stack_list['stacks']]}
|
||||||
|
|
||||||
return self._format_response('DescribeStacks', res)
|
return api_utils.format_response('DescribeStacks', res)
|
||||||
|
|
||||||
def _get_template(self, req):
|
def _get_template(self, req):
|
||||||
"""
|
"""
|
||||||
@ -310,7 +253,7 @@ class StackController(object):
|
|||||||
con = req.context
|
con = req.context
|
||||||
|
|
||||||
# Extract the stack input parameters
|
# Extract the stack input parameters
|
||||||
stack_parms = self._extract_user_params(req.params)
|
stack_parms = api_utils.extract_user_params(req.params)
|
||||||
|
|
||||||
# Extract any additional arguments ("Request Parameters")
|
# Extract any additional arguments ("Request Parameters")
|
||||||
create_args = extract_args(req.params)
|
create_args = extract_args(req.params)
|
||||||
@ -340,7 +283,7 @@ class StackController(object):
|
|||||||
except rpc_common.RemoteError as ex:
|
except rpc_common.RemoteError as ex:
|
||||||
return exception.map_remote_error(ex)
|
return exception.map_remote_error(ex)
|
||||||
|
|
||||||
return self._format_response(action, self._stackid_addprefix(res))
|
return api_utils.format_response(action, self._stackid_addprefix(res))
|
||||||
|
|
||||||
def get_template(self, req):
|
def get_template(self, req):
|
||||||
"""
|
"""
|
||||||
@ -363,14 +306,15 @@ class StackController(object):
|
|||||||
msg = _('stack not not found')
|
msg = _('stack not not found')
|
||||||
return exception.HeatInvalidParameterValueError(detail=msg)
|
return exception.HeatInvalidParameterValueError(detail=msg)
|
||||||
|
|
||||||
return self._format_response('GetTemplate', {'TemplateBody': templ})
|
return api_utils.format_response('GetTemplate',
|
||||||
|
{'TemplateBody': templ})
|
||||||
|
|
||||||
def estimate_template_cost(self, req):
|
def estimate_template_cost(self, req):
|
||||||
"""
|
"""
|
||||||
Implements the EstimateTemplateCost API action
|
Implements the EstimateTemplateCost API action
|
||||||
Get the estimated monthly cost of a template
|
Get the estimated monthly cost of a template
|
||||||
"""
|
"""
|
||||||
return self._format_response('EstimateTemplateCost',
|
return api_utils.format_response('EstimateTemplateCost',
|
||||||
{'Url': 'http://en.wikipedia.org/wiki/Gratis'})
|
{'Url': 'http://en.wikipedia.org/wiki/Gratis'})
|
||||||
|
|
||||||
def validate_template(self, req):
|
def validate_template(self, req):
|
||||||
@ -423,9 +367,9 @@ class StackController(object):
|
|||||||
return exception.map_remote_error(ex)
|
return exception.map_remote_error(ex)
|
||||||
|
|
||||||
if res is None:
|
if res is None:
|
||||||
return self._format_response('DeleteStack', '')
|
return api_utils.format_response('DeleteStack', '')
|
||||||
else:
|
else:
|
||||||
return self._format_response('DeleteStack', res['Error'])
|
return api_utils.format_response('DeleteStack', res['Error'])
|
||||||
|
|
||||||
def events_list(self, req):
|
def events_list(self, req):
|
||||||
"""
|
"""
|
||||||
@ -449,7 +393,7 @@ class StackController(object):
|
|||||||
engine_api.EVENT_TIMESTAMP: 'Timestamp',
|
engine_api.EVENT_TIMESTAMP: 'Timestamp',
|
||||||
}
|
}
|
||||||
|
|
||||||
result = self._reformat_dict_keys(keymap, e)
|
result = api_utils.reformat_dict_keys(keymap, e)
|
||||||
|
|
||||||
return self._stackid_addprefix(result)
|
return self._stackid_addprefix(result)
|
||||||
|
|
||||||
@ -468,7 +412,7 @@ class StackController(object):
|
|||||||
|
|
||||||
result = [format_stack_event(e) for e in events]
|
result = [format_stack_event(e) for e in events]
|
||||||
|
|
||||||
return self._format_response('DescribeStackEvents',
|
return api_utils.format_response('DescribeStackEvents',
|
||||||
{'StackEvents': result})
|
{'StackEvents': result})
|
||||||
|
|
||||||
def describe_stack_resource(self, req):
|
def describe_stack_resource(self, req):
|
||||||
@ -494,7 +438,7 @@ class StackController(object):
|
|||||||
engine_api.RES_STACK_NAME: 'StackName',
|
engine_api.RES_STACK_NAME: 'StackName',
|
||||||
}
|
}
|
||||||
|
|
||||||
result = self._reformat_dict_keys(keymap, r)
|
result = api_utils.reformat_dict_keys(keymap, r)
|
||||||
|
|
||||||
return self._stackid_addprefix(result)
|
return self._stackid_addprefix(result)
|
||||||
|
|
||||||
@ -510,7 +454,7 @@ class StackController(object):
|
|||||||
|
|
||||||
result = format_resource_detail(resource_details)
|
result = format_resource_detail(resource_details)
|
||||||
|
|
||||||
return self._format_response('DescribeStackResource',
|
return api_utils.format_response('DescribeStackResource',
|
||||||
{'StackResourceDetail': result})
|
{'StackResourceDetail': result})
|
||||||
|
|
||||||
def describe_stack_resources(self, req):
|
def describe_stack_resources(self, req):
|
||||||
@ -546,7 +490,7 @@ class StackController(object):
|
|||||||
engine_api.RES_UPDATED_TIME: 'Timestamp',
|
engine_api.RES_UPDATED_TIME: 'Timestamp',
|
||||||
}
|
}
|
||||||
|
|
||||||
result = self._reformat_dict_keys(keymap, r)
|
result = api_utils.reformat_dict_keys(keymap, r)
|
||||||
|
|
||||||
return self._stackid_addprefix(result)
|
return self._stackid_addprefix(result)
|
||||||
|
|
||||||
@ -568,7 +512,7 @@ class StackController(object):
|
|||||||
|
|
||||||
result = [format_stack_resource(r) for r in resources]
|
result = [format_stack_resource(r) for r in resources]
|
||||||
|
|
||||||
return self._format_response('DescribeStackResources',
|
return api_utils.format_response('DescribeStackResources',
|
||||||
{'StackResources': result})
|
{'StackResources': result})
|
||||||
|
|
||||||
def list_stack_resources(self, req):
|
def list_stack_resources(self, req):
|
||||||
@ -589,7 +533,7 @@ class StackController(object):
|
|||||||
engine_api.RES_TYPE: 'ResourceType',
|
engine_api.RES_TYPE: 'ResourceType',
|
||||||
}
|
}
|
||||||
|
|
||||||
return self._reformat_dict_keys(keymap, r)
|
return api_utils.reformat_dict_keys(keymap, r)
|
||||||
|
|
||||||
con = req.context
|
con = req.context
|
||||||
|
|
||||||
@ -601,7 +545,7 @@ class StackController(object):
|
|||||||
|
|
||||||
summaries = [format_resource_summary(r) for r in resources]
|
summaries = [format_resource_summary(r) for r in resources]
|
||||||
|
|
||||||
return self._format_response('ListStackResources',
|
return api_utils.format_response('ListStackResources',
|
||||||
{'StackResourceSummaries': summaries})
|
{'StackResourceSummaries': summaries})
|
||||||
|
|
||||||
|
|
||||||
|
101
heat/tests/test_api_aws.py
Normal file
101
heat/tests/test_api_aws.py
Normal file
@ -0,0 +1,101 @@
|
|||||||
|
# vim: tabstop=4 shiftwidth=4 softtabstop=4
|
||||||
|
|
||||||
|
# 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 sys
|
||||||
|
import socket
|
||||||
|
import nose
|
||||||
|
import json
|
||||||
|
import unittest
|
||||||
|
from nose.plugins.attrib import attr
|
||||||
|
|
||||||
|
import re
|
||||||
|
from heat.api.aws import utils as api_utils
|
||||||
|
|
||||||
|
|
||||||
|
@attr(tag=['unit', 'api-aws', 'AWSCommon'])
|
||||||
|
@attr(speed='fast')
|
||||||
|
class AWSCommon(unittest.TestCase):
|
||||||
|
'''
|
||||||
|
Tests the api/aws common componenents
|
||||||
|
'''
|
||||||
|
# The tests
|
||||||
|
def test_format_response(self):
|
||||||
|
response = api_utils.format_response("Foo", "Bar")
|
||||||
|
expected = {'FooResponse': {'FooResult': 'Bar'}}
|
||||||
|
self.assert_(response == expected)
|
||||||
|
|
||||||
|
def test_params_extract(self):
|
||||||
|
p = {'Parameters.member.Foo.ParameterKey': 'foo',
|
||||||
|
'Parameters.member.Foo.ParameterValue': 'bar',
|
||||||
|
'Parameters.member.Blarg.ParameterKey': 'blarg',
|
||||||
|
'Parameters.member.Blarg.ParameterValue': 'wibble'}
|
||||||
|
params = api_utils.extract_user_params(p)
|
||||||
|
self.assertEqual(len(params), 2)
|
||||||
|
self.assertTrue('foo' in params)
|
||||||
|
self.assertEqual(params['foo'], 'bar')
|
||||||
|
self.assertTrue('blarg' in params)
|
||||||
|
self.assertEqual(params['blarg'], 'wibble')
|
||||||
|
|
||||||
|
def test_params_extract_dots(self):
|
||||||
|
p = {'Parameters.member.Foo.Bar.ParameterKey': 'foo',
|
||||||
|
'Parameters.member.Foo.Bar.ParameterValue': 'bar',
|
||||||
|
'Parameters.member.Foo.Baz.ParameterKey': 'blarg',
|
||||||
|
'Parameters.member.Foo.Baz.ParameterValue': 'wibble'}
|
||||||
|
params = api_utils.extract_user_params(p)
|
||||||
|
self.assertEqual(len(params), 2)
|
||||||
|
self.assertTrue('foo' in params)
|
||||||
|
self.assertEqual(params['foo'], 'bar')
|
||||||
|
self.assertTrue('blarg' in params)
|
||||||
|
self.assertEqual(params['blarg'], 'wibble')
|
||||||
|
|
||||||
|
def test_params_extract_garbage(self):
|
||||||
|
p = {'Parameters.member.Foo.Bar.ParameterKey': 'foo',
|
||||||
|
'Parameters.member.Foo.Bar.ParameterValue': 'bar',
|
||||||
|
'Foo.Baz.ParameterKey': 'blarg',
|
||||||
|
'Foo.Baz.ParameterValue': 'wibble'}
|
||||||
|
params = api_utils.extract_user_params(p)
|
||||||
|
self.assertEqual(len(params), 1)
|
||||||
|
self.assertTrue('foo' in params)
|
||||||
|
self.assertEqual(params['foo'], 'bar')
|
||||||
|
|
||||||
|
def test_params_extract_garbage_prefix(self):
|
||||||
|
p = {'prefixParameters.member.Foo.Bar.ParameterKey': 'foo',
|
||||||
|
'Parameters.member.Foo.Bar.ParameterValue': 'bar'}
|
||||||
|
params = api_utils.extract_user_params(p)
|
||||||
|
self.assertFalse(params)
|
||||||
|
|
||||||
|
def test_params_extract_garbage_suffix(self):
|
||||||
|
p = {'Parameters.member.Foo.Bar.ParameterKeysuffix': 'foo',
|
||||||
|
'Parameters.member.Foo.Bar.ParameterValue': 'bar'}
|
||||||
|
params = api_utils.extract_user_params(p)
|
||||||
|
self.assertFalse(params)
|
||||||
|
|
||||||
|
def test_reformat_dict_keys(self):
|
||||||
|
keymap = {"foo": "bar"}
|
||||||
|
data = {"foo": 123}
|
||||||
|
expected = {"bar": 123}
|
||||||
|
result = api_utils.reformat_dict_keys(keymap, data)
|
||||||
|
self.assertEqual(result, expected)
|
||||||
|
|
||||||
|
def setUp(self):
|
||||||
|
print "setup complete"
|
||||||
|
|
||||||
|
def tearDown(self):
|
||||||
|
print "teardown complete"
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
sys.argv.append(__file__)
|
||||||
|
nose.main()
|
@ -60,11 +60,6 @@ class StackControllerTest(unittest.TestCase):
|
|||||||
return req
|
return req
|
||||||
|
|
||||||
# The tests
|
# The tests
|
||||||
def test_format_response(self):
|
|
||||||
response = self.controller._format_response("Foo", "Bar")
|
|
||||||
expected = {'FooResponse': {'FooResult': 'Bar'}}
|
|
||||||
self.assert_(response == expected)
|
|
||||||
|
|
||||||
def test_stackid_addprefix(self):
|
def test_stackid_addprefix(self):
|
||||||
|
|
||||||
# Stub socket.gethostname so it returns "ahostname"
|
# Stub socket.gethostname so it returns "ahostname"
|
||||||
@ -79,59 +74,6 @@ class StackControllerTest(unittest.TestCase):
|
|||||||
'StackId': 'ahostname:8000:stack/Foo/123'}
|
'StackId': 'ahostname:8000:stack/Foo/123'}
|
||||||
self.assert_(response == expected)
|
self.assert_(response == expected)
|
||||||
|
|
||||||
def test_params_extract(self):
|
|
||||||
p = {'Parameters.member.Foo.ParameterKey': 'foo',
|
|
||||||
'Parameters.member.Foo.ParameterValue': 'bar',
|
|
||||||
'Parameters.member.Blarg.ParameterKey': 'blarg',
|
|
||||||
'Parameters.member.Blarg.ParameterValue': 'wibble'}
|
|
||||||
params = self.controller._extract_user_params(p)
|
|
||||||
self.assertEqual(len(params), 2)
|
|
||||||
self.assertTrue('foo' in params)
|
|
||||||
self.assertEqual(params['foo'], 'bar')
|
|
||||||
self.assertTrue('blarg' in params)
|
|
||||||
self.assertEqual(params['blarg'], 'wibble')
|
|
||||||
|
|
||||||
def test_params_extract_dots(self):
|
|
||||||
p = {'Parameters.member.Foo.Bar.ParameterKey': 'foo',
|
|
||||||
'Parameters.member.Foo.Bar.ParameterValue': 'bar',
|
|
||||||
'Parameters.member.Foo.Baz.ParameterKey': 'blarg',
|
|
||||||
'Parameters.member.Foo.Baz.ParameterValue': 'wibble'}
|
|
||||||
params = self.controller._extract_user_params(p)
|
|
||||||
self.assertEqual(len(params), 2)
|
|
||||||
self.assertTrue('foo' in params)
|
|
||||||
self.assertEqual(params['foo'], 'bar')
|
|
||||||
self.assertTrue('blarg' in params)
|
|
||||||
self.assertEqual(params['blarg'], 'wibble')
|
|
||||||
|
|
||||||
def test_params_extract_garbage(self):
|
|
||||||
p = {'Parameters.member.Foo.Bar.ParameterKey': 'foo',
|
|
||||||
'Parameters.member.Foo.Bar.ParameterValue': 'bar',
|
|
||||||
'Foo.Baz.ParameterKey': 'blarg',
|
|
||||||
'Foo.Baz.ParameterValue': 'wibble'}
|
|
||||||
params = self.controller._extract_user_params(p)
|
|
||||||
self.assertEqual(len(params), 1)
|
|
||||||
self.assertTrue('foo' in params)
|
|
||||||
self.assertEqual(params['foo'], 'bar')
|
|
||||||
|
|
||||||
def test_params_extract_garbage_prefix(self):
|
|
||||||
p = {'prefixParameters.member.Foo.Bar.ParameterKey': 'foo',
|
|
||||||
'Parameters.member.Foo.Bar.ParameterValue': 'bar'}
|
|
||||||
params = self.controller._extract_user_params(p)
|
|
||||||
self.assertFalse(params)
|
|
||||||
|
|
||||||
def test_params_extract_garbage_suffix(self):
|
|
||||||
p = {'Parameters.member.Foo.Bar.ParameterKeysuffix': 'foo',
|
|
||||||
'Parameters.member.Foo.Bar.ParameterValue': 'bar'}
|
|
||||||
params = self.controller._extract_user_params(p)
|
|
||||||
self.assertFalse(params)
|
|
||||||
|
|
||||||
def test_reformat_dict_keys(self):
|
|
||||||
keymap = {"foo": "bar"}
|
|
||||||
data = {"foo": 123}
|
|
||||||
expected = {"bar": 123}
|
|
||||||
result = self.controller._reformat_dict_keys(keymap, data)
|
|
||||||
self.assertEqual(result, expected)
|
|
||||||
|
|
||||||
def test_list(self):
|
def test_list(self):
|
||||||
# Format a dummy GET request to pass into the WSGI handler
|
# Format a dummy GET request to pass into the WSGI handler
|
||||||
params = {'Action': 'ListStacks'}
|
params = {'Action': 'ListStacks'}
|
||||||
|
Loading…
Reference in New Issue
Block a user