Secret Scanning with GitHub Advanced Security
Secret scanning GitHub Advanced Security detects credentials, API keys, tokens, and other secrets accidentally committed to repositories. In 2026, with over 200 supported secret types and push protection that blocks commits containing secrets before they reach the repository, this feature has become an essential layer of defense against credential leaks that lead to data breaches.
This guide covers implementing comprehensive secret scanning across your organization, including push protection configuration, custom secret patterns, incident response procedures, and integration with secret management tools like HashiCorp Vault and AWS Secrets Manager.
The Cost of Leaked Secrets
A single leaked AWS access key can result in hundreds of thousands of dollars in unauthorized charges within hours. Moreover, leaked database credentials expose customer data, triggering compliance violations and breach notification requirements. GitHub reports that over 10 million secrets are leaked in public repositories annually — and private repositories are equally at risk from insiders and compromised developer machines.
Common Secret Types Detected
┌────────────────────────────┬────────────┬──────────────┐
│ Secret Type │ Severity │ Detection │
├────────────────────────────┼────────────┼──────────────┤
│ AWS Access Keys │ Critical │ Built-in │
│ Azure Service Principal │ Critical │ Built-in │
│ GCP Service Account Key │ Critical │ Built-in │
│ GitHub PAT/OAuth Token │ High │ Built-in │
│ Database Connection String │ Critical │ Built-in │
│ Private SSH Keys │ High │ Built-in │
│ Stripe API Keys │ High │ Built-in │
│ Slack Webhook URLs │ Medium │ Built-in │
│ JWT Signing Keys │ High │ Custom │
│ Internal API Keys │ Medium │ Custom │
│ Encryption Keys │ Critical │ Custom │
└────────────────────────────┴────────────┴──────────────┘
200+ built-in patterns + custom patternsEnabling Secret Scanning
# Enable for a single repository via API
gh api repos/{owner}/{repo} \
--method PATCH \
--field security_and_analysis.secret_scanning.status=enabled \
--field security_and_analysis.secret_scanning_push_protection.status=enabled
# Enable for entire organization
gh api orgs/{org} \
--method PATCH \
--field security_and_analysis.secret_scanning.status=enabled \
--field security_and_analysis.secret_scanning_push_protection.status=enabledPush Protection Configuration
Push protection is the most valuable feature — it blocks commits containing secrets before they are pushed. Therefore, secrets never reach the repository and never appear in git history:
# .github/secret_scanning.yml — Organization-level config
paths-ignore:
- 'test/fixtures/**'
- '**/*.test.js'
- 'docs/examples/**'
# Custom patterns for internal secrets
patterns:
- name: Internal API Key
secret_type: internal_api_key
pattern: 'MYAPP_KEY_[A-Za-z0-9]{32}'
- name: Internal JWT Secret
secret_type: jwt_secret
pattern: 'JWT_SECRET=[A-Za-z0-9+/=]{44,}'
- name: Database URL
secret_type: database_url
pattern: '(postgres|mysql|mongodb)://[^\s]+:[^\s]+@[^\s]+'Custom Secret Patterns
Organizations often have internal credential formats that built-in patterns do not cover. Additionally, custom patterns let you detect company-specific secrets and configuration values:
# Create custom pattern via API
gh api orgs/{org}/secret-scanning/custom-patterns \
--method POST \
--field name="Internal Service Token" \
--field pattern="svc_tok_[a-f0-9]{40}" \
--field description="Internal microservice authentication token" \
--field severity="high"
# Create pattern with test strings for validation
gh api orgs/{org}/secret-scanning/custom-patterns \
--method POST \
--field name="Encryption Key" \
--field pattern="ENC_KEY_[A-Za-z0-9]{64}" \
--field description="Application encryption key" \
--field severity="critical" \
--field test_strings='["ENC_KEY_a1b2c3d4e5f6a1b2c3d4e5f6a1b2c3d4e5f6a1b2c3d4e5f6a1b2c3d4e5f6a1b2"]'Incident Response Workflow
When a secret is detected, speed matters. Consequently, automate the response process to minimize the exposure window:
import requests
import json
from datetime import datetime
class SecretIncidentHandler:
def __init__(self, github_token, vault_url, slack_webhook):
self.headers = {
'Authorization': f'token {github_token}',
'Accept': 'application/vnd.github+json',
}
self.vault_url = vault_url
self.slack_webhook = slack_webhook
def handle_alert(self, alert):
"""Process a secret scanning alert."""
secret_type = alert['secret_type']
severity = self.classify_severity(secret_type)
# Step 1: Rotate the compromised credential
if secret_type.startswith('aws_'):
self.rotate_aws_key(alert)
elif secret_type == 'database_url':
self.rotate_db_credential(alert)
# Step 2: Alert the team
self.notify_slack(alert, severity)
# Step 3: Resolve the alert
self.resolve_alert(alert['number'], 'revoked')
# Step 4: Log for compliance
self.log_incident(alert, severity)
def rotate_aws_key(self, alert):
"""Automatically rotate compromised AWS keys."""
import boto3
iam = boto3.client('iam')
# Deactivate the leaked key immediately
access_key = alert['secret'][:20] # AKIA...
iam.update_access_key(
AccessKeyId=access_key,
Status='Inactive'
)
# Create new key and store in Vault
new_key = iam.create_access_key(
UserName=alert.get('push_protection_bypassed_by',
{}).get('login', 'unknown')
)
self.store_in_vault(
f"aws/{alert['repository']['name']}",
new_key['AccessKey']
)
def notify_slack(self, alert, severity):
"""Send incident notification to security channel."""
color = {'critical': '#ff0000', 'high': '#ff8800',
'medium': '#ffcc00'}.get(severity, '#cccccc')
requests.post(self.slack_webhook, json={
'attachments': [{
'color': color,
'title': f'Secret Leaked: {alert["secret_type"]}',
'fields': [
{'title': 'Repository',
'value': alert['repository']['full_name']},
{'title': 'Severity', 'value': severity},
{'title': 'Committer',
'value': alert.get('push_protection_bypassed_by',
{}).get('login', 'Unknown')},
],
}]
})Pre-Commit Prevention
The best approach is preventing secrets from being committed in the first place. Furthermore, pre-commit hooks provide a local safety net before code reaches GitHub:
# .pre-commit-config.yaml
repos:
- repo: https://github.com/gitleaks/gitleaks
rev: v8.18.0
hooks:
- id: gitleaks
name: Detect secrets with Gitleaks
entry: gitleaks protect --staged --verbose
language: golang
- repo: https://github.com/trufflesecurity/trufflehog
rev: v3.63.0
hooks:
- id: trufflehog
name: TruffleHog secret scan
entry: trufflehog git file://. --only-verified --fail# .gitleaks.toml — Custom rules
[extend]
useDefault = true
[[rules]]
id = "internal-api-key"
description = "Internal API key detected"
regex = '''MYAPP_KEY_[A-Za-z0-9]{32}'''
secretGroup = 0
[[rules]]
id = "env-file-secret"
description = "Secret in environment variable assignment"
regex = '''(?i)(password|secret|api_key|token)s*=s*['"][^'"]{8,}['"]'''
secretGroup = 0
[rules.allowlist]
paths = [
'''.example$''',
'''.sample$''',
'''test/''',
]When NOT to Use GitHub Secret Scanning Alone
GitHub secret scanning only covers repositories hosted on GitHub. If your organization uses GitLab, Bitbucket, or self-hosted Git, you need additional tools like Gitleaks or TruffleHog. Additionally, secret scanning does not cover runtime environments — secrets hardcoded in deployed containers, environment variables, or CI/CD logs require separate monitoring. Secret scanning is a detection tool, not a prevention framework — it should be part of a broader secrets management strategy that includes vault-based secret storage, short-lived credentials, and workload identity federation.
Key Takeaways
- Secret scanning GitHub Advanced Security detects 200+ credential types with push protection blocking commits before they reach the repo
- Custom patterns extend detection to organization-specific secrets and internal credential formats
- Automated incident response with credential rotation minimizes the exposure window after a leak
- Pre-commit hooks with Gitleaks provide local prevention before secrets leave the developer machine
- Combine with vault-based secret storage and workload identity for a complete secrets management strategy
Related Reading
- Supply Chain Security SBOM and SLSA Guide
- Sigstore Software Signing and Verification
- OAuth 2.1 Implementation Security Guide