Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 5 additions & 3 deletions .github/workflows/build.yml
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,9 @@ jobs:
10.0.*

- name: Git checkout
uses: actions/checkout@v4
uses: actions/checkout@v6
with:
persist-credentials: false

- name: Restore packages
run: dotnet restore --verbosity minimal
Expand Down Expand Up @@ -204,7 +206,7 @@ jobs:
path: packages

- name: Setup .NET
uses: actions/setup-dotnet@v4
uses: actions/setup-dotnet@v5
with:
dotnet-version: 10.0.x
source-url: ${{ vars.AZURE_ARTIFACTS_FEED_URL }}
Expand Down Expand Up @@ -235,7 +237,7 @@ jobs:

steps:
- name: Setup .NET
uses: actions/setup-dotnet@v4
uses: actions/setup-dotnet@v5
with:
dotnet-version: 10.0.x

Expand Down
126 changes: 126 additions & 0 deletions .github/workflows/keep-alive.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,126 @@
# Prevents scheduled workflows from being disabled by GitHub after 60 days of repository inactivity.
name: Keep Scheduled Workflows Alive

on:
schedule:
- cron: "0 0 1 * *"
workflow_dispatch:

permissions:
contents: write
pull-requests: write
issues: read

jobs:
keep-alive:
name: Keep repository GitHub Actions active
runs-on: ubuntu-latest
timeout-minutes: 5

steps:
- name: Git checkout
uses: actions/checkout@v6
with:
persist-credentials: false

- name: Check for recent activity
id: check_activity
env:
GH_TOKEN: ${{ github.token }}
shell: bash
run: |
default_branch="${{ github.event.repository.default_branch }}"
if [ -z "$default_branch" ]; then
default_branch="main"
fi

echo "Checking activity on branch: $default_branch"
last_commit_date=$(gh api "repos/${{ github.repository }}/commits/$default_branch" --jq '.commit.committer.date')
echo "Last commit date: $last_commit_date"

last_commit_seconds=$(date -d "$last_commit_date" +%s)
current_seconds=$(date +%s)
days_diff=$(( (current_seconds - last_commit_seconds) / 86400 ))
echo "Days since last activity: $days_diff"

if [ "$days_diff" -lt 30 ]; then
echo "Active (< 30 days). No keep-alive needed."
echo "run_keep_alive=false" >> $GITHUB_OUTPUT
else
echo "Inactive ($days_diff days). Running keep-alive."
echo "run_keep_alive=true" >> $GITHUB_OUTPUT
fi

- name: Ensure keep-alive branch and PR exist
if: ${{ steps.check_activity.outputs.run_keep_alive == 'true' }}
env:
GH_TOKEN: ${{ github.token }}
COMMIT_MSG: |
chore: keep scheduled workflows alive
PR_BODY: |
Draft PR maintained by the keep-alive workflow. Do not merge or delete.
shell: bash
run: |
branch_name="keep-alive-workflow"
default_branch="${{ github.event.repository.default_branch }}"
if [ -z "$default_branch" ]; then
default_branch="main"
fi

git config --local user.name "github-actions[bot]"
git config --local user.email "github-actions[bot]@users.noreply.github.com"

if git ls-remote --heads origin "$branch_name" | grep -q "$branch_name"; then
echo "Branch exists"
git fetch origin "$branch_name"
git checkout "$branch_name"
git pull origin "$branch_name"
else
echo "Creating branch"
git checkout -b "$branch_name"
fi

git commit --allow-empty -m "$COMMIT_MSG"
git push origin "$branch_name"

pr_number=$(gh pr list --head "$branch_name" --state all --json number --jq '.[0].number' 2>/dev/null || echo "")

if [ -z "$pr_number" ]; then
echo "Creating draft PR"
gh pr create --draft --head "$branch_name" --base "$default_branch" \
--title "chore: keep scheduled workflows alive" --body "$PR_BODY"

pr_number=$(gh pr list --head "$branch_name" --state all --json number --jq '.[0].number')
echo "Created PR #$pr_number"
else
echo "PR #$pr_number exists"
fi

echo "pr_number=$pr_number" >> $GITHUB_OUTPUT
id: setup

- name: Reopen and close PR to maintain activity
if: ${{ steps.check_activity.outputs.run_keep_alive == 'true' }}
env:
GH_TOKEN: ${{ github.token }}
shell: bash
run: |
pr_number="${{ steps.setup.outputs.pr_number }}"

if [ -z "$pr_number" ]; then
echo "Error: PR number not found"
exit 1
fi

pr_state=$(gh pr view "$pr_number" --json state --jq '.state')
echo "PR #$pr_number is $pr_state"

if [[ "$pr_state" == "CLOSED" ]]; then
echo "Reopening PR #$pr_number"
gh pr reopen "$pr_number"
fi

echo "Closing PR #$pr_number"
gh pr close "$pr_number" --comment "Keep-alive: $(date -u '+%Y-%m-%d %H:%M:%S UTC')"

echo "Keep-alive completed"