Hide keyboard shortcuts

Hot-keys on this page

r m x p   toggle line displays

j k   next/prev highlighted chunk

0   (zero) top of page

1   (one) first highlighted chunk

1""" 

2@file 

3@brief Helpers about :epkg:`json`. 

4""" 

5import pprint 

6import numpy 

7import ujson 

8 

9 

10class JsonError(ValueError): 

11 """ 

12 Raised when serialization to json does not work. 

13 """ 

14 

15 def __init__(self, obj, data=None): 

16 

17 msg = pprint.pformat(obj) 

18 if len(msg) > 2000: 

19 msg = msg[:2000] + "\n..." 

20 msg2 = pprint.pformat(data) 

21 if len(msg2) > 2000: 

22 msg2 = msg2[:2000] + "\n..." 

23 ValueError.__init__( 

24 self, "Unable to serialize object of type '{}' into json.\n{}\n----\n{}".format( 

25 type(obj), msg, msg2)) 

26 

27 

28def json_dumps(obj): 

29 """ 

30 Dumps an object into :epkg:`json`. 

31 

32 @param X object 

33 @return json 

34 """ 

35 def _modify(o): 

36 return dict(shape=o.shape, dtype=str(o.dtype), 

37 data=o.tolist(), ___=1) 

38 

39 if isinstance(obj, numpy.ndarray): 

40 obj = _modify(obj) 

41 elif isinstance(obj, dict): 

42 obj = {k: (_modify(v) if isinstance(v, numpy.ndarray) else v) 

43 for k, v in obj.items()} 

44 try: 

45 return ujson.dumps(obj, reject_bytes=False) 

46 except UnicodeDecodeError: 

47 raise JsonError(obj) 

48 

49 

50def json_loads(jsdata): 

51 """ 

52 Loads an object from :epkg:`json`. 

53 

54 @param jsdata json 

55 @return object 

56 """ 

57 obj = ujson.loads(jsdata) 

58 if isinstance(obj, dict): 

59 if '___' in obj: 

60 # numpy array 

61 shape = obj['shape'] 

62 obj = numpy.array(obj['data'], dtype=obj['dtype']) 

63 obj = obj.reshape(tuple(shape)) 

64 else: 

65 up = {} 

66 for k, v in obj.items(): 

67 if isinstance(v, dict) and '___' in v: 

68 shape = v['shape'] 

69 v = numpy.array(v['data'], dtype=v['dtype']) 

70 v = v.reshape(tuple(shape)) 

71 up[k] = v 

72 obj.update(up) 

73 return obj