/// <inheritdoc/> public async ValueTask <ChatEventResult> ProcessCommandAsync(TextDeconstructionInformation info, ChatEvent originalChatEvent, IAsyncResponder responder, IReadOnlyDictionary <string, string> settings) { Contract.Ensures(info != null, "Text deconstruction information is required!"); var sender = originalChatEvent?.Message.Sender ?? throw new ArgumentNullException(nameof(originalChatEvent)); var item = await _googleCalendarConnector .GetNextMeetingAsync(sender.Email) .ConfigureAwait(false); if (item?.Summary == null) { return(new ChatEventResult("Can not find your next event! You may have no events or the service user account do not see your calendar.")); } var link = item.ConferenceData?.EntryPoints.FirstOrDefault(); var startDate = item.Start.DateTime.HasValue ? TimeZoneInfo.ConvertTime(item.Start.DateTime.Value, _currentTimeZoneFactory()).ToString("HH:mm", CultureInfo.InvariantCulture) : null; var keyValue = new KeyValue { Content = item.Summary, ContentMultiline = false, BottomLabel = startDate, Icon = "INVITE", Button = link == null ? null : ChatEventFactory.CreateTextButton("JOIN", link.Uri) }; var card = ChatEventFactory.CreateCard(keyValue); return(new ChatEventResult(card)); }
/// <inheritdoc/> public async ValueTask <ChatEventResult> ProcessCommandAsync( TextDeconstructionInformation info, ChatEvent originalChatEvent, IAsyncResponder responder, IPluginPropertiesAccessor accessor) { var plugins = await _storageService.GetAllPluginsAsync(); var results = plugins.SelectMany(it => it.Examples ?? Array.Empty <string>()).DefaultIfEmpty(string.Empty); return(new ChatEventResult( ChatEventFactory.CreateCard( new TextParagraph { Text = string.Join("<br />", results) }))); }
#pragma warning restore CC0021 /// <inheritdoc/> public async ValueTask <ChatEventResult> ProcessCommandAsync( TextDeconstructionInformation info, ChatEvent originalChatEvent, IAsyncResponder responder, IPluginPropertiesAccessor accessor) { var userName = info.Entities.GetValueOrDefault("Text")?.FirstOrDefault(); var senderEmail = originalChatEvent?.Message?.Sender.Email; if (string.IsNullOrWhiteSpace(userName)) { return(new ChatEventResult("User was not found!")); } var users = await _storageService.GetAllUsersAsync(); var foundUsers = users .Where(u => MatchUserByName(u, userName)) .Where(u => users.RequestorHasAccessToUserData(u, senderEmail)) .ToArray(); if (foundUsers.Length == 0) { return(new ChatEventResult($"User with name {userName} was not found!")); } return(new ChatEventResult( foundUsers.Select(user => ChatEventFactory.CreateCard( new CardBody { Icon = "PERSON", TopLabel = user.Name, Content = $"{user.Email}\n_{user.Department?.Name}, {FindManagerName(users, user.Manager?.OpenAirUserId)}_", ContentMultiline = true, BottomLabel = string.Join(", ", user.Customers?.Select(it => it.Name) ?? new string[0]), })) .ToArray())); }
/// <summary>Processes the specified timesheets.</summary> public async Task SendTimesheetNotificationsToUsersAsync( IReadOnlyList <Timesheet> timesheets, string email, string department, bool notify, bool notifyByEmail, TimesheetStates state, GoogleChatAddress address, IHangoutsChatConnector connector) { string text; var filteredTimesheet = timesheets .Where(it => department == null || department.Equals(it.DepartmentName, StringComparison.InvariantCultureIgnoreCase)) .OrderBy(it => it.ManagerName) .ThenBy(it => it.UserName) .ToArray(); var notifiedUserList = new List <string>(); if (filteredTimesheet.Length == 0) { var responses = OpenAirText.GetText(state, OpenAirTextTypes.AllAreDone).Split('|', StringSplitOptions.RemoveEmptyEntries); var rand = new Random(); text = responses[rand.Next(0, responses.Length - 1)]; } else if (notify && filteredTimesheet.Length > 0) { notifiedUserList.AddRange( await NotifyUsersOverChatAsync(connector, state, filteredTimesheet)); if (notifyByEmail) { var textMessage = OpenAirText.GetText(state, OpenAirTextTypes.Notify); var emails = filteredTimesheet .Where(it => !notifiedUserList.Contains(it.UserName)) .Apply(it => notifiedUserList.Add(it.UserName)) .Select(it => it.UserEmail) .Distinct() .ToArray(); await _mailService.SendMailAsync("Timesheet is pending", textMessage, emails); } text = notifiedUserList.Count == filteredTimesheet.Length ? string.Format( CultureInfo.InvariantCulture, OpenAirText.GetText(state, OpenAirTextTypes.AllAreNotified), notifiedUserList.Count) : OpenAirText.GetText(state, OpenAirTextTypes.SomeAreNotified) + GetCardText(filteredTimesheet, notifiedUserList); } else { text = OpenAirText.GetText(state, OpenAirTextTypes.SomeAreDone) + GetCardText(filteredTimesheet, notifiedUserList); } var paragraph = new TextParagraph { Text = text }; var card = ChatEventFactory.CreateCard(paragraph); if (address != null) { await connector.SendMessageAsync(null, address, card); } else if (email != null) { var emailedUsers = string.Join("</b><br/><b>", notifiedUserList); var emailText = $"{text}<br/><br/><b>The following people where notified by a direct massage or email:" + $"<br/><b>{emailedUsers}</b>"; await _mailService.SendMailAsync("Users not notified", emailText, email); } }
/// <summary>Processes the specified timesheets.</summary> private async Task ProcessNotify( IReadOnlyList <Timesheet> timesheets, string department, bool notify, GoogleChatAddress address, IHangoutsChatConnector connector) { string text; var filteredTimesheet = department == null ? timesheets : timesheets .Where(it => it.DepartmentName.Equals(department, StringComparison.InvariantCultureIgnoreCase)) .ToArray(); var notifiedUserList = new List <string>(); if (filteredTimesheet.Count == 0) { text = "<b>All user have submitted timesheets.</b>"; } else if (notify && filteredTimesheet.Count > 0) { var emails = filteredTimesheet.Select(it => it.UserEmail).ToArray(); var storeAddresses = _storageService.GetAddresses(); var filteredAddresses = storeAddresses.Where(it => emails.Contains(it.UserEmail)).ToArray(); var addressesForUpdate = new List <GoogleAddress>(); IReadOnlyList <GoogleAddress> privateAddresses = new GoogleAddress[0]; if (filteredAddresses.Length < timesheets.Count) { var storeAddressesNames = storeAddresses.Select(it => it.SpaceName).ToArray(); privateAddresses = connector .GetPrivateAddress(storeAddressesNames) .Select(it => new GoogleAddress { SpaceName = it.Space.Name, UserName = it.Sender.Name, UserDisplayName = it.Sender.DisplayName }) .ToArray(); // Store inactive spaces, so not to be requested the next time addressesForUpdate.AddRange(privateAddresses.Where(it => it.UserName == null)); } foreach (var timesheet in filteredTimesheet) { var message = $"{timesheet.UserName}, Please submit your timesheet. Your current hours are {timesheet.Total}."; var addr = filteredAddresses.FirstOrDefault(it => it.UserEmail == timesheet.UserEmail); if (addr == null) { addr = privateAddresses.FirstOrDefault(it => it.UserDisplayName == timesheet.UserName); if (addr == null) { continue; } addr.UserEmail = timesheet.UserEmail; addressesForUpdate.Add(addr); } notifiedUserList.Add(timesheet.UserName); await connector.SendMessageAsync( message, new GoogleChatAddress(addr.SpaceName, string.Empty, "DM", addr.UserName, addr.UserDisplayName)); } if (addressesForUpdate.Count > 0) { await _storageService.AddAddressesAsync(addressesForUpdate); } text = notifiedUserList.Count == filteredTimesheet.Count ? "All users width unsubmitted timesheets are notified! Total of " + notifiedUserList.Count : "The following people where not notified: <br>" + GetCardText(filteredTimesheet, notifiedUserList); } else { text = "The following people have to submit timesheet: <br>" + GetCardText(filteredTimesheet, notifiedUserList); } var paragraph = new TextParagraph { Text = text }; var card = ChatEventFactory.CreateCard(paragraph); await connector.SendMessageAsync(null, address, card); }