Ejemplo n.º 1
0
        public ApiResponse <OrderModel> AddOrder(ApplyOrderModel model)
        {
            // 1. 检查输入参数
            if (model == null)
            {
                throw new ApiBadRequestException("无效的参数");
            }

            // 2. 验证申请单是否有效

            /*
             * 验证不需要返回值,不符合要求弹出提示信息
             *
             *
             * **/
            ValidApplyOrder(model);

            //新增假单 如果是请假或者提交加班申请需要启动工作申请流程
            // 3. Construct API Response
            var response = new ApiResponse <OrderModel>()
            {
                Result = AskLeaveService.AddOrder(model, this.Member)
            };

            return(response);
        }
        /// <summary>
        /// 修改申请信息
        /// </summary>
        /// <returns>修改状态</returns>
        public bool UpdateOrder(int userId, int orderNo, UpdateOrderModel model)
        {
            using (var dbContext = new MissionskyOAEntities())
            {
                #region 申请信息

                //查询申请信息是否存在
                var orderEntities  = dbContext.Orders.Where(o => o.OrderNo == orderNo);
                var orderUsers     = orderEntities.Select(o => o.UserId).ToArray();
                var validateEntity = orderEntities.FirstOrDefault();

                if (validateEntity == null)
                {
                    Log.Error("申请记录不存在。");
                    throw new KeyNotFoundException("申请记录不存在。");
                }

                var validateOrder = validateEntity.ToModel();

                //model转换
                var applyModel = new ApplyOrderModel()
                {
                    OrderType    = validateOrder.OrderType,
                    StartDate    = model.StartDate,
                    EndDate      = model.EndDate,
                    IOHours      = model.IOHours,
                    UserIds      = orderUsers,
                    InformLeader = model.InformLeader,
                    WorkTransfer = model.WorkTransfer,
                    Recipient    = model.Recipient
                };

                //var orderDet = new OrderDet()
                //{
                //    StartDate = model.StartDate,
                //    EndDate = model.EndDate,
                //    StartTime = model.StartDate.TimeOfDay,
                //    EndTime = model.EndDate.TimeOfDay,
                //    Description = model.Description,
                //    InformLeader = model.InformLeader ?? false,
                //    WorkTransfer = model.WorkTransfer ?? false,
                //    Recipient = model.Recipient ?? 0,
                //    IOHours = model.IOHours
                //};

                //validateEntity.OrderDets = new List<OrderDet>() { orderDet };

                //下一步审批人
                var opprover =
                    dbContext.Users.FirstOrDefault(
                        it => validateEntity.NextAudit.HasValue && it.Id == validateEntity.NextAudit.Value);

                #endregion

                #region 验证

                var validateMsg = string.Empty;

                if (userId != validateOrder.ApplyUserId && (opprover != null && userId != opprover.Id))
                {
                    Log.Error("用户不能修改申请单。");
                    throw new InvalidOperationException("用户不能修改申请单。");
                }

                if (DateTime.Compare(model.StartDate, DateTime.Now.AddDays(-15)) < 0)
                {
                    validateMsg = "开始必须大于" + string.Format("{0:F}", DateTime.Now.AddDays(-15));
                    Log.Error(validateMsg);
                    throw new InvalidOperationException(validateMsg);
                }

                if (DateTime.Compare(model.StartDate, DateTime.Now.AddDays(15)) > 0)
                {
                    validateMsg = "开始必须小于" + string.Format("{0:F}", DateTime.Now.AddDays(15));
                    Log.Error(validateMsg);
                    throw new InvalidOperationException(validateMsg);
                }

                if (model.StartDate >= model.EndDate)
                {
                    validateMsg = "结束时间必须大于开始时间";
                    Log.Error(validateMsg);
                    throw new InvalidOperationException(validateMsg);
                }

                if (validateOrder.OrderType != OrderType.Overtime && validateOrder.OrderType != 0)
                {
                    TimeSpan dspWorkingDayAm = DateTime.Parse("08:30").TimeOfDay;
                    TimeSpan dspWorkingDayPm = DateTime.Parse("18:30:59").TimeOfDay;
                    if (model.StartDate.TimeOfDay < dspWorkingDayAm)
                    {
                        throw new InvalidOperationException("开始时间必须大于等于上午8点半");
                    }
                    if (model.EndDate.TimeOfDay > dspWorkingDayPm)
                    {
                        throw new InvalidOperationException("结束时间必须小于等于下午6点半");
                    }
                }
                else
                {
                    TimeSpan dspWorkingDayAm = DateTime.Parse("08:30").TimeOfDay;
                    if (model.StartDate.TimeOfDay < dspWorkingDayAm)
                    {
                        throw new InvalidOperationException("开始时间必须大于上午8点半");
                    }
                }

                var invalidUsers = IsOrderTimeAvailiable(applyModel, orderNo);
                if (!string.IsNullOrEmpty(invalidUsers))
                {
                    throw new InvalidOperationException(string.Format("用户({0})此申请时段已经占用。", invalidUsers));
                }

                #endregion

                #region 更新信息

                var existedUser = new List <int>(); //申请单原本已经有的用户
                if ((int)OrderStatus.Apply == validateEntity.Status ||
                    (opprover != null && opprover.ToModel().IsAdminStaff))
                {
                    #region 更新已存在的用户申请
                    orderEntities.ToList().ForEach(o =>
                    {
                        if (model.UserIds.Contains(o.UserId)) //更新用户申请单
                        {
                            OrderDet detailEntity = null;
                            if (o.OrderDets == null || o.OrderDets.Any() == false)
                            {
                                detailEntity = dbContext.OrderDets.FirstOrDefault(od => od.OrderId == o.Id);
                            }
                            else
                            {
                                detailEntity = o.OrderDets.FirstOrDefault();
                            }

                            //o.OrderType = (int)model.OrderType; 不能更新申请单类型

                            if (detailEntity != null)
                            {
                                detailEntity.StartDate    = model.StartDate.Date;
                                detailEntity.EndDate      = model.EndDate.Date;
                                detailEntity.IOHours      = model.IOHours;
                                detailEntity.StartTime    = model.StartDate.TimeOfDay;
                                detailEntity.EndTime      = model.EndDate.TimeOfDay;
                                detailEntity.Description  = model.Description;
                                detailEntity.InformLeader = model.InformLeader ?? detailEntity.InformLeader;
                                detailEntity.WorkTransfer = model.WorkTransfer ?? detailEntity.WorkTransfer;
                                detailEntity.Recipient    = model.Recipient ?? detailEntity.Recipient;
                            }

                            existedUser.Add(o.UserId); //申请单原本已经有的用户
                        }
                        else //移除用户申请单
                        {
                            o.OrderDets.ToList().ForEach(d => dbContext.OrderDets.Remove(d)); //移出申请单详细
                            dbContext.Orders.Remove(o);                                       //移出申请单
                            //o.Status = (int) OrderStatus.Canceled;
                            //o.NextAudit = 0;
                            //o.NextStep = 0;
                        }
                    });
                    #endregion

                    #region 添加新增用户申请
                    model.UserIds.ToList().ForEach(it =>
                    {
                        //validateOrder
                        if (!existedUser.Contains(it))
                        {
                            var newOrder    = validateEntity.Copyto();
                            newOrder.UserId = it;

                            //如果是修改撤销单
                            if (validateEntity.RefOrderId.HasValue)
                            {
                                var refOrder = GetOrderDetail(dbContext, validateEntity.RefOrderId.Value, false);

                                if (refOrder != null)
                                {
                                    newOrder.RefOrderId = _orderService.GetOrderIdByOrderNoAndUserId(dbContext,
                                                                                                     refOrder.OrderNo, it);
                                }
                            }

                            dbContext.Orders.Add(newOrder);
                        }
                    });
                    #endregion

                    //发送工作交接通知
                    if (model.WorkTransfer.HasValue && model.WorkTransfer.Value && model.Recipient.HasValue && validateEntity.OrderType != (int)OrderType.Overtime)
                    {
                        _orderService.AddNotification(dbContext, validateEntity.ToModel());
                    }

                    dbContext.SaveChanges();
                    return(true);
                }
                else
                {
                    Log.Error("已处于审批流程,不能更新。");
                    throw new InvalidOperationException("已处于审批流程,不能更新");
                }

                #endregion
            }
        }
        /// <summary>
        /// 添加请假信息
        ///
        /// 处理请假申请单逻辑
        ///
        /// </summary>
        /// <param name="model">申请单详细: 对应APP中的申请单详细</param>
        /// <param name="applicant">流程申请人Id</param>
        /// <returns>请假单信息</returns>
        public OrderModel AddOrder(ApplyOrderModel model, UserModel applicant)
        {
            /*
             *
             *
             *
             * **/

            #region 申请单详细

            // 1、新建申请单变量
            var order = new OrderModel()
            {
                OrderType    = model.OrderType,
                Status       = OrderStatus.Apply,
                ApplyUserId  = applicant.Id,
                IsBatchApply = (model.UserIds.Count() > 1),
                CreatedTime  = DateTime.Now,
            };

            // 2、新建申请单详情
            var orderDet = new OrderDetModel()
            {
                StartDate    = model.StartDate,
                EndDate      = model.EndDate,
                StartTime    = model.StartDate.TimeOfDay,
                EndTime      = model.EndDate.TimeOfDay,
                Description  = model.Description,
                InformLeader = model.InformLeader ?? false,
                WorkTransfer = model.WorkTransfer ?? false,
                Recipient    = model.Recipient ?? 0,
                IOHours      = model.IOHours
            };

            // 3、将申请单详情变量 放入到 申请单变量中
            order.OrderDets = new List <OrderDetModel>()
            {
                orderDet
            };
            #endregion

            // 4、逻辑处理
            using (var dbContext = new MissionskyOAEntities())
            {
                // 1、生成申请单号 、申请单用户
                // OrderNo --> int
                order.OrderNo = _orderService.GenerateOrderNo(dbContext); //生成申请单号

                /*
                 * OrderUsers -->  IList<OrderUserModel>
                 * model.UserIds --> 定义为 int[], 表示可以或者可能有多个申请用户
                 *
                 * **/
                order.OrderUsers = _userService.GetOrderUsers(dbContext, model.UserIds);


                // 2、验证申请单是否有效,并转换IOHours正负值
                ValidOrder(order, WorkflowOperation.Apply);


                // 3、添加初始审批信息
                AddAuditMessages(dbContext, order, applicant);

                // 4、添加申请单到数据库
                var dbOrders = AddOrderToDb(dbContext, order, WorkflowOperation.Apply);

                // 5、流程申请
                WorkflowProcessModel process = _orderService.Apply(dbContext, order);
                if (process == null)
                {
                    Log.Error("找不到流程。");
                    throw new InvalidOperationException("找不到流程。");
                }

                // 6、更新申请单工作流
                UpdateOrderProcess(dbContext, dbOrders, order, process, applicant);

                // 7、发送工作交接通知
                if (model.WorkTransfer.HasValue && model.WorkTransfer.Value && model.Recipient.HasValue && model.OrderType != OrderType.Overtime)
                {
                    _orderService.AddNotification(dbContext, order);
                }

                // 8、更新申请单其它信息
                dbContext.SaveChanges();

                // 9、
                return(order);
            }
        }
        /// <summary>
        /// 是否时间段重复申请
        ///
        /// 验证用户申请的时间段是否被占用
        ///
        /// </summary>
        /// <returns>是否时间段重复申请</returns>
        public string IsOrderTimeAvailiable(ApplyOrderModel model, int updateOrderNo)
        {
            using (var dbContext = new MissionskyOAEntities())
            {
                var startDate    = model.StartDate;
                var endDate      = model.EndDate;
                var invalidUsers = new List <int>(); //无效的用户

                // RefOrderId 为 审批人Id
                // 根据申请单号获取审批人Id
                var refOrderIds = dbContext.Orders.Where(it => it.OrderNo == updateOrderNo).Select(it => it.RefOrderId);

                model.UserIds.ToList().ForEach(userId =>
                {
                    //
                    var isTimeAvailabel = true;

                    /*
                     * 获取当前用户是否有正在审批或者正在执行的申请单
                     *      1、当前申请用户
                     *      2、不是现在正在申请的,也不是修改的
                     *      3、不是取消状态的
                     *      4、不是拒绝状态的
                     *      5、不是撤销状态的
                     *
                     * **/
                    var entityOrder =
                        dbContext.Orders.Where(
                            it =>
                            it.UserId == userId &&                    //查询用户的申请记录
                            it.OrderNo != updateOrderNo &&            //不是当前待添加或修改的申请记录
                            it.Status != (int)OrderStatus.Canceled && //过滤 取消状态的申请记录
                            it.Status != (int)OrderStatus.Rejected && //过滤 拒绝状态的申请记录
                            it.Status != (int)OrderStatus.Revoked);   //过滤 撤销状态的申请记录

                    var orderList = entityOrder.ToList();

                    foreach (Order item in orderList)
                    {
                        if (refOrderIds.Contains(item.Id)) //过滤撤销单
                        {
                            continue;
                        }

                        /*
                         *
                         *
                         * **/

                        //startdate>currentEndate or endate<currentStartdate
                        var avaliableStartDateTimeExist =
                            dbContext.OrderDets.FirstOrDefault(
                                it =>
                                it.OrderId == item.Id &&
                                (it.StartDate > endDate.Date || it.EndDate < startDate.Date) ||
                                (it.StartDate == startDate.Date && it.EndDate == endDate.Date));

                        if (avaliableStartDateTimeExist == null)
                        {
                            isTimeAvailabel = false;
                            break;
                        }

                        var avaliableDateInTheDbdate =
                            dbContext.OrderDets.FirstOrDefault(
                                it =>
                                it.OrderId == item.Id && (it.StartDate < startDate.Date) &&
                                it.EndDate > endDate.Date);
                        if (avaliableDateInTheDbdate != null)
                        {
                            isTimeAvailabel = false;
                            break;
                        }

                        var entityStarTimeExist =
                            dbContext.OrderDets.FirstOrDefault(
                                it =>
                                it.OrderId == item.Id && it.StartDate == startDate.Date &&
                                it.EndDate == endDate.Date && startDate.TimeOfDay >= it.StartTime &&
                                startDate.TimeOfDay < it.EndTime);
                        var entityEndTimeExist =
                            dbContext.OrderDets.FirstOrDefault(
                                it =>
                                it.OrderId == item.Id && it.StartDate == startDate.Date &&
                                it.EndDate == endDate.Date && endDate.TimeOfDay > it.StartTime &&
                                endDate.TimeOfDay <= it.EndTime);
                        var DBTimeBetweenCurrentApplyTime =
                            dbContext.OrderDets.FirstOrDefault(
                                it =>
                                it.OrderId == item.Id && it.StartDate == startDate.Date &&
                                it.EndDate == endDate.Date && startDate.TimeOfDay <= it.StartTime &&
                                endDate.TimeOfDay >= it.EndTime);
                        if ((entityStarTimeExist != null) || (entityEndTimeExist != null) || (DBTimeBetweenCurrentApplyTime != null))
                        {
                            isTimeAvailabel = false;
                            break;
                        }
                    }

                    if (!isTimeAvailabel)
                    {
                        invalidUsers.Add(userId);
                    }
                });

                /*
                 * 如果申请的时间段有被占用的话,那么返回占用时间段的申请人英文名
                 *
                 * **/
                return(invalidUsers.Count > 0
                    ? _userService.GetUsersName(dbContext, invalidUsers.ToArray())
                    : string.Empty);
            }
        }
