3

How can I send lists/arrays in POST forms and get them decoded with Colander? I've tried in several ways but no luck so far. Using a form and Colander schema like the following will throw the error: [1,2,3] is not iterable

example_1.html:

<form action="path_to_page" method="post">
  <input name="ids" type="text" value="[1,2,3]">
  <input type="submit">
</form>

example_1.py:

class IDList(colander.List):
    item = colander.SchemaNode(colander.Integer())

class IDS(colander.MappingSchema):
    ids = colander.SchemaNode(IDList())

And this other approach simply won't work because we cannot create a Colander node called ids[].

example_2.html:

<form action="path_to_page" method="post">
  <input name="ids[]" type="text" value="1">
  <input name="ids[]" type="text" value="2">
  <input name="ids[]" type="text" value="3">
  <input type="submit">
</form>

Is there a way to get this done?

Ander
  • 5,093
  • 7
  • 41
  • 70

1 Answers1

3

Note: I have updated this answer with a generalized solution.

In order to parse a URI string into a usable list for Colander to deserialize, you can create a new class which inherit's Colander's SquenceSchema and overrides the corresponding deserialize method to split your comma seperated string into a Python list:

class URISequenceSchema(SequenceSchema):
    def deserialize(self, cstruct):
        if cstruct:
            cstruct = cstruct.split(',')
        return super(URISequenceSchema, self).deserialize(cstruct)

You can then use this new class to create a SequenceSchema of any type, just as you would with a normal Colander SequenceSchema:

FooSequence(URISequenceSchema):
    foo = SchemaNode(Integer(), validator=Range(min=0))

This will accept a string (e.g. ?ages=23,13,42) and parse it into a python list.

Hopefully this helps anybody else who has the same problem.

Kobnar
  • 41
  • 4