2.5 KiB
2.5 KiB
pllist
Access-based Telegram bot for creating and managing lists of planned purchases.
A user owns lists. A list contains items. Items can be added, marked done, and
reserved by the person responsible for buying them. Items carry an urgency
level. An owner can share a list with other users as a reader or an editor.
Bot access itself is allowlisted: the owner runs /allow and /kick.
The codebase stays small but extensible.
- Architecture:
docs/architecture.md - Infrastructure:
docs/infra.md - MVP plan:
docs/roadmap-mvp.md - Other notes:
docs/temp-*.md
Stack
- Go 1.27
github.com/mymmrac/telegofor the Telegram Bot API, long polling- GORM with PostgreSQL
github.com/joho/godotenvfor local environment loading- Docker Compose for local development
- Gitea for version control and CI, Dokploy for deployment
Commands
cp .env.example .env # fill values
make build # build bin/bot
make run # run bin/bot
go test ./... # unit tests
go vet ./... # static checks
gofmt -l . # formatting check
Engineering rules
- Use constructor injection. Build concrete types in
cmd/bot/main.goand pass dependencies down. No package-level globals and noinit()side effects. - Define small interfaces where they are consumed, not next to the implementation.
- Keep business rules in
internal/domainandinternal/service. Handlers parse input and render output only. - Route every list operation through one authorization function. Do not reimplement access checks in handlers or repositories.
- Implement item changes as domain methods (
Reserve,Release,Complete,Reopen,SetUrgency). Do not assign state fields from handlers. - Apply DRY to behavior: one callback-data codec, one keyboard builder per view, one error-to-message mapper.
- Use sentinel domain errors (
ErrNotFound,ErrForbidden,ErrConflict,ErrInvalidInput) and map them in the Telegram layer. Never leak database errors to users. - Revalidate authorization on every callback. Callback data is untrusted and limited to 64 bytes.
- Reserve items with a conditional database update, not read-then-write.
- Emit future side effects through
events.Publisher. Services never call Telegram directly. - Keep Telegram types out of
domainandservice. - Test every access-matrix row and every item transition.
- Never commit secrets.
.envis ignored; keep.env.examplecurrent. - Update the docs when a design decision changes.