Files
qavion-time-tracker-assessment/README.md
T

103 lines
4.4 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# Time Tracker
A browser-based time-tracking app: log daily work against projects, review totals in weekly and
monthly views, and track project budgets with automatic cost calculation and soft breach warnings.
**Stack:** React 19 + Vite 6 (TypeScript strict) — Spring Boot 3.4 (Java 21) — PostgreSQL 17 via
Docker Compose — Flyway for schema migrations — Tailwind CSS v4 — Biome 1.9 — Vitest.
## Features
- **Daily time entries** — date, project, duration (entered as h:mm), automatic cost from hourly rate
- **Weekly view** — navigate by ISO week; see total hours per day and a running week total
- **Monthly view** — per-project summary with time and cost progress bars; red banner when a budget is exceeded
- **Project management** — create projects with time and cost budgets; set a project-level hourly rate or fall back to the user's default
- **Multi-user** — pick any seeded user from the dropdown; cost is calculated using that user's rate when no project rate is set
- **Soft budget enforcement** — entries always save; over-budget projects are highlighted with a warning banner and colored bars
## Quick start
> **Requires a full Java 21 JDK** (not just a JRE) for Maven compilation. `mise install` below
> handles this and sets `JAVA_HOME` when commands are run through `mise`. Without mise:
> `sudo apt install openjdk-21-jdk`, then ensure `java -version` reports 21 and `JAVA_HOME` points
> at that JDK.
```bash
# 1. Pin toolchain — installs Java 21 JDK, Node 22, Maven, lefthook, gitleaks
mise install
# 2. Install deps, git hooks, .env, and validate Java + Maven wrapper
mise run setup
# 3. Start the database
docker compose up -d
```
Open two terminals:
```bash
# Backend → http://localhost:8080
mise run backend
# Frontend → http://localhost:5173 (proxies /api → :8080)
mise run frontend
```
If you have activated mise in your shell, the direct commands also work:
`backend/mvnw -f backend/pom.xml spring-boot:run` and `cd frontend && npm run dev`.
## Verify everything
```bash
mise run check # format-check + lint + test (both stacks)
```
Without mise:
```bash
# one-time setup
sudo apt install openjdk-21-jdk nodejs npm docker-compose-plugin
export JAVA_HOME=/usr/lib/jvm/java-21-openjdk-amd64 # adjust if your JDK is elsewhere
npm --prefix frontend install
cp -n .env.example .env
backend/mvnw -f backend/pom.xml -v # primes the Maven wrapper cache
# checks
backend/mvnw -f backend/pom.xml spotless:check -q
cd frontend && npx biome check src
backend/mvnw -f backend/pom.xml test -q
cd frontend && npx vitest run
```
## Design notes
**Money and duration** are stored as integers (cents and minutes respectively) to avoid floating-point
drift. Cost for a time entry is computed at read time: `duration_minutes × effective_rate_cents / 60`,
where the effective rate is the project's `hourly_rate_cents` if set, otherwise the user's
`default_hourly_rate_cents`. This means changing a rate retroactively updates all historical cost
totals — a deliberate trade-off for simplicity (see `NEXT_STEPS.md` for a snapshot-based alternative).
**Budget warnings** are soft: any entry saves regardless of budget status. Breach is detected in the
reporting layer by comparing aggregated totals to the project's `time_budget_minutes` and
`cost_budget_cents`. The monthly view renders a red warning banner and saturated progress bars for
any over-budget project.
**Schema migrations** are managed exclusively by Flyway (`V1__init.sql` for schema, `V2__seed_demo_data.sql`
for demo users and projects). Hibernate is set to `validate` — it never modifies the schema.
**API shape** — aggregation is done server-side via two dedicated endpoints:
`GET /api/reports/weekly?userId=&week=YYYY-Www` and `GET /api/reports/monthly?userId=&month=YYYY-MM`.
All other CRUD endpoints follow standard REST conventions under `/api/`.
## Environment
`.env.example` documents all env vars. `mise run setup` copies it to `.env` automatically on first run.
## Troubleshooting
- `backend/mvnw: ... exec: .../apache-maven-3.9.9/bin/mvn: not found` — run `mise run setup` again.
The setup task primes the Maven wrapper cache. If it still fails, remove the broken cache with
`rm -rf ~/.m2/wrapper/dists/apache-maven-3.9.9*` and rerun `mise run setup`.
- `JAVA_HOME environment variable is not defined correctly` — install a Java 21 JDK and set
`JAVA_HOME`, or use the mise tasks (`mise run backend`, `mise run check`) after `mise install`.