Phishing Developers
- malicious OAuth app consent
- look-alike registry and support domains
- real-time phishing of 2FA codes
- stolen sessions acting as the developer
Scenario
Alex maintains a popular open-source project your company depends on. One morning a new issue appears in the repository, titled "Security Alert: Access Attempt". It says someone signed in to Alex's GitHub account from Reykjavik, and gives a link to "review activity and secure your account".
The link goes to a real github.com page: an OAuth consent screen for an app called "Security App". It asks for access to repositories, workflows and organisation data. Alex is worried and in a hurry, so clicks Authorize.
No password was typed and 2FA never came into play. The attacker now holds an OAuth token with Alex's permissions. They clone private repositories, read Actions secrets through new workflows, and edit files through the API.
Those API edits appear in history as commits signed by GitHub and marked "Verified". Commit signing proves which account made a change. It cannot tell you the account was being driven by someone else.
Real-world precedent: In March 2025 a fake "Security Alert" issue campaign hit thousands of GitHub repositories and pushed maintainers to authorise a malicious OAuth app called gitsecurityapp (Help Net Security). The same year, look-alike domains phished registry maintainers: pypj.org against PyPI in July (PyPI) and npmjs.help against npm in September (Aikido).
Reconnaissance
Explanation
Attackers build target lists from public data: commit emails, package metadata, maintainer lists and repository activity. They then send lures through channels developers trust, such as GitHub issues and notifications, or emails that look like registry support.
Insight
Your developers' public footprint is the attacker's mailing list. The 2025 PyPI campaign likely emailed addresses taken straight from package metadata.
Practical
- Check which email addresses your maintainers expose in package metadata and commits.
- Use GitHub's
noreplycommit email for public work. - List the look-alike domains for the services your team relies on: GitHub, npm, PyPI, your CI and your cloud.
# Emails exposed in recent commit history
git log --format='%ae' | sort | uniq -c | sort -rn | head
Tools/Techniques
- dnstwist to generate and check look-alike domains.
- GitHub email privacy settings.
Metrics/Signal
- Maintainers using a
noreplycommit address. - Registered look-alike domains for your key services.
Evaluate
Explanation
Find out what a phished developer could hand over: OAuth grants, tokens, sessions and publish rights.
Insight
OAuth consent phishing skips passwords and 2FA entirely. A developer with broad, long-lived grants to many third-party apps is a big target, even with perfect 2FA.
Practical
- Review the OAuth apps and GitHub Apps your developers have authorised, and the scopes they hold.
- Check whether your organisation restricts third-party OAuth app access.
- Inventory classic PATs with
repooradmin:orgscope.
Tools/Techniques
- Reviewing authorised OAuth apps.
- Organisation settings: Third-party application access policy.
Metrics/Signal
- Authorised third-party OAuth apps per developer.
- Classic PATs with broad scopes (target: zero).
Fortify
Explanation
Make the lures fail. Use 2FA that cannot be relayed, and stop unknown OAuth apps reaching your organisation.
Insight
Passkeys and security keys are bound to the real domain, so a proxy on npmjs.help or pypj.org gets nothing usable. OAuth consent phishing needs a separate control: app access restrictions.
Practical
- Turn on OAuth app access restrictions for your GitHub organisation, so apps need owner approval.
- Use passkeys or security keys for GitHub, npm and PyPI.
- Publish packages through trusted publishing, so a phished maintainer has no long-lived token to give away.
- Agree a simple rule: security alerts are checked by going to the site directly, never through a link in an issue or email.
Tools/Techniques
- GitHub: restricting OAuth app access.
- GitHub passkeys.
- npm trusted publishing and PyPI trusted publishers.
Metrics/Signal
- Organisations with OAuth app restrictions enabled.
- Developers with phishing-resistant 2FA.
Limit
Explanation
If a token or session is stolen, limit what it can change.
Insight
Branch rulesets apply to the attacker's token just as they apply to Alex. A stolen token that cannot push to main or approve its own pull request has to get past another human.
Practical
- Use rulesets that require pull request review and passing checks on default and release branches.
- Require SAML SSO authorisation for tokens, so a stolen grant is not automatically valid in your organisation.
- Prefer fine-grained PATs with expiry, scoped to specific repositories.
- Turn on secret scanning push protection so stolen code access does not also reveal committed secrets.
Tools/Techniques
Metrics/Signal
- Default branches protected by rulesets.
- Tokens with no expiry date.
Expose
Explanation
Spot the campaign and the misuse quickly.
Insight
These campaigns are noisy. Many repositories get the same "security alert" issue at once, and the stolen token is then used from new IP addresses and for unusual API calls.
Practical
- Watch for new issues or notifications that contain OAuth authorisation links, and report them to GitHub.
- Review the audit log for new OAuth authorisations, new workflows and repository clones that do not match normal behaviour.
- Do not treat "Verified" as proof that a commit was intended. Check who made the change and from where.
# Recent events by a specific user in the org audit log (GitHub Enterprise Cloud)
gh api "orgs/<org>/audit-log?phrase=actor:<user>" \
-q '.[] | "\(.created_at) \(.action) \(.repo // "")"' | head -50
Tools/Techniques
- GitHub organisation audit log.
- Reviewing security logs for individual accounts.
Metrics/Signal
- Time from a suspicious OAuth grant to revocation.
- Phishing issues reported by developers.
Exercise
Explanation
Practise recognising and reporting these lures, and revoking access fast.
Insight
Developers who have seen a fake security alert before are far more likely to stop and report the next one.
Practical
- Show the team real examples from 2025: the fake GitHub issue, the
npmjs.helpemail and thepypj.orgemail. - In a test organisation, register a harmless OAuth app you own and practise finding and revoking it from user and organisation settings.
- Time how long it takes to revoke a developer's sessions, tokens and app grants, and to rotate the secrets their account could read.
Tools/Techniques
- A test GitHub organisation and a benign OAuth app you control.
- Canarytokens placed in test repositories to show what a stolen grant could reach.
Metrics/Signal
- Minutes to revoke all of a developer's access.
- Lure reports received during and after the session.