Open-source project
electron/sheriff avatar
electron/sheriff

Sheriff: A Permission Bot That Enforces GitHub, Slack, and GSuite Policy from a YAML File

Controls and monitors organization permissions across GitHub, Slack and GSuite. Built with ❤️ by The Electron Team

153 stars20 forksTypeScriptMIT

At a glance

What is it?
Sheriff is a TypeScript bot from the Electron team that centralizes organization permissions in a YAML file and applies them across GitHub, Slack, and GSuite. It is built for Heroku deployment and relies on webhooks and a cron job to keep access controls in check.
Who is it for?
Sheriff is for organizations that already use GitHub heavily and want a single source of truth for team memberships and repository defaults, especially if they also use Slack. It is not for small teams or those without a dedicated deployment platform, since it requires a webhook server, a GitHub App, and a cron job.
Can I use it commercially?
Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
Is it still maintained?
Yes. The repository last received commits 23 days ago.
What is it written in?
Mainly TypeScript, according to GitHub's language statistics.

Answers come from the project's GitHub data, last synced on November 13, 2026, and from our analysis. They are not legal advice.

From daily snapshots

Star history

  • electron/sheriff153 ★ · +0
Star history
Repository2026-08-212026-11-13
electron/sheriff153153

0 Stars in the last 84 days, measured from the daily GitHub snapshot. Compare with other projects

Editorial analysis

The Problem Sheriff Solves

Sheriff addresses a specific pain: keeping permissions consistent across multiple SaaS tools when your organization has many repositories and many members. Without such a tool, a new hire gets added to GitHub but forgotten in Slack, or a repository's wiki gets enabled when your policy says it should be off. Sheriff centralizes these decisions in a single YAML file and applies them automatically. The README positions it for organizations with a lot of repositories and members, where manual permission management becomes error-prone and opaque. It also monitors for suspicious activity, such as new deploy keys with write access or the deletion of important branches, and posts alerts to Slack.

How Sheriff Works: Webhooks, a Cron Job, and a Config Repo

Sheriff has three core components: a webhook server, a permissions controller, and optional Slack and GSuite plugins. The webhook server receives GitHub events from an org-wide webhook that you configure to send everything. The permissions controller runs on a schedule, every 10 minutes as recommended, and compares the current state of your org against the desired state in a config.yaml file. That file lives in a separate repository named .permissions in your GitHub org, which you can keep private. The controller then makes the necessary changes to bring reality in line with the config. It also reacts to webhook events, so it can detect and alert on suspicious actions immediately. The Slack plugin posts a message to a designated channel every time Sheriff updates a permission or detects a suspect action.

Getting It Running: Commands and Environment Variables

Deployment is Heroku-first. You start the webhook server with npm start, then create an org-wide webhook on GitHub pointing to that server's URL, with content type application/json and a secret you generate. For the GitHub App, you need OAuth scopes: administration:write, contents:read, metadata:read for org, and members:write for repo. After downloading the private key, you must convert it with the command npx @electron/github-app-auth --creds={path-to-downloaded-private-key} --app-id={id-from-created-github-app} and set the output as SHERIFF_GITHUB_APP_CREDS. The cron job runs node lib/permissions/run.js --do-it-for-real-this-time, and without that flag it does a dry run. Configuration is via environment variables, with PERMISSIONS_FILE_ORG and GITHUB_WEBHOOK_SECRET required, plus SHERIFF_GITHUB_APP_CREDS. The permissions file itself is a YAML structure with an organization name, repository_defaults for things like has_wiki, and a list of teams, each with members and maintainers.

The YAML Config as the Single Source of Truth

The config.yaml file is the heart of Sheriff. It defines the org name, repository defaults such as whether wikis are enabled, and teams that are shared across GitHub, Slack, and GSuite. Teams are not platform-specific; the same team name applies everywhere. Members and maintainers are listed by GitHub username. The README suggests generating an initial config from your current org state using node lib/permissions/generate.js, but warns that you may need to edit it because all org owners are considered maintainers of teams they are in, which may not match your intended policy. This is a practical starting point, but it means your first config may encode existing drift rather than your desired state.

Limitations and Failure Modes

