Skip to content

Commit a7f233e

Browse files
committed
refactor: address code review
add snapshot testing and their runner renamed generate-guideline-templates.py to generate_guideline_templates.py general refactor
1 parent 9a30c38 commit a7f233e

10 files changed

+473
-175
lines changed

scripts/test_issue_sample.json renamed to .github/auto-pr-tests/test_issue_01.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -104,7 +104,7 @@
104104
"completed": 0,
105105
"percent_completed": 0
106106
},
107-
"body": "### Chapter\n\nConcurrency\n\n### Guideline Title\n\ntest ga\n\n### Category\n\nAdvisory\n\n### Status\n\nDraft\n\n### Release Begin\n\n1.1.1\n\n### Release End\n\n1.1.1\n\n### FLS Paragraph ID\n\nfls_fsdjkfslkdfj\n\n### Decidability\n\nDecidable\n\n### Scope\n\nCrate\n\n### Tags\n\ntest gatest ga\n\n### Amplification\n\nhehehehe\n\n### Exception(s)\n\n_No response_\n\n### Rationale\n\ntest ga\n\n### Non-Compliant Example - Prose\n\ntest ga\n\n### Non-Compliant Example - Code\n\ntest ga\n\n### Compliant Example - Prose\n\ntest ga\n\n### Compliant Example - Code\n\ntest ga",
107+
"body": "### Chapter\n\nConcurrency\n\n### Guideline Title\n\ntest ga\n\n### Category\n\nAdvisory\n\n### Status\n\nDraft\n\n### Release Begin\n\n1.1.1\n\n### Release End\n\n1.1.1\n\n### FLS Paragraph ID\n\nfls_fsdjkfslkdfj\n\n### Decidability\n\nDecidable\n\n### Scope\n\nCrate\n\n### Tags\n\ntest gatest ga\n\n### Amplification\n\nhehehehe\n\n### Exception(s)\n\n_No response_\n\n### Rationale\n\ntest ga\n\n### Non-Compliant Example - Prose\n\ntest ga\n\n### Non-Compliant Example - Code\n\ndfhsdfkjshdfskdjhftest ga\n\n### Compliant Example - Prose\n\ntest ga\n\n### Compliant Example - Code\n\ntest ga",
108108
"closed_by": null,
109109
"reactions": {
110110
"url": "https://api.github.com/repos/x0rw/safety-critical-rust-coding-guidelines/issues/4/reactions",
Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
=====CONTENT=====
2+
.. guideline:: test ga
3+
:id: gui_FWr4O8NFxpgr
4+
:category: advisory
5+
:status: draft
6+
:release: 1.1.1-1.1.1
7+
:fls: fls_fsdjkfslkdfj
8+
:decidability: decidable
9+
:scope: crate
10+
:tags: test,gatest,ga
11+
12+
hehehehe
13+
14+
.. rationale::
15+
:id: rat_y8xxrKQIfr7y
16+
:status: draft
17+
18+
test ga
19+
20+
.. non_compliant_example::
21+
:id: non_compl_ex_4cQT1M3psxLs
22+
:status: draft
23+
24+
test ga
25+
26+
.. code-block:: rust
27+
28+
dfhsdfkjshdfskdjhftest ga
29+
30+
.. compliant_example::
31+
:id: compl_ex_zrLFcPlviRu5
32+
:status: draft
33+
34+
test ga
35+
36+
.. code-block:: rust
37+
38+
test ga
39+
40+
=====CONTENT=END=====
41+
Saved guideline to src/coding-guidelines/concurrency.rst
Lines changed: 124 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,124 @@
1+
{
2+
"url": "https://api.github.com/repos/x0rw/safety-critical-rust-coding-guidelines/issues/4",
3+
"repository_url": "https://api.github.com/repos/x0rw/safety-critical-rust-coding-guidelines",
4+
"labels_url": "https://api.github.com/repos/x0rw/safety-critical-rust-coding-guidelines/issues/4/labels{/name}",
5+
"comments_url": "https://api.github.com/repos/x0rw/safety-critical-rust-coding-guidelines/issues/4/comments",
6+
"events_url": "https://api.github.com/repos/x0rw/safety-critical-rust-coding-guidelines/issues/4/events",
7+
"html_url": "https://github.com/x0rw/safety-critical-rust-coding-guidelines/issues/4",
8+
"id": 3104390263,
9+
"node_id": "I_kwDOOMMjbs65CTx3",
10+
"number": 4,
11+
"title": "[Coding Guideline]: testtt",
12+
"user": {
13+
"login": "x0rw",
14+
"id": 14003018,
15+
"node_id": "MDQ6VXNlcjE0MDAzMDE4",
16+
"avatar_url": "https://avatars.githubusercontent.com/u/14003018?v=4",
17+
"gravatar_id": "",
18+
"url": "https://api.github.com/users/x0rw",
19+
"html_url": "https://github.com/x0rw",
20+
"followers_url": "https://api.github.com/users/x0rw/followers",
21+
"following_url": "https://api.github.com/users/x0rw/following{/other_user}",
22+
"gists_url": "https://api.github.com/users/x0rw/gists{/gist_id}",
23+
"starred_url": "https://api.github.com/users/x0rw/starred{/owner}{/repo}",
24+
"subscriptions_url": "https://api.github.com/users/x0rw/subscriptions",
25+
"organizations_url": "https://api.github.com/users/x0rw/orgs",
26+
"repos_url": "https://api.github.com/users/x0rw/repos",
27+
"events_url": "https://api.github.com/users/x0rw/events{/privacy}",
28+
"received_events_url": "https://api.github.com/users/x0rw/received_events",
29+
"type": "User",
30+
"user_view_type": "public",
31+
"site_admin": false
32+
},
33+
"labels": [
34+
{
35+
"id": 8703664686,
36+
"node_id": "LA_kwDOOMMjbs8AAAACBsdiLg",
37+
"url": "https://api.github.com/repos/x0rw/safety-critical-rust-coding-guidelines/labels/category:%20advisory",
38+
"name": "category: advisory",
39+
"color": "ededed",
40+
"default": false,
41+
"description": null
42+
},
43+
{
44+
"id": 8703664688,
45+
"node_id": "LA_kwDOOMMjbs8AAAACBsdiMA",
46+
"url": "https://api.github.com/repos/x0rw/safety-critical-rust-coding-guidelines/labels/status:%20draft",
47+
"name": "status: draft",
48+
"color": "ededed",
49+
"default": false,
50+
"description": null
51+
},
52+
{
53+
"id": 8703664689,
54+
"node_id": "LA_kwDOOMMjbs8AAAACBsdiMQ",
55+
"url": "https://api.github.com/repos/x0rw/safety-critical-rust-coding-guidelines/labels/decidability:%20decidable",
56+
"name": "decidability: decidable",
57+
"color": "ededed",
58+
"default": false,
59+
"description": null
60+
},
61+
{
62+
"id": 8703686409,
63+
"node_id": "LA_kwDOOMMjbs8AAAACBse3CQ",
64+
"url": "https://api.github.com/repos/x0rw/safety-critical-rust-coding-guidelines/labels/chapter:%20concurrency",
65+
"name": "chapter: concurrency",
66+
"color": "ededed",
67+
"default": false,
68+
"description": null
69+
},
70+
{
71+
"id": 8703686412,
72+
"node_id": "LA_kwDOOMMjbs8AAAACBse3DA",
73+
"url": "https://api.github.com/repos/x0rw/safety-critical-rust-coding-guidelines/labels/scope:%20crate",
74+
"name": "scope: crate",
75+
"color": "ededed",
76+
"default": false,
77+
"description": null
78+
},
79+
{
80+
"id": 8703732885,
81+
"node_id": "LA_kwDOOMMjbs8AAAACBshslQ",
82+
"url": "https://api.github.com/repos/x0rw/safety-critical-rust-coding-guidelines/labels/accepted",
83+
"name": "accepted",
84+
"color": "6AABE8",
85+
"default": false,
86+
"description": ""
87+
}
88+
],
89+
"state": "open",
90+
"locked": false,
91+
"assignee": null,
92+
"assignees": [
93+
94+
],
95+
"milestone": null,
96+
"comments": 0,
97+
"created_at": "2025-05-30T22:24:07Z",
98+
"updated_at": "2025-05-30T22:48:17Z",
99+
"closed_at": null,
100+
"author_association": "OWNER",
101+
"active_lock_reason": null,
102+
"sub_issues_summary": {
103+
"total": 0,
104+
"completed": 0,
105+
"percent_completed": 0
106+
},
107+
"body": "### Chapter\n\nConcurrency\n\n### Guideline Title\n\ntest 2\n\n### Category\n\nAdvisory\n\n### Status\n\nDraft\n\n### Release Begin\n\n1.1.1\n\n### Release End\n\n1.1.1\n\n### FLS Paragraph ID\n\nfls_fsdjkfslkdfj\n\n### Decidability\n\nDecidable\n\n### Scope\n\nCrate\n\n### Tags\n\ntest gatest ga\n\n### Amplification\n\nhehehehe\n\n### Exception(s)\n\n_No response_\n\n### Rationale\n\ntest ga\n\n### Non-Compliant Example - Prose\n\ntest ga\n\n### Non-Compliant Example - Code\n\ndfhsdfkjshdfskdjhftest ga\n\n### Compliant Example - Prose\n\ntest ga\n\n### Compliant Example - Code\n\ntest ga",
108+
"closed_by": null,
109+
"reactions": {
110+
"url": "https://api.github.com/repos/x0rw/safety-critical-rust-coding-guidelines/issues/4/reactions",
111+
"total_count": 0,
112+
"+1": 0,
113+
"-1": 0,
114+
"laugh": 0,
115+
"hooray": 0,
116+
"confused": 0,
117+
"heart": 0,
118+
"rocket": 0,
119+
"eyes": 0
120+
},
121+
"timeline_url": "https://api.github.com/repos/x0rw/safety-critical-rust-coding-guidelines/issues/4/timeline",
122+
"performed_via_github_app": null,
123+
"state_reason": null
124+
}
Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
=====CONTENT=====
2+
.. guideline:: test 2
3+
:id: gui_10X7r6yledzw
4+
:category: advisory
5+
:status: draft
6+
:release: 1.1.1-1.1.1
7+
:fls: fls_fsdjkfslkdfj
8+
:decidability: decidable
9+
:scope: crate
10+
:tags: test,gatest,ga
11+
12+
hehehehe
13+
14+
.. rationale::
15+
:id: rat_Qpq2pZlovd7Z
16+
:status: draft
17+
18+
test ga
19+
20+
.. non_compliant_example::
21+
:id: non_compl_ex_qSOda5w4rWt4
22+
:status: draft
23+
24+
test ga
25+
26+
.. code-block:: rust
27+
28+
dfhsdfkjshdfskdjhftest ga
29+
30+
.. compliant_example::
31+
:id: compl_ex_qwzzxQs8JO27
32+
:status: draft
33+
34+
test ga
35+
36+
.. code-block:: rust
37+
38+
test ga
39+
40+
=====CONTENT=END=====
41+
Saved guideline to src/coding-guidelines/concurrency.rst

.github/auto-pr-tests/test_runner.py

Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,62 @@
1+
import subprocess
2+
import re
3+
from pathlib import Path
4+
import difflib
5+
6+
def normalize_ids(text: str) -> str:
7+
return re.sub(r'(:id:\s+[a-z_]+)_[a-zA-Z0-9]+', r'\1_IGNORED_ID', text)
8+
9+
def compare(issue_json_path: Path, snapshot_path: Path) -> bool:
10+
input_json = issue_json_path.read_text()
11+
12+
result = subprocess.run(
13+
["uv", "run", "python", "scripts/auto-pr-helper.py"],
14+
input=input_json.encode(),
15+
stdout=subprocess.PIPE,
16+
stderr=subprocess.DEVNULL,
17+
check=True
18+
)
19+
20+
# Normalize the actual output and the snapshot, this is crucial in snapshot tests to
21+
# ignore random/volatile values.
22+
actual_output = normalize_ids(result.stdout.decode())
23+
expected_output = normalize_ids(snapshot_path.read_text())
24+
25+
# Compare
26+
if actual_output != expected_output:
27+
diff = difflib.unified_diff(
28+
expected_output.splitlines(),
29+
actual_output.splitlines(),
30+
fromfile=str(snapshot_path),
31+
tofile="generated",
32+
lineterm=""
33+
)
34+
print(f"Difference found in {issue_json_path.name}:")
35+
print("\n".join(diff))
36+
return False
37+
else:
38+
print(f"{issue_json_path.name} matches snapshot.")
39+
return True
40+
41+
# to generate snapshot i use this command:
42+
# create or change the test_issue_xx file
43+
## `cat .github/auto-pr-tests/test_issue_XX.json | python3 scripts/auto-pr-helper.py 2&>/dev/null > .github/auto-pr-tests/test_issue_0XX.snapshot`
44+
tests = {
45+
"test_01": (
46+
Path(".github/auto-pr-tests/test_issue_01.json"),
47+
Path(".github/auto-pr-tests/test_issue_01.snapshot")
48+
),
49+
"test_02": (
50+
Path(".github/auto-pr-tests/test_issue_02.json"),
51+
Path(".github/auto-pr-tests/test_issue_02.snapshot")
52+
),
53+
}
54+
55+
# Run all tests
56+
all_passed = True
57+
for name, (issue_json, snapshot) in tests.items():
58+
if not compare(issue_json, snapshot):
59+
all_passed = False
60+
61+
if not all_passed:
62+
exit(1)

.github/workflows/auto-pr-on-issue.yml

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ on:
77

88
jobs:
99
auto-pr:
10-
if: "github.event.label.name == 'status: approved'"
10+
if: "github.event.label.name == 'sign-off: create pr from issue'"
1111
runs-on: ubuntu-latest
1212
permissions:
1313
contents: write
@@ -24,12 +24,12 @@ jobs:
2424
2525
# - name: Save issue JSON payload to file
2626
# run: echo '${{ toJson(github.event.issue) }}' > issue.json
27-
# pass it directly -- mayne fallback to this if an issue happened due to
27+
# pass it directly -- maybe fallback to this if an issue happened due to
2828
# pipe-ing or encoding
2929

3030
- name: Run Python script to generate guideline file
3131
run: |
32-
echo '${{ toJson(github.event.issue) }}' | python3 scripts/auto-pr-helper.py
32+
echo '${{ toJson(github.event.issue) }}' | uv run python scripts/auto-pr-helper.py
3333
3434
- name: Commit generated guideline files
3535
run: |

0 commit comments

Comments
 (0)