omdev 0.0.0.dev223__py3-none-any.whl → 0.0.0.dev225__py3-none-any.whl

Sign up to get free protection for your applications and to get access to all the features.
@@ -128,7 +128,7 @@ InjectorProviderFn = ta.Callable[['Injector'], ta.Any]
128
128
  InjectorProviderFnMap = ta.Mapping['InjectorKey', 'InjectorProviderFn']
129
129
  InjectorBindingOrBindings = ta.Union['InjectorBinding', 'InjectorBindings']
130
130
 
131
- # ../../omlish/subprocesses.py
131
+ # ../../omlish/subprocesses/base.py
132
132
  SubprocessChannelOption = ta.Literal['pipe', 'stdout', 'devnull'] # ta.TypeAlias
133
133
 
134
134
 
@@ -5625,6 +5625,98 @@ class JsonLogFormatter(logging.Formatter):
5625
5625
  return self._json_dumps(dct)
5626
5626
 
5627
5627
 
5628
+ ########################################
5629
+ # ../../../omlish/subprocesses/run.py
5630
+
5631
+
5632
+ ##
5633
+
5634
+
5635
+ @dc.dataclass(frozen=True)
5636
+ class SubprocessRunOutput(ta.Generic[T]):
5637
+ proc: T
5638
+
5639
+ returncode: int # noqa
5640
+
5641
+ stdout: ta.Optional[bytes] = None
5642
+ stderr: ta.Optional[bytes] = None
5643
+
5644
+
5645
+ ##
5646
+
5647
+
5648
+ @dc.dataclass(frozen=True)
5649
+ class SubprocessRun:
5650
+ cmd: ta.Sequence[str]
5651
+ input: ta.Any = None
5652
+ timeout: ta.Optional[float] = None
5653
+ check: bool = False
5654
+ capture_output: ta.Optional[bool] = None
5655
+ kwargs: ta.Optional[ta.Mapping[str, ta.Any]] = None
5656
+
5657
+ @classmethod
5658
+ def of(
5659
+ cls,
5660
+ *cmd: str,
5661
+ input: ta.Any = None, # noqa
5662
+ timeout: ta.Optional[float] = None,
5663
+ check: bool = False, # noqa
5664
+ capture_output: ta.Optional[bool] = None,
5665
+ **kwargs: ta.Any,
5666
+ ) -> 'SubprocessRun':
5667
+ return cls(
5668
+ cmd=cmd,
5669
+ input=input,
5670
+ timeout=timeout,
5671
+ check=check,
5672
+ capture_output=capture_output,
5673
+ kwargs=kwargs,
5674
+ )
5675
+
5676
+ #
5677
+
5678
+ _DEFAULT_SUBPROCESSES: ta.ClassVar[ta.Optional[ta.Any]] = None # AbstractSubprocesses
5679
+
5680
+ def run(
5681
+ self,
5682
+ subprocesses: ta.Optional[ta.Any] = None, # AbstractSubprocesses
5683
+ ) -> SubprocessRunOutput:
5684
+ if subprocesses is None:
5685
+ subprocesses = self._DEFAULT_SUBPROCESSES
5686
+ return check.not_none(subprocesses).run_(self) # type: ignore[attr-defined]
5687
+
5688
+ _DEFAULT_ASYNC_SUBPROCESSES: ta.ClassVar[ta.Optional[ta.Any]] = None # AbstractAsyncSubprocesses
5689
+
5690
+ async def async_run(
5691
+ self,
5692
+ async_subprocesses: ta.Optional[ta.Any] = None, # AbstractAsyncSubprocesses
5693
+ ) -> SubprocessRunOutput:
5694
+ if async_subprocesses is None:
5695
+ async_subprocesses = self._DEFAULT_ASYNC_SUBPROCESSES
5696
+ return await check.not_none(async_subprocesses).run_(self) # type: ignore[attr-defined]
5697
+
5698
+
5699
+ ##
5700
+
5701
+
5702
+ class SubprocessRunnable(abc.ABC, ta.Generic[T]):
5703
+ @abc.abstractmethod
5704
+ def make_run(self) -> SubprocessRun:
5705
+ raise NotImplementedError
5706
+
5707
+ @abc.abstractmethod
5708
+ def handle_run_output(self, output: SubprocessRunOutput) -> T:
5709
+ raise NotImplementedError
5710
+
5711
+ #
5712
+
5713
+ def run(self, subprocesses: ta.Optional[ta.Any] = None) -> T: # AbstractSubprocesses
5714
+ return self.handle_run_output(self.make_run().run(subprocesses))
5715
+
5716
+ async def async_run(self, async_subprocesses: ta.Optional[ta.Any] = None) -> T: # AbstractAsyncSubprocesses
5717
+ return self.handle_run_output(await self.make_run().async_run(async_subprocesses))
5718
+
5719
+
5628
5720
  ########################################
