Skip to content

Commit a10a942

Browse files
security: harden mirror workflow with SSH host verification (#1)
- Add SSH known_hosts verification for GitLab, Codeberg, and Bitbucket to prevent MITM attacks during mirror operations - Add 10-minute job timeout to prevent indefinite hangs - Add concurrency control to prevent race conditions on parallel pushes - Use env vars for repository name with proper quoting for shell safety Co-authored-by: Claude <noreply@anthropic.com>
1 parent 84f9429 commit a10a942

1 file changed

Lines changed: 29 additions & 3 deletions

File tree

.github/workflows/mirror.yml

Lines changed: 29 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -8,9 +8,15 @@ on:
88

99
permissions: read-all
1010

11+
# Prevent concurrent mirror operations to avoid race conditions
12+
concurrency:
13+
group: mirror-${{ github.ref }}
14+
cancel-in-progress: false
15+
1116
jobs:
1217
mirror-gitlab:
1318
runs-on: ubuntu-latest
19+
timeout-minutes: 10
1420
if: vars.GITLAB_MIRROR_ENABLED == 'true'
1521
steps:
1622
- uses: actions/checkout@b4ffde65f46336ab88eb53be808477a3936bae11 # v4
@@ -19,14 +25,21 @@ jobs:
1925
- uses: webfactory/ssh-agent@dc588b651fe13675774614f8e6a936a468676387 # v0.9.0
2026
with:
2127
ssh-private-key: ${{ secrets.GITLAB_SSH_KEY }}
28+
- name: Add GitLab SSH host key
29+
run: |
30+
mkdir -p ~/.ssh
31+
ssh-keyscan -t ed25519,rsa gitlab.com >> ~/.ssh/known_hosts 2>/dev/null
2232
- name: Mirror to GitLab
33+
env:
34+
REPO_NAME: ${{ github.event.repository.name }}
2335
run: |
24-
git remote add gitlab git@gitlab.com:hyperpolymath/${GITHUB_REPOSITORY#*/}.git || true
36+
git remote add gitlab "git@gitlab.com:hyperpolymath/${REPO_NAME}.git" || true
2537
git push gitlab --all --force
2638
git push gitlab --tags --force
2739
2840
mirror-codeberg:
2941
runs-on: ubuntu-latest
42+
timeout-minutes: 10
3043
if: vars.CODEBERG_MIRROR_ENABLED == 'true'
3144
steps:
3245
- uses: actions/checkout@b4ffde65f46336ab88eb53be808477a3936bae11 # v4
@@ -35,14 +48,21 @@ jobs:
3548
- uses: webfactory/ssh-agent@dc588b651fe13675774614f8e6a936a468676387 # v0.9.0
3649
with:
3750
ssh-private-key: ${{ secrets.CODEBERG_SSH_KEY }}
51+
- name: Add Codeberg SSH host key
52+
run: |
53+
mkdir -p ~/.ssh
54+
ssh-keyscan -t ed25519,rsa codeberg.org >> ~/.ssh/known_hosts 2>/dev/null
3855
- name: Mirror to Codeberg
56+
env:
57+
REPO_NAME: ${{ github.event.repository.name }}
3958
run: |
40-
git remote add codeberg git@codeberg.org:hyperpolymath/${GITHUB_REPOSITORY#*/}.git || true
59+
git remote add codeberg "git@codeberg.org:hyperpolymath/${REPO_NAME}.git" || true
4160
git push codeberg --all --force
4261
git push codeberg --tags --force
4362
4463
mirror-bitbucket:
4564
runs-on: ubuntu-latest
65+
timeout-minutes: 10
4666
if: vars.BITBUCKET_MIRROR_ENABLED == 'true'
4767
steps:
4868
- uses: actions/checkout@b4ffde65f46336ab88eb53be808477a3936bae11 # v4
@@ -51,8 +71,14 @@ jobs:
5171
- uses: webfactory/ssh-agent@dc588b651fe13675774614f8e6a936a468676387 # v0.9.0
5272
with:
5373
ssh-private-key: ${{ secrets.BITBUCKET_SSH_KEY }}
74+
- name: Add Bitbucket SSH host key
75+
run: |
76+
mkdir -p ~/.ssh
77+
ssh-keyscan -t ed25519,rsa bitbucket.org >> ~/.ssh/known_hosts 2>/dev/null
5478
- name: Mirror to Bitbucket
79+
env:
80+
REPO_NAME: ${{ github.event.repository.name }}
5581
run: |
56-
git remote add bitbucket git@bitbucket.org:hyperpolymath/${GITHUB_REPOSITORY#*/}.git || true
82+
git remote add bitbucket "git@bitbucket.org:hyperpolymath/${REPO_NAME}.git" || true
5783
git push bitbucket --all --force
5884
git push bitbucket --tags --force

0 commit comments

Comments
 (0)