Hey Karl, you can do that too, I made this filter earlier, and with
your example you would pass almost the same values as you have there:
foo.bar: '1'
foo.bar: '2'
foo.bar: '3'
baz : '4'
result = { 'foo' : {'bar' : ['1', '2', '3']}, 'baz' : '4'} }
Although I'm not as sure as to how you would make a validation schema
for that as easily, but once again it will be easy to access the values
in javascript with a documents.my_form['foo.bar'][0], [1], [2], etc.
### Code below
##############
class BuildTreeFilter(BaseFilter):
"""
Will build a tree for request params with periods in the name,
for an example look at _buildTree().
"""
def beforeMain(self):
cherrypy.request.paramMap =
self._buildTree(cherrypy.request.paramMap)
def _buildTree(self, oldDict):
"""
Given a dictionary with keys like 'foo.bar.joo', this will
return a new tree
with a key of foo = { 'bar': {'joo' : oldValue}}, for every
key.
Example:
>>> print _buildTree({'company': 'Unexistential Inc',
'names.firstName': ['Joe', 'Boe', 'Moe'],
'names.lastName': ['Smith', 'Myth',
'Keith'],
'phone': '555-8980'})
>>> {'company': 'Unexistential Inc',
'names': {'firstName': ['Joe', 'Boe', 'Moe'],
'lastName': ['Smith', 'Myth', 'Keith']},
'phone': '555-8980'}
"""
stack = []
y = {}
for key, value in oldDict.iteritems():
splitList = key.split(".", 1)
if len(splitList) > 1: #there was a period in the key
firstLevel = splitList[0]
secondLevel = splitList[1]
firstValue = y.get(firstLevel)
if firstValue:
if type(firstValue) != dict:
y[firstLevel] = {}
y[firstLevel].update({secondLevel : value})
else:
y[firstLevel] = {secondLevel : value}
stack.append( firstLevel ) #add to stack only once
else:
y[key] = value
for i in iter(stack):
y[i] = self._buildTree( y[i] )
return y