Monorepo for wisp.place. A static site hosting service built on top of the AT Protocol. wisp.place
96
fork

Configure Feed

Select the types of activity you want to include in your feed.

at redirects 130 lines 3.9 kB view raw view rendered
1# Wisp Hosting Service 2 3Minimal microservice for hosting static sites from the AT Protocol. Built with Hono and Bun. 4 5## Features 6 7- **Custom Domain Hosting**: Serve verified custom domains 8- **Wisp.place Subdomains**: Serve registered `*.wisp.place` subdomains 9- **DNS Hash Routing**: Support DNS verification via `hash.dns.wisp.place` 10- **Direct File Serving**: Access sites via `/s/:identifier/:site/*` (no DB lookup) 11- **Firehose Worker**: Listens to AT Protocol firehose for new `place.wisp.fs` records 12- **Automatic Caching**: Downloads and caches sites locally on first access or firehose event 13- **SSRF Protection**: Hardened fetch with timeout, size limits, and private IP blocking 14 15## Routes 16 171. **Custom Domains** (`/*`) 18 - Serves verified custom domains (example.com) 19 - DB lookup: `custom_domains` table 20 212. **Wisp Subdomains** (`/*.wisp.place/*`) 22 - Serves registered subdomains (alice.wisp.place) 23 - DB lookup: `domains` table 24 253. **DNS Hash Routing** (`/hash.dns.wisp.place/*`) 26 - DNS verification routing for custom domains 27 - DB lookup: `custom_domains` by hash 28 294. **Direct Serving** (`/s.wisp.place/:identifier/:site/*`) 30 - Direct access without DB lookup 31 - `:identifier` can be DID or handle 32 - Fetches from PDS if not cached 33 - **Automatic HTML path rewriting**: Absolute paths (`/style.css`) are rewritten to relative paths (`/s/:identifier/:site/style.css`) 34 35## Setup 36 37```bash 38# Install dependencies 39bun install 40 41# Copy environment file 42cp .env.example .env 43 44# Run in development 45bun run dev 46 47# Run in production 48bun run start 49``` 50 51## Environment Variables 52 53- `DATABASE_URL` - PostgreSQL connection string 54- `PORT` - HTTP server port (default: 3001) 55- `BASE_HOST` - Base domain (default: wisp.place) 56 57## Architecture 58 59- **Hono**: Minimal web framework 60- **Postgres**: Database for domain/site lookups 61- **AT Protocol**: Decentralized storage 62- **Jetstream**: Firehose consumer for real-time updates 63- **Bun**: Runtime and file serving 64 65## Cache Structure 66 67``` 68cache/sites/ 69 did:plc:abc123/ 70 sitename/ 71 index.html 72 style.css 73 assets/ 74 logo.png 75``` 76 77## Health Check 78 79```bash 80curl http://localhost:3001/health 81``` 82 83Returns firehose connection status and last event time. 84 85## HTML Path Rewriting 86 87When serving sites via the `/s/:identifier/:site/*` route, HTML files are automatically processed to rewrite absolute paths to work correctly in the subdirectory context. 88 89**What gets rewritten:** 90- `src` attributes (images, scripts, iframes) 91- `href` attributes (links, stylesheets) 92- `action` attributes (forms) 93- `poster`, `data` attributes (media) 94- `srcset` attributes (responsive images) 95 96**What's preserved:** 97- External URLs (`https://example.com/style.css`) 98- Protocol-relative URLs (`//cdn.example.com/script.js`) 99- Data URIs (`data:image/png;base64,...`) 100- Anchors (`/#section`) 101- Already relative paths (`./style.css`, `../images/logo.png`) 102 103**Example:** 104```html 105<!-- Original HTML --> 106<link rel="stylesheet" href="/style.css"> 107<img src="/images/logo.png"> 108 109<!-- Served at /s/did:plc:abc123/mysite/ becomes --> 110<link rel="stylesheet" href="/s/did:plc:abc123/mysite/style.css"> 111<img src="/s/did:plc:abc123/mysite/images/logo.png"> 112``` 113 114This ensures sites work correctly when served from subdirectories without requiring manual path adjustments. 115 116## Security 117 118### SSRF Protection 119 120All external HTTP requests are protected against Server-Side Request Forgery (SSRF) attacks: 121 122- **5-second timeout** on all requests 123- **Size limits**: 1MB for JSON, 10MB default, 100MB for file blobs 124- **Blocked private IP ranges**: 125 - Loopback (127.0.0.0/8, ::1) 126 - Private networks (10.0.0.0/8, 172.16.0.0/12, 192.168.0.0/16) 127 - Link-local (169.254.0.0/16, fe80::/10) 128 - Cloud metadata endpoints (169.254.169.254) 129- **Protocol validation**: Only HTTP/HTTPS allowed 130- **Streaming with size enforcement**: Prevents memory exhaustion from large responses