private async Task AddPoolsAsync() { List <long> poolIds = new List <long> { 1000, 1001, 1002, 1003 }; var usersIds = poolIds.Select(id => new UserIdentificator { IsUsed = false, UserId = id }); var chatsIds = poolIds.Select(id => new ChatIdentificator { IsUsed = false, ChatId = id }); var channelsIds = poolIds.Select(id => new ChannelIdentificator { IsUsed = false, ChannelId = id }); var filesIds = poolIds.Select(id => new FileIdentificator { IsUsed = false, FileId = id }); await _context.AddRangeAsync(usersIds); await _context.AddRangeAsync(chatsIds); await _context.AddRangeAsync(channelsIds); await _context.AddRangeAsync(filesIds); await _context.SaveChangesAsync(); }
private async Task <List <MessageDto> > SaveChannelMessagesAsync(IEnumerable <MessageDto> messages) { using (MessengerDbContext context = contextFactory.Create()) { var messagesCondition = PredicateBuilder.New <Message>(); messagesCondition = messages.Aggregate(messagesCondition, (current, value) => current.Or(opt => opt.ChannelId == value.ConversationId && opt.GlobalId == value.GlobalId).Expand()); List <Message> existingMessages = await context.Messages.Where(messagesCondition).ToListAsync().ConfigureAwait(false); IEnumerable <MessageDto> nonExistingMessages = messages.Where(opt => !existingMessages.Any(p => p.GlobalId == opt.GlobalId && p.ChannelId == opt.ConversationId)); var newMessages = MessageConverter.GetMessages(nonExistingMessages); await context.AddRangeAsync(newMessages.OrderBy(opt => opt.SendingTime)).ConfigureAwait(false); await context.SaveChangesAsync().ConfigureAwait(false); var groupedMessages = newMessages.GroupBy(opt => opt.ChannelId.GetValueOrDefault()); foreach (var group in groupedMessages) { var lastMessage = group.OrderByDescending(opt => opt.SendingTime).FirstOrDefault(); if (lastMessage != null) { ConversationsService.UpdateConversationLastMessageId(group.Key, ConversationType.Channel, lastMessage.GlobalId); } } return(messages.ToList()); } }
public async Task <List <ChannelDto> > CreateOrUpdateUserChannelsAsync(List <ChannelDto> channels) { using (MessengerDbContext context = contextFactory.Create()) { var channelsCondition = PredicateBuilder.New <Channel>(); channelsCondition = channels.Aggregate(channelsCondition, (current, value) => current.Or(opt => opt.ChannelId == value.ChannelId).Expand()); List <Channel> existingChannels = await context.Channels .Include(opt => opt.ChannelUsers) .Where(channelsCondition) .ToListAsync() .ConfigureAwait(false); for (int i = 0; i < existingChannels.Count; i++) { ChannelDto editedChannel = channels.FirstOrDefault(opt => opt.ChannelId == existingChannels[i].ChannelId); existingChannels[i] = ChannelConverter.GetChannel(existingChannels[i], editedChannel); if (!editedChannel.ChannelUsers.IsNullOrEmpty()) { existingChannels[i].ChannelUsers = ChannelConverter.GetChannelUsers(editedChannel.ChannelUsers).ToList(); } } context.UpdateRange(existingChannels); List <ChannelDto> nonExistingChannels = channels.Where(channelDto => !existingChannels.Any(channel => channelDto.ChannelId == channel.ChannelId))?.ToList(); List <Channel> newChannels = ChannelConverter.GetChannels(nonExistingChannels); await context.AddRangeAsync(newChannels).ConfigureAwait(false); await context.SaveChangesAsync().ConfigureAwait(false); return(ChannelConverter.GetChannelsDto(newChannels.Concat(existingChannels))); } }
public async Task <MessageDto> EditMessageAsync(MessageDto message, long editorId) { using (MessengerDbContext context = contextFactory.Create()) { var messageQuery = context.Messages .Include(opt => opt.Attachments) .Where(opt => !opt.Deleted && opt.SenderId == message.SenderId && opt.ReceiverId == message.ReceiverId && opt.GlobalId == message.GlobalId); switch (message.ConversationType) { case ConversationType.Dialog: { messageQuery = messageQuery.Where(opt => opt.SenderId == editorId); } break; case ConversationType.Chat: { messageQuery = messageQuery.Where(opt => opt.ChatId == message.ConversationId && opt.SenderId == editorId); } break; case ConversationType.Channel: { messageQuery = messageQuery.Where(opt => opt.ChannelId == message.ConversationId) .Where(opt => opt.Channel.ChannelUsers .Any(channelUser => channelUser.UserId == editorId && channelUser.ChannelUserRole > ChannelUserRole.Subscriber)); } break; } var editableMessages = await messageQuery.ToListAsync().ConfigureAwait(false); if (!editableMessages.Any()) { throw new ObjectDoesNotExistsException(); } var editedMessages = new List <EditedMessage>(); editedMessages = editableMessages.Select(opt => new EditedMessage(opt, editorId)).ToList(); long updatedTime = DateTime.UtcNow.ToUnixTime(); foreach (var edited in editableMessages) { edited.Text = message.Text; edited.UpdatedAt = updatedTime; if (message.Attachments != null) { edited.Attachments = AttachmentConverter.GetAttachments(message.Attachments, edited.Id); } } context.UpdateRange(editableMessages); await context.AddRangeAsync(editedMessages).ConfigureAwait(false); await context.SaveChangesAsync().ConfigureAwait(false); return(MessageConverter.GetMessageDto(editableMessages.FirstOrDefault())); } }
public async Task CreateNewUsersAsync(List <UserVm> users) { try { var usersCondition = PredicateBuilder.New <User>(); usersCondition = users.Aggregate(usersCondition, (current, value) => current.Or(opt => opt.Id == value.Id).Expand()); using (MessengerDbContext context = contextFactory.Create()) { List <User> existingUsers = await context.Users.Where(usersCondition).ToListAsync().ConfigureAwait(false); List <UserVm> nonExistingUsers = users.Where(opt => !existingUsers.Any(p => p.Id == opt.Id)).ToList(); List <User> newUsers = nonExistingUsers.Select(user => new User { Id = user.Id.GetValueOrDefault(), Tag = user.Tag, NameFirst = user.NameFirst, NodeId = user.NodeId.GetValueOrDefault(), Confirmed = true }).ToList(); await context.AddRangeAsync(newUsers).ConfigureAwait(false); await context.SaveChangesAsync().ConfigureAwait(false); } } catch (Exception ex) { Logger.WriteLog(ex); } }
public async Task SaveNodePoolsAsync(NodePools nodePools) { var usersIdentificators = nodePools.UsersIds?.Select(userId => new UserIdentificator { UserId = userId }); var chatsIdentificators = nodePools.ChatsIds?.Select(chatId => new ChatIdentificator { ChatId = chatId }); var channelsIdentificators = nodePools.ChannelsIds?.Select(channelId => new ChannelIdentificator { ChannelId = channelId }); var filesIdentificators = nodePools.FilesIds?.Select(fileId => new FileIdentificator { FileId = fileId }); using (MessengerDbContext context = contextFactory.Create()) { if (usersIdentificators != null) { await context.AddRangeAsync(usersIdentificators).ConfigureAwait(false); } if (chatsIdentificators != null) { await context.AddRangeAsync(chatsIdentificators).ConfigureAwait(false); } if (channelsIdentificators != null) { await context.AddRangeAsync(channelsIdentificators).ConfigureAwait(false); } if (filesIdentificators != null) { await context.AddRangeAsync(filesIdentificators).ConfigureAwait(false); } await context.SaveChangesAsync().ConfigureAwait(false); } }
public async Task AddUsersToChatAsync(long chatId, IEnumerable <long> usersId, long requestorId) { try { List <ChatUser> chatUsers = new List <ChatUser>(); foreach (long userId in usersId) { chatUsers.Add(ChatUserConverter.GetNewChatUser(chatId, userId, requestorId)); } using (MessengerDbContext context = contextFactory.Create()) { await context.AddRangeAsync(chatUsers).ConfigureAwait(false); await context.SaveChangesAsync().ConfigureAwait(false); } } catch (Exception ex) { Logger.WriteLog(ex); } }
public async void DownloadMessageHistoryAsync(long nodeId, long conversationId, ConversationType conversationType, Guid?messageId, bool direction = true, int length = 1000) { try { using (MessengerDbContext context = contextFactory.Create()) { var nodeConnection = NodeData.ConnectionsService.GetNodeConnection(nodeId); if (nodeConnection != null) { List <MessageDto> loadedMessages = await NodeRequestSender.GetMessagesAsync(nodeConnection, conversationId, conversationType, messageId, null, direction, length) .ConfigureAwait(false); while (loadedMessages.Any()) { IEnumerable <Message> messages = MessageConverter.GetMessages(loadedMessages); var messagesCondition = PredicateBuilder.New <Message>(); messagesCondition = messages.Aggregate(messagesCondition, (current, value) => current.Or(opt => opt.GlobalId == value.GlobalId).Expand()); List <Message> existingMessages = await context.Messages.Where(messagesCondition).ToListAsync().ConfigureAwait(false); messages = messages.Where(opt => existingMessages.All(p => p.GlobalId != opt.GlobalId)); var navigationMessage = direction ? messages.LastOrDefault() : messages.FirstOrDefault(); loadedMessages = await NodeRequestSender.GetMessagesAsync(nodeConnection, conversationId, conversationType, navigationMessage.GlobalId, null, direction, length).ConfigureAwait(false); await context.AddRangeAsync(messages).ConfigureAwait(false); await context.SaveChangesAsync().ConfigureAwait(false); } } } } catch (Exception ex) { Logger.WriteLog(ex); } }
private async Task <List <MessageDto> > SaveDialogMessagesAsync(List <MessageDto> messages, long messagesOwnerId) { using (MessengerDbContext context = contextFactory.Create()) { using (var transaction = context.Database.BeginTransaction()) { try { List <Dialog> userDialogs = await context.Dialogs .Where(opt => opt.FirstUID == messagesOwnerId) .ToListAsync() .ConfigureAwait(false); List <MessageDto> newDialogsMessages = new List <MessageDto>(); List <MessageDto> existingDialogMessages = new List <MessageDto>(); List <long> nonExistingUsersId = new List <long>(); List <Dialog> newDialogs = new List <Dialog>(); List <Message> newMessages = new List <Message>(); foreach (var message in messages) { if (!message.Deleted) { Dialog dialog = userDialogs.FirstOrDefault(opt => (opt.FirstUID == message.SenderId && opt.SecondUID == message.ReceiverId) || (opt.SecondUID == message.SenderId && opt.FirstUID == message.ReceiverId)); if (dialog == null) { newDialogsMessages.Add(message); if (message.SenderId == messagesOwnerId && !nonExistingUsersId.Contains(message.ReceiverId.GetValueOrDefault())) { nonExistingUsersId.Add(message.ReceiverId.GetValueOrDefault()); } else if (message.ReceiverId == messagesOwnerId && !nonExistingUsersId.Contains(message.SenderId.GetValueOrDefault())) { nonExistingUsersId.Add(message.SenderId.GetValueOrDefault()); } } else { message.ConversationId = dialog.Id; existingDialogMessages.Add(message); } } } if (existingDialogMessages.Any()) { var messagesCondition = PredicateBuilder.New <Message>(); messagesCondition = existingDialogMessages.Aggregate(messagesCondition, (current, value) => current.Or(opt => opt.GlobalId == value.GlobalId && opt.DialogId == value.ConversationId).Expand()); List <Message> existingMessages = await context.Messages.Where(messagesCondition).ToListAsync().ConfigureAwait(false); var additionalMessages = MessageConverter.GetMessages( existingDialogMessages.Where( messageDto => !existingMessages.Any(existing => messageDto.GlobalId == existing.GlobalId && messageDto.ConversationId == existing.DialogId))); newMessages.AddRange(additionalMessages); } foreach (long userId in nonExistingUsersId) { newDialogs.Add(new Dialog { FirstUID = messagesOwnerId, SecondUID = userId }); if (messagesOwnerId != userId) { newDialogs.Add(new Dialog { FirstUID = userId, SecondUID = messagesOwnerId }); } } await context.AddRangeAsync(newDialogs).ConfigureAwait(false); await context.SaveChangesAsync().ConfigureAwait(false); foreach (var message in newDialogsMessages) { Dialog ownerDialog = newDialogs.FirstOrDefault(opt => opt.FirstUID == messagesOwnerId && ((opt.FirstUID == message.SenderId && opt.SecondUID == message.ReceiverId) || (opt.SecondUID == message.SenderId && opt.FirstUID == message.ReceiverId))); message.ConversationId = ownerDialog.Id; } newMessages.AddRange(MessageConverter.GetMessages(newDialogsMessages)); await context.AddRangeAsync(newMessages.OrderBy(opt => opt.SendingTime)).ConfigureAwait(false); await context.SaveChangesAsync().ConfigureAwait(false); transaction.Commit(); var groupedMessages = newMessages.GroupBy(opt => opt.DialogId.GetValueOrDefault()); foreach (var group in groupedMessages) { var lastMessage = group.OrderByDescending(opt => opt.SendingTime).FirstOrDefault(); if (lastMessage != null) { ConversationsService.UpdateConversationLastMessageId(group.Key, ConversationType.Dialog, lastMessage.GlobalId); } } return(MessageConverter.GetMessagesDto(newMessages)); } catch (Exception ex) { transaction.Rollback(); throw new MessageException("Save messages error.", ex); } } } }
public async Task <List <ChannelUserVm> > CreateOrEditChannelUsersAsync(List <ChannelUserVm> channelUsers, long requestorId) { try { using (MessengerDbContext context = contextFactory.Create()) { var channelUsersCondition = PredicateBuilder.New <ChannelUser>(); channelUsersCondition = channelUsers.Aggregate(channelUsersCondition, (current, value) => current.Or(opt => opt.ChannelId == value.ChannelId && opt.UserId == value.UserId).Expand()); List <ChannelUserVm> result = new List <ChannelUserVm>(); var existingChannelsUsers = ChannelConverter.GetChannelUsers(await context.ChannelUsers.Where(channelUsersCondition).ToListAsync().ConfigureAwait(false)); List <ChannelUserVm> nonExistingChannelUsers = new List <ChannelUserVm>(); if (existingChannelsUsers?.Any() ?? false) { var groups = existingChannelsUsers.GroupBy(opt => opt.ChannelId); foreach (var group in groups) { var edited = channelUsers.Where(opt => group.Any(p => p.ChannelId == opt.ChannelId && p.UserId == opt.UserId)).ToList(); result.AddRange(await updateChannelsService.EditChannelUsersAsync(edited, requestorId, group.Key.GetValueOrDefault()).ConfigureAwait(false)); } nonExistingChannelUsers = channelUsers.Where(opt => !existingChannelsUsers.Any(p => p.ChannelId == opt.ChannelId && p.UserId == opt.UserId)).ToList(); } else { nonExistingChannelUsers = channelUsers; } if (nonExistingChannelUsers?.Any() ?? false) { var newChannelUsers = ChannelConverter.GetChannelUsers(nonExistingChannelUsers).ToList(); await context.AddRangeAsync(newChannelUsers).ConfigureAwait(false); result.AddRange(ChannelConverter.GetChannelUsers(newChannelUsers)); } var channelGroups = channelUsers.GroupBy(opt => opt.ChannelId); foreach (var group in channelGroups) { var channelsNodesIds = await context.ChannelUsers .Where(opt => opt.ChannelId == group.Key) .Include(opt => opt.User) .Select(opt => opt.User.NodeId) .ToArrayAsync() .ConfigureAwait(false); var channel = await context.Channels.FindAsync(group.Key).ConfigureAwait(false); channel.NodesId = channelsNodesIds.Select(id => id.GetValueOrDefault()).Distinct().ToArray(); context.Channels.Update(channel); } await context.SaveChangesAsync().ConfigureAwait(false); return(result); } } catch (DbUpdateException ex) { if (ex.InnerException is PostgresException postgresException) { if (postgresException.ConstraintName == "FK_ChannelUsers_Channels_ChannelId") { throw new ConversationNotFoundException(); } if (postgresException.ConstraintName == "FK_ChannelUsers_Users_UserId") { throw new UserNotFoundException(); } } throw new AddOrRemoveChannelUsersException(); } }
public async Task <List <ChannelUserVm> > AddUsersToChannelAsync(List <long> usersId, long channelId, long requestorId) { using (MessengerDbContext context = contextFactory.Create()) { var usersCondition = PredicateBuilder.New <ChannelUser>(); usersCondition = usersId.Aggregate(usersCondition, (current, value) => current.Or(opt => opt.UserId == value).Expand()); var requestorUser = await context.ChannelUsers .FirstOrDefaultAsync(opt => opt.ChannelUserRole >= ChannelUserRole.Administrator && opt.ChannelId == channelId && opt.UserId == requestorId && opt.Channel.Deleted == false) .ConfigureAwait(false); if (requestorUser == null && (usersId.Count() > 1 || (usersId.Count() == 1 && usersId.ElementAt(0) != requestorId))) { throw new AddUserToChannelException(); } List <ChannelUser> existingUsers = await context.ChannelUsers .Where(usersCondition) .Where(opt => opt.ChannelId == channelId) .ToListAsync() .ConfigureAwait(false); List <long> nonExistingUsersId; if (existingUsers?.Any() ?? false) { nonExistingUsersId = usersId.Where(id => !existingUsers.Any(opt => opt.UserId == id)).ToList(); } else { nonExistingUsersId = usersId; } List <ChannelUser> newChannelUsers = nonExistingUsersId.Select(id => new ChannelUser { ChannelId = channelId, ChannelUserRole = ChannelUserRole.Subscriber, SubscribedTime = DateTime.UtcNow.ToUnixTime(), UserId = id }).ToList(); var users = await loadUsersService.GetUsersByIdAsync(nonExistingUsersId).ConfigureAwait(false); Channel channel = await context.Channels.FirstOrDefaultAsync(opt => opt.ChannelId == channelId).ConfigureAwait(false); channel.NodesId = channel.NodesId.Concat(users.Select(opt => opt.NodeId.GetValueOrDefault())).Distinct().ToArray(); context.Update(channel); var updatedUsers = new List <ChannelUser>(); if (existingUsers != null) { existingUsers.ForEach(channelUser => { if (!channelUser.Banned && channelUser.Deleted) { channelUser.Deleted = false; updatedUsers.Add(channelUser); } }); context.UpdateRange(existingUsers); } await context.AddRangeAsync(newChannelUsers).ConfigureAwait(false); await context.SaveChangesAsync().ConfigureAwait(false); return(ChannelConverter.GetChannelUsers(newChannelUsers.Concat(updatedUsers))); } }