omlish 0.0.0.dev101__py3-none-any.whl → 0.0.0.dev103__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 CHANGED
@@ -1,5 +1,5 @@
1
- __version__ = '0.0.0.dev101'
2
- __revision__ = '44c6ff624e1a09a5024ea5cbc8a6cdcb1f54f013'
1
+ __version__ = '0.0.0.dev103'
2
+ __revision__ = 'e402b674aa19d5ca77d769f4290c26e35eb24c22'
3
3
 
4
4
 
5
5
  #
@@ -1,7 +1,9 @@
1
1
  import dataclasses as dc
2
+ import json
2
3
  import os.path
3
4
  import plistlib
4
5
  import re
6
+ import shutil
5
7
  import subprocess
6
8
  import sys
7
9
  import typing as ta
@@ -43,6 +45,26 @@ def read_darwin_pycharm_info_plist() -> ta.Mapping[str, ta.Any] | None:
43
45
  return root
44
46
 
45
47
 
48
+ #
49
+
50
+
51
+ UBUNTU_PYCHARM_HOME = '/snap/pycharm-professional/current'
52
+
53
+
54
+ def read_ubuntu_pycharm_product_info() -> ta.Mapping[str, ta.Any] | None:
55
+ json_file = os.path.join(UBUNTU_PYCHARM_HOME, 'product-info.json')
56
+ if not os.path.isfile(json_file):
57
+ return None
58
+
59
+ with open(json_file) as f:
60
+ root = json.load(f)
61
+
62
+ return root
63
+
64
+
65
+ #
66
+
67
+
46
68
  @lang.cached_function
47
69
  def get_pycharm_version() -> str | None:
48
70
  if sys.platform == 'darwin':
@@ -54,6 +76,17 @@ def get_pycharm_version() -> str | None:
54
76
  check.state(ver.startswith('PY-'))
55
77
  return ver[3:]
56
78
 
79
+ elif sys.platform == 'linux':
80
+ if shutil.which('lsb_release') is not None:
81
+ lsb_id = subprocess.check_output(['lsb_release', '-is']).decode().strip()
82
+ if lsb_id == 'Ubuntu':
83
+ pi = read_ubuntu_pycharm_product_info()
84
+ if pi is not None:
85
+ ver = check.non_empty_str(pi['buildNumber'])
86
+ return ver
87
+
88
+ return None
89
+
57
90
  else:
58
91
  return None
59
92
 
omlish/lite/cached.py CHANGED
@@ -1,7 +1,11 @@
1
1
  import functools
2
+ import typing as ta
2
3
 
3
4
 
4
- class cached_nullary: # noqa
5
+ T = ta.TypeVar('T')
6
+
7
+
8
+ class _cached_nullary: # noqa
5
9
  def __init__(self, fn):
6
10
  super().__init__()
7
11
  self._fn = fn
@@ -16,3 +20,7 @@ class cached_nullary: # noqa
16
20
  def __get__(self, instance, owner): # noqa
17
21
  bound = instance.__dict__[self._fn.__name__] = self.__class__(self._fn.__get__(instance, owner))
18
22
  return bound
23
+
24
+
25
+ def cached_nullary(fn: ta.Callable[..., T]) -> ta.Callable[..., T]:
26
+ return _cached_nullary(fn)
@@ -1,4 +1,38 @@
1
+ # ruff: noqa: UP007
1
2
  import contextlib
3
+ import typing as ta
4
+
5
+ from .check import check_not_none
6
+ from .check import check_state
7
+
8
+
9
+ T = ta.TypeVar('T')
10
+ ExitStackedT = ta.TypeVar('ExitStackedT', bound='ExitStacked')
11
+
12
+
13
+ ##
14
+
15
+
16
+ class ExitStacked:
17
+ _exit_stack: ta.Optional[contextlib.ExitStack] = None
18
+
19
+ def __enter__(self: ExitStackedT) -> ExitStackedT:
20
+ check_state(self._exit_stack is None)
21
+ es = self._exit_stack = contextlib.ExitStack()
22
+ es.__enter__()
23
+ return self
24
+
25
+ def __exit__(self, exc_type, exc_val, exc_tb):
26
+ if (es := self._exit_stack) is None:
27
+ return None
28
+ return es.__exit__(exc_type, exc_val, exc_tb)
29
+
30
+ def _enter_context(self, cm: ta.ContextManager[T]) -> T:
31
+ es = check_not_none(self._exit_stack)
32
+ return es.enter_context(cm)
33
+
34
+
35
+ ##
2
36
 
