github-rest-api 0.47.0__py3-none-any.whl → 0.47.2__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.
@@ -2,6 +2,7 @@
2
2
 
3
3
  import argparse
4
4
  import getpass
5
+ import logging
5
6
  import os
6
7
  import shutil
7
8
  import sys
@@ -12,6 +13,8 @@ from dulwich import porcelain
12
13
 
13
14
  from github_rest_api import Organization, User
14
15
 
16
+ logger = logging.getLogger(__name__)
17
+
15
18
 
16
19
  def _validate_repo(repo: str) -> None:
17
20
  parts = repo.split("/")
@@ -28,8 +31,9 @@ def _create_remote_repo(
28
31
  if is_owner_user
29
32
  else Organization(token=token, org=owner)
30
33
  )
34
+ logger.info("Creating remote GitHub repository '%s'...", repo)
31
35
  entity.create_repository(name=r, private=private)
32
- print(f"\nCreated the GitHub repo https://github.com/{repo}.\n")
36
+ logger.info("Created the GitHub repo https://github.com/%s.", repo)
33
37
 
34
38
 
35
39
  def _remote_url(repo: str, protocol: str) -> str:
@@ -41,10 +45,22 @@ def _remote_url(repo: str, protocol: str) -> str:
41
45
  def _ensure_remote(path: Path, repo: str, protocol: str) -> None:
42
46
  try:
43
47
  porcelain.remote_add(path, "origin", _remote_url(repo, protocol))
48
+ logger.info("Added remote 'origin' for %s", repo)
44
49
  except porcelain.RemoteExists:
45
50
  pass
46
51
 
47
52
 