Sheriff assumes a GitHub-centric org. Slack and GSuite plugins are optional and disabled by default, so the core value is GitHub permission control. The cron job runs every 10 minutes, which means changes to your config are not applied in real time; there is a delay. The webhook provides immediate alerts, but the actual permission enforcement is batch. If you forget the --do-it-for-real-this-time flag, Sheriff only dry-runs, which is safe but might mislead you into thinking changes were applied. The README does not specify what happens when the config.yaml is malformed or when a team member no longer exists on GitHub; those are likely failure modes. Also, the bot requires a private key for the GitHub App, and the conversion step is mandatory; skipping it will cause authentication failures.

Alternatives and How They Differ

A direct alternative is using GitHub's native team and repository settings, managed manually or with scripts like the GitHub API. That approach gives you real-time changes and no extra infrastructure, but it lacks the cross-platform consistency that Sheriff provides for Slack and GSuite. Another alternative is Terraform with the GitHub provider, which also treats permissions as code but uses a declarative state model and requires a separate state backend. Terraform applies changes on demand, not on a cron schedule, and it does not monitor for suspicious activity. Sheriff's webhook-based monitoring and Slack alerts are its differentiator; Terraform does not watch for deploy key additions or branch deletions. For organizations that only need GitHub, the native API may be simpler, but Sheriff offers a unified YAML that spans multiple platforms.

Maintenance and License Considerations

Sheriff is MIT licensed, which permits commercial use, modification, and redistribution with attribution. Maintenance cost is non-trivial: you must keep the GitHub App credentials current, rotate the webhook secret, and update the config.yaml as your team changes. The README does not mention a migration path or versioned releases, and the repository shows no recent releases, so you may be relying on the main branch. The use of npx @electron/github-app-auth suggests a dependency on a separate package that could change. The cron job and webhook server both need uptime; if the Heroku app goes down, permission changes will not be applied and alerts will not fire. You should plan for regular reviews of the config file and test the dry-run mode before applying changes.

Editorial conclusion

Sheriff is for organizations that already use GitHub heavily and want a single source of truth for team memberships and repository defaults, especially if they also use Slack. It is not for small teams or those without a dedicated deployment platform, since it requires a webhook server, a GitHub App, and a cron job. Before adopting, verify that your GitHub org can accept an org-wide webhook that sends all events, and that you can generate the GitHub App private key in the required format. Also confirm that the YAML config structure matches your team hierarchy, because Sheriff will enforce it exactly as written.

Frequently asked questions

What does the Sheriff permissions bot do?

It controls and monitors organisation permissions across GitHub, Slack, Heroku and Google Workspace. It reconciles access against a config file and posts to a Slack channel whenever it changes a setting or detects a suspect action, such as a new deploy key with write access.

How do I run the Sheriff permissions job for real?

Run node lib/permissions/run.js with the flag that says to do it for real this time. Without the flag the job dry-runs and reports what it would have done. On Heroku the schedule is configured through the Heroku Scheduler addon, and the documentation says to trigger it every ten minutes.

Where does Sheriff keep the organisation permissions config?

In a config.yaml file at the top level of a repository inside your GitHub organisation, conventionally named with a leading dot. The project's own copy is private, though you may make yours public. The file holds the org name, repository defaults, and a list of teams with members and maintainers.

What OAuth scopes does the Sheriff GitHub App need?

At organisation level, administration write, contents read and metadata read. At repository level, members write, plus actions write and pull requests read if you use the Vouched CI feature. The project notes it is a bot holding organisation administration write access, so the scope set is worth auditing before pointing it at a real org.

Is the Sheriff Slack plugin enabled by default?

No. The Slack and Google Workspace plugins are both optional and disabled by default, enabled through a comma-separated setting listing which plugins to turn on. The Slack webhook and token are still required for the reporting side.

What suspicious activity does Sheriff alert on?

New deploy keys with write access, tag deletion, and deletion of a release branch. Which branches count as important is configurable through a regular expression setting rather than a hardcoded list, since that varies by organisation.

Official sources

  1. Official README
  2. Project repository
  3. README
  4. Releases
Add this badge to your README

If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.

Add this badge to your README

markdown
[![Hysen Labs](https://hysenlabs.com/badge/electron-sheriff.svg)](https://hysenlabs.com/projects/electron-sheriff)

Star history chart for your README

markdown
[![Star history](https://hysenlabs.com/chart/electron-sheriff.svg)](https://hysenlabs.com/projects/electron-sheriff)

Was this useful?