CourseKitBackend
QueryService
Query schedules and find free time slots
Overview
QueryService provides methods to query materialized schedules and find free time slots across entities.
import { QueryService } from '@hfu.digital/coursekit-nestjs';Methods
getSchedule
Get all materialized occurrences matching a query. Expands recurring events, applies exceptions, and filters by entities.
async getSchedule(query: ScheduleQuery): Promise<MaterializedOccurrence[]>Returns occurrences sorted by start time.
const schedule = await query.getSchedule({
dateRange: {
start: new Date('2026-03-02'),
end: new Date('2026-03-08'),
},
instructorIds: ['instructor-1'],
roomIds: ['room-a1'],
});getEntitySchedule
Convenience wrapper to get the schedule for a single entity.
async getEntitySchedule(
entityType: 'instructor' | 'room' | 'group',
entityId: string,
dateRange: DateRange,
): Promise<MaterializedOccurrence[]>const schedule = await query.getEntitySchedule('instructor', 'instructor-1', {
start: new Date('2026-03-02'),
end: new Date('2026-03-08'),
});findFreeSlots
Find time slots where ALL specified entities are simultaneously free.
async findFreeSlots(query: FreeSlotQuery): Promise<FreeSlot[]>const slots = await query.findFreeSlots({
dateRange: {
start: new Date('2026-03-02'),
end: new Date('2026-03-06'),
},
durationMin: 90,
entityIds: [
{ type: 'instructor', id: 'instructor-1' },
{ type: 'room', id: 'room-a1' },
],
});How it works:
- For each entity, fetches and materializes all events in the date range
- Collects all occupied time intervals
- Sorts and merges overlapping intervals
- Returns gaps that meet the minimum duration requirement
ScheduleQuery
interface ScheduleQuery {
dateRange: DateRange;
instructorIds?: string[];
roomIds?: string[];
groupIds?: string[];
courseIds?: string[];
periodId?: string;
tags?: Record<string, unknown>;
}All filter fields are optional. When multiple filters are provided, they are combined (events must match all specified criteria).
FreeSlotQuery
interface FreeSlotQuery {
dateRange: DateRange;
durationMin: number;
entityIds: Array<{ type: 'instructor' | 'room' | 'group'; id: string }>;
}