moat-lib-codec 0.4.19__tar.gz → 0.4.22__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.
Files changed (39) hide show
  1. moat_lib_codec-0.4.22/PKG-INFO +95 -0
  2. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/debian/changelog +36 -0
  3. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/debian/control +1 -2
  4. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/pyproject.toml +6 -6
  5. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/_base.py +10 -2
  6. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/_cbor.py +14 -12
  7. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/_moat_cbor.py +1 -1
  8. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/_moat_msgpack.py +6 -4
  9. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/bool.py +2 -2
  10. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/cbor.py +1 -1
  11. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/errors.py +1 -1
  12. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/json.py +1 -1
  13. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/jsonvalstr.py +1 -1
  14. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/jsonvalue.py +1 -1
  15. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/msgpack.py +13 -12
  16. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/noop.py +2 -2
  17. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/utf8.py +1 -1
  18. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/yaml.py +19 -5
  19. moat_lib_codec-0.4.22/src/moat_lib_codec.egg-info/PKG-INFO +95 -0
  20. moat_lib_codec-0.4.22/src/moat_lib_codec.egg-info/requires.txt +5 -0
  21. moat_lib_codec-0.4.19/PKG-INFO +0 -24
  22. moat_lib_codec-0.4.19/src/moat_lib_codec.egg-info/PKG-INFO +0 -24
  23. moat_lib_codec-0.4.19/src/moat_lib_codec.egg-info/requires.txt +0 -5
  24. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/LICENSE.txt +0 -0
  25. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/Makefile +0 -0
  26. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/README.md +0 -0
  27. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/debian/.gitignore +0 -0
  28. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/debian/py3dist-overrides +0 -0
  29. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/debian/rules +0 -0
  30. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/setup.cfg +0 -0
  31. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/__init__.py +0 -0
  32. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/binary.py +0 -0
  33. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/moat_cbor.py +0 -0
  34. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/moat_kv.py +0 -0
  35. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/moat_msgpack.py +0 -0
  36. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat/lib/codec/null.py +0 -0
  37. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat_lib_codec.egg-info/SOURCES.txt +0 -0
  38. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat_lib_codec.egg-info/dependency_links.txt +0 -0
  39. {moat_lib_codec-0.4.19 → moat_lib_codec-0.4.22}/src/moat_lib_codec.egg-info/top_level.txt +0 -0