53
+ def _active_branch(path: Path) -> str:
54
+ try:
55
+ return porcelain.active_branch(path).decode()
56
+ except (IndexError, ValueError) as e:
57
+ raise ValueError(
58
+ f"HEAD of the local repo at '{path}' is detached (not on any branch), "
59
+ "which is unsupported (this happens, e.g., with a colocated Jujutsu repo). "
60
+ "Check out a branch (e.g. `git switch -c main`) before running this command."
61
+ ) from e
62
+
63
+
48
64
  def _init_local_repo(
49
65
  repo: str,
50
66
  language: str,
@@ -59,25 +75,32 @@ def _init_local_repo(
59
75
  readme = path / "README.md"
60
76
  if not readme.exists():
61
77
  readme.write_text(f"# {repo_name}\n")
78
+ logger.info("Created %s", readme)
62
79
  if not (path / ".git").exists():
63
80
  porcelain.init(path=path)
64
- initial_branch = (
65
- (path / ".git" / "HEAD").read_text().strip().partition("refs/heads/")[-1]
66
- )
67
- porcelain.add(repo=path)
81
+ logger.info("Initialized empty Git repository in %s", path)
82
+ if not porcelain.branch_list(path):
83
+ initial_branch = _active_branch(path)
84
+ porcelain.add(repo=path, paths=["README.md"])
85
+ logger.info("Added README.md to staging")
68
86
  porcelain.commit(repo=path, message="first commit")
87
+ logger.info("Created first commit")
69
88
  for branch in branches:
70
89
  if branch != initial_branch:
71
90
  porcelain.branch_create(repo=path, name=branch)
91
+ logger.info("Created branch '%s'", branch)
72
92
  porcelain.checkout(repo=path, target=branches[0])
93
+ logger.info("Checked out branch '%s'", branches[0])
73
94
  if initial_branch not in branches:
74
95
  porcelain.branch_delete(repo=path, name=initial_branch)
96
+ logger.info("Deleted initial branch '%s'", initial_branch)
75
97
  _ensure_remote(path, repo, protocol)
76
98
  local_branches = {b.decode() for b in porcelain.branch_list(path)}
77
99
  branches_to_push = [branch for branch in branches if branch in local_branches]
78
100
  if not branches_to_push:
79
- branches_to_push = [porcelain.active_branch(path).decode()]
101
+ branches_to_push = [_active_branch(path)]
80
102
  for branch in branches_to_push:
103
+ logger.info("Pushing branch '%s' to remote '%s'...", branch, repo)
81
104
  porcelain.push(
82
105
  repo=path,
83
106
  remote_location=_remote_url(repo, "https"),
@@ -85,6 +108,7 @@ def _init_local_repo(
85
108
  username="x-access-token",
86
109
  password=token,
87
110
  )
111
+ logger.info("Successfully pushed branch '%s'.", branch)
88
112
  _add_workflow(path, language)
89
113
 
90
114
 
@@ -128,6 +152,7 @@ def _add_workflow(path: Path, language: str, workflow_dir: Path | None = None) -
128
152
  for yaml in workflow_dir.glob("*.yaml"):
129
153
  if not (dir_dest / yaml.name).exists():
130
154
  shutil.copy2(yaml, dir_dest)
155
+ logger.info("Copied workflow %s to %s", yaml.name, dir_dest)
131
156
  if not language:
132
157
  return
133
158
  lang_dir = workflow_dir / language
@@ -136,6 +161,9 @@ def _add_workflow(path: Path, language: str, workflow_dir: Path | None = None) -
136
161
  for yaml in lang_dir.glob("*.yaml"):
137
162
  if not (dir_dest / yaml.name).exists():
138
163
  shutil.copy2(yaml, dir_dest)
164
+ logger.info(
165
+ "Copied %s specific workflow %s to %s", language, yaml.name, dir_dest
166
+ )
139
167
 
140
168
 
141
169
  def parse_args(args=None, namespace=None):
@@ -205,11 +233,19 @@ def parse_args(args=None, namespace=None):
205
233
  default="git",
206
234
  help="Use the HTTPS protocol for the remote URL.",
207
235
  )
236
+ parser.add_argument(
237
+ "-v",
238
+ "--verbose",
239
+ dest="verbose",
240
+ action="store_true",
241
+ help="Enable verbose output, including tracebacks on errors.",
242
+ )
208
243
  return parser.parse_args(args=args, namespace=namespace)
209
244
 
210
245
 
211
246
  def main() -> int:
212
247
  args = parse_args()
248
+ logging.basicConfig(level=logging.INFO, format="%(message)s")
213
249
  try:
214
250
  create_github_repo(
215
251
  repo=args.repo,
@@ -222,7 +258,7 @@ def main() -> int:
222
258
  protocol=args.protocol,
223
259
  )
224
260
  except Exception as e:
225
- print(str(e), file=sys.stderr)
261
+ logger.error("Failed to create GitHub repo: %s", e, exc_info=args.verbose)
226
262
  return 1
227
263
  return 0
228
264
 
@@ -0,0 +1,30 @@
1
+ name: Auto Merge PR
2
+ on:
3
+ pull_request_review:
4
+ types:
5
+ - submitted
6
+ issue_comment:
7
+ types:
8
+ - created
9
+ check_suite:
10
+ types:
11
+ - completed
12
+ schedule:
13
+ - cron: '0 * * * *'
14
+ timezone: 'America/Los_Angeles'
15
+ permissions:
16
+ contents: write
17
+ pull-requests: write
18
+ jobs:
19
+ auto_merge_pull_request:
20
+ runs-on: ubuntu-latest
21
+ steps:
22
+ - name: Install uv
23
+ run: |
24
+ curl -LsSf https://astral.sh/uv/install.sh | sudo env UV_INSTALL_DIR="/usr/local/bin" sh
25
+ - name: Auto Merge PR
26
+ run: |
27
+ uvx --from github-rest-api@latest auto_merge_pull_request \
28
+ --authors dclong \
29
+ --approvers dclong 'claude[bot]' 'gemini-code-assist[bot]' \
30
+ --token ${{ secrets.ACTIONS_TOKEN }}
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: github-rest-api
3
- Version: 0.47.0
3
+ Version: 0.47.2
4
4
  Summary: Simple wrapper of GitHub REST APIs.
5
5
  Author-email: Ben Du <longendu@yahoo.com>
6
6
  Classifier: Programming Language :: Python :: 3 :: Only
@@ -14,17 +14,18 @@ github_rest_api/scripts/container/config_container.py,sha256=BtOqgZlQFM9cWZMoHKv
14
14
  github_rest_api/scripts/container/update_version_containerfile.py,sha256=1PkuJkAsJBCEMdacMSndbuZKcmgUyXy6nBArnxKoPZk,4535
15
15
  github_rest_api/scripts/github/__init__.py,sha256=tEU1SdCS51M4M13WoqXZt3rjGEAI_QgNljt5XAyQJ_w,38
16
16
  github_rest_api/scripts/github/auto_merge_pull_request.py,sha256=_5191Xt_b8DtxjIqHrdY-gKLxvkzWd8oWoSbF2uauc8,3527
17
- github_rest_api/scripts/github/create_github_repo.py,sha256=7t2dgDcLrLPpBY5CpTtkkIe8Z_-2FGgoRo_--HXwcuw,6686
17
+ github_rest_api/scripts/github/create_github_repo.py,sha256=jH1uKOXKOxooO-PHMGlQ5YnIluWNqzRhkfgKdkH5UGU,8316
18
18
  github_rest_api/scripts/github/create_pull_request.py,sha256=gXtRRsxzegGxagHb6k3kxtRd3mt4QVwSPZQpsFnzz1Y,3968
19
19
  github_rest_api/scripts/github/release_on_github.py,sha256=9psaIv-GtrHdvE-tkw0yxCMDmW0bPts-db2vUxhoKXo,4368
20
20
  github_rest_api/scripts/github/remove_branch.py,sha256=iKZ4Y_lQlSOIfifC4plqP-B6pEMnFrknGMvV1oLnuLc,3538
21
+ github_rest_api/scripts/github/workflows/auto_merge_pull_request.yaml,sha256=LOCYzTnubAqBbeGunSdnEt453ZLwJ2870YxRlcPJ7GE,768
21
22
  github_rest_api/scripts/github/workflows/create_pr_dev_to_main.yaml,sha256=fuYNQJ_BthRWmFv2J0JZgB_LrBsmEVAc8rZ-Cs_AqrQ,517
22
23
  github_rest_api/scripts/github/workflows/create_pr_to_dev.yaml,sha256=wFekTLVWffPQOguJCMfu8NnxLQ3OFvN5aBmYih8Ag14,548
23
24
  github_rest_api/scripts/github/workflows/create_pr_to_main.yaml,sha256=mgHPlewkCZfRyMH6PYtPlo-fuE7DaD8v_jj2dSc3nPA,531
24
25
  github_rest_api/scripts/github/workflows/remove_branch.yaml,sha256=KDpB76ovrhuRdP0HN5j6Th9gjIQWSDdh8b4b4yAgtoI,544
25
26
  github_rest_api/scripts/github/workflows/python/lint.yaml,sha256=toP2oUdVIKyu_n20Dr14k5cJYxN8rPksfbX4sfflXxc,699
26
27
  github_rest_api/scripts/github/workflows/python/test.yaml,sha256=86MljYEWX1E9kJYmhMCLwu46WNEWvoyO9PwqeRew540,887
27
- github_rest_api-0.47.0.dist-info/METADATA,sha256=SjlTYqUbYuVm5n3gvDE7NE1PutETNTXXoV609PLMOsc,915
28
- github_rest_api-0.47.0.dist-info/WHEEL,sha256=lCkmxWfQsSc9CfIClYeavTdQeEX2toPqufh9gI35EQA,87
29
- github_rest_api-0.47.0.dist-info/entry_points.txt,sha256=OfbP9GuQC7SyGbymfCYrXEG-TCcKuu31v0EPNvHc1Q4,659
30
- github_rest_api-0.47.0.dist-info/RECORD,,
28
+ github_rest_api-0.47.2.dist-info/METADATA,sha256=7Z7N5_Ed4-TbTs2G9T17mSdtM74ZO2FU_8dyvfKFoOE,915
29
+ github_rest_api-0.47.2.dist-info/WHEEL,sha256=lCkmxWfQsSc9CfIClYeavTdQeEX2toPqufh9gI35EQA,87
30
+ github_rest_api-0.47.2.dist-info/entry_points.txt,sha256=OfbP9GuQC7SyGbymfCYrXEG-TCcKuu31v0EPNvHc1Q4,659
31
+ github_rest_api-0.47.2.dist-info/RECORD,,