Ejemplo n.º 5
0
        /// <summary>
        /// 验证申请单是否有效
        ///
        /// 这段验证在APP端提交表单到后台之前
        ///
        /// </summary>
        /// <param name="model">申请单</param>
        private void ValidApplyOrder(ApplyOrderModel model)
        {
            // 1、 验证申请人
            if (model.UserIds.Count() < 0)
            {
                Log.Error("请选择申请人。");
                throw new ApiBadRequestException("请选择申请人。");
            }

            // 2、验证申请时间

            /*
             * DateTime.Now.AddDays(-15) : 当前日期往前算15天
             * DateTime.Now.AddDays(15) : 当前日期往后算15天
             * **/
            if (DateTime.Compare(model.StartDate, DateTime.Now.AddDays(-15)) < 0)
            {
                throw new ApiBadRequestException("开始必须大于" + string.Format("{0:F}", DateTime.Now.AddDays(-15)));
            }

            if (DateTime.Compare(model.StartDate, DateTime.Now.AddDays(15)) > 0)
            {
                throw new ApiBadRequestException("开始必须小于" + string.Format("{0:F}", DateTime.Now.AddDays(15)));
            }

            if (model.StartDate >= model.EndDate)
            {
                throw new ApiBadRequestException("结束时间必须大于开始时间");
            }

            /*
             * 3、
             * 请假:
             *      开始时间必须大于等于上午8点半
             *      结束时间必须小于等于下午6点半
             *
             * 加班:
             *      开始时间必须大于上午8点半
             *
             * **/
            if (model.OrderType != OrderType.Overtime && model.OrderType != 0)
            {
                TimeSpan dspWorkingDayAM = DateTime.Parse("08:30").TimeOfDay;
                TimeSpan dspWorkingDayPM = DateTime.Parse("18:30:59").TimeOfDay;
                if (model.StartDate.TimeOfDay < dspWorkingDayAM)
                {
                    throw new ApiBadRequestException("开始时间必须大于等于上午8点半");
                }
                if (model.EndDate.TimeOfDay > dspWorkingDayPM)
                {
                    throw new ApiBadRequestException("结束时间必须小于等于下午6点半");
                }
            }
            else
            {
                // 加班 : 开始时间必须大于上午8点半
                TimeSpan dspWorkingDayAM = DateTime.Parse("08:30").TimeOfDay;
                if (model.StartDate.TimeOfDay < dspWorkingDayAM)
                {
                    throw new ApiBadRequestException("开始时间必须大于上午8点半");
                }
            }

            /*
             *  4、验证用户申请的时间段是否被占用
             *
             *  参数0:申请单提交到后台前,申请单号为0
             *
             * **/
            var invalidUsers = AskLeaveService.IsOrderTimeAvailiable(model, 0);


            if (!string.IsNullOrEmpty(invalidUsers))
            {
                throw new ApiBadRequestException(string.Format("用户({0})此申请时段已经占用。", invalidUsers));
            }
        }