@@ -0,0 +1,95 @@
1
+ Metadata-Version: 2.4
2
+ Name: moat-lib-codec
3
+ Version: 0.4.22
4
+ Summary: A simple command/stream multiplexer
5
+ Author-email: Matthias Urlichs <matthias@urlichs.de>
6
+ Maintainer-email: Matthias Urlichs <matthias@urlichs.de>
7
+ Project-URL: homepage, https://m-o-a-t.org
8
+ Project-URL: repository, https://github.com/M-o-a-T/moat
9
+ Keywords: MoaT
10
+ Classifier: Development Status :: 4 - Beta
11
+ Classifier: Framework :: AnyIO
12
+ Classifier: Framework :: Trio
13
+ Classifier: Framework :: AsyncIO
14
+ Classifier: Programming Language :: Python :: 3
15
+ Classifier: Intended Audience :: Developers
16
+ Requires-Python: >=3.8
17
+ Description-Content-Type: text/markdown
18
+ License-File: LICENSE.txt
19
+ Requires-Dist: anyio~=4.2
20
+ Requires-Dist: moat-lib-rpc~=0.7.6
21
+ Requires-Dist: moat-lib-micro~=0.3.4
22
+ Requires-Dist: moat-lib-proxy~=0.1.3
23
+ Requires-Dist: moat-util~=0.64.0
24
+ Dynamic: license-file
25
+
26
+ # The MoaT-Codec library
27
+
28
+ % start synopsis
29
+ % start main
30
+
31
+ This library packages various codecs used for MoaT protocols
32
+ in a way that's reason- and stream-able.
33
+
34
+ % end synopsis
35
+
36
+ ## Supplied codecs
37
+
38
+ - CBOR
39
+ - msgpack
40
+ - no-op
41
+ - UTF-8
42
+ - JSON
43
+ - YAML
44
+
45
+ % end main
46
+
47
+ ## Interface
48
+
49
+ ### Codec
50
+
51
+ - encode(obj)
52
+
53
+ Encode the object to a bytestream.
54
+
55
+ - decode(bytes)
56
+
57
+ Decode the given bytes to a single object.
58
+
59
+ - feed(bytes, final=False)
60
+
61
+ Data stream. Returns an array of objects.
62
+
63
+ This method only exists when a sequence of encoded objects can be streamed,
64
+ i.e. contains built-in message boundaries.
65
+
66
+ if @final is `True`, raise an exception if there is an incomplete
67
+ object in the buffer after this call.
68
+
69
+ - getstate(), setstate(\*args)
70
+
71
+ A streaming decoder may store partially-decoded state (unprocessed
72
+ buffer) here.
73
+
74
+ The list of accepted objects is implementation dependent.
75
+
76
+ ### Extension
77
+
78
+ Extension types vary by whether they carry binary data as in (msgpack), or
79
+ objects (as in cbor).
80
+
81
+ - binary (classvar): True if msgpack-style, False if cbor-style
82
+
83
+ - encoder(cls, key, fn)
84
+
85
+ Encode an object `obj` of type `type`. `fn(codec, obj)` must return
86
+ a bytestring / an encodeable object. If the registration key is `None`
87
+ the function must return a tuple with the key as first element.
88
+
89
+ - decoder(key, fn)
90
+
91
+ Add a decoder (key, data) to an object. `fn(codec, data)` is called with a
92
+ bytestring / a decoded object, and returns whatever has been encoded.
93
+
94
+ Extensions get the codec as their first argument. They can use it to store
95
+ data, e.g. references. The extension object is available as `codec.ext`.
@@ -1,3 +1,39 @@
1
+ moat-lib-codec (0.4.22-1) unstable; urgency=medium
2
+
3
+ * New release for 26.4.26
4
+
5
+ -- Matthias Urlichs <matthias@urlichs.de> Sat, 03 Oct 2026 12:52:54 +0200
6
+
7
+ moat-lib-codec (0.4.21-2) unstable; urgency=medium
8
+
9
+ * New release for 26.4.8
10
+
11
+ -- Matthias Urlichs <matthias@urlichs.de> Thu, 01 Oct 2026 11:15:17 +0200
12
+
13
+ moat-lib-codec (0.4.21-1) unstable; urgency=medium
14
+
15
+ * New release for 26.4.0
16
+
17
+ -- Matthias Urlichs <matthias@urlichs.de> Tue, 29 Sep 2026 16:47:21 +0200
18
+
19
+ moat-lib-codec (0.4.20-1) unstable; urgency=medium
20
+
21
+ * New release for 26.2.13
22
+
23
+ -- Matthias Urlichs <matthias@urlichs.de> Wed, 23 Sep 2026 15:11:05 +0200
24
+
25
+ moat-lib-codec (0.4.19-3) unstable; urgency=medium
26
+
27
+ * New release for 26.2.3
28
+
29
+ -- Matthias Urlichs <matthias@urlichs.de> Mon, 15 Jun 2026 17:44:22 +0200
30
+
31
+ moat-lib-codec (0.4.19-2) unstable; urgency=medium
32
+
33
+ * New release for 26.1.19
34
+
35
+ -- Matthias Urlichs <matthias@urlichs.de> Wed, 03 Jun 2026 20:27:16 +0200
36
+
1
37
  moat-lib-codec (0.4.19-1) unstable; urgency=medium
2
38
 
3
39
  * New release for 26.1.18
@@ -2,13 +2,12 @@ Source: moat-lib-codec
2
2
  Maintainer: "Matthias Urlichs" <matthias@urlichs.de>
3
3
  Section: python
4
4
  Priority: optional
5
- Build-Depends: dh-python, python3-all, debhelper (>= 13),
5
+ Build-Depends: dh-python, python3-all, debhelper (>= 13), debhelper-compat (= 13),
6
6
  python3-setuptools,
7
7
  python3-wheel,
8
8
  Standards-Version: 3.9.6
9
9
  Homepage: https://m-o-a-t.org
10
10
  Testsuite: autopkgtest-pkg-pybuild
11
- X-DH-Compat: 13
12
11
 
13
12
  Package: python3-moat-lib-codec
14
13
  Architecture: all
