|
| 1 | +# GitHub App Setup for Semantic Release |
| 2 | + |
| 3 | +This guide walks through creating a GitHub App to enable semantic-release to bypass branch protection rules securely. |
| 4 | + |
| 5 | +## Why Use a GitHub App? |
| 6 | + |
| 7 | +- ✅ Most secure authentication method (scoped permissions, short-lived tokens) |
| 8 | +- ✅ Can bypass repository rulesets when added to bypass list |
| 9 | +- ✅ Triggers downstream workflows (unlike GITHUB_TOKEN) |
| 10 | +- ✅ Auditable in GitHub's audit log |
| 11 | +- ✅ Recommended by GitHub as of 2025 |
| 12 | + |
| 13 | +## Step 1: Create the GitHub App |
| 14 | + |
| 15 | +1. **Navigate to GitHub App Settings** |
| 16 | + - Go to <https://github.com/settings/apps> |
| 17 | + - Click **"New GitHub App"** |
| 18 | + |
| 19 | +2. **Configure Basic Information** |
| 20 | + - **GitHub App name**: `peakbagger-release-bot` (or any unique name) |
| 21 | + - **Description**: `Automated release bot for peakbagger-cli using semantic-release` |
| 22 | + - **Homepage URL**: `https://github.com/dreamiurg/peakbagger-cli` |
| 23 | + - **Webhook**: Uncheck **"Active"** (we don't need webhooks) |
| 24 | + |
| 25 | +3. **Set Repository Permissions** |
| 26 | + |
| 27 | + Under "Repository permissions", set these permissions: |
| 28 | + |
| 29 | + | Permission | Access Level | Purpose | |
| 30 | + |------------|-------------|---------| |
| 31 | + | **Contents** | Read and write | Push commits, create tags | |
| 32 | + | **Issues** | Read and write | Comment on issues in releases | |
| 33 | + | **Pull requests** | Read and write | Comment on PRs in releases | |
| 34 | + | **Metadata** | Read-only | Required (auto-selected) | |
| 35 | + |
| 36 | +4. **Configure Installation** |
| 37 | + - Under "Where can this GitHub App be installed?" |
| 38 | + - Select: **"Only on this account"** |
| 39 | + |
| 40 | +5. **Create the App** |
| 41 | + - Click **"Create GitHub App"** |
| 42 | + - You'll be redirected to the app's settings page |
| 43 | + |
| 44 | +## Step 2: Generate Private Key |
| 45 | + |
| 46 | +1. On your app's settings page, scroll to **"Private keys"** |
| 47 | +2. Click **"Generate a private key"** |
| 48 | +3. A `.pem` file will download automatically |
| 49 | +4. **IMPORTANT**: Save this file securely - you'll need it in Step 4 |
| 50 | + |
| 51 | +## Step 3: Note the App ID |
| 52 | + |
| 53 | +1. At the top of the app settings page, find **"App ID"** |
| 54 | +2. Copy this number (e.g., `123456`) |
| 55 | +3. Save it for Step 4 |
| 56 | + |
| 57 | +## Step 4: Install the App on Your Repository |
| 58 | + |
| 59 | +1. On your app's settings page, click **"Install App"** in the left sidebar |
| 60 | +2. Click **"Install"** next to your username/organization |
| 61 | +3. Select: **"Only select repositories"** |
| 62 | +4. Choose: `peakbagger-cli` |
| 63 | +5. Click **"Install"** |
| 64 | + |
| 65 | +## Step 5: Add Repository Secrets |
| 66 | + |
| 67 | +1. **Go to repository secrets** |
| 68 | + - Navigate to <https://github.com/dreamiurg/peakbagger-cli/settings/secrets/actions> |
| 69 | + - Click **"New repository secret"** |
| 70 | + |
| 71 | +2. **Add App ID** |
| 72 | + - Name: `RELEASE_APP_ID` |
| 73 | + - Value: The App ID from Step 3 (e.g., `123456`) |
| 74 | + - Click **"Add secret"** |
| 75 | + |
| 76 | +3. **Add Private Key** |
| 77 | + - Click **"New repository secret"** again |
| 78 | + - Name: `RELEASE_APP_PRIVATE_KEY` |
| 79 | + - Value: Open the `.pem` file from Step 2 and paste the **entire contents** including: |
| 80 | + |
| 81 | + ```text |
| 82 | + -----BEGIN RSA PRIVATE KEY----- |
| 83 | + ... (your key content) ... |
| 84 | + -----END RSA PRIVATE KEY----- |
| 85 | + ``` |
| 86 | +
|
| 87 | + - Click **"Add secret"** |
| 88 | +
|
| 89 | +## Step 6: Add App to Ruleset Bypass List |
| 90 | +
|
| 91 | +1. **Navigate to Repository Rules** |
| 92 | + - Go to <https://github.com/dreamiurg/peakbagger-cli/settings/rules> |
| 93 | + - Click on the **"main"** ruleset |
| 94 | +
|
| 95 | +2. **Add Bypass Actor** |
| 96 | + - Scroll to **"Bypass list"** |
| 97 | + - Click **"Add bypass"** |
| 98 | + - Select **"Apps"** |
| 99 | + - Find and select your app: `peakbagger-release-bot` |
| 100 | + - Bypass mode: **"Always allow"** |
| 101 | + - Click **"Save changes"** |
| 102 | +
|
| 103 | +## Step 7: Verify Configuration |
| 104 | +
|
| 105 | +After merging the workflow PR, the release workflow will: |
| 106 | +
|
| 107 | +1. Generate a short-lived token from your GitHub App |
| 108 | +2. Use that token to checkout and push to the repository |
| 109 | +3. Bypass the ruleset rules because the app is in the bypass list |
| 110 | +4. Create releases, update changelog, and bump versions automatically |
| 111 | +
|
| 112 | +## Troubleshooting |
| 113 | +
|
| 114 | +### "App not found in bypass list" |
| 115 | +
|
| 116 | +- Make sure you installed the app on the repository (Step 4) |
| 117 | +- Verify the app appears in Settings → Integrations → GitHub Apps |
| 118 | +
|
| 119 | +### "Invalid private key" |
| 120 | +
|
| 121 | +- Ensure you copied the entire `.pem` file including header/footer |
| 122 | +- Check for no extra spaces or newlines |
| 123 | +
|
| 124 | +### "Insufficient permissions" |
| 125 | +
|
| 126 | +- Review Step 3 and ensure all required permissions are granted |
| 127 | +- You may need to update permissions in the app settings |
| 128 | +
|
| 129 | +## Security Notes |
| 130 | +
|
| 131 | +- **Private key**: Never commit the `.pem` file to version control |
| 132 | +- **Token lifetime**: App tokens expire after 1 hour (much safer than PATs) |
| 133 | +- **Scope**: The app only has access to repositories where it's installed |
| 134 | +- **Rotation**: Regenerate private keys periodically for security |
| 135 | +
|
| 136 | +## References |
| 137 | +
|
| 138 | +- [GitHub Apps Documentation](https://docs.github.com/en/apps) |
| 139 | +- [Repository Rulesets](https://docs.github.com/en/repositories/configuring-branches-and-merges-in-your-repository/managing-rulesets/about-rulesets) |
| 140 | +- [actions/create-github-app-token](https://github.com/actions/create-github-app-token) |
0 commit comments