How to structure GitHub team hierarchies in a private company
GitHub team hierarchy should make permissions easier to reason about, not harder.
The common failure is over-nesting. It looks tidy on paper, then six months later nobody can explain effective access without clicking through parent and child teams one by one.
TL;DR
- Problem: many orgs overuse nesting, mix broad membership groups with ownership teams, and end up with inheritance chains that are hard to audit.
- Who this is for: GitHub org admins, engineering managers, and platform teams designing team structure for a private company.
- What this helps you fix: a shallow hierarchy model with separate top-level membership teams, clearer department structure, safer contractor handling, and less inheritance confusion.
1. The practical default
Keep broad membership teams separate from ownership teams. That means everyone should be a top-level team, not the parent of every other team.
everyone
engineering
product
operations
security
contractors
engineering
+-- engineering-platform
+-- engineering-backend
`-- engineering-frontend
product
+-- product-payments
+-- product-portal
`-- product-analytics
The point is simple: universal membership and ownership are different concepts. Do not hide both inside the same inheritance chain.
2. Why everyone should stay separate
- Clear purpose:
everyonemeans all org members. Functional teams mean ownership or responsibility. - Safer inheritance: if broad membership sits above narrower teams, inherited access becomes much harder to reason about.
- Simpler onboarding: add the person to
everyone, then to the department team, then to the squad or product team if needed. - Cleaner audits: you can explain access in plain language instead of tracing a clever tree.
3. When to nest and when not to
Nest narrower ownership teams under real departments or domains. Do not nest everything under a universal bucket just because it makes the chart look complete.
- Good nesting:
engineering-platform,engineering-backend,engineering-frontend. - Good nesting:
product-payments,product-portal,product-analytics. - Bad nesting: putting
engineering,security, andcontractorsundereveryone.
Shallow hierarchy beats clever hierarchy. If you need a long explanation to justify the tree, the tree is probably wrong.
4. Contractors should be explicit
Keep contractors and vendors as separate top-level teams where practical. Do not fold them into broad employee groups by default.
- Separate legal or employment categories from core staff membership.
- Keep contractor access narrow and reviewable.
- Prefer short-lived exceptions and named owners over vague inherited access.
5. Decision rule for most companies
- Use top-level teams for universal membership groups, departments, and cross-company audiences.
- Use nested teams for subdepartments, squads, specialties, or product ownership groups.
- Attach repo access at the narrowest layer that still matches real ownership.
- Avoid direct user grants becoming the real structure.
If the live model still depends on lots of individual exceptions, you have a permissions problem as well as a hierarchy problem. Read the team access vs direct access guide for that decision.
6. Where repod helps
GitHub already gives you teams and inheritance. The pain is operating the live model at scale once the hierarchy and repo mappings have drifted. repod helps you review the structure, spot broad access, and clean up repo-team mappings without treating GitHub org admin as the day-to-day tool.
For the broader access model, read the GitHub governance and permission drift guide. If you need the high-stakes example, continue with how to restrict GitHub repo visibility to one team.
Restrict repo visibility to one team
Related guides
- GitHub governance and permission drift guide for private orgs
- GitHub team access vs direct repository access
- How to restrict GitHub repo visibility to one team in a private org
- GitHub offboarding playbook for private engineering teams
- How to delegate GitHub repo-team access work without handing out org admin