forked from retoor/devplacepy
feat: add DiceBear avatar proxy with style picker on signup and profile pages
Implement avatar generation via local proxy at `/avatar/{style}/{seed}` that fetches from DiceBear 9.x API with in-memory caching and fallback to initial-based SVG. Add avatar style selection dropdown to signup form and profile edit page, storing `avatar_style` in user records. Update comment rendering to support nested threading with parent-child relationships in post view. Add `avatar_url` and `avatar_styles` template globals, register avatar router in main app, and include avatar CSS classes for rounded image display.
This commit is contained in:
@@ -0,0 +1,91 @@
|
||||
# DevPlace — The Developer Social Network
|
||||
|
||||
Server-rendered social network for developers. FastAPI backend serving Jinja2 templates with ES6 interactivity. Avatar generation via DiceBear proxy. SQLite storage via `dataset`.
|
||||
|
||||
## Quick start
|
||||
|
||||
```bash
|
||||
make install # pip install -e .
|
||||
make dev # uvicorn --reload on port 10500
|
||||
make test # 95 Playwright integration tests, headless
|
||||
make test-headed # same tests in visible browser
|
||||
make demo # absurd full-journey demo (headed)
|
||||
```
|
||||
|
||||
Open `http://localhost:10500`.
|
||||
|
||||
## Stack
|
||||
|
||||
| Layer | Technology |
|
||||
|-------|-----------|
|
||||
| Backend | Python 3.13+, FastAPI, Uvicorn |
|
||||
| Templates | Jinja2 (server-side rendered) |
|
||||
| Frontend | Pure ES6 JavaScript, one class per file |
|
||||
| Database | SQLite via `dataset` (auto-sync schema, `uid` PKs) |
|
||||
| Auth | Session cookies, SHA256+SALT via passlib |
|
||||
| Avatars | DiceBear 9.x via local proxy (`/avatar/{style}/{seed}`) |
|
||||
| Validation | `hawk` (Python/JS/CSS/HTML) |
|
||||
|
||||
## Project structure
|
||||
|
||||
```
|
||||
devplacepy/
|
||||
main.py # FastAPI app, router registration
|
||||
config.py # Settings from env vars + .env
|
||||
database.py # dataset connection, index creation
|
||||
templating.py # Shared Jinja2 environment + globals
|
||||
avatar.py # DiceBear styles, URL generation
|
||||
utils.py # Password hashing, session mgmt, time_ago
|
||||
models.py # Pydantic schemas (validated but unused in routes)
|
||||
routers/ # One file per domain (auth, feed, posts, ...)
|
||||
templates/ # Jinja2 HTML templates
|
||||
static/css/ # Page-specific CSS files
|
||||
static/js/ # Application.js (ES6 module)
|
||||
```
|
||||
|
||||
## Routes
|
||||
|
||||
| Prefix | Purpose |
|
||||
|--------|---------|
|
||||
| `/auth` | Signup, login, logout |
|
||||
| `/feed` | Post feed with topic/tab filtering |
|
||||
| `/posts` | Post detail, creation |
|
||||
| `/comments` | Comment creation, deletion |
|
||||
| `/projects` | Project listing, creation |
|
||||
| `/profile` | Profile view, editing |
|
||||
| `/messages` | Direct messaging |
|
||||
| `/notifications` | Notification list, mark read |
|
||||
| `/votes` | Upvote/downvote on posts and comments |
|
||||
| `/avatar` | DiceBear avatar proxy with caching |
|
||||
|
||||
## API
|
||||
|
||||
No REST API — everything is form-based POST + redirect. All state lives in the session cookie. Endpoints return HTML or redirect.
|
||||
|
||||
## Configuration
|
||||
|
||||
| Env var | Default | Purpose |
|
||||
|---------|---------|---------|
|
||||
| `DEVPLACE_DATABASE_URL` | `sqlite:///devplace.db` | Database connection string |
|
||||
| `SECRET_KEY` | hardcoded fallback | Session signing key |
|
||||
|
||||
## Testing
|
||||
|
||||
- **95 integration tests** across 9 files using Playwright (NOT pytest-playwright plugin)
|
||||
- Server starts as subprocess on port 10501 with isolated temp database
|
||||
- Test users `alice_test` / `bob_test` seeded via HTTP at session start
|
||||
- Failure screenshots auto-save to `/tmp/devplace_test_screenshots/`
|
||||
- Headed mode: `PLAYWRIGHT_HEADLESS=0 make test`
|
||||
|
||||
## Feature workflow
|
||||
|
||||
1. Implement the feature (router + template + CSS + JS)
|
||||
2. `hawk .` — validate all source files
|
||||
3. `make test` — run all 95 tests headless
|
||||
4. If adding new functionality, write Playwright tests in `tests/test_*.py`
|
||||
5. For visual features, take a screenshot and verify with `falcon describe`
|
||||
6. Update `AGENTS.md` if any new conventions were introduced
|
||||
|
||||
## License
|
||||
|
||||
MIT — DevPlace
|
||||
Reference in New Issue
Block a user