@@ -13,19 +13,19 @@ classifiers = [
13
13
  ]
14
14
  dependencies = [
15
15
  "anyio ~= 4.2",
16
- "moat-lib-rpc ~= 0.7.0",
17
- "moat-lib-micro ~= 0.3.0",
18
- "moat-lib-proxy ~= 0.1.1",
19
- "moat-util ~= 0.63.0",
16
+ "moat-lib-rpc ~= 0.7.6",
17
+ "moat-lib-micro ~= 0.3.4",
18
+ "moat-lib-proxy ~= 0.1.3",
19
+ "moat-util ~= 0.64.0",
20
20
  ]
21
21
  keywords = ["MoaT"]
22
22
  requires-python = ">=3.8"
23
23
  name = "moat-lib-codec"
24
24
  maintainers = [{email = "matthias@urlichs.de",name = "Matthias Urlichs"}]
25
25
  description='A simple command/stream multiplexer'
26
- readme = "README.rst"
26
+ readme = "README.md"
27
27
  authors = [{email = "matthias@urlichs.de",name = "Matthias Urlichs"}]
28
- version = "0.4.19"
28
+ version = "0.4.22"
29
29
 
30
30
  [project.urls]
31
31
  homepage = "https://m-o-a-t.org"
@@ -42,7 +42,7 @@ class Codec:
42
42
  ``__anext__``.
43
43
  """
44
44
 
45
- def __init__(self, ext=None):
45
+ def __init__(self, ext=None) -> None:
46
46
  if ext is None:
47
47
  ext = Extension() # empty
48
48
  self.ext = ext
@@ -90,6 +90,14 @@ class Codec:
90
90
  """
91
91
  raise NotImplementedError
92
92
 
93
+ def eof(self) -> None:
94
+ """
95
+ Signal that no more data will be fed.
96
+
97
+ Afterwards, iterating returns any objects still in the buffer
98
+ that are not terminated explicitly. The default does nothing.
99
+ """
100
+
93
101
  def unfeed(self, buf: VarByteType) -> int:
