Changeset 21:6e73325a5473 in ralphm-patches
- Timestamp:
- Dec 30, 2009, 10:01:00 PM (12 years ago)
- Branch:
- default
- Files:
-
- 4 added
- 3 edited
Legend:
- Unmodified
- Added
- Removed
-
pubsub-create-configure.patch
r20 r21 1 diff -r 26ba5a2ff579 wokkel/data_form.py 2 --- a/wokkel/data_form.py Wed Dec 30 17:55:07 2009 +0100 3 +++ b/wokkel/data_form.py Wed Dec 30 20:46:36 2009 +0100 4 @@ -253,10 +253,10 @@ 5 field['var'] = self.var 6 7 for value in self.values: 8 - if self.fieldType == 'boolean': 9 + if isinstance(value, bool): 10 value = unicode(value).lower() 11 - elif self.fieldType in ('jid-single', 'jid-multi'): 12 - value = value.full() 13 + else: 14 + value = unicode(value) 15 16 field.addElement('value', content=unicode(value)) 17 18 @@ -616,3 +616,24 @@ 19 20 for field in filtered: 21 self.removeField(field) 22 + 23 + 24 +def findForm(element, formNamespace): 25 + """ 26 + Find a Data Form. 27 + 28 + Look for an element that represents a Data Form with the specified 29 + form namespace as a child element of the given element. 30 + """ 31 + if not element: 32 + return None 33 + 34 + for child in element.elements(): 35 + if (child.uri, child.name) == ((NS_X_DATA, 'x')): 36 + form = Form.fromElement(child) 37 + 38 + if (form.formNamespace == formNamespace or 39 + not form.formNamespace and form.formType=='cancel'): 40 + return form 41 + 42 + return None 43 diff -r 26ba5a2ff579 wokkel/pubsub.py 44 --- a/wokkel/pubsub.py Wed Dec 30 17:55:07 2009 +0100 45 +++ b/wokkel/pubsub.py Wed Dec 30 20:46:36 2009 +0100 1 diff -r d64e96596c50 -r 8425a88d49f5 wokkel/pubsub.py 2 --- a/wokkel/pubsub.py Wed Dec 30 21:41:55 2009 +0100 3 +++ b/wokkel/pubsub.py Wed Dec 30 21:42:27 2009 +0100 46 4 @@ -234,7 +234,7 @@ 47 5 'optionsSet': ['nodeOrEmpty', 'jid', 'options'], … … 53 11 'configureGet': ['nodeOrEmpty'], 54 12 'configureSet': ['nodeOrEmpty', 'configure'], 55 @@ -252,30 +252,6 @@ 56 self.verb = verb 57 58 59 - @staticmethod 60 - def _findForm(element, formNamespace): 61 - """ 62 - Find a Data Form. 63 - 64 - Look for an element that represents a Data Form with the specified 65 - form namespace as a child element of the given element. 66 - """ 67 - if not element: 68 - return None 69 - 70 - form = None 71 - for child in element.elements(): 72 - try: 73 - form = data_form.Form.fromElement(child) 74 - except data_form.Error: 75 - continue 76 - 77 - if form.formNamespace != NS_PUBSUB_NODE_CONFIG: 78 - continue 79 - 80 - return form 81 - 82 - 83 def _parse_node(self, verbElement): 84 """ 85 Parse the required node identifier out of the verbElement. 86 @@ -366,7 +342,7 @@ 87 """ 88 Parse node type out of a request for the default node configuration. 89 """ 90 - form = PubSubRequest._findForm(verbElement, NS_PUBSUB_NODE_CONFIG) 91 + form = data_form.findForm(verbElement, NS_PUBSUB_NODE_CONFIG) 92 if form and form.formType == 'submit': 93 values = form.getValues() 94 self.nodeType = values.get('pubsub#node_type', 'leaf') 95 @@ -378,7 +354,7 @@ 96 """ 97 Parse options out of a request for setting the node configuration. 98 """ 99 - form = PubSubRequest._findForm(verbElement, NS_PUBSUB_NODE_CONFIG) 100 + form = data_form.findForm(verbElement, NS_PUBSUB_NODE_CONFIG) 101 if form: 102 if form.formType in ('submit', 'cancel'): 103 self.options = form 104 @@ -388,6 +364,33 @@ 13 @@ -364,6 +364,33 @@ 105 14 raise BadRequest(text="Missing configuration form") 106 15 … … 136 45 def _parse_itemIdentifiers(self, verbElement): 137 46 """ 138 @@ -435,7 +438,7 @@ 139 140 141 def _parse_options(self, verbElement): 142 - form = PubSubRequest._findForm(verbElement, NS_PUBSUB_SUBSCRIBE_OPTIONS) 143 + form = data_form.findForm(verbElement, NS_PUBSUB_SUBSCRIBE_OPTIONS) 144 if form: 145 if form.formType not in ('submit', 'cancel'): 146 raise BadRequest(text="Unexpected form type %r" % form.formType) 147 @@ -451,8 +454,8 @@ 148 def _parse_optionsWithSubscribe(self, verbElement): 149 for element in verbElement.parent.elements(): 150 if element.name == 'options' and element.uri == NS_PUBSUB: 151 - form = PubSubRequest._findForm(element, 152 - NS_PUBSUB_SUBSCRIBE_OPTIONS) 153 + form = data_form.findForm(element, 154 + NS_PUBSUB_SUBSCRIBE_OPTIONS) 155 if not form: 156 continue 157 158 @@ -662,7 +665,8 @@ 47 @@ -602,7 +629,8 @@ 159 48 pass 160 49 … … 166 55 Create a publish subscribe node. 167 56 168 @@ -6 70,12 +674,20 @@57 @@ -610,12 +638,20 @@ 169 58 @type service: L{JID} 170 59 @param nodeIdentifier: Optional suggestion for the id of the node. … … 187 76 try: 188 77 new_node = iq.pubsub.create["node"] 189 @@ - 956,8 +968,6 @@78 @@ -887,8 +923,6 @@ 190 79 d = self.getNodes(requestor, target) 191 80 else: … … 196 85 d.addCallback(lambda nodes: [disco.DiscoItem(target, node) 197 86 for node in nodes]) 198 @@ - 1067,6 +1077,12 @@87 @@ -998,6 +1032,12 @@ 199 88 form.typeCheck(fieldDefs, filterUnknown=True) 200 89 … … 209 98 if request.nodeType not in ('leaf', 'collection'): 210 99 raise error.StanzaError('not-acceptable') 211 diff -r 26ba5a2ff579wokkel/test/test_pubsub.py212 --- a/wokkel/test/test_pubsub.py Wed Dec 30 17:55:072009 +0100213 +++ b/wokkel/test/test_pubsub.py Wed Dec 30 2 0:46:362009 +0100100 diff -r d64e96596c50 -r 8425a88d49f5 wokkel/test/test_pubsub.py 101 --- a/wokkel/test/test_pubsub.py Wed Dec 30 21:41:55 2009 +0100 102 +++ b/wokkel/test/test_pubsub.py Wed Dec 30 21:42:27 2009 +0100 214 103 @@ -19,7 +19,7 @@ 215 104 from wokkel.test.helpers import TestableRequestHandlerMixin, XmlStreamStub … … 262 151 """ 263 152 Test sending delete request. 264 @@ -9 98,6 +1032,7 @@153 @@ -935,6 +969,7 @@ 265 154 self.assertEqual(JID('user@example.org'), request.sender) 266 155 self.assertEqual(JID('pubsub.example.org'), request.recipient) … … 270 159 271 160 def test_fromElementCreateInstant(self): 272 @@ - 1018,6 +1053,78 @@161 @@ -955,6 +990,78 @@ 273 162 self.assertIdentical(None, request.nodeIdentifier) 274 163 … … 349 238 """ 350 239 Test parsing a request for the default node configuration. 351 @@ -1 804,6 +1911,52 @@240 @@ -1741,6 +1848,52 @@ 352 241 return d 353 242 … … 402 291 """ 403 292 A default request should result in 404 @@ -1 837,7 +1990,7 @@293 @@ -1774,7 +1927,7 @@ 405 294 self.assertEqual(NS_PUBSUB_OWNER, element.uri) 406 295 self.assertEqual(NS_PUBSUB_OWNER, element.default.uri) … … 411 300 self.resource.getConfigurationOptions = getConfigurationOptions 412 301 self.resource.default = default 413 @@ -19 66,7 +2119,7 @@302 @@ -1903,7 +2056,7 @@ 414 303 self.assertEqual(NS_PUBSUB_OWNER, element.uri) 415 304 self.assertEqual(NS_PUBSUB_OWNER, element.configure.uri) -
pubsub-subscription-options.patch
r20 r21 1 diff -r 3ef9bc7a0d70 wokkel/data_form.py 2 --- a/wokkel/data_form.py Wed Dec 30 16:53:05 2009 +0100 3 +++ b/wokkel/data_form.py Wed Dec 30 21:05:59 2009 +0100 4 @@ -76,6 +76,7 @@ 5 option['label'] = self.label 6 return option 7 8 + 9 @staticmethod 10 def fromElement(element): 11 valueElements = list(domish.generateElementsQNamed(element.children, 12 @@ -212,7 +213,7 @@ 13 14 if self.values: 15 if (self.fieldType not in ('hidden', 'jid-multi', 'list-multi', 16 - 'text-multi') and 17 + 'text-multi') and 18 len(self.values) > 1): 19 raise TooManyValuesError() 20 21 @@ -233,6 +234,7 @@ 22 23 self.values = newValues 24 25 + 26 def toElement(self, asForm=False): 27 """ 28 Return the DOM representation of this Field. 29 @@ -256,7 +258,7 @@ 30 elif self.fieldType in ('jid-single', 'jid-multi'): 31 value = value.full() 32 33 - field.addElement('value', content=value) 34 + field.addElement('value', content=unicode(value)) 35 36 if asForm: 37 if self.fieldType in ('list-single', 'list-multi'): 38 @@ -322,16 +324,16 @@ 39 40 41 @staticmethod 42 - def fromDict(dictionary): 43 - kwargs = dictionary.copy() 44 + def fromDict(fieldDict): 45 + kwargs = fieldDict.copy() 46 47 - if 'type' in dictionary: 48 - kwargs['fieldType'] = dictionary['type'] 49 + if 'type' in fieldDict: 50 + kwargs['fieldType'] = fieldDict['type'] 51 del kwargs['type'] 52 53 - if 'options' in dictionary: 54 + if 'options' in fieldDict: 55 options = [] 56 - for value, label in dictionary['options'].iteritems(): 57 + for value, label in fieldDict['options'].iteritems(): 58 options.append(Option(value, label)) 59 kwargs['options'] = options 60 61 @@ -343,7 +345,7 @@ 62 """ 63 Data Form. 64 65 - There are two similarly named properties of forms. The L{formType} is the 66 + There are two similarly named properties of forms. The C{formType} is the 67 the so-called type of the form, and is set as the C{'type'} attribute 68 on the form's root element. 69 70 @@ -351,19 +353,25 @@ 71 provide a context for the field names used in this form, by setting a 72 special hidden field named C{'FORM_TYPE'}, to put the names of all 73 other fields in the namespace of the value of that field. This namespace 74 - is recorded in the L{formNamespace} instance variable. 75 + is recorded in the C{formNamespace} instance variable. 76 77 @ivar formType: Type of form. One of C{'form'}, C{'submit'}, {'cancel'}, 78 or {'result'}. 79 - @type formType: C{str}. 80 + @type formType: C{str} 81 + 82 @ivar formNamespace: The optional namespace of the field names for this 83 - form. This goes in the special field named 84 - C{'FORM_TYPE'}, if set. 85 - @type formNamespace: C{str}. 86 - @ivar fields: Dictionary of fields that have a name. Note that this is 87 - meant to be used for reading, only. One should use 88 - L{addField} for adding fields. 89 + form. This goes in the special field named C{'FORM_TYPE'}, if set. 90 + @type formNamespace: C{str} 91 + 92 + @ivar fields: Dictionary of named fields. Note that this is meant to be 93 + used for reading, only. One should use L{addField} or L{makeFields} and 94 + L{removeField} for adding and removing fields. 95 @type fields: C{dict} 96 + 97 + @ivar fieldList: List of all fields, in the order they are added. Like 98 + C{fields}, this is meant to be used for reading, only. 99 + @type fieldList: C{list} 100 + 101 """ 102 103 def __init__(self, formType, title=None, instructions=None, 104 @@ -403,7 +411,7 @@ 105 """ 106 Add a field to this form. 107 108 - Fields are added in order, and L{fields} is a dictionary of the 109 + Fields are added in order, and C{fields} is a dictionary of the 110 named fields, that is kept in sync only if this method is used for 111 adding new fields. Multiple fields with the same name are disallowed. 112 """ 113 @@ -416,7 +424,71 @@ 114 self.fieldList.append(field) 115 116 117 + def removeField(self, field): 118 + """ 119 + Remove a field from this form. 120 + """ 121 + self.fieldList.remove(field) 122 + 123 + if field.var is not None: 124 + del self.fields[field.var] 125 + 126 + 127 + def makeFields(self, values, fieldDefs=None, filterUnknown=True): 128 + """ 129 + Create fields from values and add them to this form. 130 + 131 + This creates fields from a mapping of name to value(s) and adds them to 132 + this form. If C{fieldDefs} is not C{None}, this is used to fill in 133 + additional properties of fields, like the field types, labels and 134 + possible options. If C{filterUnknown} is C{True} and C{fieldDefs} is 135 + not C{None}, fields will only be created from C{values} with a 136 + corresponding entry in C{fieldDefs}. 137 + 138 + @param values: Values to create fields from. 139 + @type values: C{dict} 140 + 141 + @param fieldDefs: Field definitions as a dictionary. See 142 + L{wokkel.iwokkel.IPubSubService.getConfigurationOptions} 143 + @type fieldDefs: C{dict} 144 + 145 + @param filterUnknown: If C{True}, ignore fields that are not in 146 + C{fieldDefs}. 147 + @type filterUnknown: C{bool} 148 + """ 149 + for name, value in values.iteritems(): 150 + fieldDict = {'var': name} 151 + 152 + if fieldDefs is not None: 153 + if name in fieldDefs: 154 + fieldDict.update(fieldDefs[name]) 155 + elif filterUnknown: 156 + continue 157 + 158 + if isinstance(value, list): 159 + fieldDict['values'] = value 160 + if 'type' not in fieldDict: 161 + if value and hasattr(value[0], 'full'): 162 + fieldDict['type'] = 'jid-multi' 163 + else: 164 + fieldDict['type'] = 'text-multi' 165 + else: 166 + fieldDict['value'] = value 167 + if 'type' not in fieldDict: 168 + if hasattr(value, 'full'): 169 + fieldDict['type'] = 'jid-single' 170 + elif isinstance(value, bool): 171 + fieldDict['type'] = 'boolean' 172 + 173 + self.addField(Field.fromDict(fieldDict)) 174 + 175 + 176 def toElement(self): 177 + """ 178 + Return the DOM representation of this Form. 179 + 180 + @rtype: L{domish.Element} 181 + """ 182 form = domish.Element((NS_X_DATA, 'x')) 183 form['type'] = self.formType 184 185 @@ -477,7 +549,17 @@ 186 187 return form 188 189 + 190 def getValues(self): 191 + """ 192 + Extract values from the named form fields. 193 + 194 + For all named fields, the corresponding value or values are 195 + returned in a dictionary keyed by the field name. For multi-value 196 + fields, the dictionary value is a list, otherwise a single value. 197 + 198 + @rtype: C{dict} 199 + """ 200 values = {} 201 202 for name, field in self.fields.iteritems(): 203 @@ -489,3 +571,48 @@ 204 values[name] = value 205 206 return values 207 + 208 + 209 + def typeCheck(self, fieldDefs, filterUnknown=False): 210 + """ 211 + Check values of fields according to the field definition. 212 + 213 + This method walks all named fields to check their values against their 214 + type. The field definition in C{fieldDefs} is used to check the field 215 + type. Unknown fields are ignored. 216 + 217 + If the field type is C{None} (when not set by the receiving entity), 218 + C{'text-single'} is assumed, as this is the default value. 219 + 220 + @param fieldDefs: Field definitions as a dictionary. See 221 + L{wokkel.iwokkel.IPubSubService.getConfigurationOptions} 222 + @type fieldDefs: C{dict} 223 + 224 + @param filterUnknown: If C{True}, remove fields that are not in 225 + C{fieldDefs}. 226 + @type filterUnknown: C{bool} 227 + """ 228 + 229 + filtered = [] 230 + 231 + for name, field in self.fields.iteritems(): 232 + if name in fieldDefs: 233 + if field.fieldType is None: 234 + field.fieldType = fieldDefs[name]['type'] 235 + elif field.fieldType != fieldDefs[name]['type']: 236 + raise TypeError("Field type for %r is %r, expected %r" % 237 + (name, 238 + field.fieldType, 239 + fieldDefs[name]['type'])) 240 + else: 241 + # Field type is correct 242 + pass 243 + field.typeCheck() 244 + elif filterUnknown: 245 + filtered.append(field) 246 + else: 247 + # Unknown field, not filtering 248 + pass 249 + 250 + for field in filtered: 251 + self.removeField(field) 252 diff -r 3ef9bc7a0d70 wokkel/pubsub.py 253 --- a/wokkel/pubsub.py Wed Dec 30 16:53:05 2009 +0100 254 +++ b/wokkel/pubsub.py Wed Dec 30 21:05:59 2009 +0100 1 diff -r 3f7b69ddecb4 wokkel/pubsub.py 2 --- a/wokkel/pubsub.py Wed Dec 30 21:44:18 2009 +0100 3 +++ b/wokkel/pubsub.py Wed Dec 30 21:45:01 2009 +0100 255 4 @@ -228,7 +228,7 @@ 256 5 # Map request verb to parameter handler names … … 262 11 'optionsGet': ['nodeOrEmpty', 'jid'], 263 12 'optionsSet': ['nodeOrEmpty', 'jid', 'options'], 264 @@ -380,10 +380,8 @@ 265 """ 266 form = PubSubRequest._findForm(verbElement, NS_PUBSUB_NODE_CONFIG) 267 if form: 268 - if form.formType == 'submit': 269 - self.options = form.getValues() 270 - elif form.formType == 'cancel': 271 - self.options = {} 272 + if form.formType in ('submit', 'cancel'): 273 + self.options = form 274 else: 275 raise BadRequest(text="Unexpected form type %r" % form.formType) 276 else: 277 @@ -439,38 +437,71 @@ 278 def _parse_options(self, verbElement): 279 form = PubSubRequest._findForm(verbElement, NS_PUBSUB_SUBSCRIBE_OPTIONS) 280 if form: 281 - if form.formType == 'submit': 282 - self.options = form.getValues() 283 - elif form.formType == 'cancel': 284 - self.options = {} 285 - else: 286 + if form.formType not in ('submit', 'cancel'): 287 raise BadRequest(text="Unexpected form type %r" % form.formType) 288 + self.options = form 13 @@ -419,29 +419,65 @@ 289 14 else: 290 15 raise BadRequest(text="Missing options form") … … 298 23 + for element in verbElement.parent.elements(): 299 24 + if element.name == 'options' and element.uri == NS_PUBSUB: 300 + form = PubSubRequest._findForm(element,301 + 25 + form = data_form.findForm(element, 26 + NS_PUBSUB_SUBSCRIBE_OPTIONS) 302 27 + if not form: 303 28 + continue … … 357 82 """ 358 83 Send this request to its recipient. 359 @@ -6 74,7 +705,8 @@84 @@ -645,7 +681,8 @@ 360 85 return request.send(self.xmlstream) 361 86 … … 367 92 Subscribe to a publish subscribe node. 368 93 369 @@ -6 85,6 +717,8 @@94 @@ -656,6 +693,8 @@ 370 95 @param subscriber: The entity to subscribe to the node. This entity 371 96 will get notifications of new published items. … … 376 101 request = PubSubRequest('subscribe') 377 102 request.recipient = service 378 @@ -6 92,6 +726,12 @@103 @@ -663,6 +702,12 @@ 379 104 request.subscriber = subscriber 380 105 request.sender = sender … … 389 114 subscription = iq.pubsub.subscription["subscription"] 390 115 391 @@ -956,6 +996,8 @@ 392 handlerName, argNames = self._legacyHandlers[request.verb] 393 handler = getattr(self, handlerName) 394 args = [getattr(request, arg) for arg in argNames] 395 + if 'options' in argNames: 396 + args[argNames.index('options')] = request.options.getValues() 397 d = handler(*args) 398 399 # If needed, translate the result into a response 400 @@ -1012,55 +1054,17 @@ 401 return None 402 403 404 - def _makeFields(self, options, values): 405 - fields = [] 406 - for name, value in values.iteritems(): 407 - if name not in options: 408 - continue 409 - 410 - option = {'var': name} 411 - option.update(options[name]) 412 - if isinstance(value, list): 413 - option['values'] = value 414 - else: 415 - option['value'] = value 416 - fields.append(data_form.Field.fromDict(option)) 417 - return fields 418 - 419 - 420 def _formFromConfiguration(self, resource, values): 421 - options = resource.getConfigurationOptions() 422 - fields = self._makeFields(options, values) 423 + fieldDefs = resource.getConfigurationOptions() 424 form = data_form.Form(formType="form", 425 - formNamespace=NS_PUBSUB_NODE_CONFIG, 426 - fields=fields) 427 - 428 + formNamespace=NS_PUBSUB_NODE_CONFIG) 429 + form.makeFields(values, fieldDefs) 430 return form 431 432 433 - def _checkConfiguration(self, resource, values): 434 - options = resource.getConfigurationOptions() 435 - processedValues = {} 436 - 437 - for key, value in values.iteritems(): 438 - if key not in options: 439 - continue 440 - 441 - option = {'var': key} 442 - option.update(options[key]) 443 - field = data_form.Field.fromDict(option) 444 - if isinstance(value, list): 445 - field.values = value 446 - else: 447 - field.value = value 448 - field.typeCheck() 449 - 450 - if isinstance(value, list): 451 - processedValues[key] = field.values 452 - else: 453 - processedValues[key] = field.value 454 - 455 - return processedValues 456 + def _checkConfiguration(self, resource, form): 457 + fieldDefs = resource.getConfigurationOptions() 458 + form.typeCheck(fieldDefs, filterUnknown=True) 459 460 461 def _preProcess_default(self, resource, request): 462 @@ -1091,12 +1095,11 @@ 463 464 465 def _preProcess_configureSet(self, resource, request): 466 - if request.options: 467 - request.options = self._checkConfiguration(resource, 468 - request.options) 469 + if request.options.formType == 'cancel': 470 + return None 471 + else: 472 + self._checkConfiguration(resource, request.options) 473 return request 474 - else: 475 - return None 476 477 478 def _toResponse_items(self, result, resource, request): 479 diff -r 3ef9bc7a0d70 wokkel/test/test_pubsub.py 480 --- a/wokkel/test/test_pubsub.py Wed Dec 30 16:53:05 2009 +0100 481 +++ b/wokkel/test/test_pubsub.py Wed Dec 30 21:05:59 2009 +0100 116 diff -r 3f7b69ddecb4 wokkel/test/test_pubsub.py 117 --- a/wokkel/test/test_pubsub.py Wed Dec 30 21:44:18 2009 +0100 118 +++ b/wokkel/test/test_pubsub.py Wed Dec 30 21:45:01 2009 +0100 482 119 @@ -447,6 +447,37 @@ 483 120 return d … … 557 194 """ 558 195 Test parsing an unsubscription request. 559 @@ -805,7 +868,7 @@560 self.assertEqual(JID('pubsub.example.org'), request.recipient)561 self.assertEqual('test', request.nodeIdentifier)562 self.assertEqual(JID('user@example.org/Home'), request.subscriber)563 - self.assertEqual({'pubsub#deliver': '1'}, request.options)564 + self.assertEqual({'pubsub#deliver': '1'}, request.options.getValues())565 566 567 def test_fromElementOptionsSetCancel(self):568 @@ -825,7 +888,7 @@569 """570 571 request = pubsub.PubSubRequest.fromElement(parseXml(xml))572 - self.assertEqual({}, request.options)573 + self.assertEqual('cancel', request.options.formType)574 575 576 def test_fromElementOptionsSetBadFormType(self):577 @@ -1053,7 +1116,8 @@578 self.assertEqual(JID('pubsub.example.org'), request.recipient)579 self.assertEqual('test', request.nodeIdentifier)580 self.assertEqual({'pubsub#deliver_payloads': '0',581 - 'pubsub#persist_items': '1'}, request.options)582 + 'pubsub#persist_items': '1'},583 + request.options.getValues())584 585 586 def test_fromElementConfigureSetCancel(self):587 @@ -1073,7 +1137,7 @@588 """589 590 request = pubsub.PubSubRequest.fromElement(parseXml(xml))591 - self.assertEqual({}, request.options)592 + self.assertEqual('cancel', request.options.formType)593 594 595 def test_fromElementConfigureSetBadFormType(self):596 @@ -1895,7 +1959,7 @@597 return defer.succeed({'pubsub#deliver_payloads': '0',598 'pubsub#persist_items': '1',599 'pubsub#owner': JID('user@example.org'),600 - 'x-myfield': ['a', 'b']})601 + 'x-myfield': 'a'})602 603 def cb(element):604 self.assertEqual('pubsub', element.name)605 @@ -1968,7 +2032,8 @@606 607 def configureSet(request):608 self.assertEqual({'pubsub#deliver_payloads': False,609 - 'pubsub#persist_items': True}, request.options)610 + 'pubsub#persist_items': True},611 + request.options.getValues())612 return defer.succeed(None)613 614 self.resource.getConfigurationOptions = getConfigurationOptions615 @@ -2040,7 +2105,7 @@616 617 def configureSet(request):618 self.assertEquals(['pubsub#deliver_payloads'],619 - request.options.keys())620 + request.options.fields.keys())621 622 self.resource.getConfigurationOptions = getConfigurationOptions623 self.resource.configureSet = configureSet624 @@ -2595,6 +2660,48 @@625 return d626 627 628 + def test_setConfigurationOptionsDict(self):629 + """630 + Options should be passed as a dictionary, not a form.631 + """632 +633 + xml = """634 + <iq type='set' to='pubsub.example.org'635 + from='user@example.org'>636 + <pubsub xmlns='http://jabber.org/protocol/pubsub#owner'>637 + <configure node='test'>638 + <x xmlns='jabber:x:data' type='submit'>639 + <field var='FORM_TYPE' type='hidden'>640 + <value>http://jabber.org/protocol/pubsub#node_config</value>641 + </field>642 + <field var='pubsub#deliver_payloads'><value>0</value></field>643 + <field var='pubsub#persist_items'><value>1</value></field>644 + </x>645 + </configure>646 + </pubsub>647 + </iq>648 + """649 +650 + def getConfigurationOptions():651 + return {652 + "pubsub#persist_items":653 + {"type": "boolean",654 + "label": "Persist items to storage"},655 + "pubsub#deliver_payloads":656 + {"type": "boolean",657 + "label": "Deliver payloads with event notifications"}658 + }659 +660 + def setConfiguration(requestor, service, nodeIdentifier, options):661 + self.assertEquals({'pubsub#deliver_payloads': False,662 + 'pubsub#persist_items': True}, options)663 +664 +665 + self.service.getConfigurationOptions = getConfigurationOptions666 + self.service.setConfiguration = setConfiguration667 + return self.handleRequest(xml)668 +669 +670 def test_items(self):671 """672 Non-overridden L{PubSubService.items} yields unsupported error. -
series
r18 r21 1 pubsub-forms.patch 2 pubsub-request-options-form.patch 3 findform.patch 4 form-coerce-values.patch 1 5 pubsub-subscription-options.patch 2 6 pubsub-create-configure.patch
Note: See TracChangeset
for help on using the changeset viewer.