Changeset 4454
- Timestamp:
- 01/30/07 16:34:15 (2 years ago)
- Files:
-
- django/trunk/django/utils/simplejson/decoder.py (modified) (3 diffs)
- django/trunk/django/utils/simplejson/encoder.py (modified) (10 diffs)
- django/trunk/django/utils/simplejson/__init__.py (modified) (8 diffs)
- django/trunk/django/utils/simplejson/jsonfilter.py (added)
- django/trunk/django/utils/simplejson/LICENSE.txt (modified) (1 diff)
- django/trunk/django/utils/simplejson/scanner.py (modified) (1 diff)
Legend:
- Unmodified
- Added
- Removed
- Modified
- Copied
- Moved
django/trunk/django/utils/simplejson/decoder.py
r4265 r4454 128 128 end += 1 129 129 encoding = getattr(context, 'encoding', None) 130 iterscan = JSONScanner.iterscan 130 131 while True: 131 132 key, end = scanstring(s, end, encoding) … … 135 136 end = _w(s, end + 1).end() 136 137 try: 137 value, end = JSONScanner.iterscan(s, idx=end).next()138 value, end = iterscan(s, idx=end, context=context).next() 138 139 except StopIteration: 139 140 raise ValueError(errmsg("Expecting object", s, end)) … … 165 166 if nextchar == ']': 166 167 return values, end + 1 168 iterscan = JSONScanner.iterscan 167 169 while True: 168 170 try: 169 value, end = JSONScanner.iterscan(s, idx=end).next()171 value, end = iterscan(s, idx=end, context=context).next() 170 172 except StopIteration: 171 173 raise ValueError(errmsg("Expecting object", s, end)) django/trunk/django/utils/simplejson/encoder.py
r4265 r4454 4 4 import re 5 5 6 # this should match any kind of infinity7 INFCHARS = re.compile(r'[infINF]')8 6 ESCAPE = re.compile(r'[\x00-\x19\\"\b\f\n\r\t]') 9 ESCAPE_ASCII = re.compile(r'([\\" ]|[^\ -~])')7 ESCAPE_ASCII = re.compile(r'([\\"/]|[^\ -~])') 10 8 ESCAPE_DCT = { 9 # escape all forward slashes to prevent </script> attack 10 '/': '\\/', 11 11 '\\': '\\\\', 12 12 '"': '\\"', … … 17 17 '\t': '\\t', 18 18 } 19 for i in range( 20):19 for i in range(0x20): 20 20 ESCAPE_DCT.setdefault(chr(i), '\\u%04x' % (i,)) 21 21 22 # assume this produces an infinity on all machines (probably not guaranteed) 23 INFINITY = float('1e66666') 24 22 25 def floatstr(o, allow_nan=True): 23 s = str(o) 24 # If the first non-sign is a digit then it's not a special value 25 if (o < 0.0 and s[1].isdigit()) or s[0].isdigit(): 26 return s 27 elif not allow_nan: 26 # Check for specials. Note that this type of test is processor- and/or 27 # platform-specific, so do tests which don't depend on the internals. 28 29 if o != o: 30 text = 'NaN' 31 elif o == INFINITY: 32 text = 'Infinity' 33 elif o == -INFINITY: 34 text = '-Infinity' 35 else: 36 return str(o) 37 38 if not allow_nan: 28 39 raise ValueError("Out of range float values are not JSON compliant: %r" 29 40 % (o,)) 30 # These are the string representations on the platforms I've tried 31 if s == 'nan': 32 return 'NaN' 33 if s == 'inf': 34 return 'Infinity' 35 if s == '-inf': 36 return '-Infinity' 37 # NaN should either be inequal to itself, or equal to everything 38 if o != o or o == 0.0: 39 return 'NaN' 40 # Last ditch effort, assume inf 41 if o < 0: 42 return '-Infinity' 43 return 'Infinity' 41 42 return text 43 44 44 45 45 def encode_basestring(s): … … 91 91 """ 92 92 __all__ = ['__init__', 'default', 'encode', 'iterencode'] 93 item_separator = ', ' 94 key_separator = ': ' 93 95 def __init__(self, skipkeys=False, ensure_ascii=True, 94 check_circular=True, allow_nan=True, sort_keys=False): 96 check_circular=True, allow_nan=True, sort_keys=False, 97 indent=None, separators=None): 95 98 """ 96 99 Constructor for JSONEncoder, with sensible defaults. … … 117 120 sorted by key; this is useful for regression tests to ensure 118 121 that JSON serializations can be compared on a day-to-day basis. 122 123 If indent is a non-negative integer, then JSON array 124 elements and object members will be pretty-printed with that 125 indent level. An indent level of 0 will only insert newlines. 126 None is the most compact representation. 127 128 If specified, separators should be a (item_separator, key_separator) 129 tuple. The default is (', ', ': '). To get the most compact JSON 130 representation you should specify (',', ':') to eliminate whitespace. 119 131 """ 120 132 … … 124 136 self.allow_nan = allow_nan 125 137 self.sort_keys = sort_keys 138 self.indent = indent 139 self.current_indent_level = 0 140 if separators is not None: 141 self.item_separator, self.key_separator = separators 142 143 def _newline_indent(self): 144 return '\n' + (' ' * (self.indent * self.current_indent_level)) 126 145 127 146 def _iterencode_list(self, lst, markers=None): … … 135 154 markers[markerid] = lst 136 155 yield '[' 156 if self.indent is not None: 157 self.current_indent_level += 1 158 newline_indent = self._newline_indent() 159 separator = self.item_separator + newline_indent 160 yield newline_indent 161 else: 162 newline_indent = None 163 separator = self.item_separator 137 164 first = True 138 165 for value in lst: … … 140 167 first = False 141 168 else: 142 yield ', '169 yield separator 143 170 for chunk in self._iterencode(value, markers): 144 171 yield chunk 172 if newline_indent is not None: 173 self.current_indent_level -= 1 174 yield self._newline_indent() 145 175 yield ']' 146 176 if markers is not None: … … 157 187 markers[markerid] = dct 158 188 yield '{' 189 key_separator = self.key_separator 190 if self.indent is not None: 191 self.current_indent_level += 1 192 newline_indent = self._newline_indent() 193 item_separator = self.item_separator + newline_indent 194 yield newline_indent 195 else: 196 newline_indent = None 197 item_separator = self.item_separator 159 198 first = True 160 199 if self.ensure_ascii: … … 166 205 keys = dct.keys() 167 206 keys.sort() 168 items = [(k, dct[k]) for k in keys]207 items = [(k, dct[k]) for k in keys] 169 208 else: 170 209 items = dct.iteritems() … … 191 230 first = False 192 231 else: 193 yield ', '232 yield item_separator 194 233 yield encoder(key) 195 yield ': '234 yield key_separator 196 235 for chunk in self._iterencode(value, markers): 197 236 yield chunk 237 if newline_indent is not None: 238 self.current_indent_level -= 1 239 yield self._newline_indent() 198 240 yield '}' 199 241 if markers is not None: django/trunk/django/utils/simplejson/__init__.py
r4265 r4454 28 28 '["streaming API"]' 29 29 30 Compact encoding:: 31 32 >>> import simplejson 33 >>> simplejson.dumps([1,2,3,{'4': 5, '6': 7}], separators=(',',':')) 34 '[1,2,3,{"4":5,"6":7}]' 35 36 Pretty printing:: 37 38 >>> import simplejson 39 >>> print simplejson.dumps({'4': 5, '6': 7}, sort_keys=True, indent=4) 40 { 41 "4": 5, 42 "6": 7 43 } 44 30 45 Decoding JSON:: 31 46 … … 69 84 70 85 71 Note that the JSON produced by this module is a subset of YAML,72 so it may be used as a serializer for that as well.86 Note that the JSON produced by this module's default settings 87 is a subset of YAML, so it may be used as a serializer for that as well. 73 88 """ 74 __version__ = '1. 3'89 __version__ = '1.5' 75 90 __all__ = [ 76 91 'dump', 'dumps', 'load', 'loads', … … 82 97 83 98 def dump(obj, fp, skipkeys=False, ensure_ascii=True, check_circular=True, 84 allow_nan=True, cls=None, **kw):99 allow_nan=True, cls=None, indent=None, **kw): 85 100 """ 86 101 Serialize ``obj`` as a JSON formatted stream to ``fp`` (a … … 106 121 JavaScript equivalents (``NaN``, ``Infinity``, ``-Infinity``). 107 122 123 If ``indent`` is a non-negative integer, then JSON array elements and object 124 members will be pretty-printed with that indent level. An indent level 125 of 0 will only insert newlines. ``None`` is the most compact representation. 126 108 127 To use a custom ``JSONEncoder`` subclass (e.g. one that overrides the 109 128 ``.default()`` method to serialize additional types), specify it with … … 113 132 cls = JSONEncoder 114 133 iterable = cls(skipkeys=skipkeys, ensure_ascii=ensure_ascii, 115 check_circular=check_circular, allow_nan=allow_nan, 134 check_circular=check_circular, allow_nan=allow_nan, indent=indent, 116 135 **kw).iterencode(obj) 117 136 # could accelerate with writelines in some versions of Python, at … … 121 140 122 141 def dumps(obj, skipkeys=False, ensure_ascii=True, check_circular=True, 123 allow_nan=True, cls=None, **kw):142 allow_nan=True, cls=None, indent=None, separators=None, **kw): 124 143 """ 125 144 Serialize ``obj`` to a JSON formatted ``str``. … … 142 161 JavaScript equivalents (``NaN``, ``Infinity``, ``-Infinity``). 143 162 163 If ``indent`` is a non-negative integer, then JSON array elements and 164 object members will be pretty-printed with that indent level. An indent 165 level of 0 will only insert newlines. ``None`` is the most compact 166 representation. 167 168 If ``separators`` is an ``(item_separator, dict_separator)`` tuple 169 then it will be used instead of the default ``(', ', ': ')`` separators. 170 ``(',', ':')`` is the most compact JSON representation. 171 144 172 To use a custom ``JSONEncoder`` subclass (e.g. one that overrides the 145 173 ``.default()`` method to serialize additional types), specify it with … … 148 176 if cls is None: 149 177 cls = JSONEncoder 150 return cls(skipkeys=skipkeys, ensure_ascii=ensure_ascii, 151 check_circular=check_circular, allow_nan=allow_nan, **kw).encode(obj) 178 return cls( 179 skipkeys=skipkeys, ensure_ascii=ensure_ascii, 180 check_circular=check_circular, allow_nan=allow_nan, indent=indent, 181 separators=separators, 182 **kw).encode(obj) 152 183 153 184 def load(fp, encoding=None, cls=None, object_hook=None, **kw): django/trunk/django/utils/simplejson/LICENSE.txt
r3232 r4454 1 simplejson 1. 31 simplejson 1.5 2 2 Copyright (c) 2006 Bob Ippolito 3 3 django/trunk/django/utils/simplejson/scanner.py
r4265 r4454 4 4 import sre_parse, sre_compile, sre_constants 5 5 from sre_constants import BRANCH, SUBPATTERN 6 from re import VERBOSE, MULTILINE, DOTALL 6 7 import re 7 8 8 9 __all__ = ['Scanner', 'pattern'] 9 10 10 FLAGS = ( re.VERBOSE | re.MULTILINE | re.DOTALL)11 FLAGS = (VERBOSE | MULTILINE | DOTALL) 11 12 class Scanner(object): 12 13 def __init__(self, lexicon, flags=FLAGS):
