Skip to content

Development Guide

raktim edited this page Aug 21, 2026 · 1 revision

Development Guide

For contributors setting up KinetiRx locally, outside Docker.

Prerequisites

  • Go 1.26+ (backend go.mod targets go 1.26)
  • Node.js (for the Vite/React frontend)
  • A local PostgreSQL instance — either install Postgres natively, or run just the database service from the Compose file:
    docker compose -f deploy/docker-compose.yml --env-file deploy/.env up postgres

Backend (backend/)

cd backend
cp .env.example .env

Edit .env:

  • DATABASE_URL — point at your local Postgres (the example default assumes postgres://kinetirx:changeme@localhost:5432/kinetirx?sslmode=disable).
  • JWT_SECRET — any string 16+ chars for local dev is fine; use a real random secret for anything beyond your own machine.
  • KINETIRX_ADMIN_PASSWORD — sets the seeded admin password on first run against an empty database.
  • GEMINI_API_KEY — optional, leave blank to develop against the OCR/AI fallback responses.

Run it:

go run ./cmd/server

SQL migrations under backend/migrations/ run automatically against DATABASE_URL on startup — no separate migration command to remember. Default port is 8080; ALLOWED_ORIGINS defaults to http://localhost:5173,http://localhost:3000 (the Vite dev server ports), so a locally-running frontend can call it directly without CORS errors.

Backend code structure conventions

  • One handler file per resource in internal/handlers/ (medicines.go, patients.go, etc.) — new resources should follow the same pattern: standard CRUD (GET list, GET :id, POST, PUT :id, DELETE :id) wired in router.go, permission-gated in internal/middleware/.
  • Request/response JSON shapes live as Go structs in internal/models/.
  • All non-2xx responses go through the shared error envelope helpers in internal/httpx/ — don't hand-roll c.JSON error bodies in a handler; use the existing envelope so type/title/status/errors/request_id stay consistent across the API (see API Reference for the shape).
  • IDs: accept an optional client-supplied id on create, generate a UUID server-side if omitted; IDs are immutable after creation.
  • Timestamps (createdAt/updatedAt) are always server-managed — never trust or accept them from a request body.

Tests

There are currently no *_test.go files in backend/ and no test files under frontend/src/ — this codebase does not yet have an automated test suite. If you're adding one, Go's standard testing package (go test ./...) is the natural fit for the backend; no frontend test runner is configured yet either (no Vitest/Jest in package.json).

Frontend (frontend/)

cd frontend
cp .env.example .env   # optional — only needed if the backend isn't at the default localhost:8080
npm install
npm run dev

Vite dev server runs on http://localhost:5173 by default and talks directly to VITE_API_URL (or http://localhost:8080 if unset) — no proxy layer in local dev, unlike the Docker Compose deployment where nginx proxies /api/*.

Available scripts (package.json):

Script Purpose
npm run dev Vite dev server with HMR
npm run build Production build to dist/
npm run start / npm run preview Serve the production build locally
npm run clean Remove dist/
npm run lint Type-check only (tsc --noEmit) — there is no separate ESLint config wired up yet

Frontend code structure conventions

  • src/components/tabs/ — one component per top-level nav section; the TabType union in src/types.ts is the authoritative list of sections and doubles as the permission-key vocabulary shared with the backend (see Architecture).
  • src/components/modals/ — dialogs, one file (or a small related group, e.g. EmployeeModals.tsx) per modal.
  • src/lib/api.ts — the only place that should call fetch against the backend. Add new typed functions here rather than calling fetch directly from a component, so auth headers, the error envelope, and the 401 handler stay centralized.
  • src/hooks/useSyncedResource.ts — generic hook for load/create/update/ delete against a REST resource; prefer reusing it over hand-rolled useState/useEffect data fetching in a new tab.
  • src/hooks/useTheme.ts — dark/light mode; Tailwind CSS v4 is configured via @tailwindcss/vite, styling lives in src/index.css plus Tailwind utility classes in components.
  • TypeScript: strict types in src/types.ts shared across API calls and components — extend these, don't duplicate ad hoc shapes locally.

Full local stack (both services + Postgres)

Run Postgres via Compose (docker compose -f deploy/docker-compose.yml up postgres), go run ./cmd/server in one terminal, npm run dev in another. This gives hot-reload on the frontend and fast rebuild/restart on the backend, which is generally faster to iterate against than rebuilding the full Docker images on every change.

Contributing

No CONTRIBUTING.md, issue templates, or CI workflow exist in the repo yet (.github/workflows/ is absent) — until those land, open a PR against main and describe what you tested manually (there's no automated test suite to point to yet, see above).

Clone this wiki locally