public static string BookAppointment(TurnDetailsDTO appointment)
        {
            try
            {
                ActivityTimeDTO activityTime = ActivityTimeBL.GetActivityTime(appointment.EstimatedHour, appointment.ServiceId);

                customersInLine turn = new customersInLine()
                {
                    activityTimeId = activityTime.ActivityTimeId,
                    custId         = appointment.CustId,
                    estimatedHour  = appointment.EstimatedHour,
                    preAlert       = appointment.PreAlert,
                    statusTurn     = (int)eStatus.ADVANCE,
                    enterHour      = ConfigureHour(appointment.EstimatedHour, activityTime),
                    isActive       = true
                };
                turn.TurnId = TurnDal.AddAppointment(turn);
                string verificationCode = TurnBL.CreateVerificationCode(turn);
                turn.verificationCode = verificationCode;
                TurnDal.UpdateTurn(turn);
                return(verificationCode);
            }
            catch (Exception)
            {
                throw;
            }
        }
        //toask: סטטי או מופעים של המחלקות



        /// <summary>
        /// push the turns till the end of the activity time or stop if an empty time was found
        /// </summary>
        /// <param name="line">רשימת התורים שבהם אמורה להתבצע הדחיפה</param>
        /// <param name="time">שעת התור</param>
        /// <param name="activityTime"></param>
        /// <returns>num of pushed turns</returns>
        private static int pushTurns(List <customersInLine> line, TimeSpan time, ActivityTimeDTO activityTime)
        {
            TimeSpan ts             = TimeSpan.FromMinutes((double)activityTime.AvgServiceDuration);
            int      pushedTurnsCnt = 0;

            for (int i = 0; i < line.Count(); i++)
            {
                if ((line[i].statusTurn == (int)eStatus.IMMEDIATELY && line[i].estimatedHour.TimeOfDay >= time && line[i].estimatedHour.TimeOfDay < time.Add(ts)) || (line[i].statusTurn == (int)eStatus.ADVANCE && line[i].enterHour >= time && line[i].enterHour < time.Add(ts)))
                {
                    pushedTurnsCnt++;
                    if (line[i].statusTurn == (int)eStatus.IMMEDIATELY)
                    {
                        line[i].estimatedHour = line[i].estimatedHour.Add(ts);
                        time = line[i].estimatedHour.TimeOfDay;
                    }
                    else
                    {
                        line[i].enterHour = line[i].enterHour.Value.Add(ts);
                        time = line[i].enterHour.Value;
                    }
                }
                else
                {
                    break;
                }
            }
            return(pushedTurnsCnt);
        }
Exemple #3
0
        public static TurnDetailsDTO GetNearestTurn(int serviceId)
        {
            try
            {
                ActivityTimeDTO        activityTime = ActivityTimeBL.GetActivityTime(DateTime.Now, serviceId);
                List <customersInLine> line         = new List <customersInLine>();
                if (activityTime != null)
                {
                    line = TurnDal.GetLinePerActivityTime(activityTime.ActivityTimeId);
                    if (line.Count() == 0)
                    {
                        throw new Exception("there is no turns now");
                    }
                }


                else
                {
                    throw new Exception("there is no activityTime now");
                }
                if (line[0].actualHour == null)
                {
                    line[0].actualHour = new TimeSpan();
                }
                return(converters.TurnDetailsConverters.GetTurnDetailsDTO(line[0]));
            }
            catch (Exception ex)
            {
                throw ex;
            }
        }
//totake:
/// <summary>
/// looks for available turn in activityTime,begin to search from the time she got.
/// </summary>
/// <param name="activityTime"></param>
/// <param name="pushFlag"></param>
/// <param name="timeToLookFor"></param>
/// <returns></returns>
        private static TimeSpan?lookForAvailableTurn(ActivityTimeDTO activityTime, ref bool pushFlag, TimeSpan timeToLookFor)
        {
            List <customersInLine> line = TurnDal.GetLinePerActivityTime(activityTime.ActivityTimeId);

            pushFlag = false;
            double durationOfService = (double)activityTime.AvgServiceDuration;
            //מחשב את ההפרש בין זמן התחלת המשמרת לזמן שקבלנו בפרמטר ע"מ למצוא את הזמן שבו יתחיל לחפש תור
            int totalPassedShifts = (int)((timeToLookFor.TotalMinutes - activityTime.StartTime.TotalMinutes) / durationOfService) + 1;
            //  פרמטר של פנוי שיהיה לפי ממוצע זמן ההמתנה
            const int maxStandbyTime = 3;
            const int maxPushedTimes = 2;
            TimeSpan  hour;
            TimeSpan  ts = TimeSpan.FromMinutes(durationOfService * totalPassedShifts);
            int       index = 0, numOfStandbyTime = 0;

            timeToLookFor = activityTime.StartTime.Add(ts);
            line          = line.Where(t => t.estimatedHour.TimeOfDay >= timeToLookFor).ToList();
            //השעה המבוקשת פנויה
            if (line.Count() == 0 && timeToLookFor < activityTime.EndTime)
            {
                return(timeToLookFor);
            }
            ts = TimeSpan.FromMinutes(durationOfService);
            //לולאה המתחילה מהזמן שקבלה ומחפשת תור פנוי
            for (hour = timeToLookFor; numOfStandbyTime < maxStandbyTime && hour < activityTime.EndTime; hour = hour.Add(ts), numOfStandbyTime++)
            {
                if (TurnBL.IsAvailableHour(ref index, activityTime.NumOfWorkers, hour.Add(ts), line))
                {
                    return(hour);
                }
                index++;
            }
            //אם לא נמצא תור פנוי בתוך זמן ההמתנה המקסימלי שמאופשר:
            //אם כבר המשמרת הנוכחית תפוסה לגמרי
            if (hour >= activityTime.EndTime)
            {
                //מחפש את המשמרת הבאה הקרובה ביותר
                activityTime = ActivityTimeBL.GetNearestActivityTime(hour, activityTime.ServiceId);
                if (activityTime == null)
                {
                    return(null);
                }
                //קורא בצורה רקורסיבית לפונקציה הנוכחית ומתחיל את החיפוש תור פנוי במשמרת החדשה מההתחלה
                return(lookForAvailableTurn(activityTime, ref pushFlag, activityTime.StartTime));
            }
            //אם המשמרת עדיין לא נגמרה אבל הזמן המקסימלי להמתנה עבר ואין תור פנוי אז יש צורך לדחוף את  התור בין התורים
            pushFlag = true;
            while (index < line.Count() && line[index].estimatedHour.TimeOfDay == hour && line[index].numOfPushTimes == maxPushedTimes)
            {
                index++;
                hour = hour.Add(ts);
            }

            return(hour);
        }
