omlish 0.0.0.dev14__py3-none-any.whl → 0.0.0.dev15__py3-none-any.whl
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.
- omlish/__about__.py +9 -4
- omlish/bootstrap.py +9 -0
- omlish/concurrent.py +5 -4
- omlish/formats/json.py +3 -279
- omlish/multiprocessing.py +173 -0
- {omlish-0.0.0.dev14.dist-info → omlish-0.0.0.dev15.dist-info}/METADATA +5 -5
- {omlish-0.0.0.dev14.dist-info → omlish-0.0.0.dev15.dist-info}/RECORD +10 -9
- {omlish-0.0.0.dev14.dist-info → omlish-0.0.0.dev15.dist-info}/LICENSE +0 -0
- {omlish-0.0.0.dev14.dist-info → omlish-0.0.0.dev15.dist-info}/WHEEL +0 -0
- {omlish-0.0.0.dev14.dist-info → omlish-0.0.0.dev15.dist-info}/top_level.txt +0 -0
omlish/__about__.py
CHANGED
@@ -1,5 +1,5 @@
|
|
1
|
-
__version__ = '0.0.0.
|
2
|
-
__revision__ = '
|
1
|
+
__version__ = '0.0.0.dev15'
|
2
|
+
__revision__ = '52225b19abf6c8dc3f10bdccebdc0a7ca9f48ed1'
|
3
3
|
|
4
4
|
|
5
5
|
#
|
@@ -50,10 +50,15 @@ class Project(ProjectBase):
|
|
50
50
|
],
|
51
51
|
|
52
52
|
'formats': [
|
53
|
-
'
|
53
|
+
'orjson ~= 3.10',
|
54
|
+
# 'python-rapidjson ~= 1.18',
|
55
|
+
# 'ujson ~= 5.10',
|
56
|
+
|
54
57
|
'json5 ~= 0.9',
|
55
|
-
|
58
|
+
|
56
59
|
'pyyaml ~= 5.0',
|
60
|
+
|
61
|
+
'cloudpickle ~= 3.0',
|
57
62
|
],
|
58
63
|
|
59
64
|
'http': [
|
omlish/bootstrap.py
CHANGED
@@ -2,6 +2,15 @@
|
|
2
2
|
TODO:
|
3
3
|
- more logging options
|
4
4
|
- a more powerful interface would be run_fn_with_bootstrap..
|
5
|
+
- ./python -m gprof2dot -f pstats prof.pstats | dot -Tpdf -o prof.pstats.pdf && open prof.pstats.pdf
|
6
|
+
|
7
|
+
TODO diag:
|
8
|
+
- yappi
|
9
|
+
- stackscope
|
10
|
+
- https://github.com/pythonspeed/filprofiler
|
11
|
+
- https://pypi.org/project/guppy3/
|
12
|
+
- https://pypi.org/project/memory-profiler/
|
13
|
+
- https://pypi.org/project/Pympler/
|
5
14
|
|
6
15
|
TODO new items:
|
7
16
|
- pydevd connect-back
|
omlish/concurrent.py
CHANGED
@@ -161,20 +161,21 @@ class ImmediateExecutor(cf.Executor):
|
|
161
161
|
|
162
162
|
|
163
163
|
@contextlib.contextmanager
|
164
|
-
def
|
164
|
+
def new_executor(
|
165
165
|
max_workers: int | None = None,
|
166
|
+
cls: type[cf.Executor] = cf.ThreadPoolExecutor,
|
166
167
|
*,
|
167
168
|
immediate_exceptions: bool = False,
|
168
|
-
thread_name_prefix: str = '',
|
169
169
|
**kwargs: ta.Any,
|
170
170
|
) -> ta.Generator[cf.Executor, None, None]:
|
171
171
|
if max_workers == 0:
|
172
172
|
yield ImmediateExecutor(
|
173
173
|
immediate_exceptions=immediate_exceptions,
|
174
174
|
)
|
175
|
+
|
175
176
|
else:
|
176
|
-
with
|
177
|
-
|
177
|
+
with cls( # type: ignore
|
178
|
+
max_workers,
|
178
179
|
**kwargs,
|
179
180
|
) as exe:
|
180
181
|
yield exe
|
omlish/formats/json.py
CHANGED
@@ -1,125 +1,7 @@
|
|
1
1
|
"""
|
2
|
-
|
3
|
-
|
4
|
-
|
5
|
-
ensure_ascii=True
|
6
|
-
check_circular=True
|
7
|
-
allow_nan=True
|
8
|
-
cls=None
|
9
|
-
indent=None
|
10
|
-
separators=None
|
11
|
-
default=None
|
12
|
-
sort_keys=False
|
13
|
-
dumps
|
14
|
-
^
|
15
|
-
load
|
16
|
-
cls=None
|
17
|
-
object_hook=None
|
18
|
-
parse_float=None
|
19
|
-
parse_int=None
|
20
|
-
parse_constant=None
|
21
|
-
object_pairs_hook=None
|
22
|
-
loads
|
23
|
-
^
|
24
|
-
|
25
|
-
ujson
|
26
|
-
dump
|
27
|
-
ensure_ascii
|
28
|
-
encode_html_chars
|
29
|
-
escape_forward_slashes
|
30
|
-
sort_keys
|
31
|
-
indent
|
32
|
-
allow_nan
|
33
|
-
reject_bytes
|
34
|
-
default
|
35
|
-
separators
|
36
|
-
dumps
|
37
|
-
^
|
38
|
-
load
|
39
|
-
loads
|
40
|
-
|
41
|
-
orjson
|
42
|
-
dumps
|
43
|
-
default
|
44
|
-
option
|
45
|
-
OPT_INDENT_2
|
46
|
-
OPT_NAIVE_UTC
|
47
|
-
OPT_NON_STR_KEYS
|
48
|
-
OPT_OMIT_MICROSECONDS
|
49
|
-
OPT_PASSTHROUGH_DATACLASS
|
50
|
-
OPT_PASSTHROUGH_DATETIME
|
51
|
-
OPT_PASSTHROUGH_SUBCLASS
|
52
|
-
OPT_SERIALIZE_DATACLASS
|
53
|
-
OPT_SERIALIZE_NUMPY
|
54
|
-
OPT_SERIALIZE_UUID
|
55
|
-
OPT_SORT_KEYS
|
56
|
-
OPT_STRICT_INTEGER
|
57
|
-
OPT_UTC_Z
|
58
|
-
loads
|
59
|
-
|
60
|
-
rapidjson
|
61
|
-
dump
|
62
|
-
skipkeys=False,
|
63
|
-
ensure_ascii=True,
|
64
|
-
write_mode=WM_COMPACT,
|
65
|
-
WM_COMPACT
|
66
|
-
WM_PRETTY
|
67
|
-
WM_SINGLE_LINE_ARRAY
|
68
|
-
indent=4,
|
69
|
-
default=None,
|
70
|
-
sort_keys=False,
|
71
|
-
number_mode=None,
|
72
|
-
NM_NONE
|
73
|
-
NM_DECIMAL
|
74
|
-
NM_NAN
|
75
|
-
NM_NATIVE
|
76
|
-
datetime_mode=None,
|
77
|
-
DM_NONE
|
78
|
-
DM_ISO8601
|
79
|
-
DM_UNIX_TIME
|
80
|
-
DM_ONLY_SECONDS
|
81
|
-
DM_IGNORE_TZ
|
82
|
-
DM_NAIVE_IS_UTC
|
83
|
-
DM_SHIFT_TO_UTC
|
84
|
-
uuid_mode=None,
|
85
|
-
UM_NONE
|
86
|
-
UM_CANONICAL
|
87
|
-
UM_HEX
|
88
|
-
bytes_mode=BM_UTF8,
|
89
|
-
BM_NONE
|
90
|
-
BM_UTF8
|
91
|
-
iterable_mode=IM_ANY_ITERABLE,
|
92
|
-
IM_ANY_ITERABLE
|
93
|
-
IM_ONLY_LISTS
|
94
|
-
mapping_mode=MM_ANY_MAPPING,
|
95
|
-
MM_ANY_MAPPING
|
96
|
-
MM_ONLY_DICTS
|
97
|
-
MM_COERCE_KEYS_TO_STRINGS
|
98
|
-
MM_SKIP_NON_STRING_KEYS
|
99
|
-
MM_SORT_KEYS
|
100
|
-
chunk_size
|
101
|
-
allow_nan=True
|
102
|
-
dumps
|
103
|
-
^
|
104
|
-
-chunk_size
|
105
|
-
load
|
106
|
-
object_hook=None,
|
107
|
-
number_mode=None,
|
108
|
-
^
|
109
|
-
datetime_mode=None,
|
110
|
-
^
|
111
|
-
uuid_mode=None,
|
112
|
-
^
|
113
|
-
parse_mode=None,
|
114
|
-
PM_NONE
|
115
|
-
PM_COMMENTS
|
116
|
-
PM_TRAILING_COMMAS
|
117
|
-
chunk_size=65536,
|
118
|
-
allow_nan=True
|
119
|
-
loads
|
120
|
-
^
|
121
|
-
-chunk_size
|
122
|
-
|
2
|
+
TODO:
|
3
|
+
- backend abstr
|
4
|
+
- streaming
|
123
5
|
"""
|
124
6
|
import functools
|
125
7
|
import json as _json
|
@@ -173,161 +55,3 @@ COMPACT_KWARGS: ta.Mapping[str, ta.Any] = dict(
|
|
173
55
|
|
174
56
|
dump_compact: ta.Callable[..., bytes] = functools.partial(dump, **COMPACT_KWARGS) # type: ignore
|
175
57
|
dumps_compact: ta.Callable[..., str] = functools.partial(dumps, **COMPACT_KWARGS)
|
176
|
-
|
177
|
-
|
178
|
-
##
|
179
|
-
|
180
|
-
|
181
|
-
# import functools
|
182
|
-
# import typing as ta
|
183
|
-
#
|
184
|
-
# from . import cached
|
185
|
-
# from . import dataclasses as dc
|
186
|
-
#
|
187
|
-
#
|
188
|
-
# F = ta.TypeVar('F')
|
189
|
-
# T = ta.TypeVar('T')
|
190
|
-
# StrMap = ta.Mapping[str, ta.Any]
|
191
|
-
#
|
192
|
-
#
|
193
|
-
# ENCODING = 'utf-8'
|
194
|
-
# PRETTY_INDENT = 2
|
195
|
-
# COMPACT_SEPARATORS = (',', ':')
|
196
|
-
#
|
197
|
-
#
|
198
|
-
# Dumps = ta.Callable[[ta.Any], str]
|
199
|
-
# Dumpb = ta.Callable[[ta.Any], bytes]
|
200
|
-
# Loads = ta.Callable[[ta.Union[str, bytes, bytearray]], ta.Any]
|
201
|
-
#
|
202
|
-
#
|
203
|
-
# @dc.dataclass(frozen=True)
|
204
|
-
# class _Provider:
|
205
|
-
# pretty_kwargs: StrMap = dc.field(default_factory=dict)
|
206
|
-
# compact_kwargs: StrMap = dc.field(default_factory=dict)
|
207
|
-
#
|
208
|
-
#
|
209
|
-
# class Provider:
|
210
|
-
#
|
211
|
-
# def __init__(self, json: ta.Any) -> None:
|
212
|
-
# super().__init__()
|
213
|
-
# self._json = json
|
214
|
-
#
|
215
|
-
# @property
|
216
|
-
# def json(self) -> ta.Any:
|
217
|
-
# return self._json
|
218
|
-
#
|
219
|
-
# @cached.property
|
220
|
-
# def dumps(self) -> Dumps:
|
221
|
-
# return self.json.dumps
|
222
|
-
#
|
223
|
-
# @cached.property
|
224
|
-
# def dumpb(self) -> Dumpb:
|
225
|
-
# def dumpb(*args, **kwargs):
|
226
|
-
# return fn(*args, **kwargs).encode(ENCODING)
|
227
|
-
# fn = self.json.dumps
|
228
|
-
# return functools.wraps(fn)(dumpb)
|
229
|
-
#
|
230
|
-
# @cached.property
|
231
|
-
# def loads(self) -> Loads:
|
232
|
-
# return self.json.loads
|
233
|
-
#
|
234
|
-
# @cached.property
|
235
|
-
# def pretty_kwargs(self) -> StrMap:
|
236
|
-
# return {}
|
237
|
-
#
|
238
|
-
# @cached.property
|
239
|
-
# def compact_kwargs(self) -> StrMap:
|
240
|
-
# return {}
|
241
|
-
#
|
242
|
-
#
|
243
|
-
# class OrjsonProvider(Provider):
|
244
|
-
#
|
245
|
-
# def __init__(self) -> None:
|
246
|
-
# import orjson
|
247
|
-
# super().__init__(orjson)
|
248
|
-
#
|
249
|
-
# @cached.property
|
250
|
-
# def pretty_kwargs(self) -> StrMap:
|
251
|
-
# return {
|
252
|
-
# 'option': self.json.OPT_INDENT_2,
|
253
|
-
# }
|
254
|
-
#
|
255
|
-
# @cached.property
|
256
|
-
# def dumps(self) -> Dumps:
|
257
|
-
# def dumps(*args, **kwargs):
|
258
|
-
# return fn(*args, **kwargs).decode(ENCODING)
|
259
|
-
# fn = self.json.dumps
|
260
|
-
# return functools.wraps(fn)(dumps)
|
261
|
-
#
|
262
|
-
# @cached.property
|
263
|
-
# def dumpb(self) -> Dumpb:
|
264
|
-
# return self.json.dumps
|
265
|
-
#
|
266
|
-
#
|
267
|
-
# class UjsonProvider(Provider):
|
268
|
-
#
|
269
|
-
# def __init__(self) -> None:
|
270
|
-
# import ujson
|
271
|
-
# super().__init__(ujson)
|
272
|
-
#
|
273
|
-
# @cached.property
|
274
|
-
# def pretty_kwargs(self) -> StrMap:
|
275
|
-
# return {
|
276
|
-
# 'indent': PRETTY_INDENT,
|
277
|
-
# }
|
278
|
-
#
|
279
|
-
# @cached.property
|
280
|
-
# def loads(self) -> Loads:
|
281
|
-
# def loads(arg, *args, **kwargs):
|
282
|
-
# if isinstance(arg, (bytes, bytearray)):
|
283
|
-
# arg = arg.decode(ENCODING)
|
284
|
-
# return fn(arg, *args, **kwargs)
|
285
|
-
# fn = self.json.loads
|
286
|
-
# return functools.wraps(fn)(loads)
|
287
|
-
#
|
288
|
-
#
|
289
|
-
# class BuiltinProvider(Provider):
|
290
|
-
#
|
291
|
-
# def __init__(self) -> None:
|
292
|
-
# import json
|
293
|
-
# super().__init__(json)
|
294
|
-
#
|
295
|
-
# @cached.property
|
296
|
-
# def pretty_kwargs(self) -> StrMap:
|
297
|
-
# return {
|
298
|
-
# 'indent': PRETTY_INDENT,
|
299
|
-
# }
|
300
|
-
#
|
301
|
-
# @cached.property
|
302
|
-
# def compact_kwargs(self) -> StrMap:
|
303
|
-
# return {
|
304
|
-
# 'indent': 0,
|
305
|
-
# 'separators': COMPACT_SEPARATORS,
|
306
|
-
# }
|
307
|
-
#
|
308
|
-
#
|
309
|
-
# def _select_provider(typs: ta.Iterable[ta.Callable[[], Provider]]) -> Provider:
|
310
|
-
# for typ in typs:
|
311
|
-
# try:
|
312
|
-
# return typ()
|
313
|
-
# except ImportError:
|
314
|
-
# pass
|
315
|
-
# raise TypeError('No suitable json providers')
|
316
|
-
#
|
317
|
-
#
|
318
|
-
# PROVIDER: Provider = _select_provider([
|
319
|
-
# OrjsonProvider,
|
320
|
-
# UjsonProvider,
|
321
|
-
# BuiltinProvider,
|
322
|
-
# ])
|
323
|
-
#
|
324
|
-
#
|
325
|
-
# dumps: Dumps = PROVIDER.dumps
|
326
|
-
# dumpb: Dumpb = PROVIDER.dumpb
|
327
|
-
# loads: Loads = PROVIDER.loads
|
328
|
-
#
|
329
|
-
# dumps_compact: Dumps = functools.partial(dumps, **PROVIDER.compact_kwargs)
|
330
|
-
# dumpb_compact: Dumpb = functools.partial(dumpb, **PROVIDER.compact_kwargs)
|
331
|
-
#
|
332
|
-
# dumps_pretty: Dumps = functools.partial(dumps, **PROVIDER.pretty_kwargs)
|
333
|
-
# dumpb_pretty: Dumpb = functools.partial(dumpb, **PROVIDER.pretty_kwargs)
|
@@ -0,0 +1,173 @@
|
|
1
|
+
import abc
|
2
|
+
import dataclasses as dc
|
3
|
+
import multiprocessing as mp
|
4
|
+
import multiprocessing.popen_spawn_posix
|
5
|
+
import os
|
6
|
+
import signal
|
7
|
+
import sys
|
8
|
+
import time
|
9
|
+
import typing as ta
|
10
|
+
|
11
|
+
from . import check
|
12
|
+
from . import libc
|
13
|
+
|
14
|
+
|
15
|
+
##
|
16
|
+
|
17
|
+
|
18
|
+
@dc.dataclass(frozen=True, kw_only=True)
|
19
|
+
class SpawnExtras:
|
20
|
+
fds: ta.AbstractSet[int] | None = None
|
21
|
+
deathsig: int | None = None
|
22
|
+
|
23
|
+
|
24
|
+
class ExtrasSpawnPosixPopen(mp.popen_spawn_posix.Popen):
|
25
|
+
def __init__(self, process_obj: 'ExtrasSpawnProcess', *, extras: SpawnExtras) -> None:
|
26
|
+
self.__extras = extras
|
27
|
+
self.__extra_fds = extras.fds
|
28
|
+
super().__init__(process_obj)
|
29
|
+
|
30
|
+
def _launch(self, process_obj: 'ExtrasSpawnProcess') -> None:
|
31
|
+
if self.__extra_fds:
|
32
|
+
for fd in self.__extra_fds:
|
33
|
+
self.duplicate_for_child(fd)
|
34
|
+
self._extra_fds = None
|
35
|
+
super()._launch(process_obj) # type: ignore # noqa
|
36
|
+
|
37
|
+
|
38
|
+
class ExtrasSpawnProcess(mp.context.SpawnProcess):
|
39
|
+
def __init__(self, *args: ta.Any, extras: SpawnExtras, **kwargs: ta.Any) -> None:
|
40
|
+
self.__extras = extras
|
41
|
+
super().__init__(*args, **kwargs)
|
42
|
+
|
43
|
+
def _Popen(self, process_obj: 'ExtrasSpawnProcess') -> ExtrasSpawnPosixPopen: # type: ignore # noqa
|
44
|
+
return ExtrasSpawnPosixPopen(process_obj, extras=self.__extras)
|
45
|
+
|
46
|
+
def run(self) -> None:
|
47
|
+
if self.__extras.deathsig is not None and sys.platform == 'linux':
|
48
|
+
libc.prctl(libc.PR_SET_PDEATHSIG, self.__extras.deathsig, 0, 0, 0, 0)
|
49
|
+
|
50
|
+
super().run()
|
51
|
+
|
52
|
+
|
53
|
+
class ExtrasSpawnContext(mp.context.SpawnContext):
|
54
|
+
def __init__(self, extras: SpawnExtras = SpawnExtras()) -> None:
|
55
|
+
super().__init__()
|
56
|
+
self.__extras = extras
|
57
|
+
|
58
|
+
def Process(self, *args: ta.Any, **kwargs: ta.Any): # type: ignore # noqa
|
59
|
+
return ExtrasSpawnProcess(*args, extras=self.__extras, **kwargs)
|
60
|
+
|
61
|
+
|
62
|
+
##
|
63
|
+
|
64
|
+
|
65
|
+
class Deathpact(abc.ABC):
|
66
|
+
@abc.abstractmethod
|
67
|
+
def poll(self) -> None:
|
68
|
+
raise NotImplementedError
|
69
|
+
|
70
|
+
|
71
|
+
#
|
72
|
+
|
73
|
+
|
74
|
+
class BaseDeathpact(Deathpact, abc.ABC):
|
75
|
+
def __init__(
|
76
|
+
self,
|
77
|
+
*,
|
78
|
+
interval_s: float = .5,
|
79
|
+
signal: int | None = signal.SIGTERM,
|
80
|
+
output: ta.Literal['stdout', 'stderr'] | None = 'stderr',
|
81
|
+
on_die: ta.Callable[[], None] | None = None,
|
82
|
+
) -> None:
|
83
|
+
super().__init__()
|
84
|
+
|
85
|
+
self._interval_s = interval_s
|
86
|
+
self._signal = signal
|
87
|
+
self._output = output
|
88
|
+
self._on_die = on_die
|
89
|
+
|
90
|
+
self._last_check_t: float | None = None
|
91
|
+
|
92
|
+
def _print(self, msg: str) -> None:
|
93
|
+
match self._output:
|
94
|
+
case 'stdout':
|
95
|
+
f = sys.stdout
|
96
|
+
case 'stderr':
|
97
|
+
f = sys.stderr
|
98
|
+
case _:
|
99
|
+
return
|
100
|
+
print(f'{self} pid={os.getpid()}: {msg}', file=f)
|
101
|
+
|
102
|
+
def die(self) -> None:
|
103
|
+
self._print('Triggered! Process terminating!')
|
104
|
+
|
105
|
+
if self._on_die is not None:
|
106
|
+
self._on_die()
|
107
|
+
|
108
|
+
if self._signal is not None:
|
109
|
+
os.kill(os.getpid(), self._signal)
|
110
|
+
|
111
|
+
sys.exit(1)
|
112
|
+
|
113
|
+
@abc.abstractmethod
|
114
|
+
def should_die(self) -> bool:
|
115
|
+
raise NotImplementedError
|
116
|
+
|
117
|
+
def maybe_die(self) -> None:
|
118
|
+
if self.should_die():
|
119
|
+
self.die()
|
120
|
+
|
121
|
+
def poll(self) -> None:
|
122
|
+
if self._last_check_t is None or (time.monotonic() - self._last_check_t) >= self._interval_s:
|
123
|
+
self.maybe_die()
|
124
|
+
self._last_check_t = time.monotonic()
|
125
|
+
|
126
|
+
|
127
|
+
#
|
128
|
+
|
129
|
+
|
130
|
+
class PipeDeathpact(BaseDeathpact):
|
131
|
+
def __init__(self, **kwargs: ta.Any) -> None:
|
132
|
+
super().__init__(**kwargs)
|
133
|
+
|
134
|
+
self._rfd: int | None = None
|
135
|
+
self._wfd: int | None = None
|
136
|
+
|
137
|
+
def __repr__(self) -> str:
|
138
|
+
return f'{self.__class__.__name__}(rfd={self._rfd}, wfd={self._wfd})'
|
139
|
+
|
140
|
+
@property
|
141
|
+
def fd(self) -> int:
|
142
|
+
return check.not_none(self._rfd)
|
143
|
+
|
144
|
+
def __enter__(self) -> ta.Self:
|
145
|
+
check.none(self._rfd)
|
146
|
+
check.none(self._wfd)
|
147
|
+
|
148
|
+
self._rfd, self._wfd = os.pipe()
|
149
|
+
|
150
|
+
os.set_inheritable(self._rfd, True)
|
151
|
+
os.set_blocking(self._rfd, False)
|
152
|
+
|
153
|
+
return self
|
154
|
+
|
155
|
+
def __exit__(self, exc_type, exc_val, exc_tb):
|
156
|
+
if self._rfd is not None:
|
157
|
+
os.close(check.not_none(self._wfd))
|
158
|
+
self._wfd = None
|
159
|
+
|
160
|
+
os.close(self._rfd)
|
161
|
+
self._rfd = None
|
162
|
+
|
163
|
+
def should_die(self) -> bool:
|
164
|
+
try:
|
165
|
+
buf = os.read(check.not_none(self._rfd), 1)
|
166
|
+
except BlockingIOError:
|
167
|
+
return False
|
168
|
+
|
169
|
+
if buf:
|
170
|
+
self._print(f'Read data from pipe! This should not happen! Process state corrupt!')
|
171
|
+
self.die()
|
172
|
+
|
173
|
+
return True
|
@@ -1,6 +1,6 @@
|
|
1
1
|
Metadata-Version: 2.1
|
2
2
|
Name: omlish
|
3
|
-
Version: 0.0.0.
|
3
|
+
Version: 0.0.0.dev15
|
4
4
|
Summary: omlish
|
5
5
|
Author: wrmsr
|
6
6
|
License: BSD-3-Clause
|
@@ -19,10 +19,10 @@ Requires-Dist: trio ~=0.26 ; extra == 'all'
|
|
19
19
|
Requires-Dist: lz4 ~=4.0 ; extra == 'all'
|
20
20
|
Requires-Dist: zstd ~=1.5 ; extra == 'all'
|
21
21
|
Requires-Dist: psutil ~=6.0 ; extra == 'all'
|
22
|
-
Requires-Dist:
|
22
|
+
Requires-Dist: orjson ~=3.10 ; extra == 'all'
|
23
23
|
Requires-Dist: json5 ~=0.9 ; extra == 'all'
|
24
|
-
Requires-Dist: orjson >3.10 ; extra == 'all'
|
25
24
|
Requires-Dist: pyyaml ~=5.0 ; extra == 'all'
|
25
|
+
Requires-Dist: cloudpickle ~=3.0 ; extra == 'all'
|
26
26
|
Requires-Dist: httpx[http2] ~=0.27 ; extra == 'all'
|
27
27
|
Requires-Dist: jinja2 ~=3.1 ; extra == 'all'
|
28
28
|
Requires-Dist: wrapt ~=1.14 ; extra == 'all'
|
@@ -53,10 +53,10 @@ Requires-Dist: python-snappy ~=0.7 ; (python_version < "3.13") and extra == 'com
|
|
53
53
|
Provides-Extra: diag
|
54
54
|
Requires-Dist: psutil ~=6.0 ; extra == 'diag'
|
55
55
|
Provides-Extra: formats
|
56
|
-
Requires-Dist:
|
56
|
+
Requires-Dist: orjson ~=3.10 ; extra == 'formats'
|
57
57
|
Requires-Dist: json5 ~=0.9 ; extra == 'formats'
|
58
|
-
Requires-Dist: orjson >3.10 ; extra == 'formats'
|
59
58
|
Requires-Dist: pyyaml ~=5.0 ; extra == 'formats'
|
59
|
+
Requires-Dist: cloudpickle ~=3.0 ; extra == 'formats'
|
60
60
|
Provides-Extra: http
|
61
61
|
Requires-Dist: httpx[http2] ~=0.27 ; extra == 'http'
|
62
62
|
Provides-Extra: misc
|
@@ -1,11 +1,11 @@
|
|
1
|
-
omlish/__about__.py,sha256=
|
1
|
+
omlish/__about__.py,sha256=WLo5QZVhe2UU53contNJDxYZA3mKjiHL6lZTAr_rAvE,2493
|
2
2
|
omlish/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
3
3
|
omlish/argparse.py,sha256=QRQmX9G0-L_nATkFtGHvpd4qrpYzKATdjuFLbBqzJPM,6224
|
4
|
-
omlish/bootstrap.py,sha256=
|
4
|
+
omlish/bootstrap.py,sha256=ENqzMlNbZWEAc2hzM9QwEoruShcgE_M7bdzJF6_fJ9w,19121
|
5
5
|
omlish/c3.py,sha256=W5EwYx9Por3rWYLkKUitJ6OoRMLLgVTfLTyroOz41Y0,8047
|
6
6
|
omlish/cached.py,sha256=UAizxlH4eMWHPzQtmItmyE6FEpFEUFzIkxaO2BHWZ5s,196
|
7
7
|
omlish/check.py,sha256=o3UJnIEmmRsv9ggIIDtz8fDSudW1CatxbwxP42M4dno,5543
|
8
|
-
omlish/concurrent.py,sha256=
|
8
|
+
omlish/concurrent.py,sha256=jCGG76Ca_8761g1uY3nCJONg_Nxcf4JQQZYvvrmsKE4,5395
|
9
9
|
omlish/datetimes.py,sha256=HajeM1kBvwlTa-uR1TTZHmZ3zTPnnUr1uGGQhiO1XQ0,2152
|
10
10
|
omlish/defs.py,sha256=N8O1murtr4mdSE_vjAcWGfnN7GyBXbW8rJM4qPF8na0,4737
|
11
11
|
omlish/docker.py,sha256=5WyXJyFwqIJJ11QWwPIjHjDHnsaOVZszZAjyTvg3xew,4693
|
@@ -15,6 +15,7 @@ omlish/iterators.py,sha256=GGLC7RIT86uXMjhIIIqnff_Iu5SI_b9rXYywYGFyzmo,7292
|
|
15
15
|
omlish/libc.py,sha256=u0481imCiTFqP_e-v9g0pD-0WD249j5vYzhtn-fnNkY,15308
|
16
16
|
omlish/matchfns.py,sha256=o2evI7q0CAMHR8RQ_Jks6L0UoNpEDltnLjOiamJDtmU,6155
|
17
17
|
omlish/math.py,sha256=AVqp5Y8yxKA-wO0BgrzaxA0Ga3PZiCXnYcwivMneC-0,3804
|
18
|
+
omlish/multiprocessing.py,sha256=6WI48mGUzLhDSwRjQs3ohxKWfl0v7wbxTjUvf_oOV4k,4584
|
18
19
|
omlish/os.py,sha256=cz4nL2ujaxH_-XRq3JUD8af8mSe1JXGPIoXP9XAEd0M,2607
|
19
20
|
omlish/runmodule.py,sha256=PWvuAaJ9wQQn6bx9ftEL3_d04DyotNn8dR_twm2pgw0,700
|
20
21
|
omlish/stats.py,sha256=uqjN-focDVssFZMagj22HqmyJ1TBO4Wt-XnHp8-EtVw,9927
|
@@ -96,7 +97,7 @@ omlish/dispatch/functions.py,sha256=S8ElsLi6DKxTdtFGigWaF0vAquwy2sK-3f4iRLaYq70,
|
|
96
97
|
omlish/dispatch/methods.py,sha256=XHjwwC9Gn4iDWxbyLAcbdSwRgVaq-8Bnn5cAwf5oZdA,5403
|
97
98
|
omlish/formats/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
98
99
|
omlish/formats/dotenv.py,sha256=UjZl3gac-0U24sDjCCGMcCqO1UCWG2Zs8PZ4JdAg2YE,17348
|
99
|
-
omlish/formats/json.py,sha256=
|
100
|
+
omlish/formats/json.py,sha256=SgPpt-j0yLQDJaw_TkF471G2NrJPiTkhl8_Src81HGg,1016
|
100
101
|
omlish/formats/props.py,sha256=diYjZDsG1s50ImJhkpeinMwjr8952nIVI-0gYhBIvCY,18897
|
101
102
|
omlish/formats/yaml.py,sha256=5gvH-e9fVn6C-xpcagnrtM0bSLOsuk3sAQT-aaE4PD4,6653
|
102
103
|
omlish/graphs/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
@@ -261,8 +262,8 @@ omlish/text/delimit.py,sha256=ubPXcXQmtbOVrUsNh5gH1mDq5H-n1y2R4cPL5_DQf68,4928
|
|
261
262
|
omlish/text/glyphsplit.py,sha256=Ug-dPRO7x-OrNNr8g1y6DotSZ2KH0S-VcOmUobwa4B0,3296
|
262
263
|
omlish/text/indent.py,sha256=6Jj6TFY9unaPa4xPzrnZemJ-fHsV53IamP93XGjSUHs,1274
|
263
264
|
omlish/text/parts.py,sha256=KGgo0wHOIMVMZtDso-rhSWKAcAkYAH2IGpg9tULabu8,6505
|
264
|
-
omlish-0.0.0.
|
265
|
-
omlish-0.0.0.
|
266
|
-
omlish-0.0.0.
|
267
|
-
omlish-0.0.0.
|
268
|
-
omlish-0.0.0.
|
265
|
+
omlish-0.0.0.dev15.dist-info/LICENSE,sha256=B_hVtavaA8zCYDW99DYdcpDLKz1n3BBRjZrcbv8uG8c,1451
|
266
|
+
omlish-0.0.0.dev15.dist-info/METADATA,sha256=IQXYzG4J9O7yaQvr5oHOVZ0piwijNGYK5LQ9TxhdzhM,3718
|
267
|
+
omlish-0.0.0.dev15.dist-info/WHEEL,sha256=uCRv0ZEik_232NlR4YDw4Pv3Ajt5bKvMH13NUU7hFuI,91
|
268
|
+
omlish-0.0.0.dev15.dist-info/top_level.txt,sha256=pePsKdLu7DvtUiecdYXJ78iO80uDNmBlqe-8hOzOmfs,7
|
269
|
+
omlish-0.0.0.dev15.dist-info/RECORD,,
|
File without changes
|
File without changes
|
File without changes
|