94
102
  """
95
103
  Take from the front of the decoder's buffer.
@@ -105,7 +113,7 @@ if TYPE_CHECKING:
105
113
 
106
114
 
107
115
  class Extension:
108
- def __init__(self):
116
+ def __init__(self) -> None:
109
117
  self.enc: dict[type, tuple[int | None, Callable]] = {}
110
118
  self.dec: dict[int, Callable] = {}
111
119
 
@@ -13,6 +13,8 @@ from moat.util import OutOfData
13
13
  from ._base import Codec as _Codec
14
14
  from ._base import NoCodecError
15
15
 
16
+ from collections.abc import Mapping
17
+
16
18
  # Typing
17
19
  from typing import TYPE_CHECKING, cast # isort:skip
18
20
 
@@ -40,11 +42,11 @@ CBOR_TAG_CBOR_LEADER = const(55800) # header for multiple CBOR items
40
42
  class Tag:
41
43
  "a random CBOR tag"
42
44
 
43
- def __init__(self, tag: int, value: Any = None):
45
+ def __init__(self, tag: int, value: Any = None) -> None:
44
46
  self.tag = tag
45
47
  self.value = value
46
48
 
47
- def __repr__(self):
49
+ def __repr__(self) -> str:
48
50
  return f"Tag({self.tag!r}, {self.value!r})"
49
51
 
50
52
  def __eq__(self, other):
@@ -105,7 +107,7 @@ def _bignum_to_bytearray(val):
105
107
  class ExtraData(ValueError):
106
108
  "buffer contains data beyond end of encoded object"
107
109
 
108
- def __str__(self):
110
+ def __str__(self) -> str:
109
111
  return "decoder received extra data."
110
112
 
111
113
 
@@ -117,7 +119,7 @@ class Codec(_Codec):
117
119
 
118
120
  _buf_out: bytearray | None = None
119
121
 
120
- def __init__(self, use_attrdict: bool = False, **kw):
122
+ def __init__(self, use_attrdict: bool = False, **kw) -> None:
121
123
  super().__init__(**kw)
122
124
  self.use_attrdict = use_attrdict
123
125
  self.__kw = kw
@@ -245,7 +247,7 @@ class Codec(_Codec):
245
247
  self._enc_type_num(CBOR_BYTES, len(outb))
246
248
  w(outb)
247
249
 
248
- def _enc_string(self, val):
250
+ def _enc_string(self, val) -> None:
249
251
  if isinstance(val, str):
250
252
  val = val.encode("utf8", "surrogateescape")
251
253
  self._enc_type_num(CBOR_TEXT, len(val))
@@ -253,7 +255,7 @@ class Codec(_Codec):
253
255
  self._enc_type_num(CBOR_BYTES, len(val))
254
256
  self._w(val)
255
257
 
256
- def _enc_array(self, arr):
258
+ def _enc_array(self, arr) -> None:
257
259
  try:
258
260
  self._enc_type_num(CBOR_ARRAY, len(arr))
259
261
  except TypeError:
@@ -265,26 +267,26 @@ class Codec(_Codec):
265
267
  for x in arr:
266
268
  self._enc_any(x)
267
269
 
268
- def _enc_dict(self, d):
270
+ def _enc_dict(self, d) -> None:
269
271
  self._enc_type_num(CBOR_MAP, len(d))
270
272
  for k, v in d.items():
271
273
  self._enc_any(k)
272
274
  self._enc_any(v)
273
275
 
274
- def _enc_bool(self, b):
276
+ def _enc_bool(self, b) -> None:
275
277
  self._w(struct.pack("B", CBOR_TRUE if b else CBOR_FALSE))
276
278
 
277
- def _enc_tag(self, t, val=...):
279
+ def _enc_tag(self, t, val=...) -> None:
278
280
  if val is Ellipsis:
279
281
  t, val = t.tag, t.value
280
282
  self._enc_type_num(CBOR_TAG, t)
281
283
  self._enc_any(val)
282
284
 
283
- def _w(self, d):
285
+ def _w(self, d) -> None:
284
286
  assert self._buf_out is not None # set by encode() before calling _enc_any()
285
287
  self._buf_out.extend(d)
286
288
 
287
- def _enc_any(self, ob):
289
+ def _enc_any(self, ob) -> None:
288
290
  w = self._w
289
291
  if ob is None:
290
292
  w(struct.pack("B", CBOR_NULL))
@@ -297,7 +299,7 @@ class Codec(_Codec):
297
299
  elif isinstance(ob, (list, tuple)):
298
300
  self._enc_array(ob)
299
301
  # TODO: accept other enumerables and emit a variable length array
300
- elif isinstance(ob, dict):
302
+ elif isinstance(ob, Mapping):
301
303
  self._enc_dict(ob)
302
304
  elif isinstance(ob, float):
303
305
  self._enc_float(ob)
@@ -34,7 +34,7 @@ class Codec(_cbor.Codec):
34
34
  CBOR codec with MoaT's standard extensions.
35
35
  """
36
36
 
37
- def __init__(self):
37
+ def __init__(self) -> None:
38
38
  super().__init__(ext=std_ext)
39
39
 
40
40
  def decode(self, data: ByteType): # noqa:D102,RUF100
@@ -12,11 +12,13 @@ Extension types defined here:
12
12
  from __future__ import annotations
13
13
 
14
14
  from moat.lib.path import Path
15
- from moat.lib.proxy import DProxy, Proxy, _CProxy, get_proxy, obj2name, unwrap_obj, wrap_obj
15
+ from moat.lib.proxy import DProxy, Proxy, _lookup_proxy, get_proxy, obj2name, unwrap_obj, wrap_obj
16
16
 
17
17
  from . import Extension
18
18
  from . import msgpack as _msgpack
19
19
 
20
+ from collections.abc import Mapping
21
+
20
22
  __all__ = ["Codec", "std_ext"]
21
23
 
22
24
 
@@ -27,14 +29,14 @@ ExtType = _msgpack.ExtType
27
29
  class Codec(_msgpack.Codec):
28
30
  "A MsgPack codec with our extensions"
29
31
 
30
- def __init__(self):
32
+ def __init__(self) -> None:
31
33
  super().__init__(ext=std_ext, use_attrdict=True)
32
34
 
33
35
 
34
36
  @std_ext.encoder(5, DProxy)
35
37
  def _enc_dproxy(codec, obj):
36
38
  a = obj.a[:]
