# Gitea Mobile A mobile-first Progressive Web App (PWA) for managing Gitea issues and pull requests across multiple repositories and organizations from an iPhone. Built with Go, HTMX, and hand-rolled CSS -- no JavaScript frameworks, no build step, no node_modules. ## Tech Stack | Layer | Choice | |-------|--------| | Backend | Go + Gitea SDK (`code.gitea.io/sdk/gitea`) | | Frontend | HTMX + Go `html/template` + hand-rolled CSS | | Container | Multi-stage Dockerfile -> distroless (~15MB) | | Deployment | Kustomize manifests + FluxCD GitOps | ## Project Structure ``` / ├── cmd/server/main.go # entrypoint ├── internal/ │ ├── config/config.go # env-based configuration │ ├── gitea/client.go # Gitea SDK wrapper / aggregation layer │ ├── handlers/ # HTTP handlers (issues, PRs, triage, settings) │ ├── auth/ # cookie-based token auth │ ├── middleware/ # auth middleware, logging │ └── templates/ # Go html/template files (for HTMX) ├── static/ # CSS, JS (htmx.min.js), icons, manifest ├── .gitea/workflows/build.yaml # CI pipeline (Gitea Actions) ├── Dockerfile ├── flake.nix # Nix dev shell with Go + air └── go.mod ``` ## Local Development ### Prerequisites - [Nix](https://nixos.org/download/) with flakes enabled, **or** Go 1.22+ - A Gitea instance with an API token ### Quick Start ```bash # Enter the Nix dev shell (provides Go, gopls, air) nix develop # Set required environment variables export GITEA_URL=https://gitea.leeworks.dev export SESSION_SECRET=$(openssl rand -hex 32) # Optional: set a default API token export GITEA_TOKEN=your-gitea-api-token # Start the server with live reload air ``` If you are not using Nix, install Go 1.22+ and [air](https://github.com/air-verse/air) manually, then run the same commands above starting from the export lines. ### Environment Variables | Variable | Required | Default | Description | |----------|----------|---------|-------------| | `GITEA_URL` | Yes | -- | Base URL of the Gitea instance | | `SESSION_SECRET` | Yes | -- | HMAC key for signing session cookies (min 32 chars) | | `GITEA_TOKEN` | No | -- | Default API token (users can set their own via the settings page) | | `LISTEN_ADDR` | No | `:8080` | Server listen address | ### Live Reload with Air The dev shell includes [air](https://github.com/air-verse/air) for automatic recompilation on file changes. Configuration is in `.air.toml`. Air watches `.go` and `.html` files under `cmd/`, `internal/`, and `static/` and rebuilds/restarts the server automatically. ## Running Tests ```bash # Run all tests go test ./... # Run tests with race detection go test -race ./... ``` ## Building the Container ```bash # Build the Docker image docker build -t gitea-mobile . # Run locally docker run -p 8080:8080 \ -e GITEA_URL=https://gitea.leeworks.dev \ -e SESSION_SECRET=$(openssl rand -hex 32) \ gitea-mobile ``` The Dockerfile uses a multi-stage build: Go binary compiled in an Alpine builder stage, then copied into a distroless image (~15MB final size). ## Deployment Kubernetes manifests for this app live in the Talos cluster repo under `testing1/first-cluster/apps/gitea-mobile/`. FluxCD syncs from that repo and handles automated image updates via `ImagePolicy` annotations. Key deployment resources: - `deployment.yaml` -- Pod spec with health checks - `service.yaml` -- ClusterIP service on port 8080 - `ingressroute.yaml` -- Traefik IngressRoute for `gitea-mobile.testing.leeworks.dev` - `kustomization.yaml` -- Kustomize overlay ## Contributing 1. Fork the repository 2. Create a feature branch: `git checkout -b feature/your-feature` 3. Make your changes and add tests 4. Run `go test -race ./...` to verify 5. Commit with a clear message referencing the issue number 6. Push to your fork and open a pull request All PRs target the fork (`leeworks-agents/gitea-mobile`), not the upstream repo.