mirror of
https://github.com/yanislav-igonin/micrach
synced 2026-07-27 05:14:17 +03:00
docs: expand repository and setup guides
This commit is contained in:
parent
e28cc97465
commit
e3026e99f4
174
AGENTS.md
174
AGENTS.md
@ -1,28 +1,166 @@
|
|||||||
# Repository Guidelines
|
# AGENTS.md
|
||||||
|
|
||||||
## Project Structure & Module Organization
|
Guidance for coding agents working in this repository. Keep changes focused,
|
||||||
|
preserve existing behavior unless the task explicitly changes it, and verify
|
||||||
|
all claims with fresh commands.
|
||||||
|
|
||||||
`main.go` wires the Fiber application, middleware, routes, database startup, and template engine. Keep HTTP handlers in `controllers/`, persistence logic and data types in `repositories/`, database setup in `db/`, and environment parsing in `config/`. Gateway integration belongs in `gateway/`; shared helpers live in `utils/` and `files/`. Server-rendered HTML is organized under `templates/{pages,components,head}`, while browser assets live in `static/`. Add ordered PostgreSQL changes to `migrations/` using the existing `<number>-<description>.sql` pattern. Load-testing scripts belong in `tests/`.
|
## Project Overview
|
||||||
|
|
||||||
## Build, Test, and Development Commands
|
micrach is a small, server-rendered, single-board imageboard. It uses Go,
|
||||||
|
Fiber v2, Fiber HTML templates, PostgreSQL through `pgx`, and filesystem-backed
|
||||||
|
image uploads. It intentionally uses little browser-side JavaScript.
|
||||||
|
|
||||||
- `cp .env.example .env` creates local configuration; adjust `POSTGRES_URL` before starting.
|
The service supports thread creation, replies, JPEG/PNG attachments,
|
||||||
- `go run .` starts the service and applies migrations against the configured PostgreSQL database.
|
thumbnails, CAPTCHA, rate limiting, pagination, bump limits, `sage`, thread
|
||||||
- `make dev` runs the app through `nodemon` for automatic restarts.
|
archival, and optional external gateway registration.
|
||||||
- `go build .` produces the local `micrach` binary.
|
|
||||||
- `GO111MODULE=on CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build .` matches the CI Linux build.
|
|
||||||
- `go test ./...` runs all Go tests.
|
|
||||||
- `go vet ./...` performs standard static checks.
|
|
||||||
- `sh tests/load.sh` runs the optional Vegeta load test; review its target URL first.
|
|
||||||
|
|
||||||
## Coding Style & Naming Conventions
|
## Repository Map
|
||||||
|
|
||||||
Use `gofmt` (tabs for Go indentation) and run `go fmt ./...` before submitting. Keep package names short and lowercase. Use `PascalCase` for exported identifiers, `camelCase` for unexported identifiers, and descriptive handler names such as `CreateThread`. Keep controllers thin: validation and HTTP concerns stay in handlers, while SQL and persistence behavior stay in repositories. Follow existing kebab-case names for CSS, templates, and migration descriptions.
|
- `main.go`: application startup, middleware, static mounts, routes, and server.
|
||||||
|
- `controllers/`: Fiber handlers, request parsing, HTTP responses, and form flow.
|
||||||
|
- `repositories/`: SQL queries, persistence types, and template view data.
|
||||||
|
- `db/`: PostgreSQL pool initialization and startup migration runner.
|
||||||
|
- `config/`: environment parsing and defaults.
|
||||||
|
- `gateway/`: optional gateway registration and authenticated ping endpoint.
|
||||||
|
- `utils/`: post validation, upload directories, and image thumbnail handling.
|
||||||
|
- `files/`: shared filesystem read helpers.
|
||||||
|
- `build/`: production CSS cache-busting rewrite.
|
||||||
|
- `templates/{pages,components,head}`: server-rendered HTML.
|
||||||
|
- `static/`: checked-in CSS, icons, and error images.
|
||||||
|
- `uploads/`: generated runtime files; ignored by Git and never commit them.
|
||||||
|
- `migrations/`: ordered PostgreSQL changes named `<number>-<description>.sql`.
|
||||||
|
- `tests/`: optional Vegeta load test, not the unit-test suite.
|
||||||
|
|
||||||
## Testing Guidelines
|
## Runtime Flow and Routes
|
||||||
|
|
||||||
The repository currently has no unit tests or enforced coverage threshold. Add tests beside the code as `*_test.go`, using `TestXxx` and table-driven cases where practical. Avoid shared production databases; isolate repository tests with disposable test data or a dedicated database. Run `go test ./...` and `go vet ./...` for every change. Use Vegeta only for explicit performance work.
|
Startup loads `.env`, initializes configuration and the DB pool, applies
|
||||||
|
missing migrations, optionally seeds data, performs production CSS rewriting,
|
||||||
|
creates `uploads/`, then starts Fiber.
|
||||||
|
|
||||||
## Commit & Pull Request Guidelines
|
| Method | Path | Handler / purpose |
|
||||||
|
| --- | --- | --- |
|
||||||
|
| `GET` | `/` | Render paginated thread catalog. |
|
||||||
|
| `POST` | `/` | Validate and create a thread. |
|
||||||
|
| `GET` | `/:threadID` | Render one thread and its replies. |
|
||||||
|
| `POST` | `/:threadID` | Validate and add a reply. |
|
||||||
|
| `GET` | `/captcha/:captchaID` | Render CAPTCHA PNG. |
|
||||||
|
| `GET` | `/api/ping` | Gateway health endpoint; registered only when `GATEWAY_URL` is set. |
|
||||||
|
|
||||||
History mixes terse imperative subjects with `feat:` and `fix:` prefixes. Prefer focused Conventional Commit subjects, for example `fix: reject oversized uploads`. Keep each commit buildable. Pull requests should explain behavior changes, configuration or migration impact, and verification commands. Link relevant issues and include screenshots for template or CSS changes. Never commit `.env`, uploads, generated load-test artifacts, or credentials.
|
Static content is served from `/static`; generated files are served from
|
||||||
|
`/uploads`. Thread and reply creation spans PostgreSQL plus filesystem writes,
|
||||||
|
so review both paths when changing upload behavior.
|
||||||
|
|
||||||
|
## Local Setup and Commands
|
||||||
|
|
||||||
|
Create a PostgreSQL database, then:
|
||||||
|
|
||||||
|
```sh
|
||||||
|
cp .env.example .env
|
||||||
|
# Edit POSTGRES_URL and normally set IS_DB_SEEDED=false.
|
||||||
|
go run .
|
||||||
|
```
|
||||||
|
|
||||||
|
Common checks:
|
||||||
|
|
||||||
|
```sh
|
||||||
|
go fmt ./...
|
||||||
|
go test ./...
|
||||||
|
go vet ./...
|
||||||
|
go build .
|
||||||
|
GO111MODULE=on CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build .
|
||||||
|
```
|
||||||
|
|
||||||
|
`make dev` requires `nodemon`. `sh tests/load.sh` requires Vegeta and targets a
|
||||||
|
historical public URL by default; change the target to a controlled environment
|
||||||
|
before use. Do not run the load test as routine verification.
|
||||||
|
|
||||||
|
The module declares Go 1.15 and CI installs Go 1.17. Avoid language or standard
|
||||||
|
library features newer than Go 1.17 unless the task also upgrades the supported
|
||||||
|
Go version and CI configuration.
|
||||||
|
|
||||||
|
## Configuration and Generated State
|
||||||
|
|
||||||
|
- `.env` is local and must never be committed.
|
||||||
|
- `POSTGRES_URL` selects the database; startup applies migrations automatically.
|
||||||
|
- `IS_DB_SEEDED=true` adds sample data on every startup, not only once.
|
||||||
|
- `ENV=production` renames CSS files and rewrites templates in place at startup.
|
||||||
|
Do not use this mode in a development checkout unless that mutation is wanted.
|
||||||
|
- `GATEWAY_URL=""` disables gateway routes and registration.
|
||||||
|
- Uploads are limited to four JPEG/PNG files, 3 MiB each. Titles allow 100
|
||||||
|
runes; post text allows 1,000 runes.
|
||||||
|
- Runtime uploads, built binaries, `.env`, and load-test artifacts are ignored
|
||||||
|
and must remain untracked.
|
||||||
|
|
||||||
|
## Architecture and Coding Conventions
|
||||||
|
|
||||||
|
- Keep handlers thin: HTTP parsing/status/rendering in `controllers/`; SQL and
|
||||||
|
persistence behavior in `repositories/`.
|
||||||
|
- Keep DB startup and migration mechanics in `db/`, environment parsing in
|
||||||
|
`config/`, gateway behavior in `gateway/`, and reusable helpers in `utils/`
|
||||||
|
or `files/`.
|
||||||
|
- Follow existing package naming: short, lowercase names. Use `PascalCase` for
|
||||||
|
exported identifiers and `camelCase` for unexported identifiers.
|
||||||
|
- Format Go with `gofmt`/`go fmt`; do not hand-format with spaces.
|
||||||
|
- Follow existing kebab-case naming for templates, CSS, and migration
|
||||||
|
descriptions. Preserve current server-rendered approach and minimal-JS goal.
|
||||||
|
- Use parameterized SQL. Keep related DB operations transactional where the
|
||||||
|
existing workflow requires atomicity.
|
||||||
|
- Avoid unrelated refactors. If a task exposes adjacent problems, report them
|
||||||
|
separately unless they block the requested work.
|
||||||
|
|
||||||
|
## Change Guide
|
||||||
|
|
||||||
|
- Route or request behavior: update `main.go` and/or `controllers/`, then cover
|
||||||
|
status codes, redirects, validation errors, and template data.
|
||||||
|
- Persistence behavior: update `repositories/`; add a migration for schema
|
||||||
|
changes rather than editing an already-applied migration.
|
||||||
|
- Schema changes: add the next numeric file in `migrations/`. Keep filename
|
||||||
|
shape exactly `<number>-<description>.sql`; the runner parses it directly.
|
||||||
|
- Page or component changes: edit `templates/` and matching `static/styles/`.
|
||||||
|
Check catalog, thread, error, empty, and pagination states as relevant.
|
||||||
|
- Upload changes: inspect controller transaction flow, `utils/`, repository file
|
||||||
|
records, original/thumbnail paths, validation limits, and cleanup behavior.
|
||||||
|
- Config changes: update `config/config.go`, `.env.example`, README config table,
|
||||||
|
and deployment environment forwarding together.
|
||||||
|
- Deployment changes: note that `Dockerfile` expects a prebuilt Linux binary and
|
||||||
|
`docker-compose.yml` assumes Swarm, Traefik, an external network, and a
|
||||||
|
persistent host upload mount.
|
||||||
|
|
||||||
|
## Testing Expectations
|
||||||
|
|
||||||
|
There are currently no checked-in Go unit tests and no coverage threshold. Add
|
||||||
|
`*_test.go` files beside changed code, use `TestXxx`, and prefer table-driven
|
||||||
|
cases when practical. Repository tests must use disposable test data or a
|
||||||
|
dedicated database, never a shared production database.
|
||||||
|
|
||||||
|
Minimum verification for code changes:
|
||||||
|
|
||||||
|
1. Run `go fmt ./...` and review the resulting diff.
|
||||||
|
2. Run `go test ./...`.
|
||||||
|
3. Run `go vet ./...`.
|
||||||
|
4. Run `go build .` (or the Linux CI build for deployment-sensitive work).
|
||||||
|
5. For templates/CSS, start the app and manually inspect affected responsive
|
||||||
|
states; include screenshots in the PR.
|
||||||
|
|
||||||
|
For documentation-only changes, inspect the rendered Markdown, verify all local
|
||||||
|
links and commands against the repository, and review `git diff --check`.
|
||||||
|
|
||||||
|
## Git, Commits, and Pull Requests
|
||||||
|
|
||||||
|
- Inspect `git status` before editing. Preserve user changes and unrelated files.
|
||||||
|
- Never commit `.env`, credentials, uploads, binaries, or generated load-test
|
||||||
|
outputs.
|
||||||
|
- Prefer focused Conventional Commit subjects, such as
|
||||||
|
`fix: reject oversized uploads` or `docs: expand setup guide`.
|
||||||
|
- Keep each commit buildable. Do not rewrite history or discard local changes
|
||||||
|
unless explicitly requested.
|
||||||
|
- PRs should describe behavior, config/migration impact, verification commands,
|
||||||
|
linked issues, and screenshots for UI changes.
|
||||||
|
|
||||||
|
## Agent Completion Checklist
|
||||||
|
|
||||||
|
- Requested scope is fully addressed; unrelated behavior is untouched.
|
||||||
|
- New behavior has tests where practical.
|
||||||
|
- Documentation and `.env.example` match config/code changes.
|
||||||
|
- No secret, upload, binary, or generated artifact is included.
|
||||||
|
- Fresh verification commands pass, and final report names commands actually run.
|
||||||
|
|||||||
147
README.md
147
README.md
@ -1,27 +1,140 @@
|
|||||||
# micrach
|
# micrach
|
||||||
Go tryout. Single board imageboard.
|
|
||||||
|
|
||||||
UPD: stopped the service from the link above, too much shit posted from TOR, don't have time to moderate :(
|
micrach is a small, server-rendered imageboard written in Go. It provides one
|
||||||
|
board where visitors can create threads, reply with text or images, bump or
|
||||||
|
`sage` threads, and browse the thread catalog without a client-side SPA.
|
||||||
|
|
||||||
## Motivation
|
The project began as a Go learning project and as an experiment in building a
|
||||||
Tired of a fucking SPAs, so I decided to write this simple and lightweight imageboard (microboard, actually) with as less JS as possible.
|
lightweight imageboard with very little JavaScript. The former public instance
|
||||||
Also, I wanted to learn Go, so I decided to write this in Go.
|
is offline because it required more moderation than the maintainer could
|
||||||
|
provide; the source remains available for local use and development.
|
||||||
|
|
||||||
Maybe I'll add an api and create a SPA with the Next.js framework in the future, but right now I'm trying to make this as simple as possible.
|
## Features
|
||||||
|
|
||||||
## Prerequisites
|
- Server-rendered HTML using Fiber templates
|
||||||
1. Go 1.13+.
|
- Thread creation, replies, catalog pagination, bump limits, and `sage`
|
||||||
2. PostgreSQL.
|
- JPEG and PNG uploads with generated thumbnails
|
||||||
3. Create `.env` file from `.env.example`, change env vars to your needs.
|
- Optional CAPTCHA and request rate limiting
|
||||||
4. Create db with the name that is specified in `.env` file in `POSTGRES_URL` env var.
|
- Automatic PostgreSQL migrations on startup
|
||||||
|
- Automatic archival when the active-thread limit is reached
|
||||||
|
- Optional registration with an external board gateway
|
||||||
|
|
||||||
|
## Stack
|
||||||
|
|
||||||
|
- Go (the module declares Go 1.15; CI builds with Go 1.17)
|
||||||
|
- [Fiber v2](https://github.com/gofiber/fiber)
|
||||||
|
- PostgreSQL via `pgx`
|
||||||
|
- Plain HTML templates and CSS
|
||||||
|
|
||||||
|
## Run locally
|
||||||
|
|
||||||
|
### Prerequisites
|
||||||
|
|
||||||
|
- Go 1.17 or newer
|
||||||
|
- PostgreSQL
|
||||||
|
- A PostgreSQL database that the configured user can create tables in
|
||||||
|
|
||||||
|
### Setup
|
||||||
|
|
||||||
|
1. Create the database. With standard local PostgreSQL tooling:
|
||||||
|
|
||||||
## Run
|
|
||||||
Just run:
|
|
||||||
```sh
|
```sh
|
||||||
go run main.go
|
createdb micrach
|
||||||
```
|
```
|
||||||
|
|
||||||
**In development** I prefer to run it with [nodemon](https://github.com/remy/nodemon) for live reload.
|
2. Copy the example configuration:
|
||||||
|
|
||||||
## How it looks
|
```sh
|
||||||

|
cp .env.example .env
|
||||||
|
```
|
||||||
|
|
||||||
|
3. Edit `.env`. At minimum, make `POSTGRES_URL` match your local database.
|
||||||
|
For normal development, set `IS_DB_SEEDED=false`; when true, sample rows are
|
||||||
|
inserted every time the application starts.
|
||||||
|
|
||||||
|
4. Start the application from the repository root:
|
||||||
|
|
||||||
|
```sh
|
||||||
|
go run .
|
||||||
|
```
|
||||||
|
|
||||||
|
5. Open [http://localhost:3000](http://localhost:3000), or the port configured
|
||||||
|
by `PORT`.
|
||||||
|
|
||||||
|
Startup connects to PostgreSQL, applies missing files from `migrations/`, and
|
||||||
|
creates the ignored local `uploads/` directory. Uploaded originals and
|
||||||
|
thumbnails are stored on disk, so keep that directory persistent when running
|
||||||
|
the service in a container.
|
||||||
|
|
||||||
|
## Configuration
|
||||||
|
|
||||||
|
`.env` is loaded automatically and is ignored by Git.
|
||||||
|
|
||||||
|
| Variable | Default in code | Purpose |
|
||||||
|
| --- | --- | --- |
|
||||||
|
| `ENV` | `release` | Runtime mode. `production` enables CSS filename rewriting at startup. |
|
||||||
|
| `PORT` | `3000` | HTTP listen port. |
|
||||||
|
| `POSTGRES_URL` | `postgresql://localhost/micrach` | PostgreSQL connection URL. |
|
||||||
|
| `IS_DB_SEEDED` | `false` | Insert sample posts at startup. Avoid enabling repeatedly. |
|
||||||
|
| `IS_RATE_LIMITER_ENABLED` | `true` | Enable Fiber request limiting. |
|
||||||
|
| `THREADS_MAX_COUNT` | `50` | Maximum active threads before old threads are archived. |
|
||||||
|
| `THREAD_BUMP_LIMIT` | `500` | Reply count after which a thread no longer bumps. |
|
||||||
|
| `IS_CAPTCHA_ACTIVE` | `true` | Require CAPTCHA for new threads and replies. |
|
||||||
|
| `GATEWAY_URL` | empty | External gateway base URL. Empty disables gateway integration. |
|
||||||
|
| `GATEWAY_API_KEY` | empty | Shared key used for gateway registration and `/api/ping`. |
|
||||||
|
| `GATEWAY_BOARD_ID` | empty | Board identifier sent to the gateway. |
|
||||||
|
| `GATEWAY_BOARD_URL` | empty | Parsed from the environment but not currently used by the gateway client. |
|
||||||
|
| `GATEWAY_BOARD_DESCRIPTION` | empty | Board description sent to the gateway. |
|
||||||
|
|
||||||
|
See [.env.example](.env.example) for a complete example.
|
||||||
|
|
||||||
|
## Development commands
|
||||||
|
|
||||||
|
```sh
|
||||||
|
# Run with automatic restart; requires nodemon.
|
||||||
|
make dev
|
||||||
|
|
||||||
|
# Format, test, vet, and build.
|
||||||
|
go fmt ./...
|
||||||
|
go test ./...
|
||||||
|
go vet ./...
|
||||||
|
go build .
|
||||||
|
|
||||||
|
# Reproduce the Linux CI build.
|
||||||
|
GO111MODULE=on CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build .
|
||||||
|
```
|
||||||
|
|
||||||
|
`tests/load.sh` is an optional Vegeta load test. Its checked-in target is a
|
||||||
|
historical public URL, so change it to an environment you own before running
|
||||||
|
the script. Generated load-test files are ignored by Git.
|
||||||
|
|
||||||
|
## Containers and deployment
|
||||||
|
|
||||||
|
The `Dockerfile` packages a prebuilt `micrach` binary together with templates,
|
||||||
|
static assets, and migrations. Build the Linux binary before building the
|
||||||
|
image. The checked-in `docker-compose.yml` is production-oriented: it expects
|
||||||
|
Docker Swarm, an existing `web` overlay network, Traefik, a published image,
|
||||||
|
and host-mounted upload storage. It is not a standalone local PostgreSQL setup.
|
||||||
|
|
||||||
|
## Project layout
|
||||||
|
|
||||||
|
```text
|
||||||
|
controllers/ HTTP handlers and request validation flow
|
||||||
|
repositories/ PostgreSQL queries and view data types
|
||||||
|
db/ connection pool and migration runner
|
||||||
|
config/ environment parsing
|
||||||
|
gateway/ optional external gateway integration
|
||||||
|
templates/ server-rendered pages, components, and head fragments
|
||||||
|
static/ CSS, icons, and error images
|
||||||
|
uploads/ runtime uploads (created locally, ignored by Git)
|
||||||
|
migrations/ ordered PostgreSQL schema changes
|
||||||
|
tests/ optional load-test scripts
|
||||||
|
```
|
||||||
|
|
||||||
|
## Screenshot
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
## License
|
||||||
|
|
||||||
|
[MIT](LICENSE)
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user