37
- if obj.k or (a and isinstance(a[-1], dict)):
39
+ if obj.k or (a and isinstance(a[-1], Mapping)):
38
40
  a.append(obj.k)
39
41
  return codec.encode(obj.name) + b"".join(codec.encode(x) for x in a)
40
42
 
@@ -103,7 +105,7 @@ def _dec_proxy(codec, data):
103
105
  except UnicodeError:
104
106
  n = str(data)
105
107
  try:
106
- return _CProxy[n]
108
+ return _lookup_proxy(n)
107
109
  except KeyError:
108
110
  return Proxy(n)
109
111
 
@@ -14,7 +14,7 @@ class Codec(_Codec):
14
14
 
15
15
  null: bytes | None = None
16
16
 
17
- def __init__(self, on="on", off="off", null=None, **kw):
17
+ def __init__(self, on="on", off="off", null=None, **kw) -> None:
18
18
  super().__init__(**kw)
19
19
  if on is not None:
20
20
  self.on = on.encode("utf-8", "surrogateescape")
@@ -33,7 +33,7 @@ class Codec(_Codec):
33
33
  return self.on
34
34
  raise ValueError(obj)
35
35
 
36
- def decode(self, data):
36
+ def decode(self, data) -> bool | None:
37
37
  "some text > bool"
38
38
  if data == self.on:
39
39
  return True
@@ -21,7 +21,7 @@ def _tag_repr(dumper, data):
21
21
 
22
22
 
23
23
  class XTag: # noqa: D101
24
- def __init__(self, tag):
24
+ def __init__(self, tag) -> None:
25
25
  self.tag = tag
26
26
 
27
27
 
@@ -28,7 +28,7 @@ class SilentRemoteError(RemoteError): # ty:ignore[unsupported-base] # RemoteEr
28
28
  class NoPathError(KeyError):
29
29
  """An error that marks a nonexisting path"""
30
30
 
31
- def __str__(self):
31
+ def __str__(self) -> str:
32
32
  from moat.lib.path import Path # noqa: PLC0415
33
33
 
34
34
  return (
@@ -15,7 +15,7 @@ except ImportError:
15
15
  class Codec(_Codec):
16
16
  "basic JSON codec"
17
17
 
18
- def __init__(self, ext=None):
18
+ def __init__(self, ext=None) -> None:
19
19
  if ext is not None:
20
20
  raise ValueError("You can't extend the JSON codec")
21
21
  super().__init__()
@@ -10,7 +10,7 @@ from .jsonvalue import Codec as _Codec
10
10
  class Codec(_Codec):
11
11
  "JSON+Value using a stringified element"
12
12
 
13
- def __init__(self, ext=None):
13
+ def __init__(self, ext=None) -> None:
14
14
  if ext is not None:
15
15
  raise ValueError("You can't extend the JSON codec")
16
16
  super().__init__()
@@ -8,7 +8,7 @@ from .json import Codec as _Codec
8
8
  class Codec(_Codec):
9
9
  "JSON codec with 'value' element"
10
10
 
11
- def __init__(self, ext=None):
11
+ def __init__(self, ext=None) -> None:
12
12
  if ext is not None:
13
13
  raise ValueError("You can't extend the JSON codec")
14
14
  super().__init__()
@@ -27,6 +27,7 @@ from moat.lib.micro import byte2utf8, const
27
27
  from ._base import Codec as _Codec
28
28
  from ._base import NoCodecError
29
29
 
30
+ from collections.abc import Mapping
30
31
  from typing import TYPE_CHECKING, cast
31
32
 
32
33
  if TYPE_CHECKING:
@@ -38,7 +39,7 @@ __all__ = ["Codec", "ExtType"]
38
39
  class Codec(_Codec):
39
40
  "Extensible msgpack codec"
40
41
 
41
- def __init__(self, use_attrdict: bool = False, **kw):
42
+ def __init__(self, use_attrdict: bool = False, **kw) -> None:
42
43
  # TODO add keywords for msgpack enc/dec settings
43
44
  super().__init__(**kw)
44
45
  self.use_attrdict = use_attrdict
@@ -75,7 +76,7 @@ class Codec(_Codec):
75
76
  except NoCodecError:
76
77
  return ExtType(key, data)
77
78
 
78
- def feed(self, data):
79
+ def feed(self, data) -> None:
79
80
  "Add more bytes. Returns an iterator for the result."
80
81
  self.stream.feed(data)
81
82
 
@@ -106,24 +107,24 @@ class FormatError(UnpackException):
106
107
  class ExtraData(ValueError):
107
108
  "too much data in buffer"
108
109
 
109
- def __init__(self, unpacked, extra):
110
+ def __init__(self, unpacked, extra) -> None:
110
111
  self.unpacked = unpacked
111
112
  self.extra = extra
112
113
 
113
- def __str__(self):
114
+ def __str__(self) -> str:
114
115
  return "unpack(b) received extra data."
115
116
 
116
117
 
117
118
  class ExtType:
118
119
  """ExtType represents extension types in msgpack."""
119
120
 
120
- def __init__(self, code, data):
121
+ def __init__(self, code, data) -> None:
121
122
  if isinstance(data, memoryview):
122
123
  data = bytes(data)
123
124
  self.code = code
124
125
  self.data = data
125
126
 
126
- def __repr__(self):
127
+ def __repr__(self) -> str:
127
128
  return f"Ext({self.code}:{self.data})"
128
129
 
129
130
 
@@ -179,7 +180,7 @@ class Unpacker:
179
180
  ext_hook=ExtType,
180
181
  use_attrdict=False,
181
182
  min_memview_len=-1,
182
- ):
183
+ ) -> None:
183
184
  #: array of bytes fed.
