Source code for uw.web.wsgi.form

"""HTML form result handling.

Routines for easily creating WSGI handlers which handle HTML form results.
"""

from operator import attrgetter

from .delegate import DelegateHandler
from .parameter import get_form_fields as delegate_get_form_fields, ParamHandler

[docs]class CGIFormResults (dict): """A representation of the form results component of a CGI request. :param cgi.FieldStorage cgi_fields: The values to be inserted into this form results dictionary. """ def __init__ (self, cgi_fields): super (CGIFormResults, self).__init__ () if cgi_fields.list is not None: for item in cgi_fields.list: if item.name not in self: self[item.name] = [] self[item.name].append (item) def __missing__ (self, name): return []
[docs] def optional_field (self, name): """Obtain an optional field from the CGI results. :param name: the name of the field. Return the single result for the named field, or None if there are none. If there are multiple results, an exception will be raised. """ if name in self: (result,) = self[name] return result else: return None
[docs] def optional_field_value (self, name): """Obtain an optional field value from the CGI results. :param name: the name of the field. Return the value of the single result for the named field, or None if there are none. If there are multiple results, an exception will be raised. """ result = self.optional_field (name) return None if result is None else result.value
[docs] def required_field (self, name): """Obtain a required field from the CGI results. :param name: the name of the field. Return the single result for the named field, or raise an exception if there are none. If there are multiple results, an exception will be raised. """ (result,) = self[name] return result
[docs] def required_field_value (self, name): """Obtain a required field value from the CGI results. :param name: the name of the field. Return the value of the single result for the named field, or raise an exception if there are none. If there are multiple results, an exception will be raised. """ return self.required_field (name).value
[docs] def multiple_field (self, name): """Obtain a multiple field from the CGI results. :param name: the name of the field. Return a list of all results for the named field. """ return self[name]
[docs] def multiple_field_value (self, name): """Obtain multiple field values from the CGI results. :param name: the name of the field. Return a list of the values of all the results for the named field. """ return list(map (attrgetter ('value'), self.multiple_field (name)))
[docs]def get_form_fields (environ): """Extract submitted HTML form results from the WSGI environment. :param environ: the WSGI environment. Builds a CGIFormResults from the wsgi.input environment entry. """ return CGIFormResults (delegate_get_form_fields (environ))
[docs]def use_form_param (handler): """Wrap a hander; extract form variable values as a parameter. Returns a handler which constructs a CGIFormResults dictionary and save it in the 'form' parameter before chaining to the provided handler. """ return ParamHandler (handler, 'form', get_form_fields)
[docs]def parse_form_value (value, parser): """Parse a form value in a way that is usually appropriate. :param value: the string value, typically obtained from the form results. :param parser: the parser to convert a non-empty string into a typed result. The value may be None or a string. If it is None or a blank string then None is returned. Otherwise the value, stripped of leading and trailing whitespace, is passed to the parser and the result returned. Typically parsers include the standard float and int functions. """ if value is None: return None value = value.strip () if not value: return None return parser (value)
#def delegate_field (name, main_handler, value_handler): # def delegate_field_handler (form, **params): # if form.has_key (name): # return value_handler ... # else: # return main_handler ... # return delegate_field_handler
[docs]class DelegateField (DelegateHandler): """Delegate to an inner handler based on a CGI field value. :param page_handler: The handler for requests with none of the specified fields present. :param get_form_handler(\*\*field_values): The handler for requests with the given values for the specified fields. :param fields: A dictionary from field names to the procedure to use to extract the field value from the CGIFormResults form value. Typical values include CGIFormResults.optional_field_value and friends. """ def __init__ (self, page_handler, get_form_handler, fields): self.__page_handler = page_handler self.__get_form_handler = get_form_handler self.__fields = fields @property def page_handler (self): return self.__page_handler @property def get_form_handler (self): return self.__get_form_handler @property def fields (self): return self.__fields
[docs] def get_handler (self, environ): """Get the handler which will be used to handle the specified request. """ form = get_params (environ)['form'] field_values = {} for name, field in self.fields.entries (): field_values[name] = field.get_field (form, name) return self.get_form_handler (**field_values)
#def make_form_handler (parse_form, render_form, action): # def get_handler (): # form_value = parse_form (form) # return title, render_form (form_value) # # def post_handler (): # form_value = parse_form (form) # try: # result = action (form_value) # return title, result # except FormActionError, x: # return title, [x.format (), render_form (form_value)] # # return delegate_get_post (get_handler, post_handler)