3
37
 
4
38
  @contextlib.contextmanager
omlish/lite/marshal.py CHANGED
@@ -150,7 +150,7 @@ class DataclassObjMarshaler(ObjMarshaler):
150
150
  return {k: m.marshal(getattr(o, k)) for k, m in self.fs.items()}
151
151
 
152
152
  def unmarshal(self, o: ta.Any) -> ta.Any:
153
- return self.ty(**{k: self.fs[k].unmarshal(v) for k, v in o.items() if self.nonstrict or k in self.fs})
153
+ return self.ty(**{k: self.fs[k].unmarshal(v) for k, v in o.items() if not self.nonstrict or k in self.fs})
154
154
 
155
155
 
156
156
  @dc.dataclass(frozen=True)
omlish/lite/pidfile.py CHANGED
@@ -30,7 +30,7 @@ class Pidfile:
30
30
  return self
31
31
 
32
32
  def __exit__(self, exc_type, exc_val, exc_tb):
33
- if self._f is not None:
33
+ if hasattr(self, '_f'):
34
34
  self._f.close()
35
35
  del self._f
36
36
 
@@ -110,3 +110,21 @@ def subprocess_try_output(
110
110
  def subprocess_try_output_str(*args: str, **kwargs: ta.Any) -> ta.Optional[str]:
111
111
  out = subprocess_try_output(*args, **kwargs)
112
112
  return out.decode().strip() if out is not None else None
113
+
114
+
115
+ ##
116
+
117
+
118
+ def subprocess_close(
119
+ proc: subprocess.Popen,
120
+ timeout: ta.Optional[float] = None,
121
+ ) -> None:
122
+ # TODO: terminate, sleep, kill
123
+ if proc.stdout:
124
+ proc.stdout.close()
125
+ if proc.stderr:
126
+ proc.stderr.close()
127
+ if proc.stdin:
128
+ proc.stdin.close()
129
+
130
+ proc.wait(timeout)
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: omlish
3
- Version: 0.0.0.dev101
3
+ Version: 0.0.0.dev103
4
4
  Summary: omlish
5
5
  Author: wrmsr
6
6
  License: BSD-3-Clause
@@ -1,5 +1,5 @@
1
1
  omlish/.manifests.json,sha256=hTFp9tvE72BxKloIq1s1SS0LRQlIsvMtO69Sbc47rKg,1704
2
- omlish/__about__.py,sha256=ErHDG6f5lFLkJwUUwDUw1PAqOlASMsYP_zEuWJY2hGI,3352
2
+ omlish/__about__.py,sha256=2FoZ6Jc4EVw0ktjCpXD7hwO_dcHH4tOlvoj9GJedqdM,3352
3
3
  omlish/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
4
4
  omlish/argparse.py,sha256=Dc73G8lyoQBLvXhMYUbzQUh4SJu_OTvKUXjSUxq_ang,7499
5
5
  omlish/c3.py,sha256=4vogWgwPb8TbNS2KkZxpoWbwjj7MuHG2lQG-hdtkvjI,8062
@@ -162,7 +162,7 @@ omlish/diag/_pycharm/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hS
162
162
  omlish/diag/_pycharm/runhack.py,sha256=eJlaUXIcFzAjOop_793RwNS_KF9NmhLv0i22xRVVeo0,34951
163
163
  omlish/diag/pycharm/__init__.py,sha256=-hZryZ3RfuoH4arwhBl-RmCZ6j-ybuUIEUf9C8o37iY,180
164
164
  omlish/diag/pycharm/cli.py,sha256=7SRh6yj8S5YGda4bq9BD4Kzwtgg4_Wa-K202ReZN2iI,1011
165
- omlish/diag/pycharm/pycharm.py,sha256=GFcnkNedY3bbwRM3l7_9lFiaW9BcxOB0KZl01Nk_xPs,3854
165
+ omlish/diag/pycharm/pycharm.py,sha256=Xmh0PyOe51NSI7kYODvhjYCKIqSddyYOAqjx9v6zNlw,4647
166
166
  omlish/diag/replserver/__init__.py,sha256=uLo6V2aQ29v9z3IMELlPDSlG3_2iOT4-_X8VniF-EgE,235
167
167
  omlish/diag/replserver/__main__.py,sha256=LmU41lQ58bm1h4Mx7S8zhE_uEBSC6kPcp9mn5JRpulA,32
168
168
  omlish/diag/replserver/console.py,sha256=XzBDVhYlr8FY6ym4OwoaIHuFOHnGK3dTYlMDIOMUUlA,7410
@@ -290,19 +290,19 @@ omlish/lifecycles/manager.py,sha256=Au66KaO-fI-SEJALaPUJsCHYW2GE20xextk1wKn2BEU,
290
290
  omlish/lifecycles/states.py,sha256=zqMOU2ZU-MDNnWuwauM3_anIAiXM8LoBDElDEraptFg,1292
291
291
  omlish/lifecycles/transitions.py,sha256=qQtFby-h4VzbvgaUqT2NnbNumlcOx9FVVADP9t83xj4,1939
292
292
  omlish/lite/__init__.py,sha256=Y3l4WY4JRi2uLG6kgbGp93fuGfkxkKwZDvhsa0Rwgtk,15
293
- omlish/lite/cached.py,sha256=dUm647FbIsoxWT23XUFM51F7i-C2Buxr5b5zzgbCtQI,546
293
+ omlish/lite/cached.py,sha256=2Yuoi1edt2nnq3RxF3xDS40RZABmHrnommwv8iGEYQE,690
294
294
  omlish/lite/check.py,sha256=ouJme9tkzWXKymm_xZDK4mngdYSkxDrok6CSegvf-1w,1015
295
- omlish/lite/contextmanagers.py,sha256=HnQJiyrOmSvTL22XRJrFl5CLpCyHD9fsntEUAr9G-60,427
295
+ omlish/lite/contextmanagers.py,sha256=_n6a9xhn06BD8H6A_SDtcipMrSBpzBqcxI0Ob2juomM,1226
296
296
  omlish/lite/io.py,sha256=lcpI1cS_Kn90tvYMg8ZWkSlYloS4RFqXCk-rKyclhdg,3148
297
297
  omlish/lite/json.py,sha256=7-02Ny4fq-6YAu5ynvqoijhuYXWpLmfCI19GUeZnb1c,740
298
298
  omlish/lite/logs.py,sha256=vkFkSX0Izb2P-NNMqqNLSec0BzeLOtHoQWgdXwQuDPU,6007
299
- omlish/lite/marshal.py,sha256=kZtfIiFfmxEi8ZKne3fT0R8g8kLmJ-Q5nq4kOvwhiqk,8656
300
- omlish/lite/pidfile.py,sha256=ymcr6JhEt33caZMsay_auQI0Ok-OTc6qpn49Zena5KQ,1723
299
+ omlish/lite/marshal.py,sha256=NPy2eV6wDMIhE8ZBSN6kDeOCt0aU46c53o-7QIhp-DI,8660
300
+ omlish/lite/pidfile.py,sha256=PRSDOAXmNkNwxh-Vwif0Nrs8RAmWroiNhLKIbdjwzBc,1723
301
301
  omlish/lite/reflect.py,sha256=9QYJwdINraq1JNMEgvoqeSlVvRRgOXpxAkpgX8EgRXc,1307
302
302
  omlish/lite/runtime.py,sha256=VUhmNQvwf8QzkWSKj4Q0ReieJA_PzHaJNRBivfTseow,452
303
303
  omlish/lite/secrets.py,sha256=3Mz3V2jf__XU9qNHcH56sBSw95L3U2UPL24bjvobG0c,816
304
304
  omlish/lite/strings.py,sha256=QURcE4-1pKVW8eT_5VCJpXaHDWR2dW2pYOChTJnZDiQ,1504
305
- omlish/lite/subprocesses.py,sha256=KuGV3ImehMjCUK0JoV3pUtG_7o5wei1lRDn9HxzByAg,3063
305
+ omlish/lite/subprocesses.py,sha256=_YwUpvfaC2pV5TMC9-Ivuw1Ao-YxteD3a1NQwGERft4,3380
306
306
  omlish/logs/__init__.py,sha256=FbOyAW-lGH8gyBlSVArwljdYAU6RnwZLI5LwAfuNnrk,438
307
307
  omlish/logs/_abc.py,sha256=UgrCUQVUi_PvT3p1CEkb3P74CFrFcZq2AFby3GEUv9M,5974
308
308
  omlish/logs/configs.py,sha256=EE0jlNaXJbGnM7V-y4xS5VwyTBSTzFzc0BYaVjg0JmA,1283
@@ -458,9 +458,9 @@ omlish/text/delimit.py,sha256=ubPXcXQmtbOVrUsNh5gH1mDq5H-n1y2R4cPL5_DQf68,4928
458
458
  omlish/text/glyphsplit.py,sha256=Ug-dPRO7x-OrNNr8g1y6DotSZ2KH0S-VcOmUobwa4B0,3296
459
459
  omlish/text/indent.py,sha256=6Jj6TFY9unaPa4xPzrnZemJ-fHsV53IamP93XGjSUHs,1274
460
460
  omlish/text/parts.py,sha256=7vPF1aTZdvLVYJ4EwBZVzRSy8XB3YqPd7JwEnNGGAOo,6495
461
- omlish-0.0.0.dev101.dist-info/LICENSE,sha256=B_hVtavaA8zCYDW99DYdcpDLKz1n3BBRjZrcbv8uG8c,1451
462
- omlish-0.0.0.dev101.dist-info/METADATA,sha256=Sug6yZWDsEcx7G0mfxCnrho_nLMA-X_TTRvbl2l2fXs,4000
463
- omlish-0.0.0.dev101.dist-info/WHEEL,sha256=P9jw-gEje8ByB7_hXoICnHtVCrEwMQh-630tKvQWehc,91
464
- omlish-0.0.0.dev101.dist-info/entry_points.txt,sha256=Lt84WvRZJskWCAS7xnQGZIeVWksprtUHj0llrvVmod8,35
465
- omlish-0.0.0.dev101.dist-info/top_level.txt,sha256=pePsKdLu7DvtUiecdYXJ78iO80uDNmBlqe-8hOzOmfs,7
466
- omlish-0.0.0.dev101.dist-info/RECORD,,
461
+ omlish-0.0.0.dev103.dist-info/LICENSE,sha256=B_hVtavaA8zCYDW99DYdcpDLKz1n3BBRjZrcbv8uG8c,1451
462
+ omlish-0.0.0.dev103.dist-info/METADATA,sha256=xpRaIXI0C7A878exoxOF6Ntzr0NWU3R66b_5MQ6BuPY,4000
463
+ omlish-0.0.0.dev103.dist-info/WHEEL,sha256=P9jw-gEje8ByB7_hXoICnHtVCrEwMQh-630tKvQWehc,91
464
+ omlish-0.0.0.dev103.dist-info/entry_points.txt,sha256=Lt84WvRZJskWCAS7xnQGZIeVWksprtUHj0llrvVmod8,35
465
+ omlish-0.0.0.dev103.dist-info/top_level.txt,sha256=pePsKdLu7DvtUiecdYXJ78iO80uDNmBlqe-8hOzOmfs,7
466
+ omlish-0.0.0.dev103.dist-info/RECORD,,