Exemple #5
0
        /// <summary>
        /// הפונקציה מקבלת שעה וקוד שירות ומחפשת את המשמרת בשירות הספציפי בהתאם לשעה שקיבלה
        /// </summary>
        /// <param name="time">שעה</param>
        /// <param name="serviceId">קוד שירות</param>
        /// <returns>קוד משמרת </returns>


        public static ActivityTimeDTO GetActivityTime(DateTime time, int serviceId)
        {
            List <ActivityTimeDTO> activityTimes = new List <ActivityTimeDTO>();

            activityTimes = converters.ActivityTimeConverters.GetListActivityTimesDTO(ActivityTimeDal.GetActivityTimes(serviceId));
            ActivityTimeDTO activityTime = activityTimes.FirstOrDefault(a => a.DayInWeek == ((int)time.DayOfWeek + 1) && a.StartTime <= time.TimeOfDay && a.EndTime > time.TimeOfDay && a.StartDate <= time && (a.EndDate == null || a.EndDate >= time));

            if (activityTime == null)
            {
                activityTime = ActivityTimeBL.GetNearestActivityTime(time.TimeOfDay, serviceId);
            }
            return(activityTime);
        }
        /// <summary>
        ///
        /// </summary>
        /// <param name="businessId"></param>
        /// <returns>optional hour for immidate turn for the required business</returns>
        public static TimeSpan GetOptionalHourPerBusiness(int serviceId, TimeSpan timeToLookFor, ref bool pushFlag)
        {
            //to ask: ... לכתוב את החילוץ פעמיים
            DateTime time = DateTime.Now;

            time = time.Add(timeToLookFor - time.TimeOfDay);
            ActivityTimeDTO activityTime = ActivityTimeBL.GetActivityTime(time, serviceId);

            if (activityTime == null)
            {
                return(new TimeSpan());
            }
            return((TimeSpan)lookForAvailableTurn(activityTime, ref pushFlag, timeToLookFor));
        }
        /// <summary>
        /// פונקציה המחשבת את השעה עבור תור הנקבע מראש ומטרתה לחסוך המתנה בזמני עומס
        /// </summary>
        /// <param name="date"></param>
        /// <param name="activityTime"></param>
        /// <returns>שעה לוגית  </returns>
        public static TimeSpan ConfigureHour(DateTime date, ActivityTimeDTO activityTime)
        {
            if (activityTime.AverageNumOfWaitingPeople == null)
            {
                return(date.TimeOfDay);
            }
            TimeSpan logicHour = new TimeSpan();
            //todoever: לקבוע את המשתנה בהתאם לאמינות-לסטית תקן
            int numOfIgnoreServiceDuration = 3;
            //

            int numOfSub = (int)(activityTime.AverageNumOfWaitingPeople.Value / activityTime.AvgServiceDuration - numOfIgnoreServiceDuration);

            logicHour = date.TimeOfDay.Subtract(TimeSpan.FromMinutes(activityTime.AvgServiceDuration.Value * numOfSub));
            if (logicHour > activityTime.StartTime)
            {
                return(logicHour);
            }
            else
            {
                return(activityTime.StartTime);
            }
        }
        /// <summary>
        /// הפונקציה קובעת תור זמני עבור שעה אופציונלית בעסק
        /// </summary>
        /// <param name="turn"></param>
        /// <returns>turn id</returns>
        public static int MakeTemporaryTurn(TurnInBusinessDTO turn, bool pushFlag, int custId)
        {
            DateTime        time         = DateTime.Now;
            ActivityTimeDTO activityTime = ActivityTimeBL.GetActivityTime(time.Add(turn.EstimatedHour.Value - time.TimeOfDay), turn.ServiceId);

            if (activityTime == null)
            {
                throw new Exception("אין משמרת פעילה כרגע");
            }

            //todoever: להחליף בהמשך לאינדקסים
            try
            {
                int status = (int)eStatus.TEMPORARY;
                if (pushFlag)
                {
                    status = (int)eStatus.TEMPORARY_WITH_PUSH;
                }
                customersInLine temporaryTurn = new customersInLine()
                {
                    activityTimeId = activityTime.ActivityTimeId,
                    custId         = custId,
                    enterHour      = TimeSpan.FromMinutes(turn.Duration).Add(DateTime.Now.TimeOfDay),
                    estimatedHour  = DateTime.Today.Add(turn.EstimatedHour.Value),
                    isActive       = true,
                    preAlert       = 0,
                    statusTurn     = status
                };

                int turnId = TurnDal.AddAppointment(temporaryTurn);
                return(turnId);
            }
            catch (Exception)
            {
                throw;
            }
        }