Skip to content

Commit c46b652

Browse files
authored
determine git metadata from commit that introduced changeset file (#5)
1 parent fb8ea83 commit c46b652

File tree

3 files changed

+113
-5
lines changed

3 files changed

+113
-5
lines changed

.changeset/brilliant-unique-hyena.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
"changeset": patch
3+
---
4+
5+
fix pr metadata grabbing

changeset/changelog.py

Lines changed: 105 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -92,6 +92,99 @@ def get_pr_metadata() -> dict:
9292
return metadata
9393

9494

95+
def get_changeset_metadata(changeset_path: Path) -> dict:
96+
"""Get PR metadata for a specific changeset file.
97+
98+
Finds the commit that introduced the changeset and extracts metadata.
99+
"""
100+
metadata = {}
101+
git_info = get_git_info()
102+
metadata["repo_url"] = git_info.get("repo_url", "")
103+
104+
try:
105+
# Find the commit that introduced this changeset file
106+
result = subprocess.run(
107+
["git", "log", "--format=%H", "--diff-filter=A", "--", str(changeset_path)],
108+
capture_output=True,
109+
text=True,
110+
check=True,
111+
)
112+
113+
if result.stdout.strip():
114+
commit_hash = result.stdout.strip().split("\n")[0]
115+
metadata["commit_hash"] = commit_hash
116+
117+
# Get the commit message to extract PR number
118+
msg_result = subprocess.run(
119+
["git", "log", "-1", "--format=%B", commit_hash],
120+
capture_output=True,
121+
text=True,
122+
check=True,
123+
)
124+
125+
commit_msg = msg_result.stdout.strip()
126+
127+
# Extract PR number from commit message (common patterns)
128+
# Pattern 1: (#123)
129+
# Pattern 2: Merge pull request #123
130+
pr_match = re.search(r"(?:#|pull request #)(\d+)", commit_msg)
131+
if pr_match:
132+
pr_number = pr_match.group(1)
133+
metadata["pr_number"] = pr_number
134+
135+
# Try to get PR author using GitHub CLI if available
136+
try:
137+
gh_result = subprocess.run(
138+
[
139+
"gh",
140+
"api",
141+
f"repos/{git_info.get('owner', '')}/"
142+
f"{git_info.get('repo', '')}/pulls/{pr_number}",
143+
"--jq",
144+
".user.login",
145+
],
146+
capture_output=True,
147+
text=True,
148+
check=True,
149+
)
150+
if gh_result.stdout.strip():
151+
metadata["pr_author"] = gh_result.stdout.strip()
152+
except Exception:
153+
# If gh command fails, try to extract from commit author
154+
author_result = subprocess.run(
155+
["git", "log", "-1", "--format=%an", commit_hash],
156+
capture_output=True,
157+
text=True,
158+
)
159+
if author_result.stdout.strip():
160+
metadata["pr_author"] = author_result.stdout.strip()
161+
else:
162+
# No PR number found, use commit author
163+
author_result = subprocess.run(
164+
["git", "log", "-1", "--format=%an", commit_hash],
165+
capture_output=True,
166+
text=True,
167+
)
168+
if author_result.stdout.strip():
169+
metadata["pr_author"] = author_result.stdout.strip()
170+
171+
except subprocess.CalledProcessError:
172+
# If git commands fail, return empty metadata
173+
pass
174+
175+
# Fall back to environment variables if no specific metadata found
176+
if not metadata.get("pr_number"):
177+
metadata["pr_number"] = os.environ.get("PR_NUMBER", "")
178+
if not metadata.get("pr_author"):
179+
metadata["pr_author"] = os.environ.get("PR_AUTHOR", "")
180+
if not metadata.get("commit_hash"):
181+
metadata["commit_hash"] = os.environ.get(
182+
"COMMIT_SHA", git_info.get("commit", "")
183+
)
184+
185+
return metadata
186+
187+
95188
def format_changelog_entry(entry: dict, config: dict, pr_metadata: dict) -> str:
96189
"""Format a single changelog entry with PR and commit info."""
97190
description = entry["description"]
@@ -156,7 +249,12 @@ def generate_changelog_section(
156249

157250
# Add each entry
158251
for entry in grouped[change_type]:
159-
lines.append(format_changelog_entry(entry, config, pr_metadata))
252+
# Get metadata specific to this changeset if available
253+
if "filepath" in entry:
254+
changeset_metadata = get_changeset_metadata(entry["filepath"])
255+
else:
256+
changeset_metadata = pr_metadata
257+
lines.append(format_changelog_entry(entry, config, changeset_metadata))
160258

161259
lines.append("")
162260

@@ -252,7 +350,12 @@ def process_changesets_for_changelog() -> tuple[list[dict], str]:
252350
package_changes[package] = {"changes": [], "descriptions": []}
253351
package_changes[package]["changes"].append(change_type)
254352
package_changes[package]["descriptions"].append(
255-
{"type": change_type, "description": desc, "changeset": filepath.name}
353+
{
354+
"type": change_type,
355+
"description": desc,
356+
"changeset": filepath.name,
357+
"filepath": filepath,
358+
}
256359
)
257360

258361
# Process each package

ruff.toml

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
# Ruff configuration for pychangeset
22

3-
# Assume Python 3.13
4-
target-version = "py313"
3+
# Assume Python 3.12
4+
target-version = "py312"
55

66
# Line length to match Black's default
77
line-length = 88
@@ -30,4 +30,4 @@ known-first-party = ["changeset"]
3030
quote-style = "double"
3131
indent-style = "space"
3232
skip-magic-trailing-comma = false
33-
line-ending = "auto"
33+
line-ending = "auto"

0 commit comments

Comments
 (0)