private static async Task ApproveOrRejectLeaveRequest(IDialogContext context, Activity activity, string type, Employee employee)
        {
            var managerResponse = JsonConvert.DeserializeObject <ManagerResponse>(activity.Value.ToString());
            var leaveDetails    = await DocumentDBRepository.GetItemAsync <LeaveDetails>(managerResponse.LeaveId);

            var appliedByEmployee = await DocumentDBRepository.GetItemAsync <Employee>(leaveDetails.AppliedByEmailId);

            // Check the leave type and reduce in DB.
            leaveDetails.Status         = type == Constants.ApproveLeave ? LeaveStatus.Approved : LeaveStatus.Rejected;
            leaveDetails.ManagerComment = managerResponse.ManagerComment;
            await DocumentDBRepository.UpdateItemAsync(leaveDetails.LeaveId, leaveDetails);

            var conunt = EchoBot.GetDayCount(leaveDetails);

            var employeeView = EchoBot.EmployeeViewCard(appliedByEmployee, leaveDetails);
            UpdateMessageInfo managerMessageIds = leaveDetails.UpdateMessageInfo;

            ConnectorClient connector = new ConnectorClient(new Uri(activity.ServiceUrl));

            var managerCardUpdate = activity.CreateReply();
            var managerView       = EchoBot.ManagerViewCard(appliedByEmployee, leaveDetails);

            managerCardUpdate.Attachments.Add(managerView);

            if (!string.IsNullOrEmpty(managerMessageIds.Manager))
            {
                await connector.Conversations.UpdateActivityAsync(managerCardUpdate.Conversation.Id, managerMessageIds.Manager, managerCardUpdate);
            }

            bool isGroup = !string.IsNullOrEmpty(leaveDetails.ChannelId);

            if (!isGroup)
            {
                var messageId = await SendNotification(context, isGroup?leaveDetails.ChannelId : appliedByEmployee.UserUniqueId, null, employeeView, managerMessageIds.Employee, isGroup);  // Update card.

                var msg = $"Your {conunt} days leave has been {leaveDetails.Status.ToString()} by your manager.";
                messageId = await SendNotification(context, isGroup?leaveDetails.ChannelId : appliedByEmployee.UserUniqueId, msg, null, null, isGroup);   // Send message.

                if (string.IsNullOrEmpty(messageId))
                {
                    var reply = activity.CreateReply();
                    reply.Text = $"Failed to notify {appliedByEmployee.DisplayName}. Please try again later.";
                    await context.PostAsync(reply);
                }
            }
            else
            {
                var msg       = $" - Your {conunt} days leave has been {leaveDetails.Status.ToString()} by your manager.";
                var messageId = await SendChannelNotification(context, leaveDetails.ChannelId, null, employeeView, appliedByEmployee, managerMessageIds.Employee, leaveDetails.ConversationId, false); // Update card.

                messageId = await SendChannelNotification(context, leaveDetails.ChannelId, msg, null, appliedByEmployee, null, leaveDetails.ConversationId, true);                                     // Send message.

                if (string.IsNullOrEmpty(messageId))
                {
                    var reply = activity.CreateReply();
                    reply.Text = $"Failed to notify {appliedByEmployee.DisplayName}. Please try again later.";
                    await context.PostAsync(reply);
                }
            }
        }
        private static async Task WithdrawLeave(IDialogContext context, Activity activity, Employee employee, string leaveCategory)
        {
            var managerId = await GetManagerId(employee);

            if (managerId == null)
            {
                var reply = activity.CreateReply();
                reply.Text = "Unable to fetch your manager details. Please make sure that your manager has installed the Leave App.";
                await context.PostAsync(reply);
            }
            else
            {
                EditLeaveDetails vacationDetails = JsonConvert.DeserializeObject <EditLeaveDetails>(activity.Value.ToString());
                LeaveDetails     leaveDetails    = await DocumentDBRepository.GetItemAsync <LeaveDetails>(vacationDetails.LeaveId);

                leaveDetails.Status = LeaveStatus.Withdrawn;
                var attachment = EchoBot.ManagerViewCard(employee, leaveDetails);

                // Manger Updates.
                var conversationId = await SendNotification(context, managerId, null, attachment, leaveDetails.UpdateMessageInfo.Manager, false);

                if (!String.IsNullOrEmpty(conversationId))
                {
                    leaveDetails.UpdateMessageInfo.Manager = conversationId;
                }

                if (!String.IsNullOrEmpty(conversationId))
                {
                    ConnectorClient connector = new ConnectorClient(new Uri(activity.ServiceUrl));

                    var employeeCardReply = activity.CreateReply();
                    var employeeView      = EchoBot.EmployeeViewCard(employee, leaveDetails);
                    employeeCardReply.Attachments.Add(employeeView);

                    if (!string.IsNullOrEmpty(leaveDetails.UpdateMessageInfo.Employee))
                    {
                        await connector.Conversations.UpdateActivityAsync(employeeCardReply.Conversation.Id, leaveDetails.UpdateMessageInfo.Employee, employeeCardReply);
                    }
                    else
                    {
                        var reply = activity.CreateReply();
                        reply.Text = "Your leave request has been successfully withdrawn!";
                        await context.PostAsync(reply);

                        var msgToUpdate = await connector.Conversations.ReplyToActivityAsync(employeeCardReply);
                    }
                }
                else
                {
                    var reply = activity.CreateReply();
                    reply.Text = "Failed to send notification to your manger. Please try again later.";
                    await context.PostAsync(reply);
                }
                // Update DB for all the message Id realted changes
                await DocumentDBRepository.UpdateItemAsync(leaveDetails.LeaveId, leaveDetails);
            }
        }
        private static async Task ApplyForLeave(IDialogContext context, Activity activity, Employee employee, string leaveCategory)

        {
            if (string.IsNullOrEmpty(employee.ManagerEmailId) && string.IsNullOrEmpty(employee.DemoManagerEmailId))

            {
                var reply = activity.CreateReply();

                reply.Text = "Please set your manager and try again.";

                reply.Attachments.Add(EchoBot.SetManagerCard());

                await context.PostAsync(reply);

                return;
            }

            var managerId = await GetManagerId(employee);

            if (managerId == null)

            {
                var reply = activity.CreateReply();

                reply.Text = "Unable to fetch your manager details. Please make sure that your manager has installed the Leave App.";

                await context.PostAsync(reply);
            }
            else

            {
                VacationDetails vacationDetails = null;

                if (activity.Name == Constants.EditLeave) // Edit request

                {
                    var editRequest = JsonConvert.DeserializeObject <EditRequest>(activity.Value.ToString());

                    vacationDetails = editRequest.data;
                }
                else
                {
                    vacationDetails = JsonConvert.DeserializeObject <VacationDetails>(activity.Value.ToString());
                }

                LeaveDetails leaveDetails;

                if (!string.IsNullOrEmpty(vacationDetails.LeaveId))

                {
                    // Edit request

                    leaveDetails = await DocumentDBRepository.GetItemAsync <LeaveDetails>(vacationDetails.LeaveId);
                }
                else

                {
                    leaveDetails = new LeaveDetails();

                    leaveDetails.LeaveId = Guid.NewGuid().ToString();
                }

                leaveDetails.AppliedByEmailId = employee.EmailId;

                leaveDetails.EmployeeComment = vacationDetails.LeaveReason;

                var channelData = context.Activity.GetChannelData <TeamsChannelData>();

                leaveDetails.ChannelId = channelData.Channel?.Id; // Set channel Data if request is coming from a channel.

                if (!string.IsNullOrEmpty(leaveDetails.ChannelId))
                {
                    leaveDetails.ConversationId = activity.Conversation.Id;
                }

                leaveDetails.StartDate = new LeaveDate()

                {
                    Date = DateTime.Parse(vacationDetails.FromDate),

                    Type = (DayType)Enum.Parse(typeof(DayType), vacationDetails.FromDuration)
                };

                leaveDetails.EndDate = new LeaveDate()

                {
                    Date = DateTime.Parse(vacationDetails.ToDate),

                    Type = (DayType)Enum.Parse(typeof(DayType), vacationDetails.ToDuration)
                };

                leaveDetails.LeaveType = (LeaveType)Enum.Parse(typeof(LeaveType), vacationDetails.LeaveType);

                leaveDetails.Status = LeaveStatus.Pending;

                leaveDetails.ManagerEmailId = employee.ManagerEmailId;// Added for easy reporting.

                switch (leaveCategory)

                {
                case Constants.ApplyForPersonalLeave:

                    leaveDetails.LeaveCategory = LeaveCategory.Personal;

                    break;

                case Constants.ApplyForSickLeave:

                    leaveDetails.LeaveCategory = LeaveCategory.Sickness;

                    break;

                case Constants.ApplyForVacation:

                    leaveDetails.LeaveCategory = LeaveCategory.Vacation;

                    break;

                case Constants.ApplyForOtherLeave:

                default:

                    leaveDetails.LeaveCategory = LeaveCategory.Other;

                    break;
                }

                if (!string.IsNullOrEmpty(vacationDetails.LeaveId))

                {
                    // Edit request

                    await DocumentDBRepository.UpdateItemAsync(leaveDetails.LeaveId, leaveDetails);
                }
                else

                {
                    await DocumentDBRepository.CreateItemAsync(leaveDetails);
                }

                var attachment = EchoBot.ManagerViewCard(employee, leaveDetails);

                UpdateMessageInfo managerMessageIds = leaveDetails.UpdateMessageInfo;

                // Manger Updates.

                var conversationId = await SendNotification(context, managerId, null, attachment, managerMessageIds.Manager, false);

                if (!string.IsNullOrEmpty(conversationId))

                {
                    managerMessageIds.Manager = conversationId;
                }

                if (!string.IsNullOrEmpty(conversationId))

                {
                    ConnectorClient connector = new ConnectorClient(new Uri(activity.ServiceUrl));

                    var employeeCardReply = activity.CreateReply();

                    var employeeView = EchoBot.EmployeeViewCard(employee, leaveDetails);

                    employeeCardReply.Attachments.Add(employeeView);

                    if (!string.IsNullOrEmpty(managerMessageIds.Employee))

                    {
                        // Update existing item.

                        await connector.Conversations.UpdateActivityAsync(employeeCardReply.Conversation.Id, managerMessageIds.Employee, employeeCardReply);
                    }
                    else

                    {
                        var reply = activity.CreateReply();

                        reply.Text = "Your leave request has been successfully submitted to your manager! Please review your details below:";

                        await context.PostAsync(reply);

                        var msgToUpdate = await connector.Conversations.ReplyToActivityAsync(employeeCardReply);

                        managerMessageIds.Employee = msgToUpdate.Id;
                    }
                }
                else

                {
                    var reply = activity.CreateReply();

                    reply.Text = "Failed to send notification to your manger. Please try again later.";

                    await context.PostAsync(reply);
                }

                await DocumentDBRepository.UpdateItemAsync(leaveDetails.LeaveId, leaveDetails);
            }
        }