Skip to content

Commit 0c074c5

Browse files
Phlogistiqueclaude
andauthored
Simplify setup code for user repositories (#20)
* Simplify user setup by moving checkout and mode detection into action - Action now handles checkout with fetch-depth: 0 internally - Auto-detects mode (squash-merge vs conflict-resolved) from event context - Removes need for users to specify mode or pr-branch inputs - Simplifies workflow to just trigger + single action call - E2e tests now copy workflow from repo and sed the action reference - E2e tests verify repo is clean and commit exists on origin before running * Fix e2e tests to use remote action at current SHA instead of local copy * Fix e2e test job detection and bash glob pattern for label matching * Skip checkout when no action needed to avoid wasteful git operations --------- Co-authored-by: Claude <noreply@anthropic.com>
1 parent 5af8925 commit 0c074c5

3 files changed

Lines changed: 74 additions & 100 deletions

File tree

.github/workflows/update-pr-stack.yml

Lines changed: 1 addition & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -7,35 +7,11 @@ on:
77
permissions:
88
contents: write
99
pull-requests: write
10-
repository-projects: read # See https://github.com/cli/cli/discussions/5307
1110

1211
jobs:
1312
update-pr-stack:
14-
if: github.event.action == 'closed' && github.event.pull_request.merged == true && github.event.pull_request.merge_commit_sha != ''
1513
runs-on: ubuntu-latest
1614
steps:
17-
- name: Checkout repository
18-
uses: actions/checkout@v3
19-
with:
20-
fetch-depth: 0
21-
22-
- name: Update PR stack
23-
uses: ./
24-
with:
25-
github-token: ${{ secrets.GITHUB_TOKEN }}
26-
27-
continue-after-conflict-resolution:
28-
if: github.event.action == 'synchronize' && contains(github.event.pull_request.labels.*.name, 'autorestack-needs-conflict-resolution')
29-
runs-on: ubuntu-latest
30-
steps:
31-
- name: Checkout repository
32-
uses: actions/checkout@v3
33-
with:
34-
fetch-depth: 0
35-
36-
- name: Continue PR stack update after conflict resolution
37-
uses: ./
15+
- uses: Phlogistique/autorestack-action@main
3816
with:
3917
github-token: ${{ secrets.GITHUB_TOKEN }}
40-
mode: conflict-resolved
41-
pr-branch: ${{ github.event.pull_request.head.ref }}

action.yml

Lines changed: 31 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -7,32 +7,52 @@ inputs:
77
description: 'GitHub token for API access'
88
required: true
99
default: ${{ github.token }}
10-
mode:
11-
description: 'Action mode: squash-merge (after PR merge) or conflict-resolved (after manual resolution)'
12-
required: false
13-
default: 'squash-merge'
14-
pr-branch:
15-
description: 'The PR branch that was pushed (required for conflict-resolved mode)'
16-
required: false
17-
default: ''
1810

1911
runs:
2012
using: 'composite'
2113
steps:
14+
- name: Check if action should run
15+
id: check
16+
shell: bash
17+
env:
18+
EVENT_ACTION: ${{ github.event.action }}
19+
PR_LABELS: ${{ join(github.event.pull_request.labels.*.name, ',') }}
20+
PR_MERGED: ${{ github.event.pull_request.merged }}
21+
MERGE_COMMIT_SHA: ${{ github.event.pull_request.merge_commit_sha }}
22+
run: |
23+
if [[ "$EVENT_ACTION" == "closed" && "$PR_MERGED" == "true" && -n "$MERGE_COMMIT_SHA" ]]; then
24+
echo "mode=squash-merge" >> $GITHUB_OUTPUT
25+
elif [[ "$EVENT_ACTION" == "synchronize" && "$PR_LABELS" == *autorestack-needs-conflict-resolution* ]]; then
26+
echo "mode=conflict-resolved" >> $GITHUB_OUTPUT
27+
else
28+
echo "Event does not match any action trigger (action=$EVENT_ACTION, merged=$PR_MERGED, labels=$PR_LABELS)"
29+
echo "mode=skip" >> $GITHUB_OUTPUT
30+
fi
31+
32+
- name: Checkout repository
33+
if: steps.check.outputs.mode != 'skip'
34+
uses: actions/checkout@v4
35+
with:
36+
fetch-depth: 0
37+
token: ${{ inputs.github-token }}
38+
2239
- name: Update PR stack
40+
if: steps.check.outputs.mode != 'skip'
2341
shell: bash
2442
env:
2543
GITHUB_TOKEN: ${{ inputs.github-token }}
2644
GIT_AUTHOR_NAME: github-actions
2745
GIT_AUTHOR_EMAIL: github-actions@github.com
2846
GIT_COMMITTER_NAME: github-actions
2947
GIT_COMMITTER_EMAIL: github-actions@github.com
30-
ACTION_MODE: ${{ inputs.mode }}
48+
ACTION_MODE: ${{ steps.check.outputs.mode }}
3149
SQUASH_COMMIT: ${{ github.event.pull_request.merge_commit_sha }}
3250
MERGED_BRANCH: ${{ github.event.pull_request.head.ref }}
3351
TARGET_BRANCH: ${{ github.event.pull_request.base.ref }}
34-
PR_BRANCH: ${{ inputs.pr-branch }}
35-
run: ${{ github.action_path }}/update-pr-stack.sh
52+
PR_BRANCH: ${{ github.event.pull_request.head.ref }}
53+
run: |
54+
echo "Running in $ACTION_MODE mode"
55+
${{ github.action_path }}/update-pr-stack.sh
3656
3757
branding:
3858
icon: 'git-pull-request'

tests/test_e2e.sh

Lines changed: 42 additions & 64 deletions
Original file line numberDiff line numberDiff line change
@@ -210,16 +210,14 @@ wait_for_synchronize_workflow() {
210210
echo >&2 "Found candidate run IDs: $candidate_run_ids. Checking runs..."
211211
for run_id in $candidate_run_ids; do
212212
echo >&2 "Checking candidate run ID: $run_id"
213-
run_info=$(log_cmd gh run view "$run_id" --repo "$REPO_FULL_NAME" --json headBranch,jobs || echo "{}")
213+
run_info=$(log_cmd gh run view "$run_id" --repo "$REPO_FULL_NAME" --json headBranch || echo "{}")
214214

215215
run_head_branch=$(echo "$run_info" | jq -r '.headBranch // ""')
216-
# Check if this run has the continue-after-conflict-resolution job
217-
has_continue_job=$(echo "$run_info" | jq -r '.jobs[] | select(.name == "continue-after-conflict-resolution") | .name' || echo "")
218216

219-
echo >&2 " Run head branch: $run_head_branch, has continue job: $has_continue_job"
217+
echo >&2 " Run head branch: $run_head_branch"
220218

221-
if [[ "$run_head_branch" == "$branch_name" && -n "$has_continue_job" ]]; then
222-
echo >&2 "Found matching workflow run ID: $run_id (synchronize with continue job)"
219+
if [[ "$run_head_branch" == "$branch_name" ]]; then
220+
echo >&2 "Found matching workflow run ID: $run_id (branch matches)"
223221
target_run_id="$run_id"
224222
break
225223
fi
@@ -372,6 +370,34 @@ wait_for_workflow() {
372370
# --- Test Execution ---
373371
echo >&2 "--- Starting E2E Test ---"
374372

373+
# 0. Sanity checks - ensure we're testing committed code
374+
echo >&2 "0. Running sanity checks..."
375+
376+
# Check that the working directory is clean
377+
if ! git -C "$PROJECT_ROOT" diff --quiet HEAD 2>/dev/null; then
378+
echo >&2 "ERROR: Repository has uncommitted changes."
379+
echo >&2 "Please commit your changes before running e2e tests."
380+
echo >&2 "This ensures we test exactly what will be deployed."
381+
git -C "$PROJECT_ROOT" status --short >&2
382+
exit 1
383+
fi
384+
385+
# Get the current commit SHA from the action repo
386+
ACTION_REPO_COMMIT=$(git -C "$PROJECT_ROOT" rev-parse HEAD)
387+
echo >&2 "Testing commit: $ACTION_REPO_COMMIT"
388+
389+
# Check that the current commit exists on origin
390+
if ! git -C "$PROJECT_ROOT" fetch origin --quiet 2>/dev/null; then
391+
echo >&2 "WARNING: Could not fetch from origin, skipping remote check"
392+
elif ! git -C "$PROJECT_ROOT" branch -r --contains "$ACTION_REPO_COMMIT" 2>/dev/null | grep -q .; then
393+
echo >&2 "ERROR: Current commit $ACTION_REPO_COMMIT does not exist on origin."
394+
echo >&2 "Please push your changes before running e2e tests."
395+
echo >&2 "This ensures the workflow can reference the action at this commit."
396+
exit 1
397+
fi
398+
399+
echo >&2 "✅ Sanity checks passed"
400+
375401
# 1. Setup local repository
376402
echo >&2 "1. Setting up local test repository..."
377403
TEST_DIR=$(mktemp -d)
@@ -394,65 +420,17 @@ log_cmd git add file.txt
394420
log_cmd git commit -m "Initial commit"
395421
INITIAL_COMMIT_SHA=$(git rev-parse HEAD)
396422

397-
# Copy action files
398-
echo >&2 "Copying action files..."
399-
cp "$PROJECT_ROOT/action.yml" .
400-
cp "$PROJECT_ROOT/update-pr-stack.sh" .
401-
cp "$PROJECT_ROOT/command_utils.sh" .
402-
403-
# Create workflow file pointing to the local action
404-
echo >&2 "Creating workflow file..."
423+
# Copy workflow file from the repo and modify it to use the current commit SHA
424+
# This tests the actual deployed action, not a local copy
425+
echo >&2 "Copying workflow file from repo..."
405426
mkdir -p .github/workflows
406-
cat > .github/workflows/"$WORKFLOW_FILE" <<EOF
407-
name: Update Stacked PRs on Squash Merge (E2E Test)
408-
on:
409-
pull_request:
410-
types: [closed, synchronize]
411-
permissions:
412-
contents: write
413-
pull-requests: write
414-
jobs:
415-
update-pr-stack:
416-
# Only run on actual squash merges initiated by the test script
417-
if: |
418-
github.event.action == 'closed' &&
419-
github.event.pull_request.merged == true &&
420-
github.event.pull_request.merge_commit_sha != ''
421-
runs-on: ubuntu-latest
422-
steps:
423-
- name: Checkout repository
424-
uses: actions/checkout@v4
425-
with:
426-
# Fetch all history for all branches and tags
427-
fetch-depth: 0
428-
# Use a PAT token for checkout to allow pushing updates
429-
token: \${{ secrets.GITHUB_TOKEN }}
430-
- name: Update PR stack
431-
# Use the action from the current repository checkout
432-
uses: ./
433-
with:
434-
github-token: \${{ secrets.GITHUB_TOKEN }}
435-
continue-after-conflict-resolution:
436-
# Run when a PR with the conflict label is updated (user pushed conflict resolution)
437-
if: |
438-
github.event.action == 'synchronize' &&
439-
contains(github.event.pull_request.labels.*.name, 'autorestack-needs-conflict-resolution')
440-
runs-on: ubuntu-latest
441-
steps:
442-
- name: Checkout repository
443-
uses: actions/checkout@v4
444-
with:
445-
fetch-depth: 0
446-
token: \${{ secrets.GITHUB_TOKEN }}
447-
- name: Continue PR stack update after conflict resolution
448-
uses: ./
449-
with:
450-
github-token: \${{ secrets.GITHUB_TOKEN }}
451-
mode: conflict-resolved
452-
pr-branch: \${{ github.event.pull_request.head.ref }}
453-
EOF
454-
455-
log_cmd git add action.yml update-pr-stack.sh command_utils.sh .github/workflows/"$WORKFLOW_FILE"
427+
cp "$PROJECT_ROOT/.github/workflows/$WORKFLOW_FILE" .github/workflows/
428+
429+
# Replace @main with the current commit SHA to test exactly what we pushed
430+
sed -i "s|uses: Phlogistique/autorestack-action@main|uses: Phlogistique/autorestack-action@$ACTION_REPO_COMMIT|g" .github/workflows/"$WORKFLOW_FILE"
431+
echo >&2 "Modified workflow to use action at commit $ACTION_REPO_COMMIT"
432+
433+
log_cmd git add .github/workflows/"$WORKFLOW_FILE"
456434
log_cmd git commit -m "Add action and workflow files"
457435
ACTION_COMMIT_SHA=$(git rev-parse HEAD)
458436

0 commit comments

Comments
 (0)