Skip to content

Data Layer and Repository

Radch-enko edited this page Jul 24, 2025 · 1 revision

Data Layer & Repositories

This document covers the data access layer architecture, repository pattern implementations, and data coordination strategies used throughout the Effective Office system. It focuses on how data flows between network APIs, local storage, and business logic components in both the backend and tablet client applications.

For business logic and use case patterns, see [Domain Use Cases](Data and DOmain Architecture/Domain Use Cases). For specific booking workflows, see Room Booking Workflow.

Architecture Overview

The data layer follows clean architecture principles with clear separation between data sources, repositories, and domain logic. The system uses the repository pattern to abstract data access and provide consistent interfaces for both network and local data operations.

architecture-overvie.svg

Repository Pattern Implementation

Client-Side Repository

The tablet client implements repositories that handle both network and local data coordination. The RoomRepositoryImpl serves as the primary example of this pattern.

client-side-repository.svg

The RoomRepositoryImpl demonstrates key repository characteristics:

Method Purpose Data Source Return Type
subscribeOnUpdates() Real-time data subscription Network via BookingApi Flow<Either<ErrorWithData, List<RoomInfo>>>
getRoomsInfo() Fetch room availability Network via WorkspaceApi Either<ErrorWithData, List<RoomInfo>>

Backend Repository Pattern

The backend uses repositories for data persistence and external API coordination. The ChannelRepository manages Google Calendar notification channels.

Data Access Strategies

Time-Based Data Retrieval

The getRoomsInfo() method in RoomRepositoryImpl implements sophisticated time management for booking data:

time-based-data-retrieval.svg

The implementation rounds the current time to 15-minute intervals and fetches booking data for a 14-day window.

Reactive Data Subscription

The repository implements reactive data patterns using Kotlin Flow for real-time updates:

retrieve-data-subscription.svg

The ResourceDisposerUseCase manages subscription lifecycle and implements debouncing to prevent excessive refresh operations.

Error Handling and Data Coordination

Either Type Pattern

The data layer uses the Either<Error, Success> type for consistent error handling across all repository methods:

Either State Purpose Error Handling
Either.Error Network failures, validation errors Wraps error with ErrorWithData<T>
Either.Success Successful data retrieval Contains transformed domain objects

Data Transformation Pipeline

data-transformation-pipeline.svg

The RoomInfoMapper handles transformation between network DTOs and domain models, while the backend WorkspaceController converts domain entities to API DTOs.

Integration Patterns

Dependency Injection with Koin

The data layer uses Koin for dependency injection, allowing use cases to access repositories through interfaces:

dependency-injection-with-koin.svg

Components inject use cases using by inject().

Resource Management

The ResourceDisposerUseCase demonstrates proper resource cleanup patterns:

Resource Management Strategy Implementation
Coroutine Scope SupervisorJob() with Dispatchers.IO ResourceDisposerUseCase.kt
Subscription Job Cancellable job tracking ResourceDisposerUseCase.kt
Cleanup Explicit dispose() method ResourceDisposerUseCase.kt
Clone this wiki locally