omlish 0.0.0.dev162__py3-none-any.whl → 0.0.0.dev164__py3-none-any.whl
Sign up to get free protection for your applications and to get access to all the features.
- omlish/.manifests.json +228 -0
- omlish/__about__.py +2 -2
- omlish/codecs/__init__.py +69 -0
- omlish/codecs/base.py +102 -0
- omlish/codecs/bytes.py +119 -0
- omlish/codecs/chain.py +23 -0
- omlish/codecs/funcs.py +28 -0
- omlish/codecs/registry.py +139 -0
- omlish/codecs/standard.py +4 -0
- omlish/codecs/text.py +217 -0
- omlish/formats/cbor.py +31 -0
- omlish/formats/codecs.py +93 -0
- omlish/formats/json/codecs.py +33 -0
- omlish/formats/json5.py +31 -0
- omlish/formats/pickle.py +31 -0
- omlish/formats/toml.py +17 -0
- omlish/formats/yaml.py +18 -0
- omlish/io/compress/brotli.py +15 -1
- omlish/io/compress/bz2.py +14 -0
- omlish/io/compress/codecs.py +58 -0
- omlish/io/compress/gzip.py +11 -0
- omlish/io/compress/lz4.py +14 -0
- omlish/io/compress/lzma.py +14 -0
- omlish/io/compress/snappy.py +14 -0
- omlish/io/compress/zlib.py +14 -0
- omlish/io/compress/zstd.py +14 -0
- omlish/lang/__init__.py +1 -0
- omlish/lang/functions.py +11 -0
- omlish/manifests/load.py +44 -6
- {omlish-0.0.0.dev162.dist-info → omlish-0.0.0.dev164.dist-info}/METADATA +1 -1
- {omlish-0.0.0.dev162.dist-info → omlish-0.0.0.dev164.dist-info}/RECORD +35 -20
- {omlish-0.0.0.dev162.dist-info → omlish-0.0.0.dev164.dist-info}/LICENSE +0 -0
- {omlish-0.0.0.dev162.dist-info → omlish-0.0.0.dev164.dist-info}/WHEEL +0 -0
- {omlish-0.0.0.dev162.dist-info → omlish-0.0.0.dev164.dist-info}/entry_points.txt +0 -0
- {omlish-0.0.0.dev162.dist-info → omlish-0.0.0.dev164.dist-info}/top_level.txt +0 -0
omlish/.manifests.json
CHANGED
@@ -23,6 +23,234 @@
|
|
23
23
|
}
|
24
24
|
}
|
25
25
|
},
|
26
|
+
{
|
27
|
+
"module": ".formats.cbor",
|
28
|
+
"attr": "_CBOR_LAZY_CODEC",
|
29
|
+
"file": "omlish/formats/cbor.py",
|
30
|
+
"line": 30,
|
31
|
+
"value": {
|
32
|
+
"$.codecs.base.LazyLoadedCodec": {
|
33
|
+
"mod_name": "omlish.formats.cbor",
|
34
|
+
"attr_name": "CBOR_CODEC",
|
35
|
+
"name": "cbor",
|
36
|
+
"aliases": null
|
37
|
+
}
|
38
|
+
}
|
39
|
+
},
|
40
|
+
{
|
41
|
+
"module": ".formats.json.codecs",
|
42
|
+
"attr": "_JSON_LAZY_CODEC",
|
43
|
+
"file": "omlish/formats/json/codecs.py",
|
44
|
+
"line": 14,
|
45
|
+
"value": {
|
46
|
+
"$.codecs.base.LazyLoadedCodec": {
|
47
|
+
"mod_name": "omlish.formats.json.codecs",
|
48
|
+
"attr_name": "JSON_CODEC",
|
49
|
+
"name": "json",
|
50
|
+
"aliases": null
|
51
|
+
}
|
52
|
+
}
|
53
|
+
},
|
54
|
+
{
|
55
|
+
"module": ".formats.json.codecs",
|
56
|
+
"attr": "_JSON_COMPACT_LAZY_CODEC",
|
57
|
+
"file": "omlish/formats/json/codecs.py",
|
58
|
+
"line": 23,
|
59
|
+
"value": {
|
60
|
+
"$.codecs.base.LazyLoadedCodec": {
|
61
|
+
"mod_name": "omlish.formats.json.codecs",
|
62
|
+
"attr_name": "JSON_COMPACT_CODEC",
|
63
|
+
"name": "json-compact",
|
64
|
+
"aliases": null
|
65
|
+
}
|
66
|
+
}
|
67
|
+
},
|
68
|
+
{
|
69
|
+
"module": ".formats.json.codecs",
|
70
|
+
"attr": "_JSON_PRETTY_LAZY_CODEC",
|
71
|
+
"file": "omlish/formats/json/codecs.py",
|
72
|
+
"line": 32,
|
73
|
+
"value": {
|
74
|
+
"$.codecs.base.LazyLoadedCodec": {
|
75
|
+
"mod_name": "omlish.formats.json.codecs",
|
76
|
+
"attr_name": "JSON_PRETTY_CODEC",
|
77
|
+
"name": "json-pretty",
|
78
|
+
"aliases": null
|
79
|
+
}
|
80
|
+
}
|
81
|
+
},
|
82
|
+
{
|
83
|
+
"module": ".formats.json5",
|
84
|
+
"attr": "_JSON5_LAZY_CODEC",
|
85
|
+
"file": "omlish/formats/json5.py",
|
86
|
+
"line": 30,
|
87
|
+
"value": {
|
88
|
+
"$.codecs.base.LazyLoadedCodec": {
|
89
|
+
"mod_name": "omlish.formats.json5",
|
90
|
+
"attr_name": "JSON5_CODEC",
|
91
|
+
"name": "json5",
|
92
|
+
"aliases": null
|
93
|
+
}
|
94
|
+
}
|
95
|
+
},
|
96
|
+
{
|
97
|
+
"module": ".formats.pickle",
|
98
|
+
"attr": "_PICKLE_LAZY_CODEC",
|
99
|
+
"file": "omlish/formats/pickle.py",
|
100
|
+
"line": 30,
|
101
|
+
"value": {
|
102
|
+
"$.codecs.base.LazyLoadedCodec": {
|
103
|
+
"mod_name": "omlish.formats.pickle",
|
104
|
+
"attr_name": "PICKLE_CODEC",
|
105
|
+
"name": "pickle",
|
106
|
+
"aliases": null
|
107
|
+
}
|
108
|
+
}
|
109
|
+
},
|
110
|
+
{
|
111
|
+
"module": ".formats.toml",
|
112
|
+
"attr": "_TOML_LAZY_CODEC",
|
113
|
+
"file": "omlish/formats/toml.py",
|
114
|
+
"line": 16,
|
115
|
+
"value": {
|
116
|
+
"$.codecs.base.LazyLoadedCodec": {
|
117
|
+
"mod_name": "omlish.formats.toml",
|
118
|
+
"attr_name": "TOML_CODEC",
|
119
|
+
"name": "toml",
|
120
|
+
"aliases": null
|
121
|
+
}
|
122
|
+
}
|
123
|
+
},
|
124
|
+
{
|
125
|
+
"module": ".formats.yaml",
|
126
|
+
"attr": "_YAML_LAZY_CODEC",
|
127
|
+
"file": "omlish/formats/yaml.py",
|
128
|
+
"line": 258,
|
129
|
+
"value": {
|
130
|
+
"$.codecs.base.LazyLoadedCodec": {
|
131
|
+
"mod_name": "omlish.formats.yaml",
|
132
|
+
"attr_name": "YAML_CODEC",
|
133
|
+
"name": "yaml",
|
134
|
+
"aliases": [
|
135
|
+
"yml"
|
136
|
+
]
|
137
|
+
}
|
138
|
+
}
|
139
|
+
},
|
140
|
+
{
|
141
|
+
"module": ".io.compress.brotli",
|
142
|
+
"attr": "_BROTLI_LAZY_CODEC",
|
143
|
+
"file": "omlish/io/compress/brotli.py",
|
144
|
+
"line": 46,
|
145
|
+
"value": {
|
146
|
+
"$.codecs.base.LazyLoadedCodec": {
|
147
|
+
"mod_name": "omlish.io.compress.brotli",
|
148
|
+
"attr_name": "BROTLI_CODEC",
|
149
|
+
"name": "brotli",
|
150
|
+
"aliases": null
|
151
|
+
}
|
152
|
+
}
|
153
|
+
},
|
154
|
+
{
|
155
|
+
"module": ".io.compress.bz2",
|
156
|
+
"attr": "_BZ2_LAZY_CODEC",
|
157
|
+
"file": "omlish/io/compress/bz2.py",
|
158
|
+
"line": 60,
|
159
|
+
"value": {
|
160
|
+
"$.codecs.base.LazyLoadedCodec": {
|
161
|
+
"mod_name": "omlish.io.compress.bz2",
|
162
|
+
"attr_name": "BZ2_CODEC",
|
163
|
+
"name": "bz2",
|
164
|
+
"aliases": null
|
165
|
+
}
|
166
|
+
}
|
167
|
+
},
|
168
|
+
{
|
169
|
+
"module": ".io.compress.gzip",
|
170
|
+
"attr": "_GZIP_LAZY_CODEC",
|
171
|
+
"file": "omlish/io/compress/gzip.py",
|
172
|
+
"line": 349,
|
173
|
+
"value": {
|
174
|
+
"$.codecs.base.LazyLoadedCodec": {
|
175
|
+
"mod_name": "omlish.io.compress.gzip",
|
176
|
+
"attr_name": "GZIP_CODEC",
|
177
|
+
"name": "gzip",
|
178
|
+
"aliases": [
|
179
|
+
"gz"
|
180
|
+
]
|
181
|
+
}
|
182
|
+
}
|
183
|
+
},
|
184
|
+
{
|
185
|
+
"module": ".io.compress.lz4",
|
186
|
+
"attr": "_LZ4_LAZY_CODEC",
|
187
|
+
"file": "omlish/io/compress/lz4.py",
|
188
|
+
"line": 90,
|
189
|
+
"value": {
|
190
|
+
"$.codecs.base.LazyLoadedCodec": {
|
191
|
+
"mod_name": "omlish.io.compress.lz4",
|
192
|
+
"attr_name": "LZ4_CODEC",
|
193
|
+
"name": "lz4",
|
194
|
+
"aliases": null
|
195
|
+
}
|
196
|
+
}
|
197
|
+
},
|
198
|
+
{
|
199
|
+
"module": ".io.compress.lzma",
|
200
|
+
"attr": "_LZMA_LAZY_CODEC",
|
201
|
+
"file": "omlish/io/compress/lzma.py",
|
202
|
+
"line": 80,
|
203
|
+
"value": {
|
204
|
+
"$.codecs.base.LazyLoadedCodec": {
|
205
|
+
"mod_name": "omlish.io.compress.lzma",
|
206
|
+
"attr_name": "LZMA_CODEC",
|
207
|
+
"name": "lzma",
|
208
|
+
"aliases": null
|
209
|
+
}
|
210
|
+
}
|
211
|
+
},
|
212
|
+
{
|
213
|
+
"module": ".io.compress.snappy",
|
214
|
+
"attr": "_SNAPPY_LAZY_CODEC",
|
215
|
+
"file": "omlish/io/compress/snappy.py",
|
216
|
+
"line": 33,
|
217
|
+
"value": {
|
218
|
+
"$.codecs.base.LazyLoadedCodec": {
|
219
|
+
"mod_name": "omlish.io.compress.snappy",
|
220
|
+
"attr_name": "SNAPPY_CODEC",
|
221
|
+
"name": "snappy",
|
222
|
+
"aliases": null
|
223
|
+
}
|
224
|
+
}
|
225
|
+
},
|
226
|
+
{
|
227
|
+
"module": ".io.compress.zlib",
|
228
|
+
"attr": "_ZLIB_LAZY_CODEC",
|
229
|
+
"file": "omlish/io/compress/zlib.py",
|
230
|
+
"line": 73,
|
231
|
+
"value": {
|
232
|
+
"$.codecs.base.LazyLoadedCodec": {
|
233
|
+
"mod_name": "omlish.io.compress.zlib",
|
234
|
+
"attr_name": "ZLIB_CODEC",
|
235
|
+
"name": "zlib",
|
236
|
+
"aliases": null
|
237
|
+
}
|
238
|
+
}
|
239
|
+
},
|
240
|
+
{
|
241
|
+
"module": ".io.compress.zstd",
|
242
|
+
"attr": "_ZSTD_LAZY_CODEC",
|
243
|
+
"file": "omlish/io/compress/zstd.py",
|
244
|
+
"line": 43,
|
245
|
+
"value": {
|
246
|
+
"$.codecs.base.LazyLoadedCodec": {
|
247
|
+
"mod_name": "omlish.io.compress.zstd",
|
248
|
+
"attr_name": "ZSTD_CODEC",
|
249
|
+
"name": "zstd",
|
250
|
+
"aliases": null
|
251
|
+
}
|
252
|
+
}
|
253
|
+
},
|
26
254
|
{
|
27
255
|
"module": ".secrets.pwgen",
|
28
256
|
"attr": "_CLI_MODULE",
|
omlish/__about__.py
CHANGED
@@ -0,0 +1,69 @@
|
|
1
|
+
from .base import ( # noqa
|
2
|
+
EagerCodec,
|
3
|
+
IncrementalCodec,
|
4
|
+
ComboCodec,
|
5
|
+
|
6
|
+
check_codec_name,
|
7
|
+
|
8
|
+
Codec,
|
9
|
+
|
10
|
+
LazyLoadedCodec,
|
11
|
+
)
|
12
|
+
|
13
|
+
from .bytes import ( # noqa
|
14
|
+
ASCII85,
|
15
|
+
BASE16,
|
16
|
+
BASE32,
|
17
|
+
BASE64,
|
18
|
+
BASE85,
|
19
|
+
BASE32_HEX,
|
20
|
+
BASE64_HEX,
|
21
|
+
BASE64_URLSAFE,
|
22
|
+
HEX,
|
23
|
+
)
|
24
|
+
|
25
|
+
from .chain import ( # noqa
|
26
|
+
ChainEagerCodec,
|
27
|
+
|
28
|
+
chain,
|
29
|
+
)
|
30
|
+
|
31
|
+
from .funcs import ( # noqa
|
32
|
+
FnPairEagerCodec,
|
33
|
+
)
|
34
|
+
|
35
|
+
from .registry import ( # noqa
|
36
|
+
CodecRegistry,
|
37
|
+
|
38
|
+
REGISTRY,
|
39
|
+
register,
|
40
|
+
lookup,
|
41
|
+
|
42
|
+
encode,
|
43
|
+
decode,
|
44
|
+
)
|
45
|
+
|
46
|
+
from .standard import ( # noqa
|
47
|
+
STANDARD_CODECS,
|
48
|
+
)
|
49
|
+
|
50
|
+
from .text import ( # noqa
|
51
|
+
TextEncodingErrors,
|
52
|
+
TextEncodingOptions,
|
53
|
+
|
54
|
+
TextEncodingComboCodec,
|
55
|
+
|
56
|
+
TextEncodingCodec,
|
57
|
+
|
58
|
+
ASCII,
|
59
|
+
LATIN1,
|
60
|
+
UTF32,
|
61
|
+
UTF32BE,
|
62
|
+
UTF32LE,
|
63
|
+
UTF16,
|
64
|
+
UTF16BE,
|
65
|
+
UTF16LE,
|
66
|
+
UTF7,
|
67
|
+
UTF8,
|
68
|
+
UTF8SIG,
|
69
|
+
)
|
omlish/codecs/base.py
ADDED
@@ -0,0 +1,102 @@
|
|
1
|
+
"""
|
2
|
+
TODO:
|
3
|
+
- bytes-like - bytearray, memoryview
|
4
|
+
"""
|
5
|
+
import abc
|
6
|
+
import typing as ta
|
7
|
+
|
8
|
+
from omlish import check
|
9
|
+
from omlish import dataclasses as dc
|
10
|
+
from omlish import lang
|
11
|
+
from omlish import reflect as rfl
|
12
|
+
|
13
|
+
|
14
|
+
I = ta.TypeVar('I')
|
15
|
+
O = ta.TypeVar('O')
|
16
|
+
|
17
|
+
|
18
|
+
##
|
19
|
+
|
20
|
+
|
21
|
+
class EagerCodec(lang.Abstract, ta.Generic[I, O]):
|
22
|
+
@abc.abstractmethod
|
23
|
+
def encode(self, i: I) -> O:
|
24
|
+
raise NotImplementedError
|
25
|
+
|
26
|
+
@abc.abstractmethod
|
27
|
+
def decode(self, o: O) -> I:
|
28
|
+
raise NotImplementedError
|
29
|
+
|
30
|
+
|
31
|
+
class IncrementalCodec(lang.Abstract, ta.Generic[I, O]):
|
32
|
+
@abc.abstractmethod
|
33
|
+
def encode_incremental(self) -> ta.Generator[O | None, I, None]:
|
34
|
+
raise NotImplementedError
|
35
|
+
|
36
|
+
@abc.abstractmethod
|
37
|
+
def decode_incremental(self) -> ta.Generator[I | None, O, None]:
|
38
|
+
raise NotImplementedError
|
39
|
+
|
40
|
+
|
41
|
+
class ComboCodec( # noqa
|
42
|
+
EagerCodec[I, O],
|
43
|
+
IncrementalCodec[I, O],
|
44
|
+
lang.Abstract,
|
45
|
+
ta.Generic[I, O],
|
46
|
+
):
|
47
|
+
pass
|
48
|
+
|
49
|
+
|
50
|
+
##
|
51
|
+
|
52
|
+
|
53
|
+
def check_codec_name(s: str) -> str:
|
54
|
+
check.non_empty_str(s)
|
55
|
+
check.not_in('_', s)
|
56
|
+
check.equal(s.strip(), s)
|
57
|
+
return s
|
58
|
+
|
59
|
+
|
60
|
+
##
|
61
|
+
|
62
|
+
|
63
|
+
@dc.dataclass(frozen=True, kw_only=True)
|
64
|
+
class Codec:
|
65
|
+
name: str = dc.xfield(coerce=check_codec_name)
|
66
|
+
aliases: ta.Collection[str] | None = dc.xfield(
|
67
|
+
default=None,
|
68
|
+
coerce=lang.opt_fn(lambda s: [check_codec_name(a) for a in s]), # type: ignore
|
69
|
+
)
|
70
|
+
|
71
|
+
input: rfl.Type = dc.xfield(coerce=rfl.type_)
|
72
|
+
output: rfl.Type = dc.xfield(coerce=rfl.type_)
|
73
|
+
|
74
|
+
options: type | None = None
|
75
|
+
|
76
|
+
new: ta.Callable[..., EagerCodec]
|
77
|
+
new_incremental: ta.Callable[..., IncrementalCodec] | None = None
|
78
|
+
|
79
|
+
|
80
|
+
##
|
81
|
+
|
82
|
+
|
83
|
+
@dc.dataclass(frozen=True, kw_only=True)
|
84
|
+
class LazyLoadedCodec:
|
85
|
+
mod_name: str
|
86
|
+
attr_name: str
|
87
|
+
name: str
|
88
|
+
aliases: ta.Collection[str] | None = None
|
89
|
+
|
90
|
+
@classmethod
|
91
|
+
def new(
|
92
|
+
cls,
|
93
|
+
mod_name: str,
|
94
|
+
attr_name: str,
|
95
|
+
codec: Codec,
|
96
|
+
) -> 'LazyLoadedCodec':
|
97
|
+
return cls(
|
98
|
+
mod_name=mod_name,
|
99
|
+
attr_name=attr_name,
|
100
|
+
name=codec.name,
|
101
|
+
aliases=codec.aliases,
|
102
|
+
)
|
omlish/codecs/bytes.py
ADDED
@@ -0,0 +1,119 @@
|
|
1
|
+
"""
|
2
|
+
TODO:
|
3
|
+
- options / kwargs
|
4
|
+
"""
|
5
|
+
import base64
|
6
|
+
import binascii
|
7
|
+
import typing as ta
|
8
|
+
|
9
|
+
from .. import check
|
10
|
+
from .base import Codec
|
11
|
+
from .funcs import FnPairEagerCodec
|
12
|
+
from .standard import STANDARD_CODECS
|
13
|
+
|
14
|
+
|
15
|
+
##
|
16
|
+
|
17
|
+
|
18
|
+
class BytesCodec(Codec):
|
19
|
+
pass
|
20
|
+
|
21
|
+
|
22
|
+
def make_bytes_encoding_codec(
|
23
|
+
name: str,
|
24
|
+
aliases: ta.Collection[str] | None,
|
25
|
+
encode: ta.Callable[[bytes], bytes],
|
26
|
+
decode: ta.Callable[[bytes], bytes],
|
27
|
+
*,
|
28
|
+
append_to: ta.MutableSequence[Codec] | None = None,
|
29
|
+
) -> BytesCodec:
|
30
|
+
codec = BytesCodec(
|
31
|
+
name=name,
|
32
|
+
aliases=check.not_isinstance(aliases, str),
|
33
|
+
|
34
|
+
input=bytes,
|
35
|
+
output=bytes,
|
36
|
+
|
37
|
+
new=lambda: FnPairEagerCodec.of(encode, decode),
|
38
|
+
)
|
39
|
+
|
40
|
+
if append_to is not None:
|
41
|
+
append_to.append(codec)
|
42
|
+
|
43
|
+
return codec
|
44
|
+
|
45
|
+
|
46
|
+
##
|
47
|
+
|
48
|
+
|
49
|
+
ASCII85 = make_bytes_encoding_codec(
|
50
|
+
'ascii85',
|
51
|
+
['a85'],
|
52
|
+
base64.a85encode,
|
53
|
+
base64.a85decode,
|
54
|
+
append_to=STANDARD_CODECS,
|
55
|
+
)
|
56
|
+
|
57
|
+
BASE16 = make_bytes_encoding_codec(
|
58
|
+
'base16',
|
59
|
+
['b16'],
|
60
|
+
base64.b16encode,
|
61
|
+
base64.b16decode,
|
62
|
+
append_to=STANDARD_CODECS,
|
63
|
+
)
|
64
|
+
|
65
|
+
BASE32 = make_bytes_encoding_codec(
|
66
|
+
'base32',
|
67
|
+
['b32'],
|
68
|
+
base64.b32encode,
|
69
|
+
base64.b32decode,
|
70
|
+
append_to=STANDARD_CODECS,
|
71
|
+
)
|
72
|
+
|
73
|
+
BASE64 = make_bytes_encoding_codec(
|
74
|
+
'base64',
|
75
|
+
['b64'],
|
76
|
+
base64.b64encode,
|
77
|
+
base64.b64decode,
|
78
|
+
append_to=STANDARD_CODECS,
|
79
|
+
)
|
80
|
+
|
81
|
+
BASE85 = make_bytes_encoding_codec(
|
82
|
+
'base85',
|
83
|
+
['b85'],
|
84
|
+
base64.b85encode,
|
85
|
+
base64.b85decode,
|
86
|
+
append_to=STANDARD_CODECS,
|
87
|
+
)
|
88
|
+
|
89
|
+
BASE32_HEX = make_bytes_encoding_codec(
|
90
|
+
'base32-hex',
|
91
|
+
['b32-hex'],
|
92
|
+
base64.b32hexencode,
|
93
|
+
base64.b32hexdecode,
|
94
|
+
append_to=STANDARD_CODECS,
|
95
|
+
)
|
96
|
+
|
97
|
+
BASE64_HEX = make_bytes_encoding_codec(
|
98
|
+
'base64-hex',
|
99
|
+
['b64-hex'],
|
100
|
+
base64.standard_b64encode,
|
101
|
+
base64.standard_b64decode,
|
102
|
+
append_to=STANDARD_CODECS,
|
103
|
+
)
|
104
|
+
|
105
|
+
BASE64_URLSAFE = make_bytes_encoding_codec(
|
106
|
+
'base64-urlsafe',
|
107
|
+
['b64-urlsafe'],
|
108
|
+
base64.urlsafe_b64encode,
|
109
|
+
base64.urlsafe_b64decode,
|
110
|
+
append_to=STANDARD_CODECS,
|
111
|
+
)
|
112
|
+
|
113
|
+
HEX = make_bytes_encoding_codec(
|
114
|
+
'hex',
|
115
|
+
[],
|
116
|
+
binascii.b2a_hex,
|
117
|
+
binascii.a2b_hex,
|
118
|
+
append_to=STANDARD_CODECS,
|
119
|
+
)
|
omlish/codecs/chain.py
ADDED
@@ -0,0 +1,23 @@
|
|
1
|
+
import dataclasses as dc
|
2
|
+
import typing as ta
|
3
|
+
|
4
|
+
from .base import EagerCodec
|
5
|
+
|
6
|
+
|
7
|
+
@dc.dataclass(frozen=True)
|
8
|
+
class ChainEagerCodec(EagerCodec[ta.Any, ta.Any]):
|
9
|
+
codecs: ta.Sequence[EagerCodec]
|
10
|
+
|
11
|
+
def encode(self, v: ta.Any) -> ta.Any:
|
12
|
+
for c in self.codecs:
|
13
|
+
v = c.encode(v)
|
14
|
+
return v
|
15
|
+
|
16
|
+
def decode(self, v: ta.Any) -> ta.Any:
|
17
|
+
for c in reversed(self.codecs):
|
18
|
+
v = c.decode(v)
|
19
|
+
return v
|
20
|
+
|
21
|
+
|
22
|
+
def chain(*codecs: EagerCodec) -> ChainEagerCodec:
|
23
|
+
return ChainEagerCodec(codecs)
|
omlish/codecs/funcs.py
ADDED
@@ -0,0 +1,28 @@
|
|
1
|
+
import dataclasses as dc
|
2
|
+
import typing as ta
|
3
|
+
|
4
|
+
from ..funcs import pairs as fps
|
5
|
+
from .base import EagerCodec
|
6
|
+
|
7
|
+
|
8
|
+
I = ta.TypeVar('I')
|
9
|
+
O = ta.TypeVar('O')
|
10
|
+
|
11
|
+
|
12
|
+
@dc.dataclass(frozen=True)
|
13
|
+
class FnPairEagerCodec(EagerCodec[I, O]):
|
14
|
+
fp: fps.FnPair[I, O]
|
15
|
+
|
16
|
+
def encode(self, i: I) -> O:
|
17
|
+
return self.fp.forward(i)
|
18
|
+
|
19
|
+
def decode(self, o: O) -> I:
|
20
|
+
return self.fp.backward(o)
|
21
|
+
|
22
|
+
@classmethod
|
23
|
+
def of(
|
24
|
+
cls,
|
25
|
+
encode: ta.Callable[[I], O],
|
26
|
+
decode: ta.Callable[[O], I],
|
27
|
+
) -> 'FnPairEagerCodec[I, O]':
|
28
|
+
return cls(fps.of(encode, decode))
|