AI Security

Securely Connecting an OpenAI Coding Agent to a Private GitHub Repository with Fine‑Grained Scopes

TL;DR: Use the OpenAI Agents SDK, create a fine‑grained GitHub personal access token (PAT) limited to the exact repository and actions the agent needs, store the token in a secret manager (e.g., Cloudflare Workers KV, HashiCorp Vault, or .env with restricted file permissions), inject it into the agent at runtime, test with a read‑only operation first, and rotate the token every 30‑60 days. Document the token’s purpose and expiry in a simple log.

Why a Dedicated, Scoped Token Matters

OpenAI’s Agents documentation describes how an agent can call external APIs, including GitHub, to fetch code, run tests, or push changes. If you grant the agent a PAT with broad permissions (e.g., repo or admin:org), a compromised prompt could expose all your private repositories or even delete them. Applying the principle of least privilege limits the blast radius of a potential injection attack.

Step 1 – Create a Fine‑Grained GitHub PAT

  1. Log in to GitHub and navigate to Settings → Developer settings → Personal access tokens → Tokens (fine‑grained).
  2. Click Generate new token and give it a clear name, e.g., openai‑coding‑agent‑repo‑access.
  3. Under Resource owner, select the organization or user that owns the target repository.
  4. In the Repository access section, choose Only select repositories and tick the exact repo(s) the agent will touch.
  5. Set the permissions you actually need:
    • Contents – Read & write if the agent will commit changes.
    • Pull requests – Read & write if it will open PRs.
    • Leave everything else (e.g., Secrets, Deployments) unchecked.
  6. Set an expiration date (GitHub now supports token expiry) – 30 days is a good baseline.
  7. Generate the token and copy it securely; you won’t see it again.

Step 2 – Store the Token Securely

Never hard‑code the PAT in source code or configuration files that end up in version control. Choose one of the following approaches:

Whichever method you pick, the token should only be readable by the process that launches the agent.

Step 3 – Wire the Token into the OpenAI Agent

The OpenAI Agents SDK lets you define custom tools. Below is a minimal Python example that injects the token as a header when calling GitHub’s REST API.

import os
import requests
from openai import OpenAI

client = OpenAI()

def github_api(path, method="GET", json=None):
    token = os.getenv("GITHUB_TOKEN")
    headers = {"Authorization": f"Bearer {token}", "Accept": "application/vnd.github+json"}
    url = f"https://api.github.com{path}"
    response = requests.request(method, url, headers=headers, json=json)
    response.raise_for_status()
    return response.json()

# Register as a tool the agent can call
client.tools.register(name="github_api", func=github_api, description="Interact with the private repo")

# Example prompt that asks the agent to list files
response = client.chat.completions.create(
    model="gpt-4o-mini",
    messages=[{"role": "user", "content": "List the top‑level files in the repo."}],
    tools=[{"type": "function", "function": {"name": "github_api"}}]
)
print(response)

Notice the token is accessed only at runtime via os.getenv. The SDK never logs the token value, and the request is limited to the repository you scoped earlier.

Step 4 – Verify the Least‑Privilege Model

Before allowing write operations, run a read‑only test:

If the agent can’t reach anything outside the chosen repo, you’ve successfully limited its scope.

Step 5 – Rotate and Revoke Tokens Regularly

Even with fine‑grained scopes, a compromised token is a risk. Implement a rotation schedule:

  1. Set a calendar reminder (or CI job) 5 days before expiry.
  2. Generate a new token with the same limited permissions.
  3. Update the secret store (e.g., replace the KV entry or .env value).
  4. Invalidate the old token from the GitHub UI.

Document each rotation in a simple log file (date, token name, expiry, who performed the change). This log can be part of your broader AI‑automation audit trail.

Step 6 – Add a Human‑in‑the‑Loop Guardrail

For any push or PR creation, have the agent return a diff and ask a human reviewer to approve before the final git push call. You can implement this with a lightweight webhook that posts the diff to Slack or email, letting the reviewer click an “Approve” button that triggers the final push.

Summary Checklist

Following this checklist lets a small team enjoy the productivity boost of an OpenAI coding agent while keeping source code safe from accidental or malicious exposure.

FAQ

Need a practical AI security review?

AISecAll reviews prompts, tool permissions, document flows, and agent behavior so small teams can use AI without guessing where the risk sits.

Book a call Discuss a project