Sync Repository, Dependabot and Codespaces secrets + variables between GitHub repositories
- Sync Secrets Action
- Inputs
- GitHub Token Requirements
- Container Usage
- Usage Examples
- Syncing Repository Secrets and Variables
- Matrix Build Example - Syncing Across Multiple Repositories
- Query Example - Syncing to Repositories by Search Query
- Syncing Environment Secrets
- Syncing Secrets Across Multiple Repositories and Environments
- Syncing Codespaces Secrets
- Syncing Dependabot Secrets
- Local Development
- High-Level Functionality
- FAQ on Security
- Why yet another action?
- Contributing & License
github-token
: Required - The GitHub token to use. Use GitHub secrets for security.target
: Optional - The repository to sync secrets and variables to. Eithertarget
orquery
must be set, but not both.secrets
: Optional - Secrets to sync. Formatted as a string of newline-separatedKEY=VALUE
pairs.variables
: Optional - Variables to sync. Formatted as a string of newline-separatedKEY=VALUE
pairs.rate-limit
: Optional - Enables rate limit checking. Set totrue
to enable. Default isfalse
.max-retries
: Optional - Maximum number of retries for operations. Must not be smaller than zero. Default is3
.dry-run
: Optional - Dry run mode. If true, no changes will be made. Useful for testing. Default isfalse
.prune
: Optional - Prunes all existing secrets and variables not in the subset of those defined. Default isfalse
.environment
: Optional - The GitHub environment to sync variables or secrets to. Use when targeting environment-specific secrets or variables.type
: Optional - Type of the secrets to manage:actions
,dependabot
, orcodespaces
. Default isactions
.query
: Optional - GitHub search query to find repositories for batch processing. Eitherquery
ortarget
must be set, but not both.
Note: To use Sync Secrets Action, you need a GitHub Token with the right permissions. The default
GITHUB_TOKEN
won't work.
For a Personal Access Token (PAT), create one in your GitHub settings with repo
and, if needed, admin:org
permissions.
For a GitHub App token, create an app in GitHub settings, set necessary permissions, install it to target repositories, and use the private key for authentication.
Store your token in GitHub secrets and use it in the github-token
input of the action.
This action can be executed independently from workflows within a container. To do so, use the following command:
podman run --rm -it ghcr.io/cbrgm/sync-secrets-action:v1 --help
Here are some usage examples to help you getting started! Feel free to contribute more.
name: Sync Repository Secrets and Variables
on:
workflow_dispatch:
jobs:
sync-repo-secrets-and-vars:
runs-on: ubuntu-latest
steps:
- name: Sync Secrets and Variables
uses: cbrgm/sync-secrets-action@v1
with:
github-token: ${{ secrets.GITHUB_TOKEN }}
target: 'user/repository'
secrets: |
SECRET_KEY=${{ secrets.SOME_SECRET }}
ANOTHER_SECRET=${{ secrets.ANOTHER_SECRET }}
variables: |
VAR_KEY=varvalue
ANOTHER_VAR=${{ secrets.A_VARIABLE }}
name: Sync Secrets Across Repositories
on:
workflow_dispatch:
jobs:
sync-secrets-across-repos:
runs-on: ubuntu-latest
strategy:
matrix:
target: ['user/repo1', 'user/repo2', 'user/repo3']
steps:
- name: Sync Secrets to ${{ matrix.target }}
uses: cbrgm/sync-secrets-action@v1
with:
github-token: ${{ secrets.GITHUB_TOKEN }}
target: ${{ matrix.target }}
secrets: |
GLOBAL_SECRET=${{ secrets.GLOBAL_SECRET }}
variables: |
GLOBAL_VAR=globalvarvalue
name: Sync Secrets to Repositories by Query
on:
workflow_dispatch:
jobs:
sync-secrets-by-query:
runs-on: ubuntu-latest
steps:
- name: Sync Secrets to Repositories Matching Query
uses: cbrgm/sync-secrets-action@v1
with:
github-token: ${{ secrets.GITHUB_TOKEN }}
query: 'org:myorganization topic:mytopic'
secrets: |
GLOBAL_SECRET=${{ secrets.GLOBAL_SECRET }}
variables: |
GLOBAL_VAR=globalvarvalue
This workflow uses the query argument to target repositories within
myorganization
that are tagged with the topicmytopic
. It syncs the specified secrets and variables to all matching repositories.
See GitHub Queries.
Tip: Make sure these environments exist before distributing secrets!
name: Sync Environment Secrets
on:
push:
branches:
- main
jobs:
sync-env-secrets:
runs-on: ubuntu-latest
steps:
- name: Sync Environment Secrets
uses: cbrgm/sync-secrets-action@v1
with:
github-token: ${{ secrets.GITHUB_TOKEN }}
target: 'user/repository'
environment: 'production'
secrets: |
PROD_DB_PASSWORD=${{ secrets.PROD_DB_PASSWORD }}
dry-run: 'false'
prune: 'true'
name: Sync Secrets Across Repositories and Environments
on:
workflow_dispatch:
jobs:
sync-secrets:
runs-on: ubuntu-latest
strategy:
matrix:
repo: ['org/repo1', 'org/repo2', 'org/repo3'] # Target repositories
environment: ['development', 'staging', 'production'] # Target environments
steps:
- name: Sync Secrets to ${{ matrix.repo }} for ${{ matrix.environment }} Environment
uses: cbrgm/sync-secrets-action@v1
with:
github-token: ${{ secrets.GITHUB_TOKEN }}
target: ${{ matrix.repo }}
environment: ${{ matrix.environment }}
secrets: |
DATABASE_URL=${{ secrets['DB_URL_' + matrix.environment] }}
API_KEY=${{ secrets['API_KEY_' + matrix.environment] }}
type: 'actions'
dry-run: 'false'
prune: 'true'
The secrets input dynamically references secrets based on the environment. For example,
DB_URL_development
,DB_URL_staging
, andDB_URL_production
should be defined in your repository's secrets. This approach allows each job to use environment-specific secret values.
name: Sync Codespaces Secrets
on:
workflow_dispatch:
jobs:
sync-codespaces-secrets:
runs-on: ubuntu-latest
steps:
- name: Sync Codespaces Secrets
uses: cbrgm/sync-secrets-action@v1
with:
github-token: ${{ secrets.GITHUB_TOKEN }}
target: 'user/repository'
secrets: |
CODESPACE_SECRET=${{ secrets.CODESPACE_SECRET }}
type: 'codespaces'
name: Sync Dependabot Secrets
on:
workflow_dispatch:
jobs:
sync-dependabot-secrets:
runs-on: ubuntu-latest
steps:
- name: Sync Dependabot Secrets
uses: cbrgm/sync-secrets-action@v1
with:
github-token: ${{ secrets.GITHUB_TOKEN }}
target: 'user/repository'
secrets: |
DEPENDABOT_SECRET=${{ secrets.DEPENDABOT_SECRET }}
type: 'dependabot'
You can build this action from source using Go
:
make build
sequenceDiagram
participant CronUser as Cron / User
participant GitHubAction
participant GitHubAPI
participant Repository
CronUser->>+GitHubAction: Execute Action
GitHubAction->>+GitHubAPI: Create API Client
GitHubAPI->>-GitHubAction: Client Created
GitHubAction->>GitHubAction: Parse Secrets & Variables
GitHubAction->>+GitHubAPI: Search Repositories (if query provided)
GitHubAPI->>-GitHubAction: Return Repositories
GitHubAction->>GitHubAction: Process Each Repository
GitHubAction->>+Repository: Process Repository
alt Environment Specific
Repository->>+GitHubAPI: List Environment Secrets & Variables Names
GitHubAPI->>-Repository: Update Secrets & Variables
else Repository Specific
Repository->>+GitHubAPI: List Repository Secrets & Variables Names
GitHubAPI->>-Repository: Update Secrets & Variables
else Dependabot
Repository->>+GitHubAPI: List Dependabot Secrets Names
GitHubAPI->>-Repository: Update Secrets
else Codespaces
Repository->>+GitHubAPI: List Codespaces Secrets Names
GitHubAPI->>-Repository: Update Secrets
end
Repository->>-GitHubAction: Processing Complete
GitHubAction->>-CronUser: Execution Finished`
Yes, it is designed with safety in mind. However, like any tool, the security level depends on proper usage and configuration. Ensure your GitHub token has the minimum required permissions.
No, secrets are encrypted and handled within GitHub's secure environment. Yet, be cautious with the output logs and error messages to avoid accidental exposure.
Yes, they are protected using GitHub's security mechanisms. Nonetheless, the security is also contingent on how well access controls and permissions are managed in your GitHub repository settings.
Yes, secrets are not exposed in code or logs, ensuring they remain secure. However, the inherent risk of public repositories means you should be extra vigilant in monitoring access and usage patterns.
Using this action does not inherently increase risk if followed by GitHub's security guidelines and best practices. Risks mainly arise from misconfigurations or improper handling of secrets on the user's part. Regular audits and updates are recommended to maintain security.
While building my GitHub Action for secret synchronization, I drew inspiration from existing solutions, focusing on addressing specific challenges and enhancing user experience:
Key design principles guiding this action development include:
- Standardizing Inputs: Adopting kebab-case for inputs, inspired by the conventions seen in the repositories listed.
- Enhancing Matching Logic: Utilizing GitHub Search syntax over regex for repository targeting.
- Explicit Secret Specification: Preferring direct secret naming to regex patterns for clarity and precision, addressing complexity and confusion observed in the existing actions.
- Contributions Welcome!: Interested in improving or adding features? Check the Contributing Guide for instructions on submitting changes and setting up development environment.
- Free & Open: Made during free time, costs nothing. See Apache 2.0 License for your rights.
- Your Involvement Matters: Code contributions, suggestions, feedback crucial for improvement and success. Let's maintain it as a useful resource for all 🌍.