Press n or j to go to the next uncovered block, b, p or k for the previous block.
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 | import { Injectable, NotFoundException } from '@nestjs/common'; import { InjectModel } from '@nestjs/mongoose'; import { Model } from 'mongoose'; import { ShiftRotation, ShiftRotationStep, ShiftRoster, ShiftRosterEntry, } from '../../schemas'; import { CreateShiftRotationDto, RotationStepDto, CreateShiftRosterDto, CreateRosterEntryDto, GenerateRosterDto, } from './dto/roster.dto'; @Injectable() export class RosterService { constructor( @InjectModel(ShiftRotation.name) private rotationModel: Model<ShiftRotation>, @InjectModel(ShiftRotationStep.name) private rotationStepModel: Model<ShiftRotationStep>, @InjectModel(ShiftRoster.name) private rosterModel: Model<ShiftRoster>, @InjectModel(ShiftRosterEntry.name) private rosterEntryModel: Model<ShiftRosterEntry>, ) {} async createRotation( tenantId: string, createDto: CreateShiftRotationDto, userId: string, ) { const created = new this.rotationModel({ ...createDto, tenantId, createdBy: userId, }); return created.save(); } async setRotationSteps( tenantId: string, rotationId: string, steps: RotationStepDto[], ) { // Basic verification const rotation = await this.rotationModel .findOne({ _id: rotationId, tenantId }) .exec(); if (!rotation) { throw new NotFoundException(`Shift rotation #${rotationId} not found`); } await this.rotationStepModel.deleteMany({ tenantId, rotationId }); const stepDocs = steps.map((step) => ({ ...step, tenantId, rotationId, })); return this.rotationStepModel.insertMany(stepDocs); } async getRotationSteps(tenantId: string, rotationId: string) { return this.rotationStepModel .find({ tenantId, rotationId }) .sort({ sequence: 1 }) .exec(); } async createRoster( tenantId: string, createDto: CreateShiftRosterDto, userId: string, ) { const created = new this.rosterModel({ ...createDto, tenantId, createdBy: userId, }); return created.save(); } async addRosterEntries( tenantId: string, rosterId: string, entriesDto: CreateRosterEntryDto[], ) { // Delete existing entries for the exact dates to avoid duplicates // Using simple approach here const entries = entriesDto.map((entry) => ({ ...entry, tenantId, rosterId, })); return this.rosterEntryModel.insertMany(entries); } async generateRoster( tenantId: string, generateDto: GenerateRosterDto, userId: string, ) { // This is a complex logic area // 1. Fetch target employees based on targetType and targetId // 2. Fetch the rotation steps if rotationId is provided, or use default shifts // 3. Iterate through dates from startDate to endDate // 4. Assign shifts sequentially based on durationDays of each step // For now, return a placeholder representing successful job start return { message: 'Roster generation started', details: generateDto, }; } } |