Improvements for the create-bulk-issues.py script (#84235)

* Improve error handling for create-bulk-issues.py

* Add support for setting assignee

* Add example YAML to feature --help output.

* Add additional help message for token issues.
pull/80678/head^2
Matt Clay 1 year ago committed by GitHub
parent 32ae3ce117
commit c49e94017a
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194

@ -35,6 +35,7 @@ class Issue:
body: str body: str
project: str project: str
labels: list[str] | None = None labels: list[str] | None = None
assignee: str | None = None
def create(self) -> str: def create(self) -> str:
cmd = ['gh', 'issue', 'create', '--title', self.title, '--body', self.body, '--project', self.project] cmd = ['gh', 'issue', 'create', '--title', self.title, '--body', self.body, '--project', self.project]
@ -43,8 +44,18 @@ class Issue:
for label in self.labels: for label in self.labels:
cmd.extend(('--label', label)) cmd.extend(('--label', label))
process = subprocess.run(cmd, capture_output=True, check=True) if self.assignee:
url = process.stdout.decode().strip() cmd.extend(('--assignee', self.assignee))
try:
process = subprocess.run(cmd, capture_output=True, check=True, text=True)
except subprocess.CalledProcessError as ex:
print('>>> Note')
print(f"You may need to run 'gh auth refresh -s project' if 'gh' reports it cannot find the project {self.project!r} when it exists.")
print(f'>>> Standard Output\n{ex.stdout.strip()}\n>>> Standard Error\n{ex.stderr.strip()}\n>>> Exception')
raise
url = process.stdout.strip()
return url return url
@ -54,6 +65,7 @@ class Feature:
summary: str summary: str
component: str component: str
labels: list[str] | None = None labels: list[str] | None = None
assignee: str | None = None
@staticmethod @staticmethod
def from_dict(data: dict[str, t.Any]) -> Feature: def from_dict(data: dict[str, t.Any]) -> Feature:
@ -61,6 +73,7 @@ class Feature:
summary = data.get('summary') summary = data.get('summary')
component = data.get('component') component = data.get('component')
labels = data.get('labels') labels = data.get('labels')
assignee = data.get('assignee')
if not isinstance(title, str): if not isinstance(title, str):
raise RuntimeError(f'`title` is not `str`: {title}') raise RuntimeError(f'`title` is not `str`: {title}')
@ -71,6 +84,9 @@ class Feature:
if not isinstance(component, str): if not isinstance(component, str):
raise RuntimeError(f'`component` is not `str`: {component}') raise RuntimeError(f'`component` is not `str`: {component}')
if not isinstance(assignee, (str, type(None))):
raise RuntimeError(f'`assignee` is not `str`: {assignee}')
if not isinstance(labels, list) or not all(isinstance(item, str) for item in labels): if not isinstance(labels, list) or not all(isinstance(item, str) for item in labels):
raise RuntimeError(f'`labels` is not `list[str]`: {labels}') raise RuntimeError(f'`labels` is not `list[str]`: {labels}')
@ -79,6 +95,7 @@ class Feature:
summary=summary, summary=summary,
component=component, component=component,
labels=labels, labels=labels,
assignee=assignee,
) )
def create_issue(self, project: str) -> Issue: def create_issue(self, project: str) -> Issue:
@ -102,6 +119,7 @@ Feature Idea
body=body.strip(), body=body.strip(),
project=project, project=project,
labels=self.labels, labels=self.labels,
assignee=self.assignee,
) )
@ -297,7 +315,21 @@ def create_deprecation_parser(subparser) -> None:
def create_feature_parser(subparser) -> None: def create_feature_parser(subparser) -> None:
parser: argparse.ArgumentParser = subparser.add_parser('feature') epilog = """
Example source YAML:
default:
component: ansible-test
labels:
- ansible-test
- feature
assignee: "@me"
features:
- title: Some title goes here
summary: A summary goes here.
"""
parser: argparse.ArgumentParser = subparser.add_parser('feature', epilog=epilog, formatter_class=argparse.RawDescriptionHelpFormatter)
parser.set_defaults(type=FeatureArgs) parser.set_defaults(type=FeatureArgs)
parser.set_defaults(command=feature_command) parser.set_defaults(command=feature_command)

Loading…
Cancel
Save