Skip to content

Commit fd8a1a3

Browse files
committed
Add CallCommand
1 parent df45086 commit fd8a1a3

File tree

5 files changed

+499
-445
lines changed

5 files changed

+499
-445
lines changed
Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
import json
2+
import shlex
3+
import subprocess
4+
from pathlib import Path
5+
6+
from mypy.state import state
7+
8+
from patchwork.logger import logger
9+
from patchwork.step import Step, StepStatus
10+
from patchwork.steps.CallCommand.typed import CallCommandInputs, CallCommandOutputs
11+
12+
13+
class CallCommand(Step, input_class=CallCommandInputs, output_class=CallCommandOutputs):
14+
def __init__(self, inputs: dict):
15+
super().__init__(inputs)
16+
self.command = inputs["command"]
17+
self.command_args = inputs.get("command_args", "")
18+
self.working_dir = inputs.get("working_dir", Path.cwd())
19+
self.env = self.__parse_env_text(inputs.get("env", ""))
20+
21+
@staticmethod
22+
def __parse_env_text(env_text):
23+
env_spliter = shlex.shlex(env_text, posix=True)
24+
env_spliter.whitespace_split = True
25+
env_spliter.whitespace += ";"
26+
27+
env = dict()
28+
for env_assign in env_spliter:
29+
env_assign_spliter = shlex.shlex(env_assign, posix=True)
30+
env_assign_spliter.whitespace_split = True
31+
env_assign_spliter.whitespace += "="
32+
env_parts = list(env_assign_spliter)
33+
if len(env_parts) < 1:
34+
continue
35+
36+
env_assign_target = env_parts[0]
37+
if len(env_parts) < 2:
38+
logger.error(f"{env_assign_target} is not assigned anything, skipping...")
39+
continue
40+
if len(env_parts) > 2:
41+
logger.error(f"{env_assign_target} has more than 1 assignment, skipping...")
42+
continue
43+
env[env_assign_target] = env_parts[1]
44+
45+
return env
46+
47+
def run(self) -> dict:
48+
cmd = [self.command, *shlex.split(self.command_args)]
49+
p = subprocess.run(cmd, capture_output=True, text=True, cwd=self.working_dir, env=self.env)
50+
try:
51+
p.check_returncode()
52+
return dict(stdout_output=p.stdout)
53+
except subprocess.CalledProcessError as e:
54+
self.set_status(StepStatus.FAILED, f"`{self.command} {self.command_args}` failed with stdout:\n{p.stdout}\nstderr:\n{e.stderr}")
55+
return dict()

patchwork/steps/CallCommand/__init__.py

Whitespace-only changes.
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
from typing_extensions import Annotated, TypedDict
2+
3+
from patchwork.common.utils.step_typing import StepTypeConfig
4+
5+
6+
class __RequiredCallCommandInputs(TypedDict):
7+
command: str
8+
9+
class CallCommandInputs(__RequiredCallCommandInputs, total=False):
10+
command_args: str
11+
working_dir: Annotated[str, StepTypeConfig(is_path=True)]
12+
env: str
13+
14+
15+
class CallCommandOutputs(TypedDict):
16+
stdout_output: str

0 commit comments

Comments
 (0)