opak 0.1.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
opak-0.1.0/PKG-INFO ADDED
@@ -0,0 +1,12 @@
1
+ Metadata-Version: 2.4
2
+ Name: opak
3
+ Version: 0.1.0
4
+ Summary: Open PAcKer
5
+ Author-email: nzturn <nzturn@gmail.com>
6
+ Classifier: Programming Language :: Python :: 3
7
+ Classifier: Framework :: Jupyter
8
+ Requires-Python: >=3.10
9
+ Description-Content-Type: text/markdown
10
+ Requires-Dist: numpy
11
+
12
+ # Open PAcKer
opak-0.1.0/README.md ADDED
@@ -0,0 +1 @@
1
+ # Open PAcKer
@@ -0,0 +1,258 @@
1
+ from __future__ import annotations
2
+ __all__ = ['encode', 'decode', 'json_patch', 'msgpack_patch']
3
+
4
+ from base64 import b64decode, b64encode
5
+ from typing import TYPE_CHECKING, Any, Callable
6
+ from numpy import frombuffer, generic, ndarray
7
+ from numpy.lib.format import descr_to_dtype, dtype_to_descr
8
+ import pickle,inspect,sys
9
+ cast = True
10
+ try:
11
+ from oasm import table
12
+ except:
13
+ table = None
14
+
15
+ if TYPE_CHECKING: # pragma: no cover
16
+ from _typeshed import SupportsRead
17
+
18
+ def encode(
19
+ o: Any, *, b64: bool = False, chain: Callable[[Any], dict[str, Any]] | None = None
20
+ ) -> dict[str, Any]:
21
+ """Encodes numpy objects to a dict-serializable dictionary.
22
+
23
+ Args:
24
+ o (object): The object to encode.
25
+ chain (Callable[[Any], dict[str, Any]] | None): A fallback encoder function to handle objects that are not numpy objects.
26
+
27
+ Returns:
28
+ dict[str, Any]: The dict-serializable dictionary representation of the numpy object, or the result of the fallback encoder if present and if the object is not a numpy object.
29
+
30
+ Raises:
31
+ TypeError: If the object is not dict serializable.
32
+ """
33
+ if isinstance(o, (ndarray, generic)):
34
+ if o.dtype == 'O':
35
+ data = o.dumps()
36
+ elif o.flags['C_CONTIGUOUS']:
37
+ data = o.data
38
+ else:
39
+ data = o.tobytes()
40
+ return {
41
+ "__numpy__": b64encode(data).decode() if b64 else bytes(data),
42
+ "dtype": dtype_to_descr(o.dtype),
43
+ "shape": list(o.shape),
44
+ }
45
+ elif isinstance(o, complex):
46
+ return {'__complex__':o.__repr__()}
47
+ elif cast and (type(o) is type or type(o).__name__ == 'function'):
48
+ try:
49
+ return {'':[o.__name__,inspect.getsource(o)]}|(
50
+ {} if type(o) is type else o.__dict__)
51
+ except:
52
+ pass
53
+ elif table is not None and isinstance(o, table):
54
+ return table.to_dict(o)
55
+
56
+ module = getattr(o,'__module__',None)
57
+ name = getattr(o,'__name__',None)
58
+ if cast and (module is not None and name is not None):
59
+ return {'':module+'.'+name}
60
+ return o if chain is None else chain(o)
61
+
62
+ env = globals()
63
+ def decode(dct: dict, b64: bool = False, chain: Callable[[Any], dict[str, Any]] | None = None) -> dict | ndarray | generic:
64
+ """Custom object hook function for decoding dict objects into numpy arrays.
65
+
66
+ Args:
67
+ dct (dict): The dictionary to decode.
68
+
69
+ Returns:
70
+ dict | np.ndarray | np.generic: The decoded numpy object or the original dictionary.
71
+ """
72
+ if "__numpy__" in dct:
73
+ data = dct['__numpy__']
74
+ if b64:
75
+ data = b64decode(data)
76
+ dtype = descr_to_dtype(dct['dtype'])
77
+ if dtype == 'O':
78
+ return pickle.loads(data)
79
+ else:
80
+ obj = frombuffer(data,dtype)
81
+ return obj.reshape(shape) if (shape := dct['shape']) else obj[0]
82
+ elif '__complex__' in dct:
83
+ return complex(dct['__complex__'])
84
+ elif cast and ('' in dct):
85
+ obj = dct['']
86
+ if type(obj) is str:
87
+ obj = obj.split('.')
88
+ module = sys.modules.get('.'.join(obj[:-1]),None)
89
+ return None if module is None else getattr(module,obj[-1],None)
90
+ else:
91
+ obj,src = obj
92
+ if obj == '<lambda>':
93
+ obj = eval('lambda '+'lambda'.join(src.split('lambda')[1:]).strip(),env)
94
+ else:
95
+ exec(src,env)
96
+ obj = env[obj]
97
+ del dct['']
98
+ if type(obj) is not type:
99
+ obj.__dict__.update(dct)
100
+ return obj
101
+ if table is not None:
102
+ dct = table.from_dict(dct)
103
+ return dct if chain is None else chain(dct)
104
+
105
+ import json
106
+ _dumps = json.dumps
107
+ _loads = json.loads
108
+ _dump = json.dump
109
+
110
+ def _encoder(
111
+ *args: Any,
112
+ default: Callable[[Any], Any] | None = None,
113
+ user_cls: type[json.JSONEncoder] | None = None,
114
+ **kwargs: Any,
115
+ ) -> json.JSONEncoder:
116
+ """Ensures cooperation with the provided `default` and/or `cls` by manipulating the JSONEncoder."""
117
+ if user_cls is None:
118
+ user_cls = json.JSONEncoder
119
+ elif default is None:
120
+ encoder = user_cls(*args, **kwargs)
121
+ encoder.default = lambda obj:encode(obj,b64=True,chain=encoder.default) # type: ignore[method-assign]
122
+ return encoder
123
+ return user_cls(
124
+ *args, default=lambda obj:encode(obj,b64=True,chain=default), **kwargs
125
+ )
126
+
127
+ def dumps(*args: Any, cls: type[json.JSONEncoder] | None = None, **kwargs: Any) -> str:
128
+ kwargs["user_cls"] = cls
129
+ return _dumps(*table.to_dict(args), cls=_encoder, **kwargs) # type: ignore[arg-type]
130
+
131
+ def loads(
132
+ *args: Any, object_hook: Callable[[dict], Any] | None = None, **kwargs: Any
133
+ ) -> Any:
134
+ return _loads(
135
+ *args,
136
+ object_hook=lambda dct:decode(dct,b64=True,chain=object_hook),
137
+ **kwargs,
138
+ )
139
+
140
+ def dump(*args: Any, cls: type[json.JSONEncoder] | None = None, **kwargs: Any) -> None:
141
+ kwargs["user_cls"] = cls
142
+ return _dump(*table.to_dict(args), cls=_encoder, **kwargs) # type: ignore[arg-type]
143
+
144
+ def load(fp: SupportsRead[str | bytes], **kwargs: Any) -> Any:
145
+ return loads(fp.read(), **kwargs)
146
+
147
+ def json_patch() -> None:
148
+ """Monkey patch json module to support encoding/decoding NumPy arrays/scalars."""
149
+ json.dumps = dumps
150
+ json.loads = loads
151
+ json.dump = dump
152
+ json.load = load
153
+
154
+ try:
155
+ import msgpack
156
+ from msgpack import Packer as _Packer, Unpacker as _Unpacker, \
157
+ unpack as _unpack, unpackb as _unpackb
158
+ except:
159
+ _Packer = object
160
+ _Unpacker = object
161
+
162
+ class Packer(_Packer):
163
+ def __init__(self,
164
+ default=None,
165
+ use_single_float=False,
166
+ autoreset=True,
167
+ use_bin_type=True,
168
+ strict_types=True,
169
+ datetime=False,
170
+ unicode_errors=None):
171
+ super(Packer, self).__init__(default=lambda obj:encode(obj,chain=default),
172
+ use_single_float=use_single_float,
173
+ autoreset=autoreset,
174
+ use_bin_type=use_bin_type,
175
+ strict_types=strict_types,
176
+ datetime=datetime,
177
+ unicode_errors=unicode_errors)
178
+
179
+ class Unpacker(_Unpacker):
180
+ def __init__(self,
181
+ file_like=None,
182
+ read_size=0,
183
+ use_list=True,
184
+ raw=False,
185
+ timestamp=0,
186
+ strict_map_key=True,
187
+ object_hook=None,
188
+ object_pairs_hook=None,
189
+ list_hook=None,
190
+ unicode_errors=None,
191
+ max_buffer_size=100 * 1024 * 1024,
192
+ ext_hook=msgpack.ExtType,
193
+ max_str_len=-1,
194
+ max_bin_len=-1,
195
+ max_array_len=-1,
196
+ max_map_len=-1,
197
+ max_ext_len=-1):
198
+ super(Unpacker, self).__init__(file_like=file_like,
199
+ read_size=read_size,
200
+ use_list=use_list,
201
+ raw=raw,
202
+ timestamp=timestamp,
203
+ strict_map_key=strict_map_key,
204
+ object_hook=lambda dct:decode(dct,chain=object_hook),
205
+ object_pairs_hook=object_pairs_hook,
206
+ list_hook=list_hook,
207
+ unicode_errors=unicode_errors,
208
+ max_buffer_size=max_buffer_size,
209
+ ext_hook=ext_hook,
210
+ max_str_len=max_str_len,
211
+ max_bin_len=max_bin_len,
212
+ max_array_len=max_array_len,
213
+ max_map_len=max_map_len,
214
+ max_ext_len=max_ext_len)
215
+
216
+ def pack(o, stream, **kwargs):
217
+ """
218
+ Pack an object and write it to a stream.
219
+ """
220
+ packer = Packer(**kwargs)
221
+ stream.write(packer.pack(o))
222
+
223
+ def packb(o, **kwargs):
224
+ """
225
+ Pack an object and return the packed bytes.
226
+ """
227
+ return Packer(**kwargs).pack(o)
228
+
229
+ def unpack(stream, **kwargs):
230
+ """
231
+ Unpack a packed object from a stream.
232
+ """
233
+ object_hook = kwargs.get('object_hook')
234
+ kwargs['object_hook'] = lambda dct:decode(dct,chain=object_hook)
235
+ return _unpack(stream, **kwargs)
236
+
237
+ def unpackb(packed, **kwargs):
238
+ """
239
+ Unpack a packed object.
240
+ """
241
+ object_hook = kwargs.get('object_hook')
242
+ kwargs['object_hook'] = lambda dct:decode(dct,chain=object_hook)
243
+ return _unpackb(packed, **kwargs)
244
+
245
+ def msgpack_patch():
246
+ """
247
+ Monkey patch msgpack module to enable support for serializing numpy types.
248
+ """
249
+ setattr(msgpack, 'Packer', Packer)
250
+ setattr(msgpack, 'Unpacker', Unpacker)
251
+ setattr(msgpack, 'load', unpack)
252
+ setattr(msgpack, 'loads', unpackb)
253
+ setattr(msgpack, 'dump', pack)
254
+ setattr(msgpack, 'dumps', packb)
255
+ setattr(msgpack, 'pack', pack)
256
+ setattr(msgpack, 'packb', packb)
257
+ setattr(msgpack, 'unpack', unpack)
258
+ setattr(msgpack, 'unpackb', unpackb)
@@ -0,0 +1,12 @@
1
+ Metadata-Version: 2.4
2
+ Name: opak
3
+ Version: 0.1.0
4
+ Summary: Open PAcKer
5
+ Author-email: nzturn <nzturn@gmail.com>
6
+ Classifier: Programming Language :: Python :: 3
7
+ Classifier: Framework :: Jupyter
8
+ Requires-Python: >=3.10
9
+ Description-Content-Type: text/markdown
10
+ Requires-Dist: numpy
11
+
12
+ # Open PAcKer
@@ -0,0 +1,8 @@
1
+ README.md
2
+ pyproject.toml
3
+ opak/__init__.py
4
+ opak.egg-info/PKG-INFO
5
+ opak.egg-info/SOURCES.txt
6
+ opak.egg-info/dependency_links.txt
7
+ opak.egg-info/requires.txt
8
+ opak.egg-info/top_level.txt
@@ -0,0 +1 @@
1
+ numpy
@@ -0,0 +1 @@
1
+ opak
@@ -0,0 +1,15 @@
1
+ [project]
2
+ name = "opak"
3
+ version = "0.1.0"
4
+ description = "Open PAcKer"
5
+ readme = "README.md"
6
+ requires-python = ">=3.10"
7
+ authors = [
8
+ { name = "nzturn", email = "nzturn@gmail.com" },
9
+ ]
10
+ classifiers = [
11
+ "Programming Language :: Python :: 3",
12
+ "Framework :: Jupyter",
13
+ ]
14
+
15
+ dependencies = ["numpy"]
opak-0.1.0/setup.cfg ADDED
@@ -0,0 +1,4 @@
1
+ [egg_info]
2
+ tag_build =
3
+ tag_date = 0
4
+