184
185
  self._buffer = bytearray()
185
186
  #: Which position we currently reads
@@ -189,7 +190,7 @@ class Unpacker:
189
190
  self._min_memview_len = min_memview_len
190
191
  self._use_attrdict = use_attrdict
191
192
 
192
- def feed(self, data):
193
+ def feed(self, data) -> None:
193
194
  "set the buffer"
194
195
  if self._buffer and self._buf_pos < len(self._buffer):
195
196
  if self._buf_pos == 0:
@@ -234,7 +235,7 @@ class Unpacker:
234
235
  self._buf_pos = i + len(ret)
235
236
  return ret
236
237
 
237
- def _reserve(self, n):
238
+ def _reserve(self, n) -> None:
238
239
  remain_bytes = len(self._buffer) - self._buf_pos - n
239
240
 
240
241
  # Fast path: buffer has n bytes already
@@ -393,12 +394,12 @@ class Packer:
393
394
  self,
394
395
  # unicode_errors=None,
395
396
  default=None,
396
- ):
397
+ ) -> None:
397
398
  self._buffer = BytesIO()
398
399
  # self._unicode_errors = unicode_errors or "strict"
399
400
  self._default = default
400
401
 
401
- def _pack(self, obj, default=None):
402
+ def _pack(self, obj, default=None) -> None:
402
403
  # Warning, does not deal with recursive data structures
403
404
  # (except by running out of memory)
404
405
  list_types = (list, tuple)
@@ -524,7 +525,7 @@ class Packer:
524
525
  n -= 1
525
526
  todo.append(obj[n])
526
527
  continue
527
- if is_(obj, dict):
528
+ if is_(obj, Mapping):
528
529
  n = len(obj)
529
530
  if n <= 0x0F:
530
531
  wb(struct.pack("B", 0x80 + n))
@@ -8,7 +8,7 @@ from ._base import Codec as _Codec
8
8
  class Codec(_Codec):
9
9
  "no-op codec"
10
10
 
11
- def __init__(self, ext=None):
11
+ def __init__(self, ext=None) -> None:
12
12
  if ext is not None:
13
13
  raise ValueError("You can't extend the Null codec")
14
14
  super().__init__()
@@ -26,7 +26,7 @@ class Codec(_Codec):
26
26
  "no-op decode"
27
27
  return data
28
28
 
29
- def feed(self, data):
29
+ def feed(self, data) -> None:
30
30
  "no-op feed"
31
31
  self._buf += data
32
32
 
@@ -24,7 +24,7 @@ if TYPE_CHECKING:
24
24
  class Codec(_Codec):
25
25
  "Basic UTF-8 codec"
26
26
 
27
- def __init__(self, ext=None):
27
+ def __init__(self, ext=None) -> None:
28
28
  if ext is not None:
