diff --git a/src/app/global/app_sections_config.nim b/src/app/global/app_sections_config.nim index 42128d8e70..8df7666217 100644 --- a/src/app/global/app_sections_config.nim +++ b/src/app/global/app_sections_config.nim @@ -1,4 +1,3 @@ -const CHAT_SECTION_ID* = "chat" const CHAT_SECTION_NAME* = "Chat" const CHAT_SECTION_ICON* = "chat" diff --git a/src/app/global/local_account_sensitive_settings.nim b/src/app/global/local_account_sensitive_settings.nim index 59190895c2..7a07a106a1 100644 --- a/src/app/global/local_account_sensitive_settings.nim +++ b/src/app/global/local_account_sensitive_settings.nim @@ -65,7 +65,7 @@ const DEFAULT_SHOW_DELETE_MESSAGE_WARNING = true const LSS_KEY_DOWNLOAD_CHANNEL_MESSAGES_ENABLED* = "downloadChannelMessagesEnabled" const DEFAULT_DOWNLOAD_CHANNEL_MESSAGES_ENABLED = false const LSS_KEY_ACTIVE_SECTION* = "activeSection" -const DEFAULT_ACTIVE_SECTION = "chat" +const DEFAULT_ACTIVE_SECTION = "" const LSS_KEY_SHOW_BROWSER_SELECTOR* = "showBrowserSelector" const DEFAULT_SHOW_BROWSER_SELECTOR = true const LSS_KEY_OPEN_LINKS_IN_STATUS* = "openLinksInStatus" diff --git a/src/app/modules/main/activity_center/module.nim b/src/app/modules/main/activity_center/module.nim index 07297209d9..df09c0ffa2 100644 --- a/src/app/modules/main/activity_center/module.nim +++ b/src/app/modules/main/activity_center/module.nim @@ -78,7 +78,10 @@ method convertToItems*( let chatDetails = self.controller.getChatDetails(n.chatId) # default section id is `Chat` section - let sectionId = if(chatDetails.communityId.len > 0): chatDetails.communityId else: conf.CHAT_SECTION_ID + let sectionId = if(chatDetails.communityId.len > 0): + chatDetails.communityId + else: + singletonInstance.userProfile.getPubKey() if (n.message.id != ""): # If there is a message in the Notification, transfer it to a MessageItem (QObject) diff --git a/src/app/modules/main/app_search/controller.nim b/src/app/modules/main/app_search/controller.nim index ffe6131549..03dcce0d4f 100644 --- a/src/app/modules/main/app_search/controller.nim +++ b/src/app/modules/main/app_search/controller.nim @@ -2,7 +2,7 @@ import Tables, chronicles import io_interface import ../../../global/app_signals -import ../../../global/app_sections_config as conf +import ../../../global/global_singleton import ../../../../app_service/service/contacts/service as contact_service import ../../../../app_service/service/chat/service as chat_service import ../../../../app_service/service/community/service as community_service @@ -90,7 +90,7 @@ proc getJoinedCommunities*(self: Controller): seq[CommunityDto] = proc getCommunityById*(self: Controller, communityId: string): CommunityDto = return self.communityService.getCommunityById(communityId) -proc getAllChatsForCommunity*(self: Controller, communityId: string): seq[Chat] = +proc getAllChatsForCommunity*(self: Controller, communityId: string): seq[ChatDto] = return self.communityService.getAllChats(communityId) proc getChatDetailsForChatTypes*(self: Controller, types: seq[ChatType]): seq[ChatDto] = @@ -110,8 +110,8 @@ proc searchMessages*(self: Controller, searchTerm: string) = if (self.searchSubLocation.len > 0): chats.add(self.searchSubLocation) elif (self.searchLocation.len > 0): - # If "Chat" is set for the meassgeSearchLocation that means we need to search in all chats from the chat section. - if (self.searchLocation != conf.CHAT_SECTION_ID): + # If user's pubkey is set for the meassgeSearchLocation that means we need to search in all chats from the personal chat section. + if (self.searchLocation != singletonInstance.userProfile.getPubKey()): communities.add(self.searchLocation) else: let types = @[ChatType.OneToOne, ChatType.Public, ChatType.PrivateGroupChat] diff --git a/src/app/modules/main/app_search/module.nim b/src/app/modules/main/app_search/module.nim index 760a22fc95..840f4ef01f 100644 --- a/src/app/modules/main/app_search/module.nim +++ b/src/app/modules/main/app_search/module.nim @@ -67,8 +67,8 @@ method getModuleAsVariant*(self: Module): QVariant = return self.viewVariant proc buildLocationMenuForChat(self: Module): location_menu_item.Item = - var item = location_menu_item.initItem(conf.CHAT_SECTION_ID, SEARCH_MENU_LOCATION_CHAT_SECTION_NAME, "", "chat", "", - false) + var item = location_menu_item.initItem(singletonInstance.userProfile.getPubKey(), + SEARCH_MENU_LOCATION_CHAT_SECTION_NAME, "", "chat", "", false) let types = @[ChatType.OneToOne, ChatType.Public, ChatType.PrivateGroupChat] let displayedChats = self.controller.getChatDetailsForChatTypes(types) @@ -176,7 +176,8 @@ method onSearchMessagesDone*(self: Module, messages: seq[MessageDto]) = channels.add(item) # Add chats - if(self.controller.searchLocation().len == 0 or self.controller.searchLocation() == conf.CHAT_SECTION_ID and + if(self.controller.searchLocation().len == 0 or + self.controller.searchLocation() == singletonInstance.userProfile.getPubKey() and self.controller.searchSubLocation().len == 0): let types = @[ChatType.OneToOne, ChatType.Public, ChatType.PrivateGroupChat] let displayedChats = self.controller.getChatDetailsForChatTypes(types) @@ -196,7 +197,7 @@ method onSearchMessagesDone*(self: Module, messages: seq[MessageDto]) = let item = result_item.initItem(c.id, "", "", c.id, chatName, SEARCH_RESULT_CHATS_SECTION_NAME, chatImage, c.color, "", "", chatImage, c.color, isIdenticon) - self.controller.addResultItemDetails(c.id, conf.CHAT_SECTION_ID, c.id) + self.controller.addResultItemDetails(c.id, singletonInstance.userProfile.getPubKey(), c.id) items.add(item) # Add channels in order as requested by the design @@ -222,7 +223,8 @@ method onSearchMessagesDone*(self: Module, messages: seq[MessageDto]) = let item = result_item.initItem(m.id, m.text, $m.timestamp, m.`from`, senderName, SEARCH_RESULT_MESSAGES_SECTION_NAME, senderImage, "", chatName, "", chatImage, chatDto.color, isIdenticon) - self.controller.addResultItemDetails(m.id, conf.CHAT_SECTION_ID, chatDto.id, m.id) + self.controller.addResultItemDetails(m.id, singletonInstance.userProfile.getPubKey(), + chatDto.id, m.id) items.add(item) else: let community = self.controller.getCommunityById(chatDto.communityId) diff --git a/src/app/modules/main/chat_section/controller.nim b/src/app/modules/main/chat_section/controller.nim index 5fbbb3a951..ca5d43c256 100644 --- a/src/app/modules/main/chat_section/controller.nim +++ b/src/app/modules/main/chat_section/controller.nim @@ -207,7 +207,7 @@ proc getMyCommunity*(self: Controller): CommunityDto = proc getCategories*(self: Controller, communityId: string): seq[Category] = return self.communityService.getCategories(communityId) -proc getChats*(self: Controller, communityId: string, categoryId: string): seq[Chat] = +proc getChats*(self: Controller, communityId: string, categoryId: string): seq[ChatDto] = return self.communityService.getChats(communityId, categoryId) proc getChatDetails*(self: Controller, communityId, chatId: string): ChatDto = diff --git a/src/app/modules/main/chat_section/module.nim b/src/app/modules/main/chat_section/module.nim index d9e5b4d05a..0bbe9185fb 100644 --- a/src/app/modules/main/chat_section/module.nim +++ b/src/app/modules/main/chat_section/module.nim @@ -148,69 +148,66 @@ proc buildCommunityUI(self: Module, events: EventEmitter, mailserversService: mailservers_service.Service) = var selectedItemId = "" var selectedSubItemId = "" - let communities = self.controller.getJoinedCommunities() - for comm in communities: - if(self.controller.getMySectionId() != comm.id): - continue + let comm = self.controller.getMyCommunity() + + # handle channels which don't belong to any category + let chats = self.controller.getChats(comm.id, "") + for c in chats: + let chatDto = self.controller.getChatDetails(comm.id, c.id) - # handle channels which don't belong to any category - let chats = self.controller.getChats(comm.id, "") - for c in chats: + let hasNotification = chatDto.unviewedMessagesCount > 0 or chatDto.unviewedMentionsCount > 0 + let notificationsCount = chatDto.unviewedMentionsCount + let amIChatAdmin = comm.admin + let channelItem = initItem(chatDto.id, chatDto.name, chatDto.identicon, false, chatDto.color, + chatDto.emoji, chatDto.description, chatDto.chatType.int, amIChatAdmin, hasNotification, + notificationsCount, chatDto.muted, blocked=false, active = false, c.position, c.categoryId) + self.view.chatsModel().appendItem(channelItem) + self.addSubmodule(chatDto.id, true, true, events, settingsService, contactService, chatService, communityService, + messageService, gifService, mailserversService) + + # make the first channel which doesn't belong to any category active when load the app + if(selectedItemId.len == 0): + selectedItemId = channelItem.id + + # handle categories and channels for each category + let categories = self.controller.getCategories(comm.id) + for cat in categories: + var hasNotificationPerCategory = false + var notificationsCountPerCategory = 0 + var categoryChannels: seq[SubItem] + + let categoryChats = self.controller.getChats(comm.id, cat.id) + for c in categoryChats: let chatDto = self.controller.getChatDetails(comm.id, c.id) let hasNotification = chatDto.unviewedMessagesCount > 0 or chatDto.unviewedMentionsCount > 0 let notificationsCount = chatDto.unviewedMentionsCount + + hasNotificationPerCategory = hasNotificationPerCategory or hasNotification + notificationsCountPerCategory += notificationsCount + let amIChatAdmin = comm.admin - let channelItem = initItem(chatDto.id, chatDto.name, chatDto.identicon, false, chatDto.color, - chatDto.emoji, chatDto.description, chatDto.chatType.int, amIChatAdmin, hasNotification, - notificationsCount, chatDto.muted, blocked=false, active = false, c.position, c.categoryId) - self.view.chatsModel().appendItem(channelItem) + + let channelItem = initSubItem(chatDto.id, cat.id, chatDto.name, chatDto.identicon, + isIdenticon=false, chatDto.color, chatDto.emoji, chatDto.description, chatDto.chatType.int, + amIChatAdmin, hasNotification, notificationsCount, chatDto.muted, blocked=false, + active=false, c.position) + categoryChannels.add(channelItem) self.addSubmodule(chatDto.id, true, true, events, settingsService, contactService, chatService, communityService, messageService, gifService, mailserversService) - # make the first channel which doesn't belong to any category active when load the app + # in case there is no channels beyond categories, + # make the first channel of the first category active when load the app if(selectedItemId.len == 0): - selectedItemId = channelItem.id + selectedItemId = cat.id + selectedSubItemId = channelItem.id - # handle categories and channels for each category - let categories = self.controller.getCategories(comm.id) - for cat in categories: - var hasNotificationPerCategory = false - var notificationsCountPerCategory = 0 - var categoryChannels: seq[SubItem] - - let categoryChats = self.controller.getChats(comm.id, cat.id) - for c in categoryChats: - let chatDto = self.controller.getChatDetails(comm.id, c.id) - - let hasNotification = chatDto.unviewedMessagesCount > 0 or chatDto.unviewedMentionsCount > 0 - let notificationsCount = chatDto.unviewedMentionsCount - - hasNotificationPerCategory = hasNotificationPerCategory or hasNotification - notificationsCountPerCategory += notificationsCount - - let amIChatAdmin = comm.admin - - let channelItem = initSubItem(chatDto.id, cat.id, chatDto.name, chatDto.identicon, - isIdenticon=false, chatDto.color, chatDto.emoji, chatDto.description, chatDto.chatType.int, - amIChatAdmin, hasNotification, notificationsCount, chatDto.muted, blocked=false, - active=false, c.position) - categoryChannels.add(channelItem) - self.addSubmodule(chatDto.id, true, true, events, settingsService, contactService, chatService, communityService, - messageService, gifService, mailserversService) - - # in case there is no channels beyond categories, - # make the first channel of the first category active when load the app - if(selectedItemId.len == 0): - selectedItemId = cat.id - selectedSubItemId = channelItem.id - - var categoryItem = initItem(cat.id, cat.name, icon="", isIdenticon=false, color="", emoji="", - description="", ChatType.Unknown.int, amIChatAdmin=false, hasNotificationPerCategory, - notificationsCountPerCategory, muted=false, blocked=false, active=false, - cat.position, cat.id) - categoryItem.prependSubItems(categoryChannels) - self.view.chatsModel().appendItem(categoryItem) + var categoryItem = initItem(cat.id, cat.name, icon="", isIdenticon=false, color="", emoji="", + description="", ChatType.Unknown.int, amIChatAdmin=false, hasNotificationPerCategory, + notificationsCountPerCategory, muted=false, blocked=false, active=false, + cat.position, cat.id) + categoryItem.prependSubItems(categoryChannels) + self.view.chatsModel().appendItem(categoryItem) self.setActiveItemSubItem(selectedItemId, selectedSubItemId) @@ -635,7 +632,8 @@ method onContactDetailsUpdated*(self: Module, publicKey: string) = self.view.contactRequestsModel().addItem(item) self.updateParentBadgeNotifications() singletonInstance.globalEvents.showNewContactRequestNotification("New Contact Request", - fmt "{contactDetails.displayName} added you as contact", conf.CHAT_SECTION_ID) + fmt "{contactDetails.displayName} added you as contact", + singletonInstance.userProfile.getPubKey()) let chatName = contactDetails.displayName let chatImage = contactDetails.icon @@ -663,8 +661,10 @@ method onNewMessagesReceived*(self: Module, chatId: string, unviewedMessagesCoun self.controller.getMySectionId(), chatId, m.id) method onMeMentionedInEditedMessage*(self: Module, chatId: string, editedMessage : MessageDto) = - if(editedMessage.communityId.len == 0 and self.controller.getMySectionId() != conf.CHAT_SECTION_ID or - editedMessage.communityId.len > 0 and self.controller.getMySectionId() != editedMessage.communityId): + if((editedMessage.communityId.len == 0 and + self.controller.getMySectionId() != singletonInstance.userProfile.getPubKey()) or + (editedMessage.communityId.len > 0 and + self.controller.getMySectionId() != editedMessage.communityId)): return var (sectionHasUnreadMessages, sectionNotificationCount) = self.view.chatsModel().getAllNotifications() self.updateBadgeNotifications(chatId, sectionHasUnreadMessages, sectionNotificationCount + 1) @@ -777,7 +777,7 @@ method addChatIfDontExist*(self: Module, let sectionId = self.controller.getMySectionId() if(belongsToCommunity and sectionId != chat.communityId or - not belongsToCommunity and sectionId != conf.CHAT_SECTION_ID): + not belongsToCommunity and sectionId != singletonInstance.userProfile.getPubKey()): return if self.doesCatOrChatExist(chat.id): diff --git a/src/app/modules/main/communities/module.nim b/src/app/modules/main/communities/module.nim index 818a7f80ac..58e3520f48 100644 --- a/src/app/modules/main/communities/module.nim +++ b/src/app/modules/main/communities/module.nim @@ -9,6 +9,7 @@ import ../../../global/global_singleton import ../../../core/eventemitter import ../../../../app_service/service/community/service as community_service import ../../../../app_service/service/contacts/service as contacts_service +import ../../../../app_service/service/chat/dto/chat export io_interface diff --git a/src/app/modules/main/controller.nim b/src/app/modules/main/controller.nim index 11d2e26d03..b871138607 100644 --- a/src/app/modules/main/controller.nim +++ b/src/app/modules/main/controller.nim @@ -171,7 +171,10 @@ proc init*(self: Controller) = self.events.on(SIGNAL_MAKE_SECTION_CHAT_ACTIVE) do(e: Args): var args = ActiveSectionChatArgs(e) - let sectionType = if args.sectionId == conf.CHAT_SECTION_ID: SectionType.Chat else: SectionType.Community + let sectionType = if args.sectionId == singletonInstance.userProfile.getPubKey(): + SectionType.Chat + else: + SectionType.Community self.setActiveSection(args.sectionId, sectionType) self.events.on(SIGNAL_OS_NOTIFICATION_CLICKED) do(e: Args): @@ -194,6 +197,9 @@ proc isConnected*(self: Controller): bool = proc getJoinedCommunities*(self: Controller): seq[CommunityDto] = return self.communityService.getJoinedCommunities() +proc getChannelGroups*(self: Controller): seq[ChannelGroupDto] = + return self.chatService.getChannelGroups() + proc checkForStoringPassword*(self: Controller) = # This proc is called once user is logged in irrespective he is logged in # through the onboarding or login view. diff --git a/src/app/modules/main/module.nim b/src/app/modules/main/module.nim index 152fb1ffd6..56240c54a1 100644 --- a/src/app/modules/main/module.nim +++ b/src/app/modules/main/module.nim @@ -62,8 +62,7 @@ type view: View viewVariant: QVariant controller: Controller - chatSectionModule: chat_section_module.AccessInterface - communitySectionsModule: OrderedTable[string, chat_section_module.AccessInterface] + channelGroupModules: OrderedTable[string, chat_section_module.AccessInterface] walletSectionModule: wallet_section_module.AccessInterface browserSectionModule: browser_section_module.AccessInterface profileSectionModule: profile_section_module.AccessInterface @@ -133,9 +132,7 @@ proc newModule*[T]( result.moduleLoaded = false # Submodules - result.chatSectionModule = chat_section_module.newModule(result, events, conf.CHAT_SECTION_ID, false, settingsService, - contactsService, chatService, communityService, messageService, gifService, mailserversService) - result.communitySectionsModule = initOrderedTable[string, chat_section_module.AccessInterface]() + result.channelGroupModules = initOrderedTable[string, chat_section_module.AccessInterface]() result.walletSectionModule = wallet_section_module.newModule( result, events, tokenService, transactionService, collectible_service, walletAccountService, @@ -158,14 +155,13 @@ proc newModule*[T]( result.networksModule = networks_module.newModule(result, events, networkService, walletAccountService, settingsService) method delete*[T](self: Module[T]) = - self.chatSectionModule.delete self.profileSectionModule.delete self.stickersModule.delete self.activityCenterModule.delete self.communitiesModule.delete - for cModule in self.communitySectionsModule.values: + for cModule in self.channelGroupModules.values: cModule.delete - self.communitySectionsModule.clear + self.channelGroupModules.clear self.walletSectionModule.delete self.browserSectionModule.delete self.appSearchModule.delete @@ -175,32 +171,43 @@ method delete*[T](self: Module[T]) = self.viewVariant.delete self.controller.delete -proc createCommunityItem[T](self: Module[T], c: CommunityDto): SectionItem = - let (unviewedCount, mentionsCount) = self.controller.getNumOfNotificationsForCommunity(c.id) +proc createChannelGroupItem[T](self: Module[T], c: ChannelGroupDto): SectionItem = + let isCommunity = c.channelGroupType == ChannelGroupType.Community + var communityDetails: CommunityDto + var unviewedCount, mentionsCount: int + if (isCommunity): + (unviewedCount, mentionsCount) = self.controller.getNumOfNotificationsForCommunity(c.id) + communityDetails = self.controller.getCommunityById(c.id) + else: + let receivedContactRequests = self.controller.getContacts(ContactsGroup.IncomingPendingContactRequests) + (unviewedCount, mentionsCount) = self.controller.getNumOfNotificaitonsForChat() + mentionsCount = mentionsCount + receivedContactRequests.len + let hasNotification = unviewedCount > 0 or mentionsCount > 0 let notificationsCount = mentionsCount # we need to add here number of requests let active = self.getActiveSectionId() == c.id # We must pass on if the current item section is currently active to keep that property as it is result = initItem( c.id, - SectionType.Community, + if isCommunity: SectionType.Community else: SectionType.Chat, c.name, c.admin, c.description, c.images.thumbnail, - icon = "", + icon = if (isCommunity): "" else: conf.CHAT_SECTION_ICON, c.color, hasNotification, notificationsCount, active, - enabled = singletonInstance.localAccountSensitiveSettings.getCommunitiesEnabled(), - c.joined, - c.canJoin, + enabled = (not isCommunity or + singletonInstance.localAccountSensitiveSettings.getCommunitiesEnabled()), + if (isCommunity): communityDetails.joined else: true, + if (isCommunity): communityDetails.canJoin else: true, c.canManageUsers, - c.canRequestAccess, - c.isMember, + if (isCommunity): communityDetails.canRequestAccess else: true, + if (isCommunity): communityDetails.isMember else: true, c.permissions.access, c.permissions.ensOnly, - c.members.map(proc(member: Member): user_item.Item = + c.members.map(proc(member: ChatMember): user_item.Item = let contactDetails = self.controller.getContactDetails(member.id) result = user_item.initItem( member.id, @@ -214,14 +221,14 @@ proc createCommunityItem[T](self: Module[T], c: CommunityDto): SectionItem = contactDetails.isidenticon, contactDetails.details.added )), - c.pendingRequestsToJoin.map(x => pending_request_item.initItem( + if (isCommunity): communityDetails.pendingRequestsToJoin.map(x => pending_request_item.initItem( x.id, x.publicKey, x.chatId, x.communityId, x.state, x.our - )) + )) else: @[] ) method load*[T]( @@ -239,15 +246,18 @@ method load*[T]( self.controller.init() self.view.load() - # Create community modules here, since we don't know earlier how many joined communities we have. - let joinedCommunities = self.controller.getJoinedCommunities() + var activeSection: SectionItem + var activeSectionId = singletonInstance.localAccountSensitiveSettings.getActiveSection() + if (activeSectionId == ""): + activeSectionId = singletonInstance.userProfile.getPubKey() - for c in joinedCommunities: - self.communitySectionsModule[c.id] = chat_section_module.newModule( + let channelGroups = self.controller.getChannelGroups() + for channelGroup in channelGroups: + self.channelGroupModules[channelGroup.id] = chat_section_module.newModule( self, events, - c.id, - isCommunity = true, + channelGroup.id, + isCommunity = channelGroup.channelGroupType == ChannelGroupType.Community, settingsService, contactsService, chatService, @@ -256,35 +266,10 @@ method load*[T]( gifService, mailserversService ) - - var activeSection: SectionItem - var activeSectionId = singletonInstance.localAccountSensitiveSettings.getActiveSection() - - # Chat Section - let receivedContactRequests = self.controller.getContacts(ContactsGroup.IncomingPendingContactRequests) - let (unviewedCount, mentionsCount) = self.controller.getNumOfNotificaitonsForChat() - let notificationsCount = mentionsCount + receivedContactRequests.len - let hasNotification = unviewedCount > 0 or notificationsCount > 0 - let chatSectionItem = initItem(conf.CHAT_SECTION_ID, SectionType.Chat, conf.CHAT_SECTION_NAME, - amISectionAdmin = false, - description = "", - image = "", - conf.CHAT_SECTION_ICON, - color = "", - hasNotification, - notificationsCount, - active = false, - enabled = true) - self.view.model().addItem(chatSectionItem) - if(activeSectionId == chatSectionItem.id): - activeSection = chatSectionItem - - # Community Section - for c in joinedCommunities: - let communitySectionItem = self.createCommunityItem(c) - self.view.model().addItem(communitySectionItem) - if(activeSectionId == communitySectionItem.id): - activeSection = communitySectionItem + let channelGroupItem = self.createChannelGroupItem(channelGroup) + self.view.model().addItem(channelGroupItem) + if(activeSectionId == channelGroupItem.id): + activeSection = channelGroupItem # Wallet Section let walletSectionItem = initItem(conf.WALLET_SECTION_ID, SectionType.Wallet, conf.WALLET_SECTION_NAME, @@ -349,9 +334,9 @@ method load*[T]( activeSection = profileSettingsSectionItem # Load all sections - self.chatSectionModule.load(events, settingsService, contactsService, chatService, communityService, messageService, gifService, mailserversService) - for cModule in self.communitySectionsModule.values: - cModule.load(events, settingsService, contactsService, chatService, communityService, messageService, gifService, mailserversService) + for cModule in self.channelGroupModules.values: + cModule.load(events, settingsService, contactsService, chatService, communityService, + messageService, gifService, mailserversService) self.browserSectionModule.load() # self.nodeManagementSectionModule.load() @@ -372,10 +357,7 @@ proc checkIfModuleDidLoad [T](self: Module[T]) = if self.moduleLoaded: return - if(not self.chatSectionModule.isLoaded()): - return - - for cModule in self.communitySectionsModule.values: + for cModule in self.channelGroupModules.values: if(not cModule.isLoaded()): return @@ -471,9 +453,7 @@ method setActiveSection*[T](self: Module[T], item: SectionItem) = self.controller.setActiveSection(item.id, item.sectionType) proc notifySubModulesAboutChange[T](self: Module[T], sectionId: string) = - self.chatSectionModule.onActiveSectionChange(sectionId) - - for cModule in self.communitySectionsModule.values: + for cModule in self.channelGroupModules.values: cModule.onActiveSectionChange(sectionId) # If there is a need other section may be notified the same way from here... @@ -518,14 +498,14 @@ method setUserStatus*[T](self: Module[T], status: bool) = self.controller.setUserStatus(status) method getChatSectionModule*[T](self: Module[T]): QVariant = - return self.chatSectionModule.getModuleAsVariant() + return self.channelGroupModules[singletonInstance.userProfile.getPubKey()].getModuleAsVariant() method getCommunitySectionModule*[T](self: Module[T], communityId: string): QVariant = - if(not self.communitySectionsModule.contains(communityId)): + if(not self.channelGroupModules.contains(communityId)): echo "main-module, unexisting community key: ", communityId return - return self.communitySectionsModule[communityId].getModuleAsVariant() + return self.channelGroupModules[communityId].getModuleAsVariant() method rebuildChatSearchModel*[T](self: Module[T]) = let transformItem = proc(item: chat_section_base_item.BaseItem, sectionId, sectionName: string): chat_search_item.Item = @@ -539,9 +519,10 @@ method rebuildChatSearchModel*[T](self: Module[T]) = for subItem in item.subItems().items(): result.add(transformItem(subItem, sectionId, sectionName)) - var items = transform(self.chatSectionModule.chatsModel().items(), conf.CHAT_SECTION_ID, conf.CHAT_SECTION_NAME) - for cId in self.communitySectionsModule.keys: - items.add(transform(self.communitySectionsModule[cId].chatsModel().items(), cId, self.view.model().getItemById(cId).name())) + var items: seq[chat_search_item.Item] = @[] + for cId in self.channelGroupModules.keys: + items.add(transform(self.channelGroupModules[cId].chatsModel().items(), cId, + self.view.model().getItemById(cId).name())) self.view.chatSearchModel().setItems(items) @@ -580,9 +561,9 @@ method communityJoined*[T]( mailserversService: mailservers_service.Service, ) = var firstCommunityJoined = false - if (self.communitySectionsModule.len == 0): + if (self.channelGroupModules.len == 1): # First one is personal chat section firstCommunityJoined = true - self.communitySectionsModule[community.id] = chat_section_module.newModule( + self.channelGroupModules[community.id] = chat_section_module.newModule( self, events, community.id, @@ -595,33 +576,37 @@ method communityJoined*[T]( gifService, mailserversService ) - self.communitySectionsModule[community.id].load(events, settingsService, contactsService, chatService, communityService, messageService, gifService, mailserversService) + self.channelGroupModules[community.id].load(events, settingsService, contactsService, chatService, + communityService, messageService, gifService, mailserversService) - let communitySectionItem = self.createCommunityItem(community) + let channelGroup = community.toChannelGroupDto() + let communitySectionItem = self.createChannelGroupItem(channelGroup) if (firstCommunityJoined): # If there are no other communities, add the first community after the Chat section in the model so that the order is respected - self.view.model().addItem(communitySectionItem, self.view.model().getItemIndex(conf.CHAT_SECTION_ID) + 1) + self.view.model().addItem(communitySectionItem, + self.view.model().getItemIndex(singletonInstance.userProfile.getPubKey()) + 1) else: self.view.model().addItem(communitySectionItem) self.setActiveSection(communitySectionItem) method communityLeft*[T](self: Module[T], communityId: string) = - if(not self.communitySectionsModule.contains(communityId)): + if(not self.channelGroupModules.contains(communityId)): echo "main-module, unexisting community key to leave: ", communityId return - self.communitySectionsModule.del(communityId) + self.channelGroupModules.del(communityId) self.view.model().removeItem(communityId) if (self.controller.getActiveSectionId() == communityId): - let item = self.view.model().getItemById(conf.CHAT_SECTION_ID) + let item = self.view.model().getItemById(singletonInstance.userProfile.getPubKey()) self.setActiveSection(item) method communityEdited*[T]( self: Module[T], community: CommunityDto) = - self.view.editItem(self.createCommunityItem(community)) + let channelGroup = community.toChannelGroupDto() + self.view.editItem(self.createChannelGroupItem(channelGroup)) method getContactDetailsAsJson*[T](self: Module[T], publicKey: string): string = let contact = self.controller.getContact(publicKey) diff --git a/src/app_service/service/chat/dto/chat.nim b/src/app_service/service/chat/dto/chat.nim index 71e35107f0..a35535e717 100644 --- a/src/app_service/service/chat/dto/chat.nim +++ b/src/app_service/service/chat/dto/chat.nim @@ -1,6 +1,6 @@ {.used.} -import json, strformat +import json, strformat, strutils include ../../../common/json_utils @@ -12,6 +12,26 @@ type ChatType* {.pure.}= enum Profile = 4, CommunityChat = 6 +type ChannelGroupType* {.pure.}= enum + Unknown = "unknown", + Personal = "personal", + Community = "community" + +type Category* = object + id*: string + name*: string + position*: int + +type + Permission* = object + access*: int + ensOnly*: bool + +type + Images* = object + thumbnail*: string + large*: string + type ChatMember* = object id*: string admin*: bool @@ -48,6 +68,24 @@ type ChatDto* = object position*: int categoryId*: string highlight*: bool + permissions*: Permission + +type ChannelGroupDto* = object + id*: string + channelGroupType*: ChannelGroupType + admin*: bool + verified*: bool + name*: string + ensName*: string + description*: string + chats*: seq[ChatDto] + categories*: seq[Category] + images*: Images + permissions*: Permission + members*: seq[ChatMember] + canManageUsers*: bool + color*: string + muted*: bool proc `$`*(self: ChatDto): string = result = fmt"""ChatDto( @@ -64,12 +102,14 @@ proc `$`*(self: ChatDto): string = readMessagesAtClockValue: {self.readMessagesAtClockValue}, unviewedMessagesCount: {self.unviewedMessagesCount}, unviewedMentionsCount: {self.unviewedMentionsCount}, + members: {self.members}, alias: {self.alias}, identicon: {self.identicon}, muted: {self.muted}, communityId: {self.communityId}, profile: {self.profile}, joined: {self.joined}, + canPost: {self.canPost}, syncedTo: {self.syncedTo}, syncedFrom: {self.syncedFrom}, categoryId: {self.categoryId}, @@ -77,12 +117,41 @@ proc `$`*(self: ChatDto): string = highlight: {self.highlight} )""" +proc toPermission*(jsonObj: JsonNode): Permission = + result = Permission() + discard jsonObj.getProp("access", result.access) + discard jsonObj.getProp("ens_only", result.ensOnly) + +proc toImages*(jsonObj: JsonNode): Images = + result = Images() + + var largeObj: JsonNode + if(jsonObj.getProp("large", largeObj)): + discard largeObj.getProp("uri", result.large) + + var thumbnailObj: JsonNode + if(jsonObj.getProp("thumbnail", thumbnailObj)): + discard thumbnailObj.getProp("uri", result.thumbnail) + +proc toCategory*(jsonObj: JsonNode): Category = + result = Category() + if (not jsonObj.getProp("category_id", result.id)): + discard jsonObj.getProp("id", result.id) + discard jsonObj.getProp("name", result.name) + discard jsonObj.getProp("position", result.position) + proc toChatMember*(jsonObj: JsonNode): ChatMember = result = ChatMember() discard jsonObj.getProp("id", result.id) discard jsonObj.getProp("admin", result.admin) discard jsonObj.getProp("joined", result.joined) +proc toChatMember(jsonObj: JsonNode, memberId: string): ChatMember = + # Mapping this DTO is not strightforward since only keys are used for id. We + # handle it a bit different. + result = jsonObj.toChatMember() + result.id = memberId + proc toChatDto*(jsonObj: JsonNode): ChatDto = result = ChatDto() discard jsonObj.getProp("id", result.id) @@ -94,13 +163,18 @@ proc toChatDto*(jsonObj: JsonNode): ChatDto = discard jsonObj.getProp("timestamp", result.timestamp) discard jsonObj.getProp("lastClockValue", result.lastClockValue) discard jsonObj.getProp("deletedAtClockValue", result.deletedAtClockValue) - discard jsonObj.getProp("ReadMessagesAtClockValue", result.readMessagesAtClockValue) + discard jsonObj.getProp("readMessagesAtClockValue", result.readMessagesAtClockValue) discard jsonObj.getProp("unviewedMessagesCount", result.unviewedMessagesCount) discard jsonObj.getProp("unviewedMentionsCount", result.unviewedMentionsCount) + discard jsonObj.getProp("canPost", result.canPost) discard jsonObj.getProp("alias", result.alias) discard jsonObj.getProp("identicon", result.identicon) discard jsonObj.getProp("muted", result.muted) discard jsonObj.getProp("categoryId", result.categoryId) + if (result.categoryId == ""): + # Communities have `categoryID` and chats have `categoryId` + # This should be fixed in status-go, but would be a breaking change + discard jsonObj.getProp("categoryID", result.categoryId) discard jsonObj.getProp("position", result.position) discard jsonObj.getProp("communityId", result.communityId) discard jsonObj.getProp("profile", result.profile) @@ -108,6 +182,9 @@ proc toChatDto*(jsonObj: JsonNode): ChatDto = discard jsonObj.getProp("syncedTo", result.syncedTo) discard jsonObj.getProp("syncedFrom", result.syncedFrom) discard jsonObj.getProp("highlight", result.highlight) + var permissionObj: JsonNode + if(jsonObj.getProp("permissions", permissionObj)): + result.permissions = toPermission(permissionObj) result.chatType = ChatType.Unknown var chatTypeInt: int @@ -120,5 +197,54 @@ proc toChatDto*(jsonObj: JsonNode): ChatDto = for memberObj in membersObj: result.members.add(toChatMember(memberObj)) + # Add community ID if needed + if (result.communityId != "" and not result.id.contains(result.communityId)): + result.id = result.communityId & result.id + +proc toChannelGroupDto*(jsonObj: JsonNode): ChannelGroupDto = + result = ChannelGroupDto() + discard jsonObj.getProp("admin", result.admin) + discard jsonObj.getProp("verified", result.verified) + discard jsonObj.getProp("name", result.name) + discard jsonObj.getProp("description", result.description) + + result.channelGroupType = ChannelGroupType.Unknown + var channelGroupTypeString: string + if (jsonObj.getProp("channelGroupType", channelGroupTypeString)): + result.channelGroupType = parseEnum[ChannelGroupType](channelGroupTypeString) + + var chatsObj: JsonNode + if(jsonObj.getProp("chats", chatsObj)): + for _, chatObj in chatsObj: + result.chats.add(toChatDto(chatObj)) + + var categoriesObj: JsonNode + if(jsonObj.getProp("categories", categoriesObj)): + for _, categoryObj in categoriesObj: + result.categories.add(toCategory(categoryObj)) + + var imagesObj: JsonNode + if(jsonObj.getProp("images", imagesObj)): + result.images = toImages(imagesObj) + + var permissionObj: JsonNode + if(jsonObj.getProp("permissions", permissionObj)): + result.permissions = toPermission(permissionObj) + + var membersObj: JsonNode + if(jsonObj.getProp("members", membersObj) and membersObj.kind == JObject): + for memberId, memberObj in membersObj: + result.members.add(toChatMember(memberObj, memberId)) + + discard jsonObj.getProp("canManageUsers", result.canManageUsers) + discard jsonObj.getProp("color", result.color) + discard jsonObj.getProp("muted", result.muted) + +# To parse Community chats to ChatDto, we need to add the commuity ID and type +proc toChatDto*(jsonObj: JsonNode, communityId: string): ChatDto = + result = jsonObj.toChatDto() + result.chatType = ChatType.CommunityChat + result.communityId = communityId + proc isPublicChat*(chatDto: ChatDto): bool = return chatDto.chatType == ChatType.Public diff --git a/src/app_service/service/chat/service.nim b/src/app_service/service/chat/service.nim index 66e3a74289..71a2abc588 100644 --- a/src/app_service/service/chat/service.nim +++ b/src/app_service/service/chat/service.nim @@ -90,6 +90,7 @@ QtObject: type Service* = ref object of QObject events: EventEmitter chats: Table[string, ChatDto] # [chat_id, ChatDto] + channelGroups: OrderedTable[string, ChannelGroupDto] # [chatGroup_id, ChannelGroupDto] contactService: contact_service.Service proc delete*(self: Service) = @@ -117,23 +118,39 @@ QtObject: self.updateOrAddChat(chatDto) self.events.emit(SIGNAL_CHAT_UPDATE, ChatUpdateArgsNew(messages: receivedData.messages, chats: chats)) + proc sortPersonnalChatAsFirst[T, D](x, y: (T, D)): int = + if (x[1].channelGroupType == Personal): return -1 + if (y[1].channelGroupType == Personal): return 1 + return 0 + proc init*(self: Service) = self.doConnect() try: let response = status_chat.getChats() - let chats = map(response.result.getElems(), proc(x: JsonNode): ChatDto = x.toChatDto()) + var chats: seq[ChatDto] = @[] + for (sectionId, section) in response.result.pairs: + var channelGroup = section.toChannelGroupDto() + channelGroup.id = sectionId + self.channelGroups[sectionId] = channelGroup + for (chatId, chat) in section["chats"].pairs: + chats.add(chat.toChatDto()) + + # Make the personal channelGroup the first one + self.channelGroups.sort(sortPersonnalChatAsFirst[string, ChannelGroupDto], SortOrder.Ascending) for chat in chats: if chat.active and chat.chatType != chat_dto.ChatType.Unknown: self.chats[chat.id] = chat - except Exception as e: let errDesription = e.msg error "error: ", errDesription return + proc getChannelGroups*(self: Service): seq[ChannelGroupDto] = + return toSeq(self.channelGroups.values) + proc hasChannel*(self: Service, chatId: string): bool = self.chats.hasKey(chatId) diff --git a/src/app_service/service/community/dto/community.nim b/src/app_service/service/community/dto/community.nim index 82c1ece853..aa0303fb6e 100644 --- a/src/app_service/service/community/dto/community.nim +++ b/src/app_service/service/community/dto/community.nim @@ -1,41 +1,32 @@ {.used.} -import json, sequtils +import json, sequtils, sugar import ../../../../backend/communities include ../../../common/json_utils -type - Permission* = object - access*: int - ensOnly*: bool +import ../../chat/dto/chat type - Images* = object - thumbnail*: string - large*: string - -type Chat* = object - id*: string - name*: string - color*: string - emoji*: string - description*: string - #members*: seq[ChatMember] ???? It's always null and a question is why do we need it here within this context ???? - permissions*: Permission - canPost*: bool - position*: int - categoryId*: string - -type Category* = object - id*: string - name*: string - position*: int + CommunityMemberRoles* {.pure.} = enum + Unknown = 0, + All = 1, + ManagerUsers = 2 type Member* = object id*: string roles*: seq[int] +proc toMember*(jsonObj: JsonNode, memberId: string): Member = + # Mapping this DTO is not strightforward since only keys are used for id. We + # handle it a bit different. + result = Member() + result.id = memberId + var rolesObj: JsonNode + if(jsonObj.getProp("roles", rolesObj)): + for roleObj in rolesObj: + result.roles.add(roleObj.getInt) + type CommunityMembershipRequestDto* = object id*: string publicKey*: string @@ -52,7 +43,7 @@ type CommunityDto* = object requestedAccessAt: int64 name*: string description*: string - chats*: seq[Chat] + chats*: seq[ChatDto] categories*: seq[Category] images*: Images permissions*: Permission @@ -66,53 +57,6 @@ type CommunityDto* = object muted*: bool pendingRequestsToJoin*: seq[CommunityMembershipRequestDto] -proc toPermission(jsonObj: JsonNode): Permission = - result = Permission() - discard jsonObj.getProp("access", result.access) - discard jsonObj.getProp("ens_only", result.ensOnly) - -proc toImages(jsonObj: JsonNode): Images = - result = Images() - - var largeObj: JsonNode - if(jsonObj.getProp("large", largeObj)): - discard largeObj.getProp("uri", result.large) - - var thumbnailObj: JsonNode - if(jsonObj.getProp("thumbnail", thumbnailObj)): - discard thumbnailObj.getProp("uri", result.thumbnail) - -proc toChat*(jsonObj: JsonNode): Chat = - result = Chat() - discard jsonObj.getProp("id", result.id) - discard jsonObj.getProp("name", result.name) - discard jsonObj.getProp("color", result.color) - discard jsonObj.getProp("emoji", result.emoji) - discard jsonObj.getProp("description", result.description) - var permissionObj: JsonNode - if(jsonObj.getProp("permissions", permissionObj)): - result.permissions = toPermission(permissionObj) - discard jsonObj.getProp("canPost", result.canPost) - discard jsonObj.getProp("position", result.position) - discard jsonObj.getProp("categoryID", result.categoryId) - -proc toCategory*(jsonObj: JsonNode): Category = - result = Category() - if (not jsonObj.getProp("category_id", result.id)): - discard jsonObj.getProp("id", result.id) - discard jsonObj.getProp("name", result.name) - discard jsonObj.getProp("position", result.position) - -proc toMember*(jsonObj: JsonNode, memberId: string): Member = - # Mapping this DTO is not strightforward since only keys are used for id. We - # handle it a bit different. - result = Member() - result.id = memberId - var rolesObj: JsonNode - if(jsonObj.getProp("roles", rolesObj)): - for roleObj in rolesObj: - result.roles.add(roleObj.getInt) - proc toCommunityDto*(jsonObj: JsonNode): CommunityDto = result = CommunityDto() discard jsonObj.getProp("id", result.id) @@ -126,7 +70,7 @@ proc toCommunityDto*(jsonObj: JsonNode): CommunityDto = var chatsObj: JsonNode if(jsonObj.getProp("chats", chatsObj)): for _, chatObj in chatsObj: - result.chats.add(toChat(chatObj)) + result.chats.add(chatObj.toChatDto(result.id)) var categoriesObj: JsonNode if(jsonObj.getProp("categories", categoriesObj)): @@ -166,3 +110,33 @@ proc toCommunityMembershipRequestDto*(jsonObj: JsonNode): CommunityMembershipReq proc parseCommunities*(response: RpcResponse[JsonNode]): seq[CommunityDto] = result = map(response.result.getElems(), proc(x: JsonNode): CommunityDto = x.toCommunityDto()) + +proc contains(arrayToSearch: seq[int], searched: int): bool = + for element in arrayToSearch: + if element == searched: + return true + return false + +proc toChannelGroupDto*(communityDto: CommunityDto): ChannelGroupDto = + ChannelGroupDto( + id: communityDto.id, + channelGroupType: ChannelGroupType.Community, + name: communityDto.name, + images: communityDto.images, + chats: communityDto.chats, + categories: communityDto.categories, + # Community doesn't have an ensName yet. Add this when it is added in status-go + # ensName: communityDto.ensName, + admin: communityDto.admin, + verified: communityDto.verified, + description: communityDto.description, + color: communityDto.color, + permissions: communityDto.permissions, + members: communityDto.members.map(m => ChatMember( + id: m.id, + joined: true, + admin: m.roles.contains(CommunityMemberRoles.ManagerUsers.int) + )), + canManageUsers: communityDto.canManageUsers, + muted: communityDto.muted + ) \ No newline at end of file diff --git a/src/app_service/service/community/service.nim b/src/app_service/service/community/service.nim index 76d8b34a91..2f281abca5 100644 --- a/src/app_service/service/community/service.nim +++ b/src/app_service/service/community/service.nim @@ -144,22 +144,8 @@ QtObject: self.events.emit(SIGNAL_NEW_REQUEST_TO_JOIN_COMMUNITY, CommunityRequestArgs(communityRequest: membershipRequest)) - proc mapChatToChatDto(chat: Chat, communityId: string): ChatDto = - result = ChatDto() - result.id = chat.id - result.communityId = communityId - result.name = chat.name - result.chatType = ChatType.CommunityChat - result.color = chat.color - result.emoji = chat.emoji - result.description = chat.description - result.canPost = chat.canPost - result.position = chat.position - result.categoryId = chat.categoryId - result.communityId = communityId - - proc updateMissingFields(chatDto: var ChatDto, chat: Chat) = - # This proc sets fields of `chatDto` which are available only for comminity channels. + proc updateMissingFields(chatDto: var ChatDto, chat: ChatDto) = + # This proc sets fields of `chatDto` which are available only for community channels. chatDto.position = chat.position chatDto.canPost = chat.canPost chatDto.categoryId = chat.categoryId @@ -169,7 +155,7 @@ QtObject: if(chat.id == id): return chat - proc findIndexById(id: string, chats: seq[Chat]): int = + proc findIndexById(id: string, chats: seq[ChatDto]): int = var idx = -1 for chat in chats: inc idx @@ -199,7 +185,6 @@ QtObject: if (chat.categoryId == categoryId): let fullChatId = community.id & chat.id var chatDetails = self.chatService.getChatById(fullChatId) - chatDetails.updateMissingFields(chat) result.add(chatDetails) proc handleCommunityUpdates(self: Service, communities: seq[CommunityDto], updatedChats: seq[ChatDto]) = @@ -368,7 +353,7 @@ QtObject: else: result.sort(sortDesc[Category]) - proc getChats*(self: Service, communityId: string, categoryId = "", order = SortOrder.Ascending): seq[Chat] = + proc getChats*(self: Service, communityId: string, categoryId = "", order = SortOrder.Ascending): seq[ChatDto] = ## By default returns chats which don't belong to any category, for passed `communityId`. ## If `categoryId` is set then only chats belonging to that category for passed `communityId` will be returned. ## Returned chats are sorted by position following set `order` parameter. @@ -383,11 +368,11 @@ QtObject: result.add(chat) if(order == SortOrder.Ascending): - result.sort(sortAsc[Chat]) + result.sort(sortAsc[ChatDto]) else: - result.sort(sortDesc[Chat]) + result.sort(sortDesc[ChatDto]) - proc getAllChats*(self: Service, communityId: string, order = SortOrder.Ascending): seq[Chat] = + proc getAllChats*(self: Service, communityId: string, order = SortOrder.Ascending): seq[ChatDto] = ## Returns all chats belonging to the community with passed `communityId`, sorted by position. ## Returned chats are sorted by position following set `order` parameter. if(not self.joinedCommunities.contains(communityId)): @@ -397,9 +382,9 @@ QtObject: result = self.joinedCommunities[communityId].chats if(order == SortOrder.Ascending): - result.sort(sortAsc[Chat]) + result.sort(sortAsc[ChatDto]) else: - result.sort(sortDesc[Chat]) + result.sort(sortDesc[ChatDto]) proc isUserMemberOfCommunity*(self: Service, communityId: string): bool = if(not self.allCommunities.contains(communityId)): @@ -439,7 +424,7 @@ QtObject: if (currentChat.id != ""): # The chat service already knows that about that chat continue - var chatDto = mapChatToChatDto(chat, communityId) + var chatDto = chat chatDto.id = fullChatId # TODO find a way to populate missing infos like the color self.chatService.updateOrAddChat(chatDto) @@ -602,7 +587,7 @@ QtObject: raise newException(RpcException, fmt"createCommunityChannel; there is no `chats` key in the response for community id: {communityId}") for chatObj in chatsJArr: - var chatDto = chatObj.toChatDto() + var chatDto = chatObj.toChatDto(communityId) self.chatService.updateOrAddChat(chatDto) let data = CommunityChatArgs(chat: chatDto) self.events.emit(SIGNAL_COMMUNITY_CHANNEL_CREATED, data) @@ -642,7 +627,7 @@ QtObject: raise newException(RpcException, fmt"editCommunityChannel; there is no `chats` key in the response for community id: {communityId}") for chatObj in chatsJArr: - var chatDto = chatObj.toChatDto() + var chatDto = chatObj.toChatDto(communityId) self.chatService.updateOrAddChat(chatDto) # we have to update chats stored in the chat service. @@ -863,7 +848,7 @@ QtObject: self.joinedCommunities[communityDto.id] = communityDto for chatObj in chatsJArr: - let chatDto = chatObj.toChatDto() + let chatDto = chatObj.toChatDto(communityDto.id) self.chatService.updateOrAddChat(chatDto) # we have to update chats stored in the chat service. for chat in communityDto.chats: diff --git a/src/backend/chat.nim b/src/backend/chat.nim index 4e6b5a4731..df43ced15e 100644 --- a/src/backend/chat.nim +++ b/src/backend/chat.nim @@ -33,7 +33,7 @@ proc saveChat*( proc getChats*(): RpcResponse[JsonNode] {.raises: [Exception].} = let payload = %* [] - result = callPrivateRPC("chats".prefix, payload) + result = callPrivateRPC("chat_getChats", payload) proc createPublicChat*(chatId: string): RpcResponse[JsonNode] {.raises: [Exception].} = let communityId = "" diff --git a/vendor/status-go b/vendor/status-go index 16311512cb..c342c8bb1a 160000 --- a/vendor/status-go +++ b/vendor/status-go @@ -1 +1 @@ -Subproject commit 16311512cbf66c9eeaf03194707faa19c9390649 +Subproject commit c342c8bb1af9183795f652a41065244c0a0bbe09