Login

Easier prefix handling for forms

Author:
gsakkis
Posted:
April 17, 2010
Language:
Python
Version:
1.1
Score:
0 (after 0 ratings)

autoprefixed is a decorator for Form classes that simplifies prefix handling by storing it in a hidden field. Thus when the form is posted, the prefix can be extracted from the posted data instead of having to pass it explicitly when instantiating the form.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
from django.forms import BaseForm, Field, HiddenInput


class AutoPrefixedForm(BaseForm):
    '''A Form type that handles prefixes transparently.

    If a (non empty) prefix is passed, forms of this class have a hidden field
    named ``self.PREFIX_FIELD_NAME`` (by default "``PREFIX``") and value the prefix.
    Additionally, bound forms probe the passed data for this hidden field and set
    the prefix to it if found (and no prefix was passed explicitly at initialization).
    '''
    PREFIX_FIELD_NAME = 'PREFIX'

    def __init__(self, *args, **kwargs):
        super(AutoPrefixedForm, self).__init__(*args, **kwargs)
        if not self.prefix and self.data:
            self.prefix = self.data.get(self.PREFIX_FIELD_NAME)
        if self.prefix:
            self.fields[self.PREFIX_FIELD_NAME] = Field(widget=HiddenInput,
                                                        initial=self.prefix)

    def add_prefix(self, field_name):
        if field_name == self.PREFIX_FIELD_NAME:
            return field_name
        return super(AutoPrefixedForm,self).add_prefix(field_name)


def autoprefixed(field_name=AutoPrefixedForm.PREFIX_FIELD_NAME):
    '''Decorates a Form class so that it handles prefixes transparently, as if
    subclassing :class:`AutoPrefixedForm`.

    Usage::

        @autoprefixed
        class MyForm(forms.Form):
            ...

        or

        @autoprefixed(field_name='__prefix__')
        class MyForm(forms.Form):
            ...
    '''
    if isinstance(field_name, type):
        return autoprefixed()(field_name)
    def decorator(cls):
        if not issubclass(cls, AutoPrefixedForm):
            cls.__bases__ = (AutoPrefixedForm,) + cls.__bases__
        cls.PREFIX_FIELD_NAME = field_name
        return cls
    return decorator


#==== usage ===================

@autoprefixed
class ContactForm(forms.Form):
    subject = forms.CharField(max_length=100)
    message = forms.CharField()
    sender = forms.EmailField()
    cc_myself = forms.BooleanField(required=False)

f = ContactForm(prefix='bugform')
print f.fields.keys()   # ['subject', 'message', 'sender', 'cc_myself', 'PREFIX']

post_data = {
    'bugform-subject': 'hello',
    'bugform-message': 'Hi there',
    'bugform-sender': '[email protected]',
    'bugform-cc_myself': True,
    'PREFIX': 'bugform',
}
# don't need to pass 'prefix'
f = ContactForm(post_data)

print f.prefix        # 'bugform'
print f.is_valid()    # True
print f.cleaned_data  # {'PREFIX': 'bugform', 'cc_myself': True, 'message': u'Hi there',
                      #  'sender': u'[email protected]', 'subject': u'hello'}

More like this

  1. Template tag - list punctuation for a list of items by shapiromatron 10 months, 2 weeks ago
  2. JSONRequestMiddleware adds a .json() method to your HttpRequests by cdcarter 10 months, 3 weeks ago
  3. Serializer factory with Django Rest Framework by julio 1 year, 5 months ago
  4. Image compression before saving the new model / work with JPG, PNG by Schleidens 1 year, 6 months ago
  5. Help text hyperlinks by sa2812 1 year, 6 months ago

Comments

Please login first before commenting.