-
Notifications
You must be signed in to change notification settings - Fork 73
Expand file tree
/
Copy pathformencode.schema.html
More file actions
492 lines (491 loc) · 51.1 KB
/
formencode.schema.html
File metadata and controls
492 lines (491 loc) · 51.1 KB
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
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
<html>
<head>
<title>formencode.schema</title>
</head>
<body>
formencode.schema
<style>
.coverage pre {float: left; margin: 0px 1em; border: none;
padding: 0px; }
.num pre { margin: 0px }
.nocov, .nocov pre {background-color: #faa}
.cov, .cov pre {background-color: #cfc}
div.coverage div { clear: both; height: 1.1em}
</style>
<div class="stats">
Covered: 133 lines<br/>
Missed: 236 lines<br/>
Skipped 98 lines<br/>
Percent: 36 %<br/>
</div>
<div class="coverage">
<div class="nocov"><span class="num"><pre> 1</pre></span><pre>from interfaces import *</pre></div>
<div class="nocov"><span class="num"><pre> 2</pre></span><pre>from api import *</pre></div>
<div class="nocov"><span class="num"><pre> 3</pre></span><pre>from api import _</pre></div>
<div class="nocov"><span class="num"><pre> 4</pre></span><pre>import declarative</pre></div>
<div class="skip"><span class="num"><pre> 5</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre> 6</pre></span><pre>__all__ = ['Schema']</pre></div>
<div class="skip"><span class="num"><pre> 7</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre> 8</pre></span><pre>class Schema(FancyValidator):</pre></div>
<div class="skip"><span class="num"><pre> 9</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre> 10</pre></span><pre> """</pre></div>
<div class="nocov"><span class="num"><pre> 11</pre></span><pre> A schema validates a dictionary of values, applying different</pre></div>
<div class="nocov"><span class="num"><pre> 12</pre></span><pre> validators (be key) to the different values. If</pre></div>
<div class="nocov"><span class="num"><pre> 13</pre></span><pre> allow_extra_fields=True, keys without validators will be allowed;</pre></div>
<div class="nocov"><span class="num"><pre> 14</pre></span><pre> otherwise they will raise Invalid. If filter_extra_fields is</pre></div>
<div class="nocov"><span class="num"><pre> 15</pre></span><pre> set to true, then extra fields are not passed back in the results.</pre></div>
<div class="skip"><span class="num"><pre> 16</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre> 17</pre></span><pre> Validators are associated with keys either with a class syntax, or</pre></div>
<div class="nocov"><span class="num"><pre> 18</pre></span><pre> as keyword arguments (class syntax is usually easier). Something</pre></div>
<div class="nocov"><span class="num"><pre> 19</pre></span><pre> like::</pre></div>
<div class="skip"><span class="num"><pre> 20</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre> 21</pre></span><pre> class MySchema(Schema):</pre></div>
<div class="nocov"><span class="num"><pre> 22</pre></span><pre> name = Validators.PlainText()</pre></div>
<div class="nocov"><span class="num"><pre> 23</pre></span><pre> phone = Validators.PhoneNumber()</pre></div>
<div class="skip"><span class="num"><pre> 24</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre> 25</pre></span><pre> These will not be available as actual instance variables, but will</pre></div>
<div class="nocov"><span class="num"><pre> 26</pre></span><pre> be collected in a dictionary. To remove a validator in a subclass</pre></div>
<div class="nocov"><span class="num"><pre> 27</pre></span><pre> that is present in a superclass, set it to None, like::</pre></div>
<div class="skip"><span class="num"><pre> 28</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre> 29</pre></span><pre> class MySubSchema(MySchema):</pre></div>
<div class="nocov"><span class="num"><pre> 30</pre></span><pre> name = None</pre></div>
<div class="skip"><span class="num"><pre> 31</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre> 32</pre></span><pre> Note that missing fields are handled at the Schema level. Missing</pre></div>
<div class="nocov"><span class="num"><pre> 33</pre></span><pre> fields can have the 'missing' message set to specify the error</pre></div>
<div class="nocov"><span class="num"><pre> 34</pre></span><pre> message, or if that does not exist the *schema* message</pre></div>
<div class="nocov"><span class="num"><pre> 35</pre></span><pre> 'missingValue' is used.</pre></div>
<div class="nocov"><span class="num"><pre> 36</pre></span><pre> """</pre></div>
<div class="skip"><span class="num"><pre> 37</pre></span><pre></pre></div>
<div class="skip"><span class="num"><pre> 38</pre></span><pre> # These validators will be applied before this schema:</pre></div>
<div class="nocov"><span class="num"><pre> 39</pre></span><pre> pre_validators = []</pre></div>
<div class="skip"><span class="num"><pre> 40</pre></span><pre> # These validators will be applied after this schema:</pre></div>
<div class="nocov"><span class="num"><pre> 41</pre></span><pre> chained_validators = []</pre></div>
<div class="skip"><span class="num"><pre> 42</pre></span><pre> # If true, then it is not an error when keys that aren't</pre></div>
<div class="skip"><span class="num"><pre> 43</pre></span><pre> # associated with a validator are present:</pre></div>
<div class="nocov"><span class="num"><pre> 44</pre></span><pre> allow_extra_fields = False</pre></div>
<div class="skip"><span class="num"><pre> 45</pre></span><pre> # If true, then keys that aren't associated with a validator</pre></div>
<div class="skip"><span class="num"><pre> 46</pre></span><pre> # are removed:</pre></div>
<div class="nocov"><span class="num"><pre> 47</pre></span><pre> filter_extra_fields = False</pre></div>
<div class="skip"><span class="num"><pre> 48</pre></span><pre> # If this is given, then any keys that aren't available but</pre></div>
<div class="skip"><span class="num"><pre> 49</pre></span><pre> # are expected will be replaced with this value (and then</pre></div>
<div class="skip"><span class="num"><pre> 50</pre></span><pre> # validated!) This does not override a present .if_missing</pre></div>
<div class="skip"><span class="num"><pre> 51</pre></span><pre> # attribute on validators:</pre></div>
<div class="nocov"><span class="num"><pre> 52</pre></span><pre> if_key_missing = NoDefault</pre></div>
<div class="skip"><span class="num"><pre> 53</pre></span><pre> # If true, then missing keys will be missing in the result,</pre></div>
<div class="skip"><span class="num"><pre> 54</pre></span><pre> # if the validator doesn't have if_missing on it already:</pre></div>
<div class="nocov"><span class="num"><pre> 55</pre></span><pre> ignore_key_missing = False</pre></div>
<div class="nocov"><span class="num"><pre> 56</pre></span><pre> compound = True</pre></div>
<div class="nocov"><span class="num"><pre> 57</pre></span><pre> fields = {}</pre></div>
<div class="nocov"><span class="num"><pre> 58</pre></span><pre> order = []</pre></div>
<div class="skip"><span class="num"><pre> 59</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre> 60</pre></span><pre> messages = {</pre></div>
<div class="nocov"><span class="num"><pre> 61</pre></span><pre> 'notExpected': _('The input field %(name)s was not expected.'),</pre></div>
<div class="nocov"><span class="num"><pre> 62</pre></span><pre> 'missingValue': _("Missing value"),</pre></div>
<div class="nocov"><span class="num"><pre> 63</pre></span><pre> 'badDictType': _("The input must be dict-like (not a %(type)s: %(value)r)"),</pre></div>
<div class="nocov"><span class="num"><pre> 64</pre></span><pre> }</pre></div>
<div class="skip"><span class="num"><pre> 65</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre> 66</pre></span><pre> __mutableattributes__ = ('fields', 'chained_validators',</pre></div>
<div class="nocov"><span class="num"><pre> 67</pre></span><pre> 'pre_validators')</pre></div>
<div class="skip"><span class="num"><pre> 68</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre> 69</pre></span><pre> def __classinit__(cls, new_attrs):</pre></div>
<div class="cov"><span class="num"><pre> 70</pre></span><pre> FancyValidator.__classinit__(cls, new_attrs)</pre></div>
<div class="skip"><span class="num"><pre> 71</pre></span><pre> # Don't bother doing anything if this is the most parent</pre></div>
<div class="skip"><span class="num"><pre> 72</pre></span><pre> # Schema class (which is the only class with just</pre></div>
<div class="skip"><span class="num"><pre> 73</pre></span><pre> # FancyValidator as a superclass):</pre></div>
<div class="cov"><span class="num"><pre> 74</pre></span><pre> if cls.__bases__ == (FancyValidator,):</pre></div>
<div class="nocov"><span class="num"><pre> 75</pre></span><pre> return cls</pre></div>
<div class="skip"><span class="num"><pre> 76</pre></span><pre> # Scan through the class variables we've defined *just*</pre></div>
<div class="skip"><span class="num"><pre> 77</pre></span><pre> # for this subclass, looking for validators (both classes</pre></div>
<div class="skip"><span class="num"><pre> 78</pre></span><pre> # and instances):</pre></div>
<div class="cov"><span class="num"><pre> 79</pre></span><pre> for key, value in new_attrs.items():</pre></div>
<div class="cov"><span class="num"><pre> 80</pre></span><pre> if key in ('pre_validators', 'chained_validators',</pre></div>
<div class="cov"><span class="num"><pre> 81</pre></span><pre> 'view'):</pre></div>
<div class="cov"><span class="num"><pre> 82</pre></span><pre> continue</pre></div>
<div class="cov"><span class="num"><pre> 83</pre></span><pre> if is_validator(value):</pre></div>
<div class="cov"><span class="num"><pre> 84</pre></span><pre> cls.fields[key] = value</pre></div>
<div class="cov"><span class="num"><pre> 85</pre></span><pre> delattr(cls, key)</pre></div>
<div class="skip"><span class="num"><pre> 86</pre></span><pre> # This last case means we're overwriting a validator</pre></div>
<div class="skip"><span class="num"><pre> 87</pre></span><pre> # from a superclass:</pre></div>
<div class="cov"><span class="num"><pre> 88</pre></span><pre> elif cls.fields.has_key(key):</pre></div>
<div class="nocov"><span class="num"><pre> 89</pre></span><pre> del cls.fields[key]</pre></div>
<div class="cov"><span class="num"><pre> 90</pre></span><pre> for name, value in cls.fields.items():</pre></div>
<div class="cov"><span class="num"><pre> 91</pre></span><pre> cls.add_field(name, value)</pre></div>
<div class="skip"><span class="num"><pre> 92</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre> 93</pre></span><pre> def __initargs__(self, new_attrs):</pre></div>
<div class="cov"><span class="num"><pre> 94</pre></span><pre> for key, value in new_attrs.items():</pre></div>
<div class="cov"><span class="num"><pre> 95</pre></span><pre> if key in ('pre_validators', 'chained_validators',</pre></div>
<div class="cov"><span class="num"><pre> 96</pre></span><pre> 'view'):</pre></div>
<div class="nocov"><span class="num"><pre> 97</pre></span><pre> continue</pre></div>
<div class="cov"><span class="num"><pre> 98</pre></span><pre> if is_validator(value):</pre></div>
<div class="nocov"><span class="num"><pre> 99</pre></span><pre> self.fields[key] = value</pre></div>
<div class="nocov"><span class="num"><pre>100</pre></span><pre> delattr(self, key)</pre></div>
<div class="skip"><span class="num"><pre>101</pre></span><pre> # This last case means we're overwriting a validator</pre></div>
<div class="skip"><span class="num"><pre>102</pre></span><pre> # from a superclass:</pre></div>
<div class="cov"><span class="num"><pre>103</pre></span><pre> elif self.fields.has_key(key):</pre></div>
<div class="nocov"><span class="num"><pre>104</pre></span><pre> del self.fields[key]</pre></div>
<div class="cov"><span class="num"><pre>105</pre></span><pre> for name, value in self.fields.items():</pre></div>
<div class="cov"><span class="num"><pre>106</pre></span><pre> self.add_field(name, value)</pre></div>
<div class="skip"><span class="num"><pre>107</pre></span><pre> </pre></div>
<div class="nocov"><span class="num"><pre>108</pre></span><pre> def assert_dict(self, value, state):</pre></div>
<div class="nocov"><span class="num"><pre>109</pre></span><pre> """</pre></div>
<div class="nocov"><span class="num"><pre>110</pre></span><pre> Helper to assure we have proper input</pre></div>
<div class="nocov"><span class="num"><pre>111</pre></span><pre> """</pre></div>
<div class="cov"><span class="num"><pre>112</pre></span><pre> if not hasattr(value, 'items'):</pre></div>
<div class="skip"><span class="num"><pre>113</pre></span><pre> # Not a dict or dict-like object</pre></div>
<div class="nocov"><span class="num"><pre>114</pre></span><pre> raise Invalid(self.message('badDictType', state, type=type(value), value=value),</pre></div>
<div class="nocov"><span class="num"><pre>115</pre></span><pre> value, state)</pre></div>
<div class="skip"><span class="num"><pre>116</pre></span><pre> </pre></div>
<div class="nocov"><span class="num"><pre>117</pre></span><pre> def _to_python(self, value_dict, state):</pre></div>
<div class="cov"><span class="num"><pre>118</pre></span><pre> if not value_dict:</pre></div>
<div class="cov"><span class="num"><pre>119</pre></span><pre> if self.if_empty is not NoDefault:</pre></div>
<div class="nocov"><span class="num"><pre>120</pre></span><pre> return self.if_empty</pre></div>
<div class="cov"><span class="num"><pre>121</pre></span><pre> else:</pre></div>
<div class="cov"><span class="num"><pre>122</pre></span><pre> value_dict = {}</pre></div>
<div class="skip"><span class="num"><pre>123</pre></span><pre></pre></div>
<div class="cov"><span class="num"><pre>124</pre></span><pre> for validator in self.pre_validators:</pre></div>
<div class="cov"><span class="num"><pre>125</pre></span><pre> value_dict = validator.to_python(value_dict, state)</pre></div>
<div class="skip"><span class="num"><pre>126</pre></span><pre></pre></div>
<div class="cov"><span class="num"><pre>127</pre></span><pre> self.assert_dict(value_dict, state)</pre></div>
<div class="skip"><span class="num"><pre>128</pre></span><pre> </pre></div>
<div class="cov"><span class="num"><pre>129</pre></span><pre> new = {}</pre></div>
<div class="cov"><span class="num"><pre>130</pre></span><pre> errors = {}</pre></div>
<div class="cov"><span class="num"><pre>131</pre></span><pre> unused = self.fields.keys()</pre></div>
<div class="cov"><span class="num"><pre>132</pre></span><pre> if state is not None:</pre></div>
<div class="cov"><span class="num"><pre>133</pre></span><pre> previous_key = getattr(state, 'key', None)</pre></div>
<div class="cov"><span class="num"><pre>134</pre></span><pre> previous_full_dict = getattr(state, 'full_dict', None)</pre></div>
<div class="cov"><span class="num"><pre>135</pre></span><pre> state.full_dict = value_dict</pre></div>
<div class="cov"><span class="num"><pre>136</pre></span><pre> try:</pre></div>
<div class="cov"><span class="num"><pre>137</pre></span><pre> for name, value in value_dict.items():</pre></div>
<div class="cov"><span class="num"><pre>138</pre></span><pre> try:</pre></div>
<div class="cov"><span class="num"><pre>139</pre></span><pre> unused.remove(name)</pre></div>
<div class="cov"><span class="num"><pre>140</pre></span><pre> except ValueError:</pre></div>
<div class="cov"><span class="num"><pre>141</pre></span><pre> if not self.allow_extra_fields:</pre></div>
<div class="cov"><span class="num"><pre>142</pre></span><pre> raise Invalid(</pre></div>
<div class="cov"><span class="num"><pre>143</pre></span><pre> self.message('notExpected', state,</pre></div>
<div class="cov"><span class="num"><pre>144</pre></span><pre> name=repr(name)),</pre></div>
<div class="cov"><span class="num"><pre>145</pre></span><pre> value_dict, state)</pre></div>
<div class="nocov"><span class="num"><pre>146</pre></span><pre> else:</pre></div>
<div class="nocov"><span class="num"><pre>147</pre></span><pre> if not self.filter_extra_fields:</pre></div>
<div class="nocov"><span class="num"><pre>148</pre></span><pre> new[name] = value</pre></div>
<div class="nocov"><span class="num"><pre>149</pre></span><pre> continue</pre></div>
<div class="cov"><span class="num"><pre>150</pre></span><pre> validator = self.fields[name]</pre></div>
<div class="skip"><span class="num"><pre>151</pre></span><pre></pre></div>
<div class="cov"><span class="num"><pre>152</pre></span><pre> try:</pre></div>
<div class="cov"><span class="num"><pre>153</pre></span><pre> new[name] = validator.to_python(value, state)</pre></div>
<div class="cov"><span class="num"><pre>154</pre></span><pre> except Invalid, e:</pre></div>
<div class="cov"><span class="num"><pre>155</pre></span><pre> errors[name] = e</pre></div>
<div class="skip"><span class="num"><pre>156</pre></span><pre></pre></div>
<div class="cov"><span class="num"><pre>157</pre></span><pre> for name in unused:</pre></div>
<div class="cov"><span class="num"><pre>158</pre></span><pre> validator = self.fields[name]</pre></div>
<div class="cov"><span class="num"><pre>159</pre></span><pre> try:</pre></div>
<div class="cov"><span class="num"><pre>160</pre></span><pre> if_missing = validator.if_missing</pre></div>
<div class="nocov"><span class="num"><pre>161</pre></span><pre> except AttributeError:</pre></div>
<div class="nocov"><span class="num"><pre>162</pre></span><pre> if_missing = NoDefault</pre></div>
<div class="cov"><span class="num"><pre>163</pre></span><pre> if if_missing is NoDefault:</pre></div>
<div class="cov"><span class="num"><pre>164</pre></span><pre> if self.ignore_key_missing:</pre></div>
<div class="nocov"><span class="num"><pre>165</pre></span><pre> continue</pre></div>
<div class="cov"><span class="num"><pre>166</pre></span><pre> if self.if_key_missing is NoDefault:</pre></div>
<div class="cov"><span class="num"><pre>167</pre></span><pre> try:</pre></div>
<div class="cov"><span class="num"><pre>168</pre></span><pre> message = validator.message('missing', state)</pre></div>
<div class="cov"><span class="num"><pre>169</pre></span><pre> except KeyError:</pre></div>
<div class="cov"><span class="num"><pre>170</pre></span><pre> message = self.message('missingValue', state)</pre></div>
<div class="cov"><span class="num"><pre>171</pre></span><pre> errors[name] = Invalid(message, None, state)</pre></div>
<div class="nocov"><span class="num"><pre>172</pre></span><pre> else:</pre></div>
<div class="nocov"><span class="num"><pre>173</pre></span><pre> try:</pre></div>
<div class="nocov"><span class="num"><pre>174</pre></span><pre> new[name] = validator.to_python(self.if_key_missing, state)</pre></div>
<div class="nocov"><span class="num"><pre>175</pre></span><pre> except Invalid, e:</pre></div>
<div class="nocov"><span class="num"><pre>176</pre></span><pre> errors[name] = e</pre></div>
<div class="cov"><span class="num"><pre>177</pre></span><pre> else:</pre></div>
<div class="cov"><span class="num"><pre>178</pre></span><pre> new[name] = validator.if_missing</pre></div>
<div class="skip"><span class="num"><pre>179</pre></span><pre></pre></div>
<div class="cov"><span class="num"><pre>180</pre></span><pre> for validator in self.chained_validators:</pre></div>
<div class="cov"><span class="num"><pre>181</pre></span><pre> if (not hasattr(validator, 'validate_partial')</pre></div>
<div class="cov"><span class="num"><pre>182</pre></span><pre> or not getattr(validator, 'validate_partial_form', False)):</pre></div>
<div class="nocov"><span class="num"><pre>183</pre></span><pre> continue</pre></div>
<div class="cov"><span class="num"><pre>184</pre></span><pre> try:</pre></div>
<div class="cov"><span class="num"><pre>185</pre></span><pre> validator.validate_partial(value_dict, state)</pre></div>
<div class="cov"><span class="num"><pre>186</pre></span><pre> except Invalid, e:</pre></div>
<div class="cov"><span class="num"><pre>187</pre></span><pre> sub_errors = e.unpack_errors()</pre></div>
<div class="cov"><span class="num"><pre>188</pre></span><pre> if not isinstance(sub_errors, dict):</pre></div>
<div class="skip"><span class="num"><pre>189</pre></span><pre> # Can't do anything here</pre></div>
<div class="nocov"><span class="num"><pre>190</pre></span><pre> continue</pre></div>
<div class="cov"><span class="num"><pre>191</pre></span><pre> merge_dicts(errors, sub_errors)</pre></div>
<div class="skip"><span class="num"><pre>192</pre></span><pre></pre></div>
<div class="cov"><span class="num"><pre>193</pre></span><pre> if errors:</pre></div>
<div class="cov"><span class="num"><pre>194</pre></span><pre> raise Invalid(</pre></div>
<div class="cov"><span class="num"><pre>195</pre></span><pre> format_compound_error(errors),</pre></div>
<div class="cov"><span class="num"><pre>196</pre></span><pre> value_dict, state,</pre></div>
<div class="cov"><span class="num"><pre>197</pre></span><pre> error_dict=errors)</pre></div>
<div class="skip"><span class="num"><pre>198</pre></span><pre></pre></div>
<div class="cov"><span class="num"><pre>199</pre></span><pre> for validator in self.chained_validators:</pre></div>
<div class="nocov"><span class="num"><pre>200</pre></span><pre> new = validator.to_python(new, state)</pre></div>
<div class="skip"><span class="num"><pre>201</pre></span><pre></pre></div>
<div class="cov"><span class="num"><pre>202</pre></span><pre> return new</pre></div>
<div class="skip"><span class="num"><pre>203</pre></span><pre></pre></div>
<div class="cov"><span class="num"><pre>204</pre></span><pre> finally:</pre></div>
<div class="cov"><span class="num"><pre>205</pre></span><pre> if state is not None:</pre></div>
<div class="cov"><span class="num"><pre>206</pre></span><pre> state.key = previous_key</pre></div>
<div class="cov"><span class="num"><pre>207</pre></span><pre> state.full_dict = previous_full_dict</pre></div>
<div class="skip"><span class="num"><pre>208</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>209</pre></span><pre> def _from_python(self, value_dict, state):</pre></div>
<div class="nocov"><span class="num"><pre>210</pre></span><pre> chained = self.chained_validators[:]</pre></div>
<div class="nocov"><span class="num"><pre>211</pre></span><pre> chained.reverse()</pre></div>
<div class="nocov"><span class="num"><pre>212</pre></span><pre> finished = []</pre></div>
<div class="nocov"><span class="num"><pre>213</pre></span><pre> for validator in chained:</pre></div>
<div class="nocov"><span class="num"><pre>214</pre></span><pre> __traceback_info__ = 'for_python chained_validator %s (finished %s)' % (validator, ', '.join(map(repr, finished)) or 'none')</pre></div>
<div class="nocov"><span class="num"><pre>215</pre></span><pre> finished.append(validator)</pre></div>
<div class="nocov"><span class="num"><pre>216</pre></span><pre> value_dict = validator.from_python(value_dict, state)</pre></div>
<div class="nocov"><span class="num"><pre>217</pre></span><pre> self.assert_dict(value_dict, state)</pre></div>
<div class="nocov"><span class="num"><pre>218</pre></span><pre> new = {}</pre></div>
<div class="nocov"><span class="num"><pre>219</pre></span><pre> errors = {}</pre></div>
<div class="nocov"><span class="num"><pre>220</pre></span><pre> unused = self.fields.keys()</pre></div>
<div class="nocov"><span class="num"><pre>221</pre></span><pre> if state is not None:</pre></div>
<div class="nocov"><span class="num"><pre>222</pre></span><pre> previous_key = getattr(state, 'key', None)</pre></div>
<div class="nocov"><span class="num"><pre>223</pre></span><pre> previous_full_dict = getattr(state, 'full_dict', None)</pre></div>
<div class="nocov"><span class="num"><pre>224</pre></span><pre> state.full_dict = value_dict</pre></div>
<div class="nocov"><span class="num"><pre>225</pre></span><pre> try:</pre></div>
<div class="nocov"><span class="num"><pre>226</pre></span><pre> __traceback_info__ = None</pre></div>
<div class="nocov"><span class="num"><pre>227</pre></span><pre> for name, value in value_dict.items():</pre></div>
<div class="nocov"><span class="num"><pre>228</pre></span><pre> __traceback_info__ = 'for_python in %s' % name</pre></div>
<div class="nocov"><span class="num"><pre>229</pre></span><pre> try:</pre></div>
<div class="nocov"><span class="num"><pre>230</pre></span><pre> unused.remove(name)</pre></div>
<div class="nocov"><span class="num"><pre>231</pre></span><pre> except ValueError:</pre></div>
<div class="nocov"><span class="num"><pre>232</pre></span><pre> if not self.allow_extra_fields:</pre></div>
<div class="nocov"><span class="num"><pre>233</pre></span><pre> raise Invalid(</pre></div>
<div class="nocov"><span class="num"><pre>234</pre></span><pre> self.message('notExpected', state,</pre></div>
<div class="nocov"><span class="num"><pre>235</pre></span><pre> name=repr(name)),</pre></div>
<div class="nocov"><span class="num"><pre>236</pre></span><pre> value_dict, state)</pre></div>
<div class="nocov"><span class="num"><pre>237</pre></span><pre> if not self.filter_extra_fields:</pre></div>
<div class="nocov"><span class="num"><pre>238</pre></span><pre> new[name] = value</pre></div>
<div class="nocov"><span class="num"><pre>239</pre></span><pre> else:</pre></div>
<div class="nocov"><span class="num"><pre>240</pre></span><pre> try:</pre></div>
<div class="nocov"><span class="num"><pre>241</pre></span><pre> new[name] = self.fields[name].from_python(value, state)</pre></div>
<div class="nocov"><span class="num"><pre>242</pre></span><pre> except Invalid, e:</pre></div>
<div class="nocov"><span class="num"><pre>243</pre></span><pre> errors[name] = e</pre></div>
<div class="skip"><span class="num"><pre>244</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>245</pre></span><pre> del __traceback_info__</pre></div>
<div class="skip"><span class="num"><pre>246</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>247</pre></span><pre> for name in unused:</pre></div>
<div class="nocov"><span class="num"><pre>248</pre></span><pre> validator = self.fields[name]</pre></div>
<div class="nocov"><span class="num"><pre>249</pre></span><pre> try:</pre></div>
<div class="nocov"><span class="num"><pre>250</pre></span><pre> new[name] = validator.from_python(None, state)</pre></div>
<div class="nocov"><span class="num"><pre>251</pre></span><pre> except Invalid, e:</pre></div>
<div class="nocov"><span class="num"><pre>252</pre></span><pre> errors[name] = e</pre></div>
<div class="skip"><span class="num"><pre>253</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>254</pre></span><pre> if errors:</pre></div>
<div class="nocov"><span class="num"><pre>255</pre></span><pre> raise Invalid(</pre></div>
<div class="nocov"><span class="num"><pre>256</pre></span><pre> format_compound_error(errors),</pre></div>
<div class="nocov"><span class="num"><pre>257</pre></span><pre> value_dict, state,</pre></div>
<div class="nocov"><span class="num"><pre>258</pre></span><pre> error_dict=errors)</pre></div>
<div class="skip"><span class="num"><pre>259</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>260</pre></span><pre> pre = self.pre_validators[:]</pre></div>
<div class="nocov"><span class="num"><pre>261</pre></span><pre> pre.reverse()</pre></div>
<div class="nocov"><span class="num"><pre>262</pre></span><pre> for validator in pre:</pre></div>
<div class="nocov"><span class="num"><pre>263</pre></span><pre> __traceback_info__ = 'for_python pre_validator %s' % validator</pre></div>
<div class="nocov"><span class="num"><pre>264</pre></span><pre> new = validator.from_python(new, state)</pre></div>
<div class="skip"><span class="num"><pre>265</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>266</pre></span><pre> return new</pre></div>
<div class="skip"><span class="num"><pre>267</pre></span><pre> </pre></div>
<div class="nocov"><span class="num"><pre>268</pre></span><pre> finally:</pre></div>
<div class="nocov"><span class="num"><pre>269</pre></span><pre> if state is not None:</pre></div>
<div class="nocov"><span class="num"><pre>270</pre></span><pre> state.key = previous_key</pre></div>
<div class="nocov"><span class="num"><pre>271</pre></span><pre> state.full_dict = previous_full_dict</pre></div>
<div class="skip"><span class="num"><pre>272</pre></span><pre> </pre></div>
<div class="skip"><span class="num"><pre>273</pre></span><pre></pre></div>
<div class="skip"><span class="num"><pre>274</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>275</pre></span><pre> def add_chained_validator(self, cls, validator):</pre></div>
<div class="nocov"><span class="num"><pre>276</pre></span><pre> if self is not None:</pre></div>
<div class="nocov"><span class="num"><pre>277</pre></span><pre> if self.chained_validators is cls.chained_validators:</pre></div>
<div class="nocov"><span class="num"><pre>278</pre></span><pre> self.chained_validators = cls.chained_validators[:]</pre></div>
<div class="nocov"><span class="num"><pre>279</pre></span><pre> self.chained_validators.append(validator)</pre></div>
<div class="nocov"><span class="num"><pre>280</pre></span><pre> else:</pre></div>
<div class="nocov"><span class="num"><pre>281</pre></span><pre> cls.chained_validators.append(validator)</pre></div>
<div class="skip"><span class="num"><pre>282</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>283</pre></span><pre> add_chained_validator = declarative.classinstancemethod(</pre></div>
<div class="nocov"><span class="num"><pre>284</pre></span><pre> add_chained_validator)</pre></div>
<div class="skip"><span class="num"><pre>285</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>286</pre></span><pre> def add_field(self, cls, name, validator):</pre></div>
<div class="cov"><span class="num"><pre>287</pre></span><pre> if self is not None:</pre></div>
<div class="cov"><span class="num"><pre>288</pre></span><pre> if self.fields is cls.fields:</pre></div>
<div class="nocov"><span class="num"><pre>289</pre></span><pre> self.fields = cls.fields.copy()</pre></div>
<div class="cov"><span class="num"><pre>290</pre></span><pre> self.fields[name] = validator</pre></div>
<div class="cov"><span class="num"><pre>291</pre></span><pre> else:</pre></div>
<div class="cov"><span class="num"><pre>292</pre></span><pre> cls.fields[name] = validator</pre></div>
<div class="skip"><span class="num"><pre>293</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>294</pre></span><pre> add_field = declarative.classinstancemethod(add_field)</pre></div>
<div class="skip"><span class="num"><pre>295</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>296</pre></span><pre> def add_pre_validator(self, cls, validator):</pre></div>
<div class="nocov"><span class="num"><pre>297</pre></span><pre> if self is not None:</pre></div>
<div class="nocov"><span class="num"><pre>298</pre></span><pre> if self.pre_validators is cls.pre_validators:</pre></div>
<div class="nocov"><span class="num"><pre>299</pre></span><pre> self.pre_validators = cls.pre_validators[:]</pre></div>
<div class="nocov"><span class="num"><pre>300</pre></span><pre> self.pre_validators.append(validator)</pre></div>
<div class="nocov"><span class="num"><pre>301</pre></span><pre> else:</pre></div>
<div class="nocov"><span class="num"><pre>302</pre></span><pre> cls.pre_validators.append(validator)</pre></div>
<div class="skip"><span class="num"><pre>303</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>304</pre></span><pre> add_pre_validator = declarative.classinstancemethod(add_pre_validator)</pre></div>
<div class="skip"><span class="num"><pre>305</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>306</pre></span><pre> def subvalidators(self):</pre></div>
<div class="nocov"><span class="num"><pre>307</pre></span><pre> result = []</pre></div>
<div class="nocov"><span class="num"><pre>308</pre></span><pre> result.extend(self.pre_validators)</pre></div>
<div class="nocov"><span class="num"><pre>309</pre></span><pre> result.extend(self.chained_validators)</pre></div>
<div class="nocov"><span class="num"><pre>310</pre></span><pre> result.extend(self.fields.values())</pre></div>
<div class="nocov"><span class="num"><pre>311</pre></span><pre> return result</pre></div>
<div class="skip"><span class="num"><pre>312</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>313</pre></span><pre> def is_empty(self, value):</pre></div>
<div class="skip"><span class="num"><pre>314</pre></span><pre> ## Generally nothing is empty for us</pre></div>
<div class="cov"><span class="num"><pre>315</pre></span><pre> return False</pre></div>
<div class="skip"><span class="num"><pre>316</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>317</pre></span><pre> def empty_value(self, value):</pre></div>
<div class="nocov"><span class="num"><pre>318</pre></span><pre> return {}</pre></div>
<div class="skip"><span class="num"><pre>319</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>320</pre></span><pre>def format_compound_error(v, indent=0):</pre></div>
<div class="cov"><span class="num"><pre>321</pre></span><pre> if isinstance(v, Exception):</pre></div>
<div class="cov"><span class="num"><pre>322</pre></span><pre> try:</pre></div>
<div class="cov"><span class="num"><pre>323</pre></span><pre> return str(v)</pre></div>
<div class="nocov"><span class="num"><pre>324</pre></span><pre> except (UnicodeDecodeError, UnicodeEncodeError):</pre></div>
<div class="skip"><span class="num"><pre>325</pre></span><pre> # There doesn't seem to be a better way to get a str()</pre></div>
<div class="skip"><span class="num"><pre>326</pre></span><pre> # version if possible, and unicode() if necessary, because</pre></div>
<div class="skip"><span class="num"><pre>327</pre></span><pre> # testing for the presence of a __unicode__ method isn't</pre></div>
<div class="skip"><span class="num"><pre>328</pre></span><pre> # enough</pre></div>
<div class="nocov"><span class="num"><pre>329</pre></span><pre> return unicode(v)</pre></div>
<div class="cov"><span class="num"><pre>330</pre></span><pre> elif isinstance(v, dict):</pre></div>
<div class="cov"><span class="num"><pre>331</pre></span><pre> l = v.items()</pre></div>
<div class="cov"><span class="num"><pre>332</pre></span><pre> l.sort()</pre></div>
<div class="cov"><span class="num"><pre>333</pre></span><pre> return ('%s\n' % (' '*indent)).join(</pre></div>
<div class="cov"><span class="num"><pre>334</pre></span><pre> ["%s: %s" % (k, format_compound_error(value, indent=len(k)+2))</pre></div>
<div class="cov"><span class="num"><pre>335</pre></span><pre> for k, value in l</pre></div>
<div class="cov"><span class="num"><pre>336</pre></span><pre> if value is not None])</pre></div>
<div class="cov"><span class="num"><pre>337</pre></span><pre> elif isinstance(v, list):</pre></div>
<div class="nocov"><span class="num"><pre>338</pre></span><pre> return ('%s\n' % (' '*indent)).join(</pre></div>
<div class="nocov"><span class="num"><pre>339</pre></span><pre> ['%s' % (format_compound_error(value, indent=indent))</pre></div>
<div class="nocov"><span class="num"><pre>340</pre></span><pre> for value in v</pre></div>
<div class="nocov"><span class="num"><pre>341</pre></span><pre> if value is not None])</pre></div>
<div class="cov"><span class="num"><pre>342</pre></span><pre> elif isinstance(v, basestring):</pre></div>
<div class="cov"><span class="num"><pre>343</pre></span><pre> return v</pre></div>
<div class="nocov"><span class="num"><pre>344</pre></span><pre> else:</pre></div>
<div class="nocov"><span class="num"><pre>345</pre></span><pre> assert 0, "I didn't expect something like %s" % repr(v)</pre></div>
<div class="skip"><span class="num"><pre>346</pre></span><pre> </pre></div>
<div class="nocov"><span class="num"><pre>347</pre></span><pre>def merge_dicts(d1, d2):</pre></div>
<div class="cov"><span class="num"><pre>348</pre></span><pre> for key in d2:</pre></div>
<div class="cov"><span class="num"><pre>349</pre></span><pre> if key in d1:</pre></div>
<div class="cov"><span class="num"><pre>350</pre></span><pre> d1[key] = merge_values(d1[key], d2[key])</pre></div>
<div class="cov"><span class="num"><pre>351</pre></span><pre> else:</pre></div>
<div class="cov"><span class="num"><pre>352</pre></span><pre> d1[key] = d2[key]</pre></div>
<div class="cov"><span class="num"><pre>353</pre></span><pre> return d1</pre></div>
<div class="skip"><span class="num"><pre>354</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>355</pre></span><pre>def merge_values(v1, v2):</pre></div>
<div class="cov"><span class="num"><pre>356</pre></span><pre> if (isinstance(v1, (str, unicode))</pre></div>
<div class="cov"><span class="num"><pre>357</pre></span><pre> and isinstance(v2, (str, unicode))):</pre></div>
<div class="cov"><span class="num"><pre>358</pre></span><pre> return v1 + '\n' + v2</pre></div>
<div class="cov"><span class="num"><pre>359</pre></span><pre> elif (isinstance(v1, (list, tuple))</pre></div>
<div class="cov"><span class="num"><pre>360</pre></span><pre> and isinstance(v2, (list, tuple))):</pre></div>
<div class="cov"><span class="num"><pre>361</pre></span><pre> return merge_lists(v1, v2)</pre></div>
<div class="cov"><span class="num"><pre>362</pre></span><pre> elif isinstance(v1, dict) and isinstance(v2, dict):</pre></div>
<div class="nocov"><span class="num"><pre>363</pre></span><pre> return merge_dicts(v1, v2)</pre></div>
<div class="cov"><span class="num"><pre>364</pre></span><pre> else:</pre></div>
<div class="skip"><span class="num"><pre>365</pre></span><pre> # @@: Should we just ignore errors? Seems we do...</pre></div>
<div class="cov"><span class="num"><pre>366</pre></span><pre> return v1</pre></div>
<div class="skip"><span class="num"><pre>367</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>368</pre></span><pre>def merge_lists(l1, l2):</pre></div>
<div class="cov"><span class="num"><pre>369</pre></span><pre> if len(l1) < len(l2):</pre></div>
<div class="cov"><span class="num"><pre>370</pre></span><pre> l1 = l1 + [None]*(len(l2)-len(l1))</pre></div>
<div class="cov"><span class="num"><pre>371</pre></span><pre> elif len(l2) < len(l1):</pre></div>
<div class="cov"><span class="num"><pre>372</pre></span><pre> l2 = l2 + [None]*(len(l1)-len(l2))</pre></div>
<div class="cov"><span class="num"><pre>373</pre></span><pre> result = []</pre></div>
<div class="cov"><span class="num"><pre>374</pre></span><pre> for l1item, l2item in zip(l1, l2):</pre></div>
<div class="cov"><span class="num"><pre>375</pre></span><pre> item = None</pre></div>
<div class="cov"><span class="num"><pre>376</pre></span><pre> if l1item is None:</pre></div>
<div class="cov"><span class="num"><pre>377</pre></span><pre> item = l2item</pre></div>
<div class="cov"><span class="num"><pre>378</pre></span><pre> elif l2item is None:</pre></div>
<div class="cov"><span class="num"><pre>379</pre></span><pre> item = l1item</pre></div>
<div class="cov"><span class="num"><pre>380</pre></span><pre> else:</pre></div>
<div class="cov"><span class="num"><pre>381</pre></span><pre> item = merge_values(l1item, l2item)</pre></div>
<div class="cov"><span class="num"><pre>382</pre></span><pre> result.append(item)</pre></div>
<div class="cov"><span class="num"><pre>383</pre></span><pre> return result</pre></div>
<div class="skip"><span class="num"><pre>384</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>385</pre></span><pre>class SimpleFormValidator(FancyValidator):</pre></div>
<div class="nocov"><span class="num"><pre>386</pre></span><pre> """</pre></div>
<div class="nocov"><span class="num"><pre>387</pre></span><pre> This validator wraps a simple function that validates the form.</pre></div>
<div class="skip"><span class="num"><pre>388</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>389</pre></span><pre> The function looks something like this::</pre></div>
<div class="skip"><span class="num"><pre>390</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>391</pre></span><pre> >>> def validate(form_values, state, validator):</pre></div>
<div class="nocov"><span class="num"><pre>392</pre></span><pre> ... if form_values.get('country', 'US') == 'US':</pre></div>
<div class="nocov"><span class="num"><pre>393</pre></span><pre> ... if not form_values.get('state'):</pre></div>
<div class="nocov"><span class="num"><pre>394</pre></span><pre> ... return {'state': 'You must enter a state'}</pre></div>
<div class="nocov"><span class="num"><pre>395</pre></span><pre> ... if not form_values.get('country'):</pre></div>
<div class="nocov"><span class="num"><pre>396</pre></span><pre> ... form_values['country'] = 'US'</pre></div>
<div class="skip"><span class="num"><pre>397</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>398</pre></span><pre> This tests that the field 'state' must be filled in if the country</pre></div>
<div class="nocov"><span class="num"><pre>399</pre></span><pre> is US, and defaults that country value to 'US'. The ``validator``</pre></div>
<div class="nocov"><span class="num"><pre>400</pre></span><pre> argument is the SimpleFormValidator instance, which you can use to</pre></div>
<div class="nocov"><span class="num"><pre>401</pre></span><pre> format messages or keep configuration state in if you like (for</pre></div>
<div class="nocov"><span class="num"><pre>402</pre></span><pre> simple ad hoc validation you are unlikely to need it).</pre></div>
<div class="skip"><span class="num"><pre>403</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>404</pre></span><pre> To create a validator from that function, you would do::</pre></div>
<div class="skip"><span class="num"><pre>405</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>406</pre></span><pre> >>> from formencode.schema import SimpleFormValidator</pre></div>
<div class="nocov"><span class="num"><pre>407</pre></span><pre> >>> validator = SimpleFormValidator(validate)</pre></div>
<div class="nocov"><span class="num"><pre>408</pre></span><pre> >>> validator.to_python({'country': 'US', 'state': ''}, None)</pre></div>
<div class="nocov"><span class="num"><pre>409</pre></span><pre> Traceback (most recent call last):</pre></div>
<div class="nocov"><span class="num"><pre>410</pre></span><pre> ...</pre></div>
<div class="nocov"><span class="num"><pre>411</pre></span><pre> Invalid: state: You must enter a state</pre></div>
<div class="nocov"><span class="num"><pre>412</pre></span><pre> >>> validator.to_python({'state': 'IL'}, None)</pre></div>
<div class="nocov"><span class="num"><pre>413</pre></span><pre> {'country': 'US', 'state': 'IL'}</pre></div>
<div class="skip"><span class="num"><pre>414</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>415</pre></span><pre> The validate function can either return a single error message</pre></div>
<div class="nocov"><span class="num"><pre>416</pre></span><pre> (that applies to the whole form), a dictionary that applies to the</pre></div>
<div class="nocov"><span class="num"><pre>417</pre></span><pre> fields, None which means the form is valid, or it can raise</pre></div>
<div class="nocov"><span class="num"><pre>418</pre></span><pre> Invalid.</pre></div>
<div class="skip"><span class="num"><pre>419</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>420</pre></span><pre> Note that you may update the value_dict *in place*, but you cannot</pre></div>
<div class="nocov"><span class="num"><pre>421</pre></span><pre> return a new value.</pre></div>
<div class="skip"><span class="num"><pre>422</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>423</pre></span><pre> Another way to instantiate a validator is like this::</pre></div>
<div class="skip"><span class="num"><pre>424</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>425</pre></span><pre> >>> @SimpleFormValidator.decorate()</pre></div>
<div class="nocov"><span class="num"><pre>426</pre></span><pre> ... def MyValidator(value_dict, state):</pre></div>
<div class="nocov"><span class="num"><pre>427</pre></span><pre> ... return None # or some more useful validation</pre></div>
<div class="skip"><span class="num"><pre>428</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>429</pre></span><pre> After this ``MyValidator`` will be a ``SimpleFormValidator``</pre></div>
<div class="nocov"><span class="num"><pre>430</pre></span><pre> instance (it won't be your function).</pre></div>
<div class="nocov"><span class="num"><pre>431</pre></span><pre> """</pre></div>
<div class="skip"><span class="num"><pre>432</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>433</pre></span><pre> __unpackargs__ = ('func',)</pre></div>
<div class="skip"><span class="num"><pre>434</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>435</pre></span><pre> validate_partial_form = False</pre></div>
<div class="skip"><span class="num"><pre>436</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>437</pre></span><pre> def __initargs__(self, new_attrs):</pre></div>
<div class="cov"><span class="num"><pre>438</pre></span><pre> self.__doc__ = getattr(self.func, '__doc__', None)</pre></div>
<div class="skip"><span class="num"><pre>439</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>440</pre></span><pre> def to_python(self, value_dict, state):</pre></div>
<div class="skip"><span class="num"><pre>441</pre></span><pre> # Since we aren't really supposed to modify things in-place,</pre></div>
<div class="skip"><span class="num"><pre>442</pre></span><pre> # we'll give the validation function a copy:</pre></div>
<div class="nocov"><span class="num"><pre>443</pre></span><pre> value_dict = value_dict.copy()</pre></div>
<div class="nocov"><span class="num"><pre>444</pre></span><pre> errors = self.func(value_dict, state, self)</pre></div>
<div class="nocov"><span class="num"><pre>445</pre></span><pre> if not errors:</pre></div>
<div class="nocov"><span class="num"><pre>446</pre></span><pre> return value_dict</pre></div>
<div class="nocov"><span class="num"><pre>447</pre></span><pre> if isinstance(errors, basestring):</pre></div>
<div class="nocov"><span class="num"><pre>448</pre></span><pre> raise Invalid(errors, value_dict, state)</pre></div>
<div class="nocov"><span class="num"><pre>449</pre></span><pre> elif isinstance(errors, dict):</pre></div>
<div class="nocov"><span class="num"><pre>450</pre></span><pre> raise Invalid(format_compound_error(errors),</pre></div>
<div class="nocov"><span class="num"><pre>451</pre></span><pre> value_dict, state, error_dict=errors)</pre></div>
<div class="nocov"><span class="num"><pre>452</pre></span><pre> elif isinstance(errors, Invalid):</pre></div>
<div class="nocov"><span class="num"><pre>453</pre></span><pre> raise errors</pre></div>
<div class="nocov"><span class="num"><pre>454</pre></span><pre> else:</pre></div>
<div class="nocov"><span class="num"><pre>455</pre></span><pre> raise TypeError(</pre></div>
<div class="nocov"><span class="num"><pre>456</pre></span><pre> "Invalid error value: %r" % errors)</pre></div>
<div class="nocov"><span class="num"><pre>457</pre></span><pre> return value_dict</pre></div>
<div class="skip"><span class="num"><pre>458</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>459</pre></span><pre> validate_partial = to_python</pre></div>
<div class="skip"><span class="num"><pre>460</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>461</pre></span><pre> def decorate(cls, **kw):</pre></div>
<div class="nocov"><span class="num"><pre>462</pre></span><pre> def decorator(func):</pre></div>
<div class="nocov"><span class="num"><pre>463</pre></span><pre> return cls(func, **kw)</pre></div>
<div class="nocov"><span class="num"><pre>464</pre></span><pre> return decorator</pre></div>
<div class="skip"><span class="num"><pre>465</pre></span><pre></pre></div>
<div class="nocov"><span class="num"><pre>466</pre></span><pre> decorate = classmethod(decorate)</pre></div>
<div class="skip"><span class="num"><pre>467</pre></span><pre></pre></div>
</div>
</body>
</html>