ominfra 0.0.0.dev156__py3-none-any.whl → 0.0.0.dev158__py3-none-any.whl

Sign up to get free protection for your applications and to get access to all the features.
@@ -5,7 +5,7 @@ import dataclasses as dc
5
5
  import os.path
6
6
  import sys
7
7
 
8
- from omlish.lite.logs import configure_standard_logging
8
+ from omlish.logs.standard import configure_standard_logging
9
9
 
10
10
  from ....configs import read_config_file
11
11
  from .driver import JournalctlToAwsDriver
@@ -410,8 +410,8 @@ import typing as ta
410
410
  from omlish.lite.cached import cached_nullary
411
411
  from omlish.lite.check import check
412
412
  from omlish.lite.logs import log
413
- from omlish.lite.subprocesses import subprocess_close
414
- from omlish.lite.subprocesses import subprocess_shell_wrap_exec
413
+ from omlish.subprocesses import subprocess_close
414
+ from omlish.subprocesses import subprocess_shell_wrap_exec
415
415
 
416
416
  from ..threadworkers import ThreadWorker
417
417
  from .messages import JournalctlMessage # noqa
@@ -1,7 +1,7 @@
1
1
  # ruff: noqa: UP006 UP007
2
2
  from omlish.lite.inject import Injector
3
3
  from omlish.lite.inject import inj
4
- from omlish.lite.logs import configure_standard_logging
4
+ from omlish.logs.standard import configure_standard_logging
5
5
 
6
6
  from .bootstrap import MainBootstrap
7
7
  from .inject import bind_main
@@ -6,11 +6,11 @@ import subprocess
6
6
  import time
7
7
  import typing as ta
8
8
 
9
- from omlish.lite.asyncio.subprocesses import asyncio_subprocesses
9
+ from omlish.asyncs.asyncio.subprocesses import asyncio_subprocesses
10
10
  from omlish.lite.check import check
11
- from omlish.lite.subprocesses import SUBPROCESS_CHANNEL_OPTION_VALUES
12
- from omlish.lite.subprocesses import SubprocessChannelOption
13
- from omlish.lite.subprocesses import subprocess_maybe_shell_wrap_exec
11
+ from omlish.subprocesses import SUBPROCESS_CHANNEL_OPTION_VALUES
12
+ from omlish.subprocesses import SubprocessChannelOption
13
+ from omlish.subprocesses import subprocess_maybe_shell_wrap_exec
14
14
 
15
15
  from .base import Command
16
16
  from .base import CommandExecutor
@@ -3,12 +3,13 @@ import datetime
3
3
  import os.path
4
4
  import typing as ta
5
5
 
6
+ from omlish.lite.cached import cached_nullary
7
+ from omlish.lite.check import check
8
+
6
9
  from .git import DeployGitManager
7
- from .git import DeployGitRepo
8
- from .git import DeployGitSpec
9
10
  from .paths import DeployPath
10
11
  from .paths import DeployPathOwner
11
- from .types import DeployApp
12
+ from .specs import DeploySpec
12
13
  from .types import DeployAppTag
13
14
  from .types import DeployHome
14
15
  from .types import DeployRev