5629
5721
  # ../../interp/types.py
5630
5722
 
@@ -5863,23 +5955,7 @@ def configure_standard_logging(
5863
5955
 
5864
5956
 
5865
5957
  ########################################
5866
- # ../../../omlish/subprocesses.py
5867
-
5868
-
5869
- ##
5870
-
5871
-
5872
- # Valid channel type kwarg values:
5873
- # - A special flag negative int
5874
- # - A positive fd int
5875
- # - A file-like object
5876
- # - None
5877
-
5878
- SUBPROCESS_CHANNEL_OPTION_VALUES: ta.Mapping[SubprocessChannelOption, int] = {
5879
- 'pipe': subprocess.PIPE,
5880
- 'stdout': subprocess.STDOUT,
5881
- 'devnull': subprocess.DEVNULL,
5882
- }
5958
+ # ../../../omlish/subprocesses/wrap.py
5883
5959
 
5884
5960
 
5885
5961
  ##
@@ -5899,22 +5975,68 @@ def subprocess_maybe_shell_wrap_exec(*cmd: str) -> ta.Tuple[str, ...]:
5899
5975
  return cmd
5900
5976
 
5901
5977
 
5978
+ ########################################
5979
+ # ../../interp/providers/base.py
5980
+ """
5981
+ TODO:
5982
+ - backends
5983
+ - local builds
5984
+ - deadsnakes?
5985
+ - uv
5986
+ - loose versions
5987
+ """
5988
+
5989
+
5902
5990
  ##
5903
5991
 
5904
5992
 
5905
- def subprocess_close(
5906
- proc: subprocess.Popen,
5907
- timeout: ta.Optional[float] = None,
5908
- ) -> None:
5909
- # TODO: terminate, sleep, kill
5910
- if proc.stdout:
5911
- proc.stdout.close()
5912
- if proc.stderr:
5913
- proc.stderr.close()
5914
- if proc.stdin:
5915
- proc.stdin.close()
5993
+ class InterpProvider(abc.ABC):
5994
+ name: ta.ClassVar[str]
5995
+
5996
+ def __init_subclass__(cls, **kwargs: ta.Any) -> None:
5997
+ super().__init_subclass__(**kwargs)
5998
+ if abc.ABC not in cls.__bases__ and 'name' not in cls.__dict__:
5999
+ sfx = 'InterpProvider'
6000
+ if not cls.__name__.endswith(sfx):
6001
+ raise NameError(cls)
6002
+ setattr(cls, 'name', snake_case(cls.__name__[:-len(sfx)]))
6003
+
6004
+ @abc.abstractmethod
6005
+ def get_installed_versions(self, spec: InterpSpecifier) -> ta.Awaitable[ta.Sequence[InterpVersion]]:
6006
+ raise NotImplementedError
6007
+
6008
+ @abc.abstractmethod
6009
+ def get_installed_version(self, version: InterpVersion) -> ta.Awaitable[Interp]:
6010
+ raise NotImplementedError
6011
+
6012
+ async def get_installable_versions(self, spec: InterpSpecifier) -> ta.Sequence[InterpVersion]:
6013
+ return []
6014
+
6015
+ async def install_version(self, version: InterpVersion) -> Interp:
6016
+ raise TypeError
6017
+
6018
+
6019
+ InterpProviders = ta.NewType('InterpProviders', ta.Sequence[InterpProvider])
6020
+
6021
+
6022
+ ########################################
6023
+ # ../../../omlish/subprocesses/base.py
6024
+
6025
+
6026
+ ##
6027
+
6028
+
6029
+ # Valid channel type kwarg values:
6030
+ # - A special flag negative int
6031
+ # - A positive fd int
6032
+ # - A file-like object
6033
+ # - None
5916
6034
 
5917
- proc.wait(timeout)
6035
+ SUBPROCESS_CHANNEL_OPTION_VALUES: ta.Mapping[SubprocessChannelOption, int] = {
6036
+ 'pipe': subprocess.PIPE,
6037
+ 'stdout': subprocess.STDOUT,
6038
+ 'devnull': subprocess.DEVNULL,
6039
+ }
5918
6040
 
5919
6041
 
5920
6042
  ##
@@ -6101,32 +6223,104 @@ class BaseSubprocesses(abc.ABC): # noqa
6101
6223
  return e
6102
6224
 
6103
6225
 
6104
- ##
6226
+ ########################################
6227
+ # ../../interp/resolvers.py
6105
6228
 
6106
6229
 
6107
6230
  @dc.dataclass(frozen=True)
6108
- class SubprocessRun:
6109
- cmd: ta.Sequence[str]
6110
- input: ta.Any = None
6111
- timeout: ta.Optional[float] = None
6112
- check: bool = False
6113
- capture_output: ta.Optional[bool] = None
6114
- kwargs: ta.Optional[ta.Mapping[str, ta.Any]] = None
6231
+ class InterpResolverProviders:
6232
+ providers: ta.Sequence[ta.Tuple[str, InterpProvider]]
6115
6233
 
6116
6234
 
6117
- @dc.dataclass(frozen=True)
6118
- class SubprocessRunOutput(ta.Generic[T]):
6119
- proc: T
6235
+ class InterpResolver:
6236
+ def __init__(
6237
+ self,
6238
+ providers: InterpResolverProviders,
6239
+ ) -> None:
6240
+ super().__init__()
6120
6241
 
6121
- returncode: int # noqa
6242
+ self._providers: ta.Mapping[str, InterpProvider] = collections.OrderedDict(providers.providers)
6122
6243
 
6123
- stdout: ta.Optional[bytes] = None
6124
- stderr: ta.Optional[bytes] = None
6244
+ async def _resolve_installed(self, spec: InterpSpecifier) -> ta.Optional[ta.Tuple[InterpProvider, InterpVersion]]:
6245
+ lst = [
6246
+ (i, si)
6247
+ for i, p in enumerate(self._providers.values())
6248
+ for si in await p.get_installed_versions(spec)
6249
+ if spec.contains(si)
6250
+ ]
6125
6251
 
6252
+ slst = sorted(lst, key=lambda t: (-t[0], t[1].version))
6253
+ if not slst:
6254
+ return None
6126
6255
 
6127
- class AbstractSubprocesses(BaseSubprocesses, abc.ABC):
6256
+ bi, bv = slst[-1]
6257
+ bp = list(self._providers.values())[bi]
6258
+ return (bp, bv)
6259
+
6260
+ async def resolve(
6261
+ self,
6262
+ spec: InterpSpecifier,
6263
+ *,
6264
+ install: bool = False,
6265
+ ) -> ta.Optional[Interp]:
6266
+ tup = await self._resolve_installed(spec)
6267
+ if tup is not None:
6268
+ bp, bv = tup
6269
+ return await bp.get_installed_version(bv)
6270
+
6271
+ if not install:
6272
+ return None
6273
+
6274
+ tp = list(self._providers.values())[0] # noqa
6275
+
6276
+ sv = sorted(
6277
+ [s for s in await tp.get_installable_versions(spec) if s in spec],
6278
+ key=lambda s: s.version,
6279
+ )
6280
+ if not sv:
6281
+ return None
6282
+
6283
+ bv = sv[-1]
6284
+ return await tp.install_version(bv)
6285
+
6286
+ async def list(self, spec: InterpSpecifier) -> None:
6287
+ print('installed:')
6288
+ for n, p in self._providers.items():
6289
+ lst = [
6290
+ si
6291
+ for si in await p.get_installed_versions(spec)
6292
+ if spec.contains(si)
6293
+ ]
6294
+ if lst:
6295
+ print(f' {n}')
6296
+ for si in lst:
6297
+ print(f' {si}')
6298
+
6299
+ print()
6300
+
6301
+ print('installable:')
6302
+ for n, p in self._providers.items():
6303
+ lst = [
6304
+ si
6305
+ for si in await p.get_installable_versions(spec)
6306
+ if spec.contains(si)
6307
+ ]
6308
+ if lst:
6309
+ print(f' {n}')
6310
+ for si in lst:
6311
+ print(f' {si}')
6312
+
6313
+
6314
+ ########################################
6315
+ # ../../../omlish/subprocesses/async_.py
6316
+
6317
+
6318
+ ##
6319
+
6320
+
6321
+ class AbstractAsyncSubprocesses(BaseSubprocesses):
6128
6322
  @abc.abstractmethod
6129
- def run_(self, run: SubprocessRun) -> SubprocessRunOutput:
6323
+ async def run_(self, run: SubprocessRun) -> SubprocessRunOutput:
6130
6324
  raise NotImplementedError
6131
6325
 
6132
6326
  def run(
@@ -6137,7 +6331,7 @@ class AbstractSubprocesses(BaseSubprocesses, abc.ABC):
6137
6331
  check: bool = False,
6138
6332
  capture_output: ta.Optional[bool] = None,
6139
6333
  **kwargs: ta.Any,
6140
- ) -> SubprocessRunOutput:
6334
+ ) -> ta.Awaitable[SubprocessRunOutput]:
6141
6335
  return self.run_(SubprocessRun(
6142
6336
  cmd=cmd,
6143
6337
  input=input,
@@ -6150,7 +6344,7 @@ class AbstractSubprocesses(BaseSubprocesses, abc.ABC):
6150
6344
  #
6151
6345
 
6152
6346
  @abc.abstractmethod
6153
- def check_call(
6347
+ async def check_call(
6154
6348
  self,
6155
6349
  *cmd: str,
6156
6350
  stdout: ta.Any = sys.stderr,
@@ -6159,7 +6353,7 @@ class AbstractSubprocesses(BaseSubprocesses, abc.ABC):
6159
6353
  raise NotImplementedError
6160
6354
 
6161
6355
  @abc.abstractmethod
6162
- def check_output(
6356
+ async def check_output(
6163
6357
  self,
6164
6358
  *cmd: str,
6165
6359
  **kwargs: ta.Any,
@@ -6168,96 +6362,56 @@ class AbstractSubprocesses(BaseSubprocesses, abc.ABC):
6168
6362
 
6169
6363
  #
6170
6364
 
6171
- def check_output_str(
6365
+ async def check_output_str(
6172
6366
  self,
6173
6367
  *cmd: str,
6174
6368
  **kwargs: ta.Any,
6175
6369
  ) -> str:
6176
- return self.check_output(*cmd, **kwargs).decode().strip()
6370
+ return (await self.check_output(*cmd, **kwargs)).decode().strip()
6177
6371
 
6178
6372
  #
6179
6373
 
6180
- def try_call(
6374
+ async def try_call(
6181
6375
  self,
6182
6376
  *cmd: str,
6183
6377
  **kwargs: ta.Any,
6184
6378
  ) -> bool:
6185
- if isinstance(self.try_fn(self.check_call, *cmd, **kwargs), Exception):
6379
+ if isinstance(await self.async_try_fn(self.check_call, *cmd, **kwargs), Exception):
6186
6380
  return False
6187
6381
  else:
6188
6382
  return True
6189
6383
 
6190
- def try_output(
6384
+ async def try_output(
6191
6385
  self,
6192
6386
  *cmd: str,
6193
6387
  **kwargs: ta.Any,
6194
6388
  ) -> ta.Optional[bytes]:
6195
- if isinstance(ret := self.try_fn(self.check_output, *cmd, **kwargs), Exception):
6389
+ if isinstance(ret := await self.async_try_fn(self.check_output, *cmd, **kwargs), Exception):
6196
6390
  return None
6197
6391
  else:
6198
6392
  return ret
6199
6393
 
6200
- def try_output_str(
6394
+ async def try_output_str(
6201
6395
  self,
6202
6396
  *cmd: str,
6203
6397
  **kwargs: ta.Any,
6204
6398
  ) -> ta.Optional[str]:
6205
- if (ret := self.try_output(*cmd, **kwargs)) is None:
6399
+ if (ret := await self.try_output(*cmd, **kwargs)) is None:
6206
6400
  return None
6207
6401
  else:
6208
6402
  return ret.decode().strip()
6209
6403
 
6210
6404
 
6211
- ##
6212
-
6213
-
6214
- class Subprocesses(AbstractSubprocesses):
6215
- def run_(self, run: SubprocessRun) -> SubprocessRunOutput[subprocess.CompletedProcess]:
6216
- proc = subprocess.run(
6217
- run.cmd,
6218
- input=run.input,
6219
- timeout=run.timeout,
6220
- check=run.check,
6221
- capture_output=run.capture_output or False,
6222
- **(run.kwargs or {}),
6223
- )
6224
-
6225
- return SubprocessRunOutput(
6226
- proc=proc,
6227
-
6228
- returncode=proc.returncode,
6229
-
6230
- stdout=proc.stdout, # noqa
6231
- stderr=proc.stderr, # noqa
6232
- )
6233
-
6234
- def check_call(
6235
- self,
6236
- *cmd: str,
6237
- stdout: ta.Any = sys.stderr,
6238
- **kwargs: ta.Any,
6239
- ) -> None:
6240
- with self.prepare_and_wrap(*cmd, stdout=stdout, **kwargs) as (cmd, kwargs): # noqa
6241
- subprocess.check_call(cmd, **kwargs)
6242
-
6243
- def check_output(
6244
- self,
6245
- *cmd: str,
6246
- **kwargs: ta.Any,
6247
- ) -> bytes:
6248
- with self.prepare_and_wrap(*cmd, **kwargs) as (cmd, kwargs): # noqa
6249
- return subprocess.check_output(cmd, **kwargs)
6250
-
6251
-
6252
- subprocesses = Subprocesses()
6405
+ ########################################
6406
+ # ../../../omlish/subprocesses/sync.py
6253
6407
 
6254
6408
 
6255
6409
  ##
6256
6410
 
6257
6411
 
6258
- class AbstractAsyncSubprocesses(BaseSubprocesses):
6412
+ class AbstractSubprocesses(BaseSubprocesses, abc.ABC):
6259
6413
  @abc.abstractmethod
6260
- async def run_(self, run: SubprocessRun) -> SubprocessRunOutput:
6414
+ def run_(self, run: SubprocessRun) -> SubprocessRunOutput:
6261
6415
  raise NotImplementedError
6262
6416
 
6263
6417
  def run(
@@ -6268,7 +6422,7 @@ class AbstractAsyncSubprocesses(BaseSubprocesses):
6268
6422
  check: bool = False,
6269
6423
  capture_output: ta.Optional[bool] = None,
6270
6424
  **kwargs: ta.Any,
6271
- ) -> ta.Awaitable[SubprocessRunOutput]:
6425
+ ) -> SubprocessRunOutput:
6272
6426
  return self.run_(SubprocessRun(
6273
6427
  cmd=cmd,
6274
6428
  input=input,
@@ -6281,7 +6435,7 @@ class AbstractAsyncSubprocesses(BaseSubprocesses):
6281
6435
  #
6282
6436
 
6283
6437
  @abc.abstractmethod
6284
- async def check_call(
6438
+ def check_call(
6285
6439
  self,
6286
6440
  *cmd: str,
6287
6441
  stdout: ta.Any = sys.stderr,
@@ -6290,7 +6444,7 @@ class AbstractAsyncSubprocesses(BaseSubprocesses):
6290
6444
  raise NotImplementedError
6291
6445
 
6292
6446
  @abc.abstractmethod
6293
- async def check_output(
6447
+ def check_output(
6294
6448
  self,
6295
6449
  *cmd: str,
6296
6450
  **kwargs: ta.Any,
@@ -6299,46 +6453,96 @@ class AbstractAsyncSubprocesses(BaseSubprocesses):
6299
6453
 
6300
6454
  #
6301
6455
 
6302
- async def check_output_str(
6456
+ def check_output_str(
6303
6457
  self,
6304
6458
  *cmd: str,
6305
6459
  **kwargs: ta.Any,
6306
6460
  ) -> str:
6307
- return (await self.check_output(*cmd, **kwargs)).decode().strip()
6461
+ return self.check_output(*cmd, **kwargs).decode().strip()
6308
6462
 
6309
6463
  #
6310
6464
 
6311
- async def try_call(
6465
+ def try_call(
6312
6466
  self,
6313
6467
  *cmd: str,
6314
6468
  **kwargs: ta.Any,
6315
6469
  ) -> bool:
6316
- if isinstance(await self.async_try_fn(self.check_call, *cmd, **kwargs), Exception):
6470
+ if isinstance(self.try_fn(self.check_call, *cmd, **kwargs), Exception):
6317
6471
  return False
6318
6472
  else:
6319
6473
  return True
6320
6474
 
6321
- async def try_output(
6475
+ def try_output(
6322
6476
  self,
6323
6477
  *cmd: str,
6324
6478
  **kwargs: ta.Any,
6325
6479
  ) -> ta.Optional[bytes]:
6326
- if isinstance(ret := await self.async_try_fn(self.check_output, *cmd, **kwargs), Exception):
6480
+ if isinstance(ret := self.try_fn(self.check_output, *cmd, **kwargs), Exception):
6327
6481
  return None
6328
6482
  else:
6329
6483
  return ret
6330
6484
 
6331
- async def try_output_str(
6485
+ def try_output_str(
6332
6486
  self,
6333
6487
  *cmd: str,
6334
6488
  **kwargs: ta.Any,
6335
6489
  ) -> ta.Optional[str]:
6336
- if (ret := await self.try_output(*cmd, **kwargs)) is None:
6490
+ if (ret := self.try_output(*cmd, **kwargs)) is None:
6337
6491
  return None
6338
6492
  else:
6339
6493
  return ret.decode().strip()
6340
6494
 
6341
6495
 
6496
+ ##
6497
+
6498
+
6499
+ class Subprocesses(AbstractSubprocesses):
6500
+ def run_(self, run: SubprocessRun) -> SubprocessRunOutput[subprocess.CompletedProcess]:
6501
+ with self.prepare_and_wrap(
6502
+ *run.cmd,
6503
+ input=run.input,
6504
+ timeout=run.timeout,
6505
+ check=run.check,
6506
+ capture_output=run.capture_output or False,
6507
+ **(run.kwargs or {}),
6508
+ ) as (cmd, kwargs):
6509
+ proc = subprocess.run(cmd, **kwargs) # noqa
6510
+
6511
+ return SubprocessRunOutput(
6512
+ proc=proc,
6513
+
6514
+ returncode=proc.returncode,
6515
+
6516
+ stdout=proc.stdout, # noqa
6517
+ stderr=proc.stderr, # noqa
6518
+ )
6519
+
6520
+ def check_call(
6521
+ self,
6522
+ *cmd: str,
6523
+ stdout: ta.Any = sys.stderr,
6524
+ **kwargs: ta.Any,
6525
+ ) -> None:
6526
+ with self.prepare_and_wrap(*cmd, stdout=stdout, **kwargs) as (cmd, kwargs): # noqa
6527
+ subprocess.check_call(cmd, **kwargs)
6528
+
6529
+ def check_output(
6530
+ self,
6531
+ *cmd: str,
6532
+ **kwargs: ta.Any,
6533
+ ) -> bytes:
6534
+ with self.prepare_and_wrap(*cmd, **kwargs) as (cmd, kwargs): # noqa
6535
+ return subprocess.check_output(cmd, **kwargs)
6536
+
6537
+
6538
+ ##
6539
+
6540
+
6541
+ subprocesses = Subprocesses()
6542
+
6543
+ SubprocessRun._DEFAULT_SUBPROCESSES = subprocesses # noqa
6544
+
6545
+
6342
6546
  ########################################
6343
6547
  # ../../git/revisions.py
6344
6548
 
@@ -6385,50 +6589,6 @@ def get_git_revision(
6385
6589
  return dirty_rev + ('-untracked' if has_untracked else '')
6386
6590
 
6387
6591
 
6388
- ########################################
6389
- # ../../interp/providers/base.py
6390
- """
6391
- TODO:
6392
- - backends
6393
- - local builds
6394
- - deadsnakes?
6395
- - uv
6396
- - loose versions
6397
- """
6398
-
6399
-
6400
- ##
6401
-
6402
-
6403
- class InterpProvider(abc.ABC):
6404
- name: ta.ClassVar[str]
6405
-
6406
- def __init_subclass__(cls, **kwargs: ta.Any) -> None:
6407
- super().__init_subclass__(**kwargs)
6408
- if abc.ABC not in cls.__bases__ and 'name' not in cls.__dict__:
6409
- sfx = 'InterpProvider'
6410
- if not cls.__name__.endswith(sfx):
6411
- raise NameError(cls)
6412
- setattr(cls, 'name', snake_case(cls.__name__[:-len(sfx)]))
6413
-
6414
- @abc.abstractmethod
6415
- def get_installed_versions(self, spec: InterpSpecifier) -> ta.Awaitable[ta.Sequence[InterpVersion]]:
6416
- raise NotImplementedError
6417
-
6418
- @abc.abstractmethod
6419
- def get_installed_version(self, version: InterpVersion) -> ta.Awaitable[Interp]:
6420
- raise NotImplementedError
6421
-
6422
- async def get_installable_versions(self, spec: InterpSpecifier) -> ta.Sequence[InterpVersion]:
6423
- return []
6424
-
6425
- async def install_version(self, version: InterpVersion) -> Interp:
6426
- raise TypeError
6427
-
6428
-
6429
- InterpProviders = ta.NewType('InterpProviders', ta.Sequence[InterpProvider])
6430
-
6431
-
6432
6592
  ########################################
6433
6593
  # ../../../omlish/asyncs/asyncio/subprocesses.py
6434
6594
 
@@ -6571,19 +6731,19 @@ class AsyncioSubprocesses(AbstractAsyncSubprocesses):
6571
6731
  timeout: ta.Optional[float] = None,
6572
6732
  **kwargs: ta.Any,
6573
6733
  ) -> ta.AsyncGenerator[asyncio.subprocess.Process, None]:
6574
- fac: ta.Any
6575
- if shell:
6576
- fac = functools.partial(
6577
- asyncio.create_subprocess_shell,
6578
- check.single(cmd),
6579
- )
6580
- else:
6581
- fac = functools.partial(
6582
- asyncio.create_subprocess_exec,
6583
- *cmd,
6584
- )
6585
-
6586
6734
  with self.prepare_and_wrap( *cmd, shell=shell, **kwargs) as (cmd, kwargs): # noqa
6735
+ fac: ta.Any
6736
+ if shell:
6737
+ fac = functools.partial(
6738
+ asyncio.create_subprocess_shell,
6739
+ check.single(cmd),
6740
+ )
6741
+ else:
6742
+ fac = functools.partial(
6743
+ asyncio.create_subprocess_exec,
6744
+ *cmd,
6745
+ )
6746
+
6587
6747
  proc: asyncio.subprocess.Process = await fac(**kwargs)
6588
6748
  try:
6589
6749
  yield proc
@@ -6824,94 +6984,6 @@ class Pyenv:
6824
6984
  return True
6825
6985
 
6826
6986
 
6827
- ########################################
6828
- # ../../interp/resolvers.py
6829
-
6830
-
6831
- @dc.dataclass(frozen=True)
6832
- class InterpResolverProviders:
6833
- providers: ta.Sequence[ta.Tuple[str, InterpProvider]]
6834
-
6835
-
6836
- class InterpResolver:
6837
- def __init__(
6838
- self,
6839
- providers: InterpResolverProviders,
6840
- ) -> None:
6841
- super().__init__()
6842
-
6843
- self._providers: ta.Mapping[str, InterpProvider] = collections.OrderedDict(providers.providers)
6844
-
6845
- async def _resolve_installed(self, spec: InterpSpecifier) -> ta.Optional[ta.Tuple[InterpProvider, InterpVersion]]:
6846
- lst = [
6847
- (i, si)
6848
- for i, p in enumerate(self._providers.values())
6849
- for si in await p.get_installed_versions(spec)
6850
- if spec.contains(si)
6851
- ]
6852
-
6853
- slst = sorted(lst, key=lambda t: (-t[0], t[1].version))
6854
- if not slst:
6855
- return None
6856
-
6857
- bi, bv = slst[-1]
6858
- bp = list(self._providers.values())[bi]
6859
- return (bp, bv)
6860
-
6861
- async def resolve(
6862
- self,
6863
- spec: InterpSpecifier,
6864
- *,
6865
- install: bool = False,
6866
- ) -> ta.Optional[Interp]:
6867
- tup = await self._resolve_installed(spec)
6868
- if tup is not None:
6869
- bp, bv = tup
6870
- return await bp.get_installed_version(bv)
6871
-
6872
- if not install:
6873
- return None
6874
-
6875
- tp = list(self._providers.values())[0] # noqa
6876
-
6877
- sv = sorted(
6878
- [s for s in await tp.get_installable_versions(spec) if s in spec],
6879
- key=lambda s: s.version,
6880
- )
6881
- if not sv:
6882
- return None
6883
-
6884
- bv = sv[-1]
6885
- return await tp.install_version(bv)
6886
-
6887
- async def list(self, spec: InterpSpecifier) -> None:
6888
- print('installed:')
6889
- for n, p in self._providers.items():
6890
- lst = [
6891
- si
6892
- for si in await p.get_installed_versions(spec)
6893
- if spec.contains(si)
6894
- ]
6895
- if lst:
6896
- print(f' {n}')
6897
- for si in lst:
6898
- print(f' {si}')
6899
-
6900
- print()
6901
-
6902
- print('installable:')
6903
- for n, p in self._providers.items():
6904
- lst = [
6905
- si
6906
- for si in await p.get_installable_versions(spec)
6907
- if spec.contains(si)
6908
- ]
6909
- if lst:
6910
- print(f' {n}')
6911
- for si in lst:
6912
- print(f' {si}')
6913
-
6914
-
6915
6987
  ########################################
6916
6988
  # ../../revisions.py
6917
6989
  """