Adds EventId type for robust event ID handling

Introduces type-safe EventId with centralized normalization logic for clone and standard event IDs

Refactors event ID management across multiple components to use consistent ID transformation methods
Improves type safety and reduces potential ID-related bugs in drag-and-drop and event rendering
This commit is contained in:
Janus C. H. Knudsen 2025-12-03 14:43:25 +01:00
parent d53af317bb
commit 73e284660f
5 changed files with 82 additions and 29 deletions

View file

@ -4,7 +4,7 @@ This file provides guidance to Claude Code (claude.ai/code) when working with co
## Project Overview
Calendar Plantempus is a professional TypeScript calendar component with offline-first architecture, drag-and-drop functionality, and real-time synchronization capabilities.
Calendar Plantempus is a professional TypeScript calendar component with offline-first architecture, drag-and-drop functionality, and real-time synchronization capabilities. Supports both date-based (day/week/month) and resource-based (people, rooms) calendar views.
## Build & Development Commands
@ -21,18 +21,18 @@ npm run clean
# Type check only
npx tsc --noEmit
# Run all tests
# Run all tests (watch mode)
npm test
# Run tests in watch mode
npm run test
# Run tests once and exit
npm run test:run
# Run tests with UI
npm run test:ui
# Run single test file
npm test -- <test-file-name>
# CSS Development
npm run css:build # Build CSS
npm run css:watch # Watch and rebuild CSS
@ -57,6 +57,21 @@ The application uses a **centralized EventBus** (`src/core/EventBus.ts`) built o
- Components subscribe via `eventBus.on(CoreEvents.EVENT_NAME, handler)`
- Never call methods directly between managers - always use events
### Calendar Modes: Date vs Resource
The calendar supports two column modes, configured at initialization in `src/index.ts`:
**Date Mode** (`DateColumnDataSource`):
- Columns represent dates (day/week/month views)
- Uses `DateHeaderRenderer` and `DateColumnRenderer`
**Resource Mode** (`ResourceColumnDataSource`):
- Columns represent resources (people, rooms, equipment)
- Uses `ResourceHeaderRenderer` and `ResourceColumnRenderer`
- Events filtered per-resource via `IColumnInfo.events`
Both modes implement `IColumnDataSource` interface, allowing polymorphic column handling.
### Manager Hierarchy
**CalendarManager** (`src/managers/CalendarManager.ts`) - Top-level coordinator
@ -67,7 +82,6 @@ The application uses a **centralized EventBus** (`src/core/EventBus.ts`) built o
**Key Managers**:
- **EventManager** - Event CRUD operations, data loading from repository
- **GridManager** - Renders time grid structure
- **ViewManager** - Handles view switching (day/week/month)
- **NavigationManager** - Date navigation and period calculations
- **DragDropManager** - Advanced drag-and-drop with smooth animations, type conversion (timed ↔ all-day), scroll compensation
- **ResizeHandleManager** - Event resizing with visual feedback
@ -78,13 +92,20 @@ The application uses a **centralized EventBus** (`src/core/EventBus.ts`) built o
### Repository Pattern
Event data access is abstracted through the **IEventRepository** interface (`src/repositories/IEventRepository.ts`):
- **IndexedDBEventRepository** - Primary: Local storage with offline support
- **ApiEventRepository** - Sends changes to backend API
- **MockEventRepository** - Legacy: Loads from JSON file
Data access is abstracted through **IApiRepository<T>** interface (`src/repositories/IApiRepository.ts`):
- **MockEventRepository**, **MockBookingRepository**, **MockCustomerRepository**, **MockResourceRepository** - Development: Load from JSON files
- **ApiEventRepository**, **ApiBookingRepository**, **ApiCustomerRepository**, **ApiResourceRepository** - Production: Backend API calls
All repository methods accept an `UpdateSource` parameter ('local' | 'remote') to distinguish user actions from remote updates.
### Entity Service Pattern
**IEntityService<T>** (`src/storage/IEntityService.ts`) provides polymorphic entity handling:
- `EventService`, `BookingService`, `CustomerService`, `ResourceService` implement this interface
- Encapsulates sync status manipulation (SyncManager delegates, never manipulates directly)
- Uses `entityType` discriminator for runtime routing without switch statements
- Enables polymorphic operations: `Array<IEntityService<any>>` works across all entity types
### Offline-First Sync Architecture
**SyncManager** (`src/workers/SyncManager.ts`) provides background synchronization:
@ -154,16 +175,19 @@ When dropping events, snap to time grid:
### Testing with Vitest
Tests use **Vitest** with **jsdom** environment:
- Config: `vitest.config.ts`
- Setup file: `test/setup.ts`
- Test helpers: `test/helpers/dom-helpers.ts`
- Test helpers: `test/helpers/dom-helpers.ts`, `test/helpers/config-helpers.ts`
- Run single test: `npm test -- <test-file-name>`
## Key Files to Know
- `src/index.ts` - DI container setup and initialization
- `src/index.ts` - DI container setup and initialization (also sets calendar mode: date vs resource)
- `src/core/EventBus.ts` - Central event dispatcher
- `src/constants/CoreEvents.ts` - All event type constants
- `src/constants/CoreEvents.ts` - All event type constants (~34 core events)
- `src/types/CalendarTypes.ts` - Core type definitions
- `src/types/ColumnDataSource.ts` - Column abstraction for date/resource modes
- `src/storage/IEntityService.ts` - Entity service interface for polymorphic sync
- `src/managers/CalendarManager.ts` - Main coordinator
- `src/managers/DragDropManager.ts` - Detailed drag-drop architecture docs
- `src/configurations/CalendarConfig.ts` - Configuration schema
@ -207,12 +231,15 @@ Access debug interface in browser console:
window.calendarDebug.eventBus.getEventLog()
window.calendarDebug.calendarManager
window.calendarDebug.eventManager
window.calendarDebug.auditService
window.calendarDebug.syncManager
window.calendarDebug.app // Full DI container
```
## Dependencies
- **@novadi/core** - Dependency injection framework
- **date-fns** / **date-fns-tz** - Date manipulation and timezone support
- **dayjs** - Date manipulation and formatting
- **fuse.js** - Fuzzy search for event filtering
- **esbuild** - Fast bundler for development
- **vitest** - Testing framework