@@ -24,14 +25,14 @@ def make_deploy_tag(
24
25
  now = datetime.datetime.utcnow() # noqa
25
26
  now_fmt = '%Y%m%dT%H%M%S'
26
27
  now_str = now.strftime(now_fmt)
27
- return DeployTag('-'.join([rev, now_str]))
28
+ return DeployTag('-'.join([now_str, rev]))
28
29
 
29
30
 
30
31
  class DeployAppManager(DeployPathOwner):
31
32
  def __init__(
32
33
  self,
33
34
  *,
34
- deploy_home: DeployHome,
35
+ deploy_home: ta.Optional[DeployHome] = None,
35
36
  git: DeployGitManager,
36
37
  venvs: DeployVenvManager,
37
38
  ) -> None:
@@ -41,7 +42,9 @@ class DeployAppManager(DeployPathOwner):
41
42
  self._git = git
42
43
  self._venvs = venvs
43
44
 
44
- self._dir = os.path.join(deploy_home, 'apps')
45
+ @cached_nullary
46
+ def _dir(self) -> str:
47
+ return os.path.join(check.non_empty_str(self._deploy_home), 'apps')
45
48
 
46
49
  def get_deploy_paths(self) -> ta.AbstractSet[DeployPath]:
47
50
  return {
@@ -50,20 +53,16 @@ class DeployAppManager(DeployPathOwner):
50
53
 
51
54
  async def prepare_app(
52
55
  self,
53
- app: DeployApp,
54
- rev: DeployRev,
55
- repo: DeployGitRepo,
56
+ spec: DeploySpec,
56
57
  ):
57
- app_tag = DeployAppTag(app, make_deploy_tag(rev))
58
- app_dir = os.path.join(self._dir, app, app_tag.tag)
58
+ app_tag = DeployAppTag(spec.app, make_deploy_tag(spec.rev))
59
+ app_dir = os.path.join(self._dir(), spec.app, app_tag.tag)
59
60
 
60
61
  #
61
62
 
62
63
  await self._git.checkout(
63
- DeployGitSpec(
64
- repo=repo,
65
- rev=rev,
66
- ),
64
+ spec.repo,
65
+ spec.rev,
67
66
  app_dir,
68
67
  )
69
68
 
@@ -3,6 +3,9 @@ import dataclasses as dc
3
3
  import typing as ta
4
4
 
5
5
 
6
+ ##
7
+
8
+
6
9
  @dc.dataclass(frozen=True)
7
10
  class DeployConfig:
8
11
  deploy_home: ta.Optional[str] = None
@@ -8,17 +8,18 @@ git/github.com/wrmsr/omlish <- bootstrap repo
8
8
 
9
9
  github.com/wrmsr/omlish@rev
10
10
  """
11
- import dataclasses as dc
12
11
  import functools
13
12
  import os.path
14
13
  import typing as ta
15
14
 
16
- from omlish.lite.asyncio.subprocesses import asyncio_subprocesses
15
+ from omlish.asyncs.asyncio.subprocesses import asyncio_subprocesses
17
16
  from omlish.lite.cached import async_cached_nullary
17
+ from omlish.lite.cached import cached_nullary
18
18
  from omlish.lite.check import check
19
19
 
20
20
  from .paths import DeployPath
21
21
  from .paths import DeployPathOwner
22
+ from .specs import DeployGitRepo
22
23
  from .types import DeployHome
23
24
  from .types import DeployRev
24
25
 
@@ -26,39 +27,22 @@ from .types import DeployRev
26
27
  ##
27
28
 
28
29
 
29
- @dc.dataclass(frozen=True)
30
- class DeployGitRepo:
31
- host: ta.Optional[str] = None
32
- username: ta.Optional[str] = None
33
- path: ta.Optional[str] = None
34
-
35
- def __post_init__(self) -> None:
36
- check.not_in('..', check.non_empty_str(self.host))
37
- check.not_in('.', check.non_empty_str(self.path))
38
-
39
-
40
- @dc.dataclass(frozen=True)
41
- class DeployGitSpec:
42
- repo: DeployGitRepo
43
- rev: DeployRev
44
-
45
-
46
- ##
47
-
48
-
49
30
  class DeployGitManager(DeployPathOwner):
50
31
  def __init__(
51
32
  self,
52
33
  *,
53
- deploy_home: DeployHome,
34
+ deploy_home: ta.Optional[DeployHome] = None,
54
35
  ) -> None:
55
36
  super().__init__()
56
37
 
57
38
  self._deploy_home = deploy_home
58
- self._dir = os.path.join(deploy_home, 'git')
59
39
 
60
40
  self._repo_dirs: ta.Dict[DeployGitRepo, DeployGitManager.RepoDir] = {}
61
41
 
42
+ @cached_nullary
43
+ def _dir(self) -> str:
44
+ return os.path.join(check.non_empty_str(self._deploy_home), 'git')
45
+
62
46
  def get_deploy_paths(self) -> ta.AbstractSet[DeployPath]:
63
47
  return {
64
48
  DeployPath.parse('git'),
@@ -75,7 +59,7 @@ class DeployGitManager(DeployPathOwner):
75
59
  self._git = git
76
60
  self._repo = repo
77
61
  self._dir = os.path.join(
78
- self._git._dir, # noqa
62
+ self._git._dir(), # noqa
79
63
  check.non_empty_str(repo.host),
80
64
  check.non_empty_str(repo.path),
81
65
  )
@@ -132,5 +116,5 @@ class DeployGitManager(DeployPathOwner):
132
116
  repo_dir = self._repo_dirs[repo] = DeployGitManager.RepoDir(self, repo)
133
117
  return repo_dir
134
118
 
135
- async def checkout(self, spec: DeployGitSpec, dst_dir: str) -> None:
136
- await self.get_repo_dir(spec.repo).checkout(spec.rev, dst_dir)
119
+ async def checkout(self, repo: DeployGitRepo, rev: DeployRev, dst_dir: str) -> None:
120
+ await self.get_repo_dir(repo).checkout(rev, dst_dir)
@@ -3,22 +3,22 @@
3
3
  ~deploy
4
4
  deploy.pid (flock)
5
5
  /app
6
- /<appspec> - shallow clone
6
+ /<appplaceholder> - shallow clone
7
7
  /conf
8
8
  /env
9
- <appspec>.env
9
+ <appplaceholder>.env
10
10
  /nginx
11
- <appspec>.conf
11
+ <appplaceholder>.conf
12
12
  /supervisor
13
- <appspec>.conf
13
+ <appplaceholder>.conf
14
14
  /venv
15
- /<appspec>
15
+ /<appplaceholder>
16
16
 
17
17
  ?
18
18
  /logs
19
- /wrmsr--omlish--<spec>
19
+ /wrmsr--omlish--<placeholder>
20
20
 
21
- spec = <name>--<rev>--<when>
21
+ placeholder = <name>--<rev>--<when>
22
22
 
23
23
  ==
24
24
 
@@ -43,16 +43,16 @@ from omlish.lite.check import check
43
43
 
44
44
 
45
45
  DeployPathKind = ta.Literal['dir', 'file'] # ta.TypeAlias
46
- DeployPathSpec = ta.Literal['app', 'tag'] # ta.TypeAlias
46
+ DeployPathPlaceholder = ta.Literal['app', 'tag'] # ta.TypeAlias
47
47
 
48
48
 
49
49
  ##
50
50
 
51
51
 
52
- DEPLOY_PATH_SPEC_PLACEHOLDER = '@'
53
- DEPLOY_PATH_SPEC_SEPARATORS = '-.'
52
+ DEPLOY_PATH_PLACEHOLDER_PLACEHOLDER = '@'
53
+ DEPLOY_PATH_PLACEHOLDER_SEPARATORS = '-.'
54
54
 
55
- DEPLOY_PATH_SPECS: ta.FrozenSet[str] = frozenset([
55
+ DEPLOY_PATH_PLACEHOLDERS: ta.FrozenSet[str] = frozenset([
56
56
  'app',
57
57
  'tag', # <rev>-<dt>
58
58
  ])
@@ -70,7 +70,7 @@ class DeployPathPart(abc.ABC): # noqa
70
70
  raise NotImplementedError
71
71
 
72
72
  @abc.abstractmethod
73
- def render(self, specs: ta.Optional[ta.Mapping[DeployPathSpec, str]] = None) -> str:
73
+ def render(self, placeholders: ta.Optional[ta.Mapping[DeployPathPlaceholder, str]] = None) -> str:
74
74
  raise NotImplementedError
75
75
 
76
76
 
@@ -84,9 +84,9 @@ class DirDeployPathPart(DeployPathPart, abc.ABC):
84
84
 
85
85
  @classmethod
86
86
  def parse(cls, s: str) -> 'DirDeployPathPart':
87
- if DEPLOY_PATH_SPEC_PLACEHOLDER in s:
88
- check.equal(s[0], DEPLOY_PATH_SPEC_PLACEHOLDER)
89
- return SpecDirDeployPathPart(s[1:])
87
+ if DEPLOY_PATH_PLACEHOLDER_PLACEHOLDER in s:
88
+ check.equal(s[0], DEPLOY_PATH_PLACEHOLDER_PLACEHOLDER)
89
+ return PlaceholderDirDeployPathPart(s[1:])
90
90
  else:
91
91
  return ConstDirDeployPathPart(s)
92
92
 
@@ -98,13 +98,13 @@ class FileDeployPathPart(DeployPathPart, abc.ABC):
98
98
 
99
99
  @classmethod
100
100
  def parse(cls, s: str) -> 'FileDeployPathPart':
101
- if DEPLOY_PATH_SPEC_PLACEHOLDER in s:
102
- check.equal(s[0], DEPLOY_PATH_SPEC_PLACEHOLDER)
103
- if not any(c in s for c in DEPLOY_PATH_SPEC_SEPARATORS):
104
- return SpecFileDeployPathPart(s[1:], '')
101
+ if DEPLOY_PATH_PLACEHOLDER_PLACEHOLDER in s:
102
+ check.equal(s[0], DEPLOY_PATH_PLACEHOLDER_PLACEHOLDER)
103
+ if not any(c in s for c in DEPLOY_PATH_PLACEHOLDER_SEPARATORS):
104
+ return PlaceholderFileDeployPathPart(s[1:], '')
105
105
  else:
106
- p = min(f for c in DEPLOY_PATH_SPEC_SEPARATORS if (f := s.find(c)) > 0)
107
- return SpecFileDeployPathPart(s[1:p], s[p:])
106
+ p = min(f for c in DEPLOY_PATH_PLACEHOLDER_SEPARATORS if (f := s.find(c)) > 0)
107
+ return PlaceholderFileDeployPathPart(s[1:p], s[p:])
108
108
  else:
109
109
  return ConstFileDeployPathPart(s)
110
110
 
@@ -119,9 +119,9 @@ class ConstDeployPathPart(DeployPathPart, abc.ABC):
119
119
  def __post_init__(self) -> None:
120
120
  check.non_empty_str(self.name)
121
121
  check.not_in('/', self.name)
122
- check.not_in(DEPLOY_PATH_SPEC_PLACEHOLDER, self.name)
122
+ check.not_in(DEPLOY_PATH_PLACEHOLDER_PLACEHOLDER, self.name)
123
123
 
124
- def render(self, specs: ta.Optional[ta.Mapping[DeployPathSpec, str]] = None) -> str:
124
+ def render(self, placeholders: ta.Optional[ta.Mapping[DeployPathPlaceholder, str]] = None) -> str:
125
125
  return self.name
126
126
 
127
127
 
@@ -137,40 +137,40 @@ class ConstFileDeployPathPart(ConstDeployPathPart, FileDeployPathPart):
137
137
 
138
138
 
139
139
  @dc.dataclass(frozen=True)
140
- class SpecDeployPathPart(DeployPathPart, abc.ABC):
141
- spec: str # DeployPathSpec
140
+ class PlaceholderDeployPathPart(DeployPathPart, abc.ABC):
141
+ placeholder: str # DeployPathPlaceholder
142
142
 
143
143
  def __post_init__(self) -> None:
144
- check.non_empty_str(self.spec)
145
- for c in [*DEPLOY_PATH_SPEC_SEPARATORS, DEPLOY_PATH_SPEC_PLACEHOLDER, '/']:
146
- check.not_in(c, self.spec)
147
- check.in_(self.spec, DEPLOY_PATH_SPECS)
148
-
149
- def _render_spec(self, specs: ta.Optional[ta.Mapping[DeployPathSpec, str]] = None) -> str:
150
- if specs is not None:
151
- return specs[self.spec] # type: ignore
144
+ check.non_empty_str(self.placeholder)
145
+ for c in [*DEPLOY_PATH_PLACEHOLDER_SEPARATORS, DEPLOY_PATH_PLACEHOLDER_PLACEHOLDER, '/']:
146
+ check.not_in(c, self.placeholder)
147
+ check.in_(self.placeholder, DEPLOY_PATH_PLACEHOLDERS)
148
+
149
+ def _render_placeholder(self, placeholders: ta.Optional[ta.Mapping[DeployPathPlaceholder, str]] = None) -> str:
150
+ if placeholders is not None:
151
+ return placeholders[self.placeholder] # type: ignore
152
152
  else:
153
- return DEPLOY_PATH_SPEC_PLACEHOLDER + self.spec
153
+ return DEPLOY_PATH_PLACEHOLDER_PLACEHOLDER + self.placeholder
154
154
 
155
155
 
156
156
  @dc.dataclass(frozen=True)
157
- class SpecDirDeployPathPart(SpecDeployPathPart, DirDeployPathPart):
158
- def render(self, specs: ta.Optional[ta.Mapping[DeployPathSpec, str]] = None) -> str:
159
- return self._render_spec(specs)
157
+ class PlaceholderDirDeployPathPart(PlaceholderDeployPathPart, DirDeployPathPart):
158
+ def render(self, placeholders: ta.Optional[ta.Mapping[DeployPathPlaceholder, str]] = None) -> str:
159
+ return self._render_placeholder(placeholders)
160
160
 
161
161
 
162
162
  @dc.dataclass(frozen=True)
163
- class SpecFileDeployPathPart(SpecDeployPathPart, FileDeployPathPart):
163
+ class PlaceholderFileDeployPathPart(PlaceholderDeployPathPart, FileDeployPathPart):
164
164
  suffix: str
165
165
 
166
166
  def __post_init__(self) -> None:
167
167
  super().__post_init__()
168
168
  if self.suffix:
169
- for c in [DEPLOY_PATH_SPEC_PLACEHOLDER, '/']:
169
+ for c in [DEPLOY_PATH_PLACEHOLDER_PLACEHOLDER, '/']:
170
170
  check.not_in(c, self.suffix)
171
171
 
172
- def render(self, specs: ta.Optional[ta.Mapping[DeployPathSpec, str]] = None) -> str:
173
- return self._render_spec(specs) + self.suffix
172
+ def render(self, placeholders: ta.Optional[ta.Mapping[DeployPathPlaceholder, str]] = None) -> str:
173
+ return self._render_placeholder(placeholders) + self.suffix
174
174
 
175
175
 
176
176
  ##
@@ -187,22 +187,22 @@ class DeployPath:
187
187
 
188
188
  pd = {}
189
189
  for i, p in enumerate(self.parts):
190
- if isinstance(p, SpecDeployPathPart):
191
- if p.spec in pd:
192
- raise DeployPathError('Duplicate specs in path', self)
193
- pd[p.spec] = i
190
+ if isinstance(p, PlaceholderDeployPathPart):
191
+ if p.placeholder in pd:
192
+ raise DeployPathError('Duplicate placeholders in path', self)
193
+ pd[p.placeholder] = i
194
194
 
195
195
  if 'tag' in pd:
196
196
  if 'app' not in pd or pd['app'] >= pd['tag']:
197
- raise DeployPathError('Tag spec in path without preceding app', self)
197
+ raise DeployPathError('Tag placeholder in path without preceding app', self)
198
198
 
199
199
  @property
200
200
  def kind(self) -> ta.Literal['file', 'dir']:
201
201
  return self.parts[-1].kind
202
202
 
203
- def render(self, specs: ta.Optional[ta.Mapping[DeployPathSpec, str]] = None) -> str:
203
+ def render(self, placeholders: ta.Optional[ta.Mapping[DeployPathPlaceholder, str]] = None) -> str:
204
204
  return os.path.join( # noqa
205
- *[p.render(specs) for p in self.parts],
205
+ *[p.render(placeholders) for p in self.parts],
206
206
  *([''] if self.kind == 'dir' else []),
207
207
  )
208
208
 
@@ -0,0 +1,32 @@
1
+ # ruff: noqa: UP006 UP007
2
+ import dataclasses as dc
3
+ import typing as ta
4
+
5
+ from omlish.lite.check import check
6
+
7
+ from .types import DeployApp
8
+ from .types import DeployRev
9
+
10
+
11
+ ##
12
+
13
+
14
+ @dc.dataclass(frozen=True)
15
+ class DeployGitRepo:
16
+ host: ta.Optional[str] = None
17
+ username: ta.Optional[str] = None
18
+ path: ta.Optional[str] = None
19
+
20
+ def __post_init__(self) -> None:
21
+ check.not_in('..', check.non_empty_str(self.host))
22
+ check.not_in('.', check.non_empty_str(self.path))
23
+
24
+
25
+ ##
26
+
27
+
28
+ @dc.dataclass(frozen=True)
29
+ class DeploySpec:
30
+ app: DeployApp
31
+ repo: DeployGitRepo
32
+ rev: DeployRev
@@ -7,7 +7,9 @@ TODO:
7
7
  import os.path
8
8
  import typing as ta
9
9
 
10
- from omlish.lite.asyncio.subprocesses import asyncio_subprocesses
10
+ from omlish.asyncs.asyncio.subprocesses import asyncio_subprocesses
11
+ from omlish.lite.cached import cached_nullary
12
+ from omlish.lite.check import check
11
13
 
12
14
  from .paths import DeployPath
13
15
  from .paths import DeployPathOwner
@@ -19,12 +21,15 @@ class DeployVenvManager(DeployPathOwner):
19
21
  def __init__(
20
22
  self,
21
23
  *,
22
- deploy_home: DeployHome,
24
+ deploy_home: ta.Optional[DeployHome] = None,
23
25
  ) -> None:
24
26
  super().__init__()
25
27
 
26
28
  self._deploy_home = deploy_home
27
- self._dir = os.path.join(deploy_home, 'venvs')
29
+
30
+ @cached_nullary
31
+ def _dir(self) -> str:
32
+ return os.path.join(check.non_empty_str(self._deploy_home), 'venvs')
28
33
 
29
34
  def get_deploy_paths(self) -> ta.AbstractSet[DeployPath]:
30
35
  return {
@@ -61,6 +66,6 @@ class DeployVenvManager(DeployPathOwner):
61
66
 
62
67
  async def setup_app_venv(self, app_tag: DeployAppTag) -> None:
63
68
  await self.setup_venv(
64
- os.path.join(self._deploy_home, 'apps', app_tag.app, app_tag.tag),
65
- os.path.join(self._deploy_home, 'venvs', app_tag.app, app_tag.tag),
69
+ os.path.join(check.non_empty_str(self._deploy_home), 'apps', app_tag.app, app_tag.tag),
70
+ os.path.join(self._dir(), app_tag.app, app_tag.tag),
66
71
  )
ominfra/manage/main.py CHANGED
@@ -6,18 +6,23 @@ manage.py -s 'docker run -i python:3.12'
6
6
  manage.py -s 'ssh -i /foo/bar.pem foo@bar.baz' -q --python=python3.8
7
7
  """
8
8
  import asyncio
9
+ import dataclasses as dc
9
10
  import json
11
+ import os.path
10
12
  import sys
11
13
  import typing as ta
12
14
 
13
15
  from omlish.argparse.cli import ArgparseCli
14
16
  from omlish.argparse.cli import argparse_arg
15
17
  from omlish.argparse.cli import argparse_command
18
+ from omlish.lite.cached import cached_nullary
19
+ from omlish.lite.check import check
16
20
  from omlish.lite.logs import log # noqa
17
21
  from omlish.lite.marshal import ObjMarshalerManager
18
22
  from omlish.lite.marshal import ObjMarshalOptions
19
23
  from omlish.lite.pycharm import PycharmRemoteDebug
20
24
 
25
+ from ..configs import read_config_file
21
26
  from .bootstrap import MainBootstrap
22
27
  from .bootstrap_ import main_bootstrap
23
28
  from .commands.base import Command
@@ -28,7 +33,28 @@ from .targets.connection import ManageTargetConnector
28
33
  from .targets.targets import ManageTarget
29
34
 
30
35
 
36
+ @dc.dataclass(frozen=True)
37
+ class ManageConfig:
38
+ targets: ta.Optional[ta.Mapping[str, ManageTarget]] = None
39
+
40
+
31
41
  class MainCli(ArgparseCli):
42
+ config_file: ta.Optional[str] = argparse_arg('--config-file', help='Config file path') # type: ignore
43
+
44
+ @cached_nullary
45
+ def config(self) -> ManageConfig:
46
+ if (cf := self.config_file) is None:
47
+ cf = os.path.expanduser('~/.omlish/manage.yml')
48
+ if not os.path.isfile(cf):
49
+ cf = None
50
+
51
+ if cf is None:
52
+ return ManageConfig()
53
+ else:
54
+ return read_config_file(cf, ManageConfig)
55
+
56
+ #
57
+
32
58
  @argparse_command(
33
59
  argparse_arg('--_payload-file'),
34
60
 
@@ -80,10 +106,13 @@ class MainCli(ArgparseCli):
80
106
 
81
107
  msh = injector[ObjMarshalerManager]
82
108
 
83
- ts = self.args.target
84
- if not ts.startswith('{'):
85
- ts = json.dumps({ts: {}})
86
- tgt: ManageTarget = msh.unmarshal_obj(json.loads(ts), ManageTarget)
109
+ tgt: ManageTarget
110
+ if not (ts := self.args.target).startswith('{'):
111
+ tgt = check.not_none(self.config().targets)[ts]
112
+ else:
113
+ tgt = msh.unmarshal_obj(json.loads(ts), ManageTarget)
114
+
115
+ #
87
116
 
88
117
  cmds: ta.List[Command] = []
89
118
  cmd: Command
@@ -7,11 +7,10 @@ import shlex
7
7
  import subprocess
8
8
  import typing as ta
9
9
 
10
- from omlish.lite.asyncio.subprocesses import asyncio_subprocesses
10
+ from omlish.asyncs.asyncio.subprocesses import asyncio_subprocesses
11
11
  from omlish.lite.check import check
12
- from omlish.lite.subprocesses import SUBPROCESS_CHANNEL_OPTION_VALUES
13
- from omlish.lite.subprocesses import SubprocessChannelOption
14
- from omlish.lite.subprocesses import subprocess_maybe_shell_wrap_exec
12
+ from omlish.subprocesses import SUBPROCESS_CHANNEL_OPTION_VALUES
13
+ from omlish.subprocesses import SubprocessChannelOption
15
14
 
16
15
 
17
16
  ##
@@ -82,12 +81,8 @@ class SubprocessRemoteSpawning(RemoteSpawning):
82
81
  ) -> ta.AsyncGenerator[RemoteSpawning.Spawned, None]:
83
82
  pc = self._prepare_cmd(tgt, src)
84
83
 
85
- cmd = pc.cmd
86
- if not debug:
87
- cmd = subprocess_maybe_shell_wrap_exec(*cmd)
88
-
89
84
  async with asyncio_subprocesses.popen(
90
- *cmd,
85
+ *pc.cmd,
91
86
  shell=pc.shell,
92
87
  stdin=subprocess.PIPE,
93
88
  stdout=subprocess.PIPE,
@@ -9,7 +9,7 @@ import json
9
9
  import os
10
10
  import typing as ta
11
11
 
12
- from omlish.lite.asyncio.subprocesses import asyncio_subprocesses
12
+ from omlish.asyncs.asyncio.subprocesses import asyncio_subprocesses
13
13
  from omlish.lite.check import check
14
14
 
15
15