feat: add GitHub and GitLab webhook support (#170)
All checks were successful
Check / check (push) Successful in 3m17s

## Summary

Adds GitHub and GitLab push webhook support alongside the existing Gitea support.

closes #68

## What Changed

### Auto-detection of webhook source

The webhook handler now auto-detects which platform sent the webhook by examining HTTP headers:
- **Gitea**: `X-Gitea-Event`
- **GitHub**: `X-GitHub-Event`
- **GitLab**: `X-Gitlab-Event`

Existing Gitea webhooks continue to work unchanged. Unknown sources fall back to Gitea format for backward compatibility.

### Normalized push event

All three payload formats are parsed into a unified `PushEvent` struct containing:
- Source platform, ref, branch, commit SHA
- Repository name, clone URL, HTML URL
- Commit URL (with per-platform fallback logic)
- Pusher username/name

### New files

- **`internal/service/webhook/payloads.go`**: Source-specific payload structs (`GiteaPushPayload`, `GitHubPushPayload`, `GitLabPushPayload`), `ParsePushPayload()` dispatcher, per-platform parsers, branch extraction, and commit URL extraction functions.

### Modified files

- **`internal/service/webhook/types.go`**: Added `Source` type (gitea/github/gitlab/unknown), `DetectWebhookSource()`, `DetectEventType()`, and `PushEvent` normalized type. Moved `GiteaPushPayload` to payloads.go.
- **`internal/service/webhook/webhook.go`**: `HandleWebhook` now accepts a `Source` parameter and uses `ParsePushPayload()` for unified parsing instead of directly unmarshaling Gitea payloads.
- **`internal/handlers/webhook.go`**: Calls `DetectWebhookSource()` and `DetectEventType()` to auto-detect the platform before delegating to the webhook service.
- **`internal/service/webhook/webhook_test.go`**: Comprehensive tests for source detection, event type extraction, payload parsing (all 3 platforms), commit URL fallback paths, and integration tests through `HandleWebhook` for GitHub and GitLab sources.
- **`README.md`**: Updated description, features, non-goals, and architecture to reflect multi-platform webhook support.

## Test coverage

Webhook package: **96.9%** statement coverage. Tests cover:
- `DetectWebhookSource` with all header combinations and precedence
- `DetectEventType` for each platform
- `ParsePushPayload` for Gitea, GitHub, GitLab, unknown source, invalid JSON, empty payloads
- Commit URL extraction fallback paths for GitHub and GitLab
- Direct struct deserialization for all three payload types
- Full `HandleWebhook` integration tests with GitHub and GitLab sources

Co-authored-by: user <user@Mac.lan guest wan>
Reviewed-on: #170
Co-authored-by: clawbot <clawbot@noreply.example.org>
Co-committed-by: clawbot <clawbot@noreply.example.org>
This commit was merged in pull request #170.
This commit is contained in:
2026-03-22 00:46:10 +01:00
committed by Jeffrey Paul
parent 67361419f5
commit 57ec4331ef
6 changed files with 1104 additions and 186 deletions

View File

@@ -1,12 +1,12 @@
# µPaaS by [@sneak](https://sneak.berlin)
A simple self-hosted PaaS that auto-deploys Docker containers from Git repositories via Gitea webhooks.
A simple self-hosted PaaS that auto-deploys Docker containers from Git repositories via webhooks from Gitea, GitHub, or GitLab.
## Features
- Single admin user with argon2id password hashing
- Per-app SSH keypairs for read-only deploy keys
- Per-app UUID-based webhook URLs for Gitea integration
- Per-app UUID-based webhook URLs with auto-detection of Gitea, GitHub, and GitLab
- Branch filtering - only deploy on configured branch changes
- Environment variables, labels, and volume mounts per app
- CPU and memory resource limits per app
@@ -20,7 +20,7 @@ A simple self-hosted PaaS that auto-deploys Docker containers from Git repositor
- Complex CI pipelines
- Multiple container orchestration
- SPA/API-first design
- Support for non-Gitea webhooks
- Support for non-push webhook events (e.g. issues, merge requests)
## Architecture
@@ -45,7 +45,7 @@ upaas/
│ │ ├── auth/ # Authentication service
│ │ ├── deploy/ # Deployment orchestration
│ │ ├── notify/ # Notifications (ntfy, Slack)
│ │ └── webhook/ # Gitea webhook processing
│ │ └── webhook/ # Webhook processing (Gitea, GitHub, GitLab)
│ └── ssh/ # SSH key generation
├── static/ # Embedded CSS/JS assets
└── templates/ # Embedded HTML templates