AI-powered pull request reviewer built with Go and Gin. CodeSage listens to GitHub PR webhooks, fetches the diff, analyzes changes with Gemini, and posts a friendly review comment back to the PR.
- Receives GitHub webhook events for pull requests
- Verifies webhook signatures (
X-Hub-Signature-256) - Fetches changed files via GitHub API
- Sends diffs to Gemini for analysis
- Posts a formatted review comment back to the PR
- Simple health endpoint (
GET /)
- Go (as specified in
go.mod) - A GitHub webhook configured for your repository
- Environment variables for GitHub and AI providers
- Create a
.envfile in the project root with values relevant to your setup:
PORT=8080
GITHUB_TOKEN=ghp_...
GEMINI_API_KEY=...
HF_API_KEY=... # optional, used by huggingface.go
GITHUB_APP_ID=... # optional, used for installation tokens
GITHUB_APP_PRIVATE_KEY=... # optional, PEM format
GITHUB_WEBHOOK_SECRET=... # required to verify webhook signatures
GITHUB_OAUTH_CLIENT_ID=... # optional, if you enable OAuth endpoints
GITHUB_OAUTH_CLIENT_SECRET=...
- Build the project:
go build ./...
- Run the server:
go run main.go
You should see logs indicating the server is listening on :8080 and the registered routes.
POST /github/webhook— GitHub webhook receiver (expects PR events). Supports raw JSON andapplication/x-www-form-urlencodedpayloads (payload=format) and verifiesX-Hub-Signature-256usingGITHUB_WEBHOOK_SECRET.GET /— Health check returning{ "message": "CodeSage is running" }.GET /auth/github/login— Placeholder endpoint for GitHub OAuth login.GET /auth/github/callback— Placeholder endpoint for GitHub OAuth callback.
- In your GitHub repo settings, add a webhook:
- Payload URL:
http://<your-host>/github/webhook - Content type:
application/json - Secret: set to the value of
GITHUB_WEBHOOK_SECRET - Events: enable “Pull requests” (and “Ping” for testing)
- Payload URL:
When a PR is opened or synchronized, CodeSage:
- Verifies the request signature
- Reads and parses the payload
- Fetches changed files from the PR
- Builds a combined diff
- Sends the diff and title to Gemini
- Posts a formatted comment back to the PR
Configuration is loaded from environment variables (with .env support) via config/:
PORT— Server port, default8080GITHUB_TOKEN— Token used for GitHub API callsGEMINI_API_KEY— Required to analyze with GeminiHF_API_KEY— Optional; used by Hugging Face integrationGITHUB_APP_ID,GITHUB_APP_PRIVATE_KEY— Optional; used to exchange installation tokens for GitHub App scenariosGITHUB_WEBHOOK_SECRET— Required to verify webhook signaturesGITHUB_OAUTH_CLIENT_ID,GITHUB_OAUTH_CLIENT_SECRET— Optional; for OAuth endpoints
main.go— Entry point that loads config and starts the Gin serverserver/router.go— Router setup and route registrationconfig/config.go— Environment configuration loadergithub/webhook.go— Webhook handler and PR flow logicgithub/api.go— GitHub API calls (PR files, comments)github/app.go— GitHub App helpers (signature verification, installation tokens)ai/gemini.go— Gemini integrationai/huggingface.go— Optional Hugging Face integrationutils/logger.go— Minimal logger helpers
- The AI analysis currently uses Gemini (
ai/gemini.go). The Hugging Face helper is available but not wired in by default. - Ensure your tokens have appropriate scopes to read PR files and post comments.
- For production, consider setting
GIN_MODE=releaseand configuring trusted proxies for Gin.