Team Time Tracker Setup
Configure and work with TimeNest, a fullstack time management tracker for businesses and teams to log work hours efficiently. The application uses React + Vite frontend and Spring Boot backend with JWT-based authentication and role-based access control.
Tech Stack
**Frontend**: React 19, React Router, TailwindCSS 4, Vite 7**Backend**: Spring Boot 3.5.4, Spring Security, JPA/Hibernate, PostgreSQL**Authentication**: JWT tokens (email-based), email verification with codes**Roles**: `EMPLOYEE` (can create time logs) and `EXECUTIVE` (full access to company data)Repository Structure
```
Timenest/
├── time-nest-frontend/ # React application
│ ├── src/
│ │ ├── pages/ # Route components organized by role
│ │ │ ├── employee/ # Employee-specific pages
│ │ │ └── executive/ # Executive-specific pages
│ │ ├── components/ # Shared components (navbar, etc.)
│ │ └── App.jsx # Route definitions
│ └── package.json
└── time-nest-backend/Mind_Forge/ # Spring Boot application
├── src/main/java/com/example/Mind_Forge/
│ ├── model/ # JPA entities (User, Company, TimeLog)
│ ├── repository/ # Spring Data JPA repositories
│ ├── service/ # Business logic layer
│ ├── controller/ # REST endpoints
│ ├── dto/ # Data transfer objects
│ ├── response/ # Response objects
│ └── config/ # Security, JWT, Email config
└── pom.xml
```
Instructions
1. Understand Core Architecture
**Authentication Flow:**
The `User` entity has both `username` and `email` fields with a critical nuance: - JWT tokens use `email` as the subject (via `User.getUsername()` override at line 88-90)
- To retrieve the actual username, use `User.getActualUsername()` method (line 83-85)
- Email verification is required before users can log in
**User Registration Flow:**
1. User registers → verification code sent via email
2. User verifies with code → account enabled
3. User logs in → JWT token issued with email as subject
**Role-Based Access Control** (defined in `SecurityConfiguration.java:36-44`):
**EMPLOYEE role**: Can create time logs (`POST /timelogs`)**EXECUTIVE role**: Full CRUD on time logs, access to company-wide dataBoth roles: Can view their own time logs (`/timelogs/me`)Role mapping happens in `User.getAuthorities()` method (line 66-81)Spring Security expects roles prefixed with `ROLE_` (e.g., `ROLE_EMPLOYEE`), but database stores plain values (`employee`, `executive`)**Data Model Relationships:**
**Company → Users → TimeLogs**One Company has many Users (via `company_id` foreign key)One User has many TimeLogs (via `user_id` foreign key)TimeLogs also reference Company directly for efficient queryingCompanies have a unique `joinCode` for employees to join`executiveId` field stores the company owner's user ID`@JsonIgnore` annotations prevent infinite recursion in JSON serializationUser's `username` field returns email for JWT compatibilityTimeLog hours are calculated from `startTime` and `endTime`2. Frontend Development
**Location:** `time-nest-frontend/`
**Available Commands:**
```bash
npm install # Install dependencies
npm run dev # Run dev server (http://localhost:5173)
npm run build # Build for production
npm run preview # Preview production build
npm run lint # Lint code
```
**Routing Structure** (defined in `App.jsx`):
`/` and `/login` - Authentication`/org` - Organization/company management`/employee/*` - Employee dashboard and profile`/executive/*` - Executive dashboard and profile**When making frontend changes:**
Routes are role-basedUpdate CORS origins in `SecurityConfiguration.java` for production deploymentFrontend expects JWT tokens in Authorization headers3. Backend Development
**Location:** `time-nest-backend/Mind_Forge/`
**Available Commands:**
```bash
mvn clean install # Build the project
mvn spring-boot:run # Run the application
mvn test # Run tests
mvn package # Package as JAR
```
**Security Configuration** (`SecurityConfiguration.java:55-65`):
**CORS Settings:**
Allowed origins: `http://localhost:5173` (frontend dev), `http://localhost:8080`Allowed methods: GET, POST, PUT, DELETECredentials enabled for auth headers**Endpoint Access:**
**Public**: `/auth/**` - Registration, login, verification, password reset**Protected**: `/timelogs/*` (role-based), `/users/*` (authenticated), `/companies/*` (company management)**JWT Configuration** (in `application.properties`):
`security.jwt.secret-key` - Base64-encoded secret key for signing`security.jwt.expiration-time` - Token expiration duration in milliseconds`JwtService` handles token generation, validation, and claims extraction4. Configuration Requirements
**Backend Environment Variables** (ensure `application.properties` includes):
Database connection: `spring.datasource.url`, `spring.datasource.username`, `spring.datasource.password`JWT settings: `security.jwt.secret-key`, `security.jwt.expiration-time`Email settings: SMTP configuration for verification emails**Important Implementation Details:**
**Password Reset Flow:**
`PasswordResetToken` entity stores reset tokens with expirationEndpoints: `/auth/forgot-password` and `/auth/reset-password`Tokens sent via email through `EmailService`**Email Verification:**
Verification codes are 6-digit strings stored in `User.verificationCode`Codes expire after configurable time (`verificationCodeExpiresAt`)Unverified users (`enabled=false`) cannot log in**Time Log Management:**
Employees can only create and view their own time logsExecutives can view all time logs for their companyTime logs include `location`, `startTime`, `endTime`, and calculated `hours`5. Testing Considerations
When writing tests:
Mock `JwtService` for authentication testsUse `@WithMockUser(roles = {"EMPLOYEE"})` or `@WithMockUser(roles = {"EXECUTIVE"})` for role-based testsRemember that usernames are actually emails in the security contextTest email verification flow separately from authenticationMock `EmailService` to avoid sending actual emails in tests6. Common Tasks
**Adding a new protected endpoint:**
1. Define endpoint in appropriate controller
2. Update `SecurityConfiguration.java` with authorization rules
3. Test with role-based access tests
**Modifying user roles:**
Edit `User.getAuthorities()` method (line 66-81)Update `SecurityConfiguration` role mappingsRemember `ROLE_` prefix requirement**Adding new time log fields:**
1. Update `TimeLog` entity in `model/`
2. Modify repository queries if needed
3. Update DTOs and controllers
4. Adjust frontend components to display/submit new fields
Constraints
JWT tokens use email as username - use `getActualUsername()` to retrieve display nameSpring Security requires `ROLE_` prefix for authorities, but database stores plain role namesCORS must be configured for frontend originsEmail verification is mandatory before loginRole-based access is enforced at controller level