Status: RETIRED.
GLG ran as a live URL shortener and link-analytics service from June to August 2026. The backend has been shut down; the code stays public as a reference. Short links issued during that period no longer resolve.
It started as a question — how much throughput can you get out of a single Spring Boot instance on a $6 droplet before you need anything fancier? — and turned into a product that real people used for a couple of months.
Users signed in with Google, shortened URLs (with optional custom slugs and QR codes), and got per-link analytics: clicks over time, referrer, country/city, device and browser breakdown, and unique-visitor estimates.
| Redirects served | 22,000+ |
| Short links created | 550+ |
| Registered users | 500+ |
| Site views | 27,000+ |
| p99 redirect latency | < 100 ms |
| Time in production | ~2 months |
Launched on Peerlist (#9 of 100+ products in Week 26) and Product Hunt.
The interesting constraint was that a redirect is a read-heavy, latency-critical path, while analytics is a write-heavy, latency-tolerant one. Almost every design decision falls out of separating those two.
Redirect path (hot)
- Slug → destination lookups served from a 10,000-entry Caffeine cache, so the common case never touches Postgres.
- Host-based routing filter (
HostBasedRoutingFilter) lets the short domain and the app domain share one deployment. - Bucket4j rate limiting in front of both the redirect and the create endpoints.
Analytics path (cold)
- Click events are pushed onto an in-memory queue (30,000-event capacity) and never block the redirect response.
- A scheduled drain runs every 3 seconds, map/reduces the batch by link and dimension, and writes it back as batched upserts — so a burst of clicks on one link collapses into a handful of statements instead of thousands of inserts.
- Enrichment (MaxMind GeoLite2 geolocation, user-agent parsing) happens on a virtual-thread executor off the request path.
- Visitor identity is a murmur3 hash of a request fingerprint — enough for unique-visitor counts, no cookies, nothing that identifies a person.
Auth and storage
- Supabase auth with Google SSO; ES256-signed JWTs verified in-process.
- Postgres for links, users, and rolled-up analytics; QR configuration stored as validated JSONB.
- ZeptoMail as custom SMTP once the default free-tier send limits became the bottleneck.
Deployment
- Spring Boot on a DigitalOcean droplet behind Caddy (automatic TLS), frontend on Cloudflare Pages.
Architecture diagrams live in the backend repo.
| Repo | What it is |
|---|---|
glg-backend |
Java / Spring Boot API — redirects, auth, analytics ingestion, QR generation |
glg-frontend |
Dashboard and landing page |
glg-extension |
Browser extension for one-click shortening |
Built by @shreyasnandurkar and @sathwikhbhat.
Backend is MIT licensed — fork it, take the ingestion pattern, do something better with it.