29
29
  raise ValueError("You can't extend the UTF8 codec")
30
30
  super().__init__()
@@ -15,11 +15,12 @@ if TYPE_CHECKING:
15
15
  class Codec(_Codec):
16
16
  "basic JSON codec"
17
17
 
18
- def __init__(self, ext=None):
18
+ def __init__(self, ext=None) -> None:
19
19
  if ext is not None:
20
20
  raise ValueError("You can't extend the JSON codec")
21
21
  super().__init__()
22
22
  self._buf = bytearray()
23
+ self._eof = False
23
24
 
24
25
  def encode(self, obj):
25
26
  "basic encoder"
@@ -32,10 +33,23 @@ class Codec(_Codec):
32
33
  def feed(self, data: ByteType) -> None: # noqa: D102
33
34
  self._buf.extend(data)
34
35
 
36
+ def eof(self) -> None: # noqa: D102
37
+ self._eof = True
38
+
35
39
  def __next__(self):
36
40
  i = self._buf.find(b"\n---\n")
37
- if i < 0:
41
+ if i >= 0:
42
+ res = yload(self._buf[0 : i + 1].decode("utf-8", "surrogateescape"))
43
+ self._buf[0 : i + 5] = b""
44
+ return res
45
+ if not self._eof:
46
+ raise StopIteration
47
+
48
+ # last document, not terminated by "---"
49
+ rest = bytes(self._buf).strip()
50
+ self._buf.clear()
51
+ if rest.endswith(b"\n---"):
52
+ rest = rest[:-4]
53
+ if not rest or rest == b"---":
38
54
  raise StopIteration
39
- res = yload(self._buf[0 : i + 1].decode("utf-8", "surrogateescape"))
40
- self._buf[0 : i + 5] = b""
41
- return res
55
+ return yload(rest.decode("utf-8", "surrogateescape"))
@@ -0,0 +1,95 @@
1
+ Metadata-Version: 2.4
2
+ Name: moat-lib-codec
3
+ Version: 0.4.22
4
+ Summary: A simple command/stream multiplexer
5
+ Author-email: Matthias Urlichs <matthias@urlichs.de>
6
+ Maintainer-email: Matthias Urlichs <matthias@urlichs.de>
7
+ Project-URL: homepage, https://m-o-a-t.org
8
+ Project-URL: repository, https://github.com/M-o-a-T/moat
9
+ Keywords: MoaT
10
+ Classifier: Development Status :: 4 - Beta
11
+ Classifier: Framework :: AnyIO
12
+ Classifier: Framework :: Trio
13
+ Classifier: Framework :: AsyncIO
14
+ Classifier: Programming Language :: Python :: 3
15
+ Classifier: Intended Audience :: Developers
16
+ Requires-Python: >=3.8
17
+ Description-Content-Type: text/markdown
18
+ License-File: LICENSE.txt
19
+ Requires-Dist: anyio~=4.2
20
+ Requires-Dist: moat-lib-rpc~=0.7.6
21
+ Requires-Dist: moat-lib-micro~=0.3.4
22
+ Requires-Dist: moat-lib-proxy~=0.1.3
23
+ Requires-Dist: moat-util~=0.64.0
24
+ Dynamic: license-file
25
+
26
+ # The MoaT-Codec library
27
+
28
+ % start synopsis
29
+ % start main
30
+
31
+ This library packages various codecs used for MoaT protocols
32
+ in a way that's reason- and stream-able.
33
+
34
+ % end synopsis
35
+
36
+ ## Supplied codecs
37
+
38
+ - CBOR
39
+ - msgpack
40
+ - no-op
41
+ - UTF-8
42
+ - JSON
43
+ - YAML
44
+
45
+ % end main
46
+
47
+ ## Interface
48
+
49
+ ### Codec
50
+
51
+ - encode(obj)
52
+
53
+ Encode the object to a bytestream.
54
+
55
+ - decode(bytes)
56
+
57
+ Decode the given bytes to a single object.
58
+
59
+ - feed(bytes, final=False)
60
+
61
+ Data stream. Returns an array of objects.
62
+
63
+ This method only exists when a sequence of encoded objects can be streamed,
64
+ i.e. contains built-in message boundaries.
65
+
66
+ if @final is `True`, raise an exception if there is an incomplete
67
+ object in the buffer after this call.
68
+
69
+ - getstate(), setstate(\*args)
70
+
71
+ A streaming decoder may store partially-decoded state (unprocessed
72
+ buffer) here.
73
+
74
+ The list of accepted objects is implementation dependent.
75
+
76
+ ### Extension
77
+
78
+ Extension types vary by whether they carry binary data as in (msgpack), or
79
+ objects (as in cbor).
80
+
81
+ - binary (classvar): True if msgpack-style, False if cbor-style
82
+
83
+ - encoder(cls, key, fn)
84
+
85
+ Encode an object `obj` of type `type`. `fn(codec, obj)` must return
86
+ a bytestring / an encodeable object. If the registration key is `None`
87
+ the function must return a tuple with the key as first element.
88
+
89
+ - decoder(key, fn)
90
+
91
+ Add a decoder (key, data) to an object. `fn(codec, data)` is called with a
92
+ bytestring / a decoded object, and returns whatever has been encoded.
93
+
94
+ Extensions get the codec as their first argument. They can use it to store
95
+ data, e.g. references. The extension object is available as `codec.ext`.
@@ -0,0 +1,5 @@
1
+ anyio~=4.2
2
+ moat-lib-micro~=0.3.4
3
+ moat-lib-proxy~=0.1.3
4
+ moat-lib-rpc~=0.7.6
5
+ moat-util~=0.64.0
@@ -1,24 +0,0 @@
1
- Metadata-Version: 2.4
2
- Name: moat-lib-codec
3
- Version: 0.4.19
4
- Summary: A simple command/stream multiplexer
5
- Author-email: Matthias Urlichs <matthias@urlichs.de>
6
- Maintainer-email: Matthias Urlichs <matthias@urlichs.de>
7
- Project-URL: homepage, https://m-o-a-t.org
8
- Project-URL: repository, https://github.com/M-o-a-T/moat
9
- Keywords: MoaT
10
- Classifier: Development Status :: 4 - Beta
11
- Classifier: Framework :: AnyIO
12
- Classifier: Framework :: Trio
13
- Classifier: Framework :: AsyncIO
14
- Classifier: Programming Language :: Python :: 3
15
- Classifier: Intended Audience :: Developers
16
- Requires-Python: >=3.8
17
- Description-Content-Type: text/x-rst
18
- License-File: LICENSE.txt
19
- Requires-Dist: anyio~=4.2
20
- Requires-Dist: moat-lib-rpc~=0.7.0
21
- Requires-Dist: moat-lib-micro~=0.3.0
22
- Requires-Dist: moat-lib-proxy~=0.1.1
23
- Requires-Dist: moat-util~=0.63.0
24
- Dynamic: license-file
@@ -1,24 +0,0 @@
1
- Metadata-Version: 2.4
2
- Name: moat-lib-codec
3
- Version: 0.4.19
4
- Summary: A simple command/stream multiplexer
5
- Author-email: Matthias Urlichs <matthias@urlichs.de>
6
- Maintainer-email: Matthias Urlichs <matthias@urlichs.de>
7
- Project-URL: homepage, https://m-o-a-t.org
8
- Project-URL: repository, https://github.com/M-o-a-T/moat
9
- Keywords: MoaT
10
- Classifier: Development Status :: 4 - Beta
11
- Classifier: Framework :: AnyIO
12
- Classifier: Framework :: Trio
13
- Classifier: Framework :: AsyncIO
14
- Classifier: Programming Language :: Python :: 3
15
- Classifier: Intended Audience :: Developers
16
- Requires-Python: >=3.8
17
- Description-Content-Type: text/x-rst
18
- License-File: LICENSE.txt
19
- Requires-Dist: anyio~=4.2
20
- Requires-Dist: moat-lib-rpc~=0.7.0
21
- Requires-Dist: moat-lib-micro~=0.3.0
22
- Requires-Dist: moat-lib-proxy~=0.1.1
23
- Requires-Dist: moat-util~=0.63.0
24
- Dynamic: license-file
@@ -1,5 +0,0 @@
1
- anyio~=4.2
2
- moat-lib-micro~=0.3.0
3
- moat-lib-proxy~=0.1.1
4
- moat-lib-rpc~=0.7.0
5
- moat-util~=0.63.0