- GitHub Engineering describes Evergreen, an app that removes outside collaborators from a shared organization when no repository owner confirms they should stay.
- GitHub's design argues that access reviews are more reliable when doing nothing is the safe result, though the post reports no outcome figures.
- Ask your team what happens when a review gets no reply, and whether an automated removal can be undone quickly.
Access is easy to give and tedious to take back. Nobody is paged when a contractor keeps read rights to a project that ended months ago. The task simply waits for someone with time. GitHub Engineering has described a way to remove that dependence on time and memory. Its answer is to make the safe outcome the one that happens when nobody does anything.
What GitHub built
The problem arose in one GitHub organization that company staff, known as Hubbers, share with customers and partners for product trials and professional services projects. Outside collaborators there need regular checks. Repositories also need archiving once they have served their purpose. GitHub Engineering says that doing this by hand gets harder as projects grow and is easy to defer.
Its tool is Evergreen, a GitHub App. It runs two jobs. One reviews outside collaborators every quarter. The other finds repositories with no human activity past a threshold, warns their owners and archives them if they stay untouched.
The idea: silence should not grant access
Most access programs fail in a quiet way. Removing access takes an action. Keeping it takes none. So access accumulates.
Evergreen reverses this. GitHub calls the principle "fail secure". If nobody answers an access review, the app revokes the access. The owner has to say who stays.
This is the lesson for leaders: the default matters more than the policy document. A rule that says "review access regularly" depends on people remembering. A system where unreviewed access ends does not.
There is a human cost, and it is a fair one to weigh. A busy repository owner who misses the deadline will lose a partner's access. GitHub's answer is to make responding easy and to make the cost of a mistake small.
How it works
A dedicated controller repository acts as the clock and the memory. Four scheduled GitHub Actions workflows send repository_dispatch events, which are signals that wake the app. The app itself is a small Go web server in a container. Reviews open two weeks before cleanup runs. A built-in grace period stops a stray manual run from skipping ahead.
Evergreen keeps its records as plain files. The controller repo holds one JSON file per repository. That file lists the people who had access, the date the review opened, the due date, the person who decided and the outcome. Because these are files in git, the commit history serves as the audit trail. GitHub says no separate database or custom audit pipeline is needed.
The owner's job happens in an ordinary issue inside their own repository. It holds a checklist of collaborators. The owner ticks the people who should stay and closes the issue. Evergreen reads the closing event, keeps the ticked people, removes the rest and posts a receipt of what it did.
Guardrails around the automation
Closing the issue is a privileged act. If someone who is not a Hubber closes it, the app reopens it and explains why.
Evergreen also has to find the right person. It first checks a custom property named evergreen_repo_owner. If that is empty, it looks at recent issue and commit authors who are on the access review team and notifies them. No spreadsheet of owners is needed.
The tool also fails closed. If some removals succeed and one hits a temporary API error, the review stays pending and the next run retries. It records "revoked" only when every removal has worked. Evergreen also logs each removal in the issue. To undo a wrong removal, someone adds back the usernames listed there.
Evergreen does not delete repositories or their contents. Archived repositories can be recovered. Org owners can exempt a repository through a custom property.
Rolling out without surprises
GitHub's organization has more than 1,400 Hubbers, plus many customers and partners. The team ran Evergreen first in a DRY_RUN mode, which logs every change it would make without making any. It sent repeated announcements before the first real run. It also logged to Splunk, which helped it find edge cases such as empty collaborator lists and repositories with issues disabled.
Scale also set a hard limit. GitHub's secondary rate limits for content creation allow 80 requests a minute and 500 an hour. Evergreen paces itself in batches with pauses between them, rather than waiting to be throttled.
Questions for your team
The post reports no figures on how many accounts were removed or how often owners missed deadlines. It describes one organization's design. It does not prove that this approach works elsewhere. The questions it raises are still useful.
First, what happens in your organization when an access review gets no reply? If the answer is "the access stays", the review depends on goodwill. Second, can you name an owner for every repository or project space without a spreadsheet? Third, if an automated removal is wrong, can someone restore access in minutes from a written record? Fourth, can the tool run in a mode that only reports, before it is allowed to act?
The lasting point is simple. Reviews are more likely to hold when the safe outcome needs no effort and the cost of a mistake is small. Build the second half before you ask people to trust the first.
Produced by the WebPulse Newsroom with AI assistance from the original reporting credited below, and checked against that source by our editorial review. How we use AI.
Original reporting: GitHub Engineering.





