Mercurial > p > roundup > code
comparison roundup/rest.py @ 5689:2c516d113620
Fix encoding for incoming json requests
First version of patch by John P. Rouillard
| author | Ralf Schlatterbeck <rsc@runtux.com> |
|---|---|
| date | Wed, 03 Apr 2019 12:08:18 +0200 |
| parents | 83037aaf3b9d |
| children | 4aae822e2cb4 |
comparison
equal
deleted
inserted
replaced
| 5688:1b9ef04b9528 | 5689:2c516d113620 |
|---|---|
| 31 dicttoxml = None | 31 dicttoxml = None |
| 32 | 32 |
| 33 from roundup import hyperdb | 33 from roundup import hyperdb |
| 34 from roundup import date | 34 from roundup import date |
| 35 from roundup import actions | 35 from roundup import actions |
| 36 from roundup.anypy.strings import bs2b, b2s | 36 from roundup.anypy.strings import bs2b, b2s, u2s, is_us |
| 37 from roundup.exceptions import * | 37 from roundup.exceptions import * |
| 38 from roundup.cgi.exceptions import * | 38 from roundup.cgi.exceptions import * |
| 39 | 39 |
| 40 from hashlib import md5 | 40 from hashlib import md5 |
| 41 | 41 |
| 600 display_props[i] = class_obj.properties[i] | 600 display_props[i] = class_obj.properties[i] |
| 601 except KeyError as err: | 601 except KeyError as err: |
| 602 raise UsageError("Failed to find property '%s' " | 602 raise UsageError("Failed to find property '%s' " |
| 603 "for class %s."%(i, class_name)) | 603 "for class %s."%(i, class_name)) |
| 604 | 604 |
| 605 | 605 |
| 606 else: # serve the filter purpose | 606 else: # serve the filter purpose |
| 607 prop = class_obj.getprops()[key] | 607 prop = class_obj.getprops()[key] |
| 608 # We drop properties without search permission silently | 608 # We drop properties without search permission silently |
| 609 # This reflects the current behavior of other roundup | 609 # This reflects the current behavior of other roundup |
| 610 # interfaces | 610 # interfaces |
| 1548 output = self.error_obj(400, msg) | 1548 output = self.error_obj(400, msg) |
| 1549 | 1549 |
| 1550 # FIXME: do we need to raise an error if client did not specify | 1550 # FIXME: do we need to raise an error if client did not specify |
| 1551 # version? This may be a good thing to require. Note that: | 1551 # version? This may be a good thing to require. Note that: |
| 1552 # Accept: application/json; version=1 may not be legal but.... | 1552 # Accept: application/json; version=1 may not be legal but.... |
| 1553 | 1553 |
| 1554 # Call the appropriate method | 1554 # Call the appropriate method |
| 1555 try: | 1555 try: |
| 1556 # If output was defined by a prior error | 1556 # If output was defined by a prior error |
| 1557 # condition skip call | 1557 # condition skip call |
| 1558 if not output: | 1558 if not output: |
| 1592 result = str(obj) | 1592 result = str(obj) |
| 1593 return result | 1593 return result |
| 1594 | 1594 |
| 1595 class SimulateFieldStorageFromJson(): | 1595 class SimulateFieldStorageFromJson(): |
| 1596 ''' | 1596 ''' |
| 1597 The internals of the rest interface assume the data was sent as | 1597 The internals of the rest interface assume the data was sent as |
| 1598 application/x-www-form-urlencoded. So we should have a | 1598 application/x-www-form-urlencoded. So we should have a |
| 1599 FieldStorage and MiniFieldStorage structure. | 1599 FieldStorage and MiniFieldStorage structure. |
| 1600 | 1600 |
| 1601 However if we want to handle json data, we need to: | 1601 However if we want to handle json data, we need to: |
| 1602 1) create the Fieldstorage/MiniFieldStorage structure | 1602 1) create the Fieldstorage/MiniFieldStorage structure |
| 1603 or | 1603 or |
| 1614 ''' | 1614 ''' |
| 1615 def __init__(self, json_string): | 1615 def __init__(self, json_string): |
| 1616 ''' Parse the json string into an internal dict. ''' | 1616 ''' Parse the json string into an internal dict. ''' |
| 1617 def raise_error_on_constant(x): | 1617 def raise_error_on_constant(x): |
| 1618 raise ValueError("Unacceptable number: %s"%x) | 1618 raise ValueError("Unacceptable number: %s"%x) |
| 1619 | |
| 1620 self.json_dict = json.loads(json_string, | 1619 self.json_dict = json.loads(json_string, |
| 1621 parse_constant = raise_error_on_constant) | 1620 parse_constant = raise_error_on_constant) |
| 1622 self.value = [ self.FsValue(index, self.json_dict[index]) for index in self.json_dict.keys() ] | 1621 self.value = [ self.FsValue(index, self.json_dict[index]) for index in self.json_dict.keys() ] |
| 1623 | 1622 |
| 1624 class FsValue: | 1623 class FsValue: |
| 1625 '''Class that does nothing but response to a .value property ''' | 1624 '''Class that does nothing but response to a .value property ''' |
| 1626 def __init__(self, name, val): | 1625 def __init__(self, name, val): |
| 1627 self.name=name | 1626 self.name=u2s(name) |
| 1628 self.value=val | 1627 if is_us(val): |
| 1628 self.value=u2s(val) | |
| 1629 elif type(val) == type([]): | |
| 1630 self.value = [ u2s(v) for v in val ] | |
| 1631 else: | |
| 1632 self.value = str(val) | |
| 1629 | 1633 |
| 1630 def __getitem__(self, index): | 1634 def __getitem__(self, index): |
| 1631 '''Return an FsValue created from the value of self.json_dict[index] | 1635 '''Return an FsValue created from the value of self.json_dict[index] |
| 1632 ''' | 1636 ''' |
| 1633 return self.FsValue(index, self.json_dict[index]) | 1637 return self.FsValue(index, self.json_dict[index]) |
