From 8b5cee8a6f55afd67f7ff8a5128e7cb9c74394e7 Mon Sep 17 00:00:00 2001 From: Jannis Date: Wed, 13 May 2026 08:36:54 +0000 Subject: [PATCH] Update README.md --- README.md | 273 +++++++++++++++++++++++++++--------------------------- 1 file changed, 137 insertions(+), 136 deletions(-) diff --git a/README.md b/README.md index c2a3323..571cc4c 100644 --- a/README.md +++ b/README.md @@ -26,175 +26,176 @@ Every repository on this Gitea instance that has the topic tag `dashboard` is au --- ## 🧱 Architecture + +``` +┌─────────────────┐ Gitea REST API v1 ┌─────────────────────┐ +│ Gitea Server │ ◄────────────────────► │ Backend Service │ +│ (Repos + Topics)│ │ (Go, net/http) │ +└─────────────────┘ └──────────┬──────────┘ + │ + ┌──────────▼───────────┐ + │ PostgreSQL DB │ + │ (Repos, Issues, │ + │ Milestones, Cache) │ + └──────────┬───────────┘ + │ + ┌──────────▼───────────┐ + │ Frontend │ + │ (SvelteKit) │ + └──────────────────────┘ ``` -┌─────────────────┐ Gitea REST API v1 ┌──────────────────────┐ -│ Gitea Server │ ◄────────────────────► │ Backend Service │ -│ (Repos + Topics)│ │ (Go, net/http) │ -└─────────────────┘ └──────────┬───────────┘ - │ - ┌──────────▼───────────┐ - │ PostgreSQL DB │ - │ (Repos, Issues, │ - │ Milestones, Cache) │ - └──────────┬───────────┘ - │ - ┌──────────▼───────────┐ - │ Frontend │ - │ (SvelteKit) │ - └──────────────────────┘ - ``` - ## 🖥️ Frontend: SvelteKit +## 🖥️ Frontend: SvelteKit - **Why SvelteKit?** +**Why SvelteKit?** - - Lightweight and fast – ideal for an internal dashboard - - Server-Side Rendering (SSR) out of the box – no flickering on load - - Simple reactivity without overhead - - Perfect for data-driven dashboards with real-time updates via SSE or WebSocket +- Lightweight and fast – ideal for an internal dashboard +- Server-Side Rendering (SSR) out of the box – no flickering on load +- Simple reactivity without overhead +- Perfect for data-driven dashboards with real-time updates via SSE or WebSocket - **Frontend features:** +**Frontend features:** - - Project cards with repo name, description, last commit, open issues - - Filter function by topics, language, activity - - Detail view: edit issues & milestones directly in the dashboard (bi-directional) - - Live updates via webhook events (Server-Sent Events) - - Dark mode, responsive design +- Project cards with repo name, description, last commit, open issues +- Filter function by topics, language, activity +- Detail view: edit issues & milestones directly in the dashboard (bi-directional) +- Live updates via webhook events (Server-Sent Events) +- Dark mode, responsive design - ## ⚙️ Backend: Go (net/http + pgx) +## ⚙️ Backend: Go (net/http + pgx) - Go is an excellent backend language – the standard library is so complete that no web framework is needed. `net/http` provides everything required: routing, handlers, middleware. The result is a dependency-light, readable codebase. +Go is an excellent backend language – the standard library is so complete that no web framework is needed. `net/http` provides everything required: routing, handlers, middleware. The result is a dependency-light, readable codebase. - **Why no framework?** +**Why no framework?** - - `net/http` from the standard library is fully sufficient for ~6 endpoints - - No framework overhead, no breaking changes from external dependencies - - The Go-typical approach: explicit, simple, readable - - Compiles to a single static binary – minimal Docker footprint +- `net/http` from the standard library is fully sufficient for ~6 endpoints +- No framework overhead, no breaking changes from external dependencies +- The Go-typical approach: explicit, simple, readable +- Compiles to a single static binary – minimal Docker footprint - **External dependencies (minimal):** +**External dependencies (minimal):** - - `pgx` – PostgreSQL driver (direct SQL, no ORM) - - `godotenv` – load `.env` file - - `golang.org/x/oauth2` – OAuth2 flow for Gitea login +- `pgx` – PostgreSQL driver (direct SQL, no ORM) +- `godotenv` – load `.env` file +- `golang.org/x/oauth2` – OAuth2 flow for Gitea login - **Backend tasks:** +**Backend tasks:** - - `GET /api/projects` – return all tagged repos from the DB - - `POST /api/webhook` – Gitea webhook listener for push, issue, tag events - - `GET /api/projects/{id}/issues` – fetch issues for a repo live from Gitea - - Background goroutine: query Gitea API every 5 minutes for repos with tag `dashboard` - - Cache repo data in PostgreSQL (incl. topics, last activity, issue count) +- `GET /api/projects` – return all tagged repos from the DB +- `POST /api/webhook` – Gitea webhook listener for push, issue, tag events +- `GET /api/projects/{id}/issues` – fetch issues for a repo live from Gitea +- Background goroutine: query Gitea API every 5 minutes for repos with tag `dashboard` +- Cache repo data in PostgreSQL (incl. topics, last activity, issue count) - **Example – HTTP server without a framework:** +**Example – HTTP server without a framework:** - ```go - mux := http.NewServeMux() - mux.HandleFunc("GET /api/projects", h.listProjects) - mux.HandleFunc("POST /api/webhook", h.handleWebhook) - mux.HandleFunc("GET /api/projects/{id}/issues", h.listIssues) +```go +mux := http.NewServeMux() +mux.HandleFunc("GET /api/projects", h.listProjects) +mux.HandleFunc("POST /api/webhook", h.handleWebhook) +mux.HandleFunc("GET /api/projects/{id}/issues", h.listIssues) - log.Fatal(http.ListenAndServe(":8080", mux)) - ``` +log.Fatal(http.ListenAndServe(":8080", mux)) +``` - ## 🔐 Auth: Gitea OAuth2 +## 🔐 Auth: Gitea OAuth2 - Gitea can act as its own OAuth2 provider – users log into the dashboard with their Gitea account, just like "Login with GitHub". +Gitea can act as its own OAuth2 provider – users log into the dashboard with their Gitea account, just like "Login with GitHub". - **Setup in Gitea:** - 1. In Gitea under **Settings → Applications → OAuth2 Applications**, register a new app - 2. Enter Client ID and Client Secret in the `.env` file - 3. Set the Redirect URI to `https://dashboard.example.com/auth/callback` +**Setup in Gitea:** +1. In Gitea under **Settings → Applications → OAuth2 Applications**, register a new app +2. Enter Client ID and Client Secret in the `.env` file +3. Set the Redirect URI to `https://dashboard.example.com/auth/callback` - **Flow:** - - User clicks "Login with Gitea" - - → Redirect to Gitea instance (Authorization Endpoint) - - → User confirms access - - → Gitea redirects back with Authorization Code - - → Backend exchanges code for Access Token - - → User is logged in, Gitea identity is known +**Flow:** +- User clicks "Login with Gitea" +- → Redirect to Gitea instance (Authorization Endpoint) +- → User confirms access +- → Gitea redirects back with Authorization Code +- → Backend exchanges code for Access Token +- → User is logged in, Gitea identity is known - **Advantages:** +**Advantages:** - - No custom auth system needed – Gitea handles passwords and sessions - - User identity directly available → repos and issues can be filtered per user - - Write permissions (create/close issues) only for the respective repo owner - - Implemented with `golang.org/x/oauth2` – official Go package, no third-party lib needed +- No custom auth system needed – Gitea handles passwords and sessions +- User identity directly available → repos and issues can be filtered per user +- Write permissions (create/close issues) only for the respective repo owner +- Implemented with `golang.org/x/oauth2` – official Go package, no third-party lib needed - ## 🗄️ Database: PostgreSQL +## 🗄️ Database: PostgreSQL - **Schema overview:** +**Schema overview:** - ```sql - -- Cached repo information - CREATE TABLE projects ( - id SERIAL PRIMARY KEY, - gitea_id INTEGER UNIQUE NOT NULL, - name VARCHAR(255) NOT NULL, - full_name VARCHAR(255) NOT NULL, - description TEXT, - html_url TEXT, - topics TEXT[], -- e.g. ["dashboard", "freelancer"] - language VARCHAR(100), - open_issues INTEGER DEFAULT 0, - last_push TIMESTAMPTZ, - is_private BOOLEAN DEFAULT false, - synced_at TIMESTAMPTZ DEFAULT NOW() - ); +```sql +-- Cached repo information +CREATE TABLE projects ( + id SERIAL PRIMARY KEY, + gitea_id INTEGER UNIQUE NOT NULL, + name VARCHAR(255) NOT NULL, + full_name VARCHAR(255) NOT NULL, + description TEXT, + html_url TEXT, + topics TEXT[], -- e.g. ["dashboard", "freelancer"] + language VARCHAR(100), + open_issues INTEGER DEFAULT 0, + last_push TIMESTAMPTZ, + is_private BOOLEAN DEFAULT false, + synced_at TIMESTAMPTZ DEFAULT NOW() +); - -- Managed issues / tasks - CREATE TABLE issues ( - id SERIAL PRIMARY KEY, - gitea_id INTEGER NOT NULL, - project_id INTEGER REFERENCES projects(id), - title TEXT NOT NULL, - state VARCHAR(20), -- open / closed - assignee VARCHAR(100), - milestone TEXT, - updated_at TIMESTAMPTZ - ); +-- Managed issues / tasks +CREATE TABLE issues ( + id SERIAL PRIMARY KEY, + gitea_id INTEGER NOT NULL, + project_id INTEGER REFERENCES projects(id), + title TEXT NOT NULL, + state VARCHAR(20), -- open / closed + assignee VARCHAR(100), + milestone TEXT, + updated_at TIMESTAMPTZ +); - -- Webhook event log - CREATE TABLE webhook_events ( - id SERIAL PRIMARY KEY, - event_type VARCHAR(50), - payload JSONB, - received_at TIMESTAMPTZ DEFAULT NOW() - ); - ``` +-- Webhook event log +CREATE TABLE webhook_events ( + id SERIAL PRIMARY KEY, + event_type VARCHAR(50), + payload JSONB, + received_at TIMESTAMPTZ DEFAULT NOW() +); +``` - ## 🚀 Roadmap - - v0.1 – Repo listing via tag `dashboard`, polling every 5 min - - v0.2 – Webhook listener for real-time updates - - v0.3 – Display issues & milestones in the dashboard - - v0.4 – Create/close issues directly from the dashboard (bi-directional) - - v0.5 – Gitea OAuth2 login - - v0.6 – Integration with freelancer dashboard (repos = projects) - - v1.0 – Multi-user, public project pages +## 🚀 Roadmap +- v0.1 – Repo listing via tag `dashboard`, polling every 5 min +- v0.2 – Webhook listener for real-time updates +- v0.3 – Display issues & milestones in the dashboard +- v0.4 – Create/close issues directly from the dashboard (bi-directional) +- v0.5 – Gitea OAuth2 login +- v0.6 – Integration with freelancer dashboard (repos = projects) +- v1.0 – Multi-user, public project pages - ## 🔧 Tech Stack +## 🔧 Tech Stack - | Layer | Technology | - |----------|-------------------------------------| - | Frontend | SvelteKit + TailwindCSS | - | Backend | Go + net/http (standard lib) | - | Database | PostgreSQL + pgx | - | Auth | Gitea OAuth2 + golang.org/x/oauth2 | - | API | Gitea REST API v1 | - | Deploy | Docker Compose | +| Layer | Technology | +|----------|-------------------------------------| +| Frontend | SvelteKit + TailwindCSS | +| Backend | Go + net/http (standard lib) | +| Database | PostgreSQL + pgx | +| Auth | Gitea OAuth2 + golang.org/x/oauth2 | +| API | Gitea REST API v1 | +| Deploy | Docker Compose | - ## 📦 Getting Started +## 📦 Getting Started - ```bash - # Clone the repo - git clone https://gitea.starfour.de/Jannis/gitea-projekt-dashboard +```bash +# Clone the repo +git clone https://gitea.starfour.de/Jannis/gitea-projekt-dashboard - # Set environment variables - cp .env.example .env - # Fill in GITEA_URL, GITEA_TOKEN, GITEA_CLIENT_ID, GITEA_CLIENT_SECRET, DATABASE_URL, DASHBOARD_TAG +# Set environment variables +cp .env.example .env +# Fill in GITEA_URL, GITEA_TOKEN, GITEA_CLIENT_ID, GITEA_CLIENT_SECRET, DATABASE_URL, DASHBOARD_TAG - # Start with Docker - docker compose up -d - ``` +# Start with Docker +docker compose up -d +``` - This project is part of the personal project ideas collection. Related overview repo: [projekt-ideen](https://gitea.starfour.de/Jannis/projekt-ideen) \ No newline at end of file +This project is part of the personal project ideas collection. Related overview repo: [projekt-ideen](https://gitea.starfour.de/Jannis/projekt-ideen) \ No newline at end of file