From b2bc4d6a5c364a2b11480444f79813ef9873ed2e Mon Sep 17 00:00:00 2001 From: spaced4ndy <8711996+spaced4ndy@users.noreply.github.com> Date: Sat, 24 May 2025 13:34:03 +0000 Subject: [PATCH] core: fix short link type when adding for group link (#5942) * core: fix short link type when adding for group link * shorten, rename * update setContactShortLink * update * fix * plans * simplexmq * ui: show error when setting short link --------- Co-authored-by: Evgeny Poberezkin --- apps/ios/Shared/Model/AppAPITypes.swift | 12 ++++---- apps/ios/Shared/Model/SimpleXAPI.swift | 10 +++---- .../Views/Chat/Group/GroupLinkView.swift | 4 +-- .../Views/UserSettings/UserAddressView.swift | 6 ++-- .../chat/simplex/common/model/SimpleXAPI.kt | 30 +++++++++++-------- .../common/views/chat/group/GroupLinkView.kt | 2 +- .../views/usersettings/UserAddressView.kt | 2 +- .../src/Directory/Service.hs | 4 +-- cabal.project | 2 +- scripts/nix/sha256map.nix | 2 +- src/Simplex/Chat/Controller.hs | 4 +-- src/Simplex/Chat/Library/Commands.hs | 30 ++++++++++--------- src/Simplex/Chat/Store/Groups.hs | 6 ++-- .../SQLite/Migrations/chat_query_plans.txt | 2 +- 14 files changed, 62 insertions(+), 54 deletions(-) diff --git a/apps/ios/Shared/Model/AppAPITypes.swift b/apps/ios/Shared/Model/AppAPITypes.swift index 9d359d9aa6..6c47d654e0 100644 --- a/apps/ios/Shared/Model/AppAPITypes.swift +++ b/apps/ios/Shared/Model/AppAPITypes.swift @@ -80,7 +80,7 @@ enum ChatCommand: ChatCmdProtocol { case apiGroupLinkMemberRole(groupId: Int64, memberRole: GroupMemberRole) case apiDeleteGroupLink(groupId: Int64) case apiGetGroupLink(groupId: Int64) - case apiAddShortLinkGroupLink(groupId: Int64) + case apiAddGroupShortLink(groupId: Int64) case apiCreateMemberContact(groupId: Int64, groupMemberId: Int64) case apiSendMemberContactInvitation(contactId: Int64, msg: MsgContent) case apiTestProtoServer(userId: Int64, server: String) @@ -135,7 +135,7 @@ enum ChatCommand: ChatCmdProtocol { case apiCreateMyAddress(userId: Int64, short: Bool) case apiDeleteMyAddress(userId: Int64) case apiShowMyAddress(userId: Int64) - case apiAddShortLinkMyAddress(userId: Int64) + case apiAddMyAddressShortLink(userId: Int64) case apiSetProfileAddress(userId: Int64, on: Bool) case apiAddressAutoAccept(userId: Int64, autoAccept: AutoAccept?) case apiAcceptContact(incognito: Bool, contactReqId: Int64) @@ -264,7 +264,7 @@ enum ChatCommand: ChatCmdProtocol { case let .apiGroupLinkMemberRole(groupId, memberRole): return "/_set link role #\(groupId) \(memberRole)" case let .apiDeleteGroupLink(groupId): return "/_delete link #\(groupId)" case let .apiGetGroupLink(groupId): return "/_get link #\(groupId)" - case let .apiAddShortLinkGroupLink(groupId): return "/_short link #\(groupId)" + case let .apiAddGroupShortLink(groupId): return "/_short link #\(groupId)" case let .apiCreateMemberContact(groupId, groupMemberId): return "/_create member contact #\(groupId) \(groupMemberId)" case let .apiSendMemberContactInvitation(contactId, mc): return "/_invite member contact @\(contactId) \(mc.cmdString)" case let .apiTestProtoServer(userId, server): return "/_server test \(userId) \(server)" @@ -329,7 +329,7 @@ enum ChatCommand: ChatCmdProtocol { case let .apiCreateMyAddress(userId, short): return "/_address \(userId) short=\(onOff(short))" case let .apiDeleteMyAddress(userId): return "/_delete_address \(userId)" case let .apiShowMyAddress(userId): return "/_show_address \(userId)" - case let .apiAddShortLinkMyAddress(userId): return "/_short_link_address \(userId)" + case let .apiAddMyAddressShortLink(userId): return "/_short_link_address \(userId)" case let .apiSetProfileAddress(userId, on): return "/_profile_address \(userId) \(onOff(on))" case let .apiAddressAutoAccept(userId, autoAccept): return "/_auto_accept \(userId) \(AutoAccept.cmdString(autoAccept))" case let .apiAcceptContact(incognito, contactReqId): return "/_accept incognito=\(onOff(incognito)) \(contactReqId)" @@ -442,7 +442,7 @@ enum ChatCommand: ChatCmdProtocol { case .apiGroupLinkMemberRole: return "apiGroupLinkMemberRole" case .apiDeleteGroupLink: return "apiDeleteGroupLink" case .apiGetGroupLink: return "apiGetGroupLink" - case .apiAddShortLinkGroupLink: return "apiAddShortLinkGroupLink" + case .apiAddGroupShortLink: return "apiAddGroupShortLink" case .apiCreateMemberContact: return "apiCreateMemberContact" case .apiSendMemberContactInvitation: return "apiSendMemberContactInvitation" case .apiTestProtoServer: return "apiTestProtoServer" @@ -496,7 +496,7 @@ enum ChatCommand: ChatCmdProtocol { case .apiCreateMyAddress: return "apiCreateMyAddress" case .apiDeleteMyAddress: return "apiDeleteMyAddress" case .apiShowMyAddress: return "apiShowMyAddress" - case .apiAddShortLinkMyAddress: return "apiAddShortLinkMyAddress" + case .apiAddMyAddressShortLink: return "apiAddMyAddressShortLink" case .apiSetProfileAddress: return "apiSetProfileAddress" case .apiAddressAutoAccept: return "apiAddressAutoAccept" case .apiAcceptContact: return "apiAcceptContact" diff --git a/apps/ios/Shared/Model/SimpleXAPI.swift b/apps/ios/Shared/Model/SimpleXAPI.swift index 952702b8a8..4f9d75bada 100644 --- a/apps/ios/Shared/Model/SimpleXAPI.swift +++ b/apps/ios/Shared/Model/SimpleXAPI.swift @@ -1210,9 +1210,9 @@ private func userAddressResponse(_ r: APIResult) throws -> UserCo } } -func apiAddShortLinkMyAddress() async throws -> UserContactLink { - let userId = try currentUserId("apiAddShortLinkMyAddress") - let r: ChatResponse1 = try await chatSendCmd(.apiAddShortLinkMyAddress(userId: userId)) +func apiAddMyAddressShortLink() async throws -> UserContactLink { + let userId = try currentUserId("apiAddMyAddressShortLink") + let r: ChatResponse1 = try await chatSendCmd(.apiAddMyAddressShortLink(userId: userId)) if case let .userContactLink(_, contactLink) = r { return contactLink } throw r.unexpected } @@ -1743,8 +1743,8 @@ func apiGetGroupLink(_ groupId: Int64) throws -> (CreatedConnLink, GroupMemberRo } } -func apiAddShortLinkGroupLink(_ groupId: Int64) async throws -> (CreatedConnLink, GroupMemberRole) { - let r: ChatResponse2 = try await chatSendCmd(.apiAddShortLinkGroupLink(groupId: groupId)) +func apiAddGroupShortLink(_ groupId: Int64) async throws -> (CreatedConnLink, GroupMemberRole) { + let r: ChatResponse2 = try await chatSendCmd(.apiAddGroupShortLink(groupId: groupId)) if case let .groupLink(_, _, connLink, memberRole) = r { return (connLink, memberRole) } throw r.unexpected } diff --git a/apps/ios/Shared/Views/Chat/Group/GroupLinkView.swift b/apps/ios/Shared/Views/Chat/Group/GroupLinkView.swift index bfc7c19fa7..49e4d49e86 100644 --- a/apps/ios/Shared/Views/Chat/Group/GroupLinkView.swift +++ b/apps/ios/Shared/Views/Chat/Group/GroupLinkView.swift @@ -175,13 +175,13 @@ struct GroupLinkView: View { Task { do { creatingLink = true - let link = try await apiAddShortLinkGroupLink(groupId) + let link = try await apiAddGroupShortLink(groupId) await MainActor.run { creatingLink = false (groupLink, groupLinkMemberRole) = link } } catch let error { - logger.error("apiAddShortLinkGroupLink: \(responseError(error))") + logger.error("apiAddGroupShortLink: \(responseError(error))") await MainActor.run { creatingLink = false let a = getErrorAlert(error, "Error adding short link") diff --git a/apps/ios/Shared/Views/UserSettings/UserAddressView.swift b/apps/ios/Shared/Views/UserSettings/UserAddressView.swift index 1140dcf0fc..f374995f78 100644 --- a/apps/ios/Shared/Views/UserSettings/UserAddressView.swift +++ b/apps/ios/Shared/Views/UserSettings/UserAddressView.swift @@ -224,13 +224,15 @@ struct UserAddressView: View { progressIndicator = true Task { do { - let userAddress = try await apiAddShortLinkMyAddress() + let userAddress = try await apiAddMyAddressShortLink() await MainActor.run { chatModel.userAddress = userAddress } await MainActor.run { progressIndicator = false } } catch let error { - logger.error("apiAddShortLinkMyAddress: \(responseError(error))") + logger.error("apiAddMyAddressShortLink: \(responseError(error))") + let a = getErrorAlert(error, "Error creating address") + alert = .error(title: a.title, error: a.message) await MainActor.run { progressIndicator = false } } } diff --git a/apps/multiplatform/common/src/commonMain/kotlin/chat/simplex/common/model/SimpleXAPI.kt b/apps/multiplatform/common/src/commonMain/kotlin/chat/simplex/common/model/SimpleXAPI.kt index a334bb9a06..0f65783152 100644 --- a/apps/multiplatform/common/src/commonMain/kotlin/chat/simplex/common/model/SimpleXAPI.kt +++ b/apps/multiplatform/common/src/commonMain/kotlin/chat/simplex/common/model/SimpleXAPI.kt @@ -1570,11 +1570,13 @@ object ChatController { return null } - suspend fun apiAddShortLinkMyAddress(rh: Long?): UserContactLinkRec? { - val userId = kotlin.runCatching { currentUserId("apiAddShortLinkMyAddress") }.getOrElse { return null } - val r = sendCmd(rh, CC.ApiAddShortLinkMyAddress(userId)) + suspend fun apiAddMyAddressShortLink(rh: Long?): UserContactLinkRec? { + val userId = kotlin.runCatching { currentUserId("apiAddMyAddressShortLink") }.getOrElse { return null } + val r = sendCmd(rh, CC.ApiAddMyAddressShortLink(userId)) if (r is API.Result && r.res is CR.UserContactLink) return r.res.contactLink - Log.e(TAG, "apiAddShortLinkMyAddress bad response: ${r.responseType} ${r.details}") + if (!(networkErrorAlert(r))) { + apiErrorAlert("apiAddMyAddressShortLink", generalGetString(MR.strings.error_creating_address), r) + } return null } @@ -2024,10 +2026,12 @@ object ChatController { return null } - suspend fun apiAddShortLinkGroupLink(rh: Long?, groupId: Long): Pair? { - val r = sendCmd(rh, CC.APIAddShortLinkGroupLink(groupId)) + suspend fun apiAddGroupShortLink(rh: Long?, groupId: Long): Pair? { + val r = sendCmd(rh, CC.ApiAddGroupShortLink(groupId)) if (r is API.Result && r.res is CR.GroupLink) return r.res.connLinkContact to r.res.memberRole - Log.e(TAG, "apiAddShortLinkGroupLink bad response: ${r.responseType} ${r.details}") + if (!(networkErrorAlert(r))) { + apiErrorAlert("apiAddGroupShortLink", generalGetString(MR.strings.error_creating_link_for_group), r) + } return null } @@ -3383,7 +3387,7 @@ sealed class CC { class APIGroupLinkMemberRole(val groupId: Long, val memberRole: GroupMemberRole): CC() class APIDeleteGroupLink(val groupId: Long): CC() class APIGetGroupLink(val groupId: Long): CC() - class APIAddShortLinkGroupLink(val groupId: Long): CC() + class ApiAddGroupShortLink(val groupId: Long): CC() class APICreateMemberContact(val groupId: Long, val groupMemberId: Long): CC() class APISendMemberContactInvitation(val contactId: Long, val mc: MsgContent): CC() class APITestProtoServer(val userId: Long, val server: String): CC() @@ -3438,7 +3442,7 @@ sealed class CC { class ApiCreateMyAddress(val userId: Long, val short: Boolean): CC() class ApiDeleteMyAddress(val userId: Long): CC() class ApiShowMyAddress(val userId: Long): CC() - class ApiAddShortLinkMyAddress(val userId: Long): CC() + class ApiAddMyAddressShortLink(val userId: Long): CC() class ApiSetProfileAddress(val userId: Long, val on: Boolean): CC() class ApiAddressAutoAccept(val userId: Long, val autoAccept: AutoAccept?): CC() class ApiGetCallInvitations: CC() @@ -3572,7 +3576,7 @@ sealed class CC { is APIGroupLinkMemberRole -> "/_set link role #$groupId ${memberRole.name.lowercase()}" is APIDeleteGroupLink -> "/_delete link #$groupId" is APIGetGroupLink -> "/_get link #$groupId" - is APIAddShortLinkGroupLink -> "/_short link #$groupId" + is ApiAddGroupShortLink -> "/_short link #$groupId" is APICreateMemberContact -> "/_create member contact #$groupId $groupMemberId" is APISendMemberContactInvitation -> "/_invite member contact @$contactId ${mc.cmdString}" is APITestProtoServer -> "/_server test $userId $server" @@ -3627,7 +3631,7 @@ sealed class CC { is ApiCreateMyAddress -> "/_address $userId short=${onOff(short)}" is ApiDeleteMyAddress -> "/_delete_address $userId" is ApiShowMyAddress -> "/_show_address $userId" - is ApiAddShortLinkMyAddress -> "/_short_link_address $userId" + is ApiAddMyAddressShortLink -> "/_short_link_address $userId" is ApiSetProfileAddress -> "/_profile_address $userId ${onOff(on)}" is ApiAddressAutoAccept -> "/_auto_accept $userId ${AutoAccept.cmdString(autoAccept)}" is ApiAcceptContact -> "/_accept incognito=${onOff(incognito)} $contactReqId" @@ -3739,7 +3743,7 @@ sealed class CC { is APIGroupLinkMemberRole -> "apiGroupLinkMemberRole" is APIDeleteGroupLink -> "apiDeleteGroupLink" is APIGetGroupLink -> "apiGetGroupLink" - is APIAddShortLinkGroupLink -> "apiAddShortLinkGroupLink" + is ApiAddGroupShortLink -> "apiAddGroupShortLink" is APICreateMemberContact -> "apiCreateMemberContact" is APISendMemberContactInvitation -> "apiSendMemberContactInvitation" is APITestProtoServer -> "testProtoServer" @@ -3794,7 +3798,7 @@ sealed class CC { is ApiCreateMyAddress -> "apiCreateMyAddress" is ApiDeleteMyAddress -> "apiDeleteMyAddress" is ApiShowMyAddress -> "apiShowMyAddress" - is ApiAddShortLinkMyAddress -> "apiAddShortLinkMyAddress" + is ApiAddMyAddressShortLink -> "apiAddMyAddressShortLink" is ApiSetProfileAddress -> "apiSetProfileAddress" is ApiAddressAutoAccept -> "apiAddressAutoAccept" is ApiAcceptContact -> "apiAcceptContact" diff --git a/apps/multiplatform/common/src/commonMain/kotlin/chat/simplex/common/views/chat/group/GroupLinkView.kt b/apps/multiplatform/common/src/commonMain/kotlin/chat/simplex/common/views/chat/group/GroupLinkView.kt index 7e3fd839e2..30c16db6a4 100644 --- a/apps/multiplatform/common/src/commonMain/kotlin/chat/simplex/common/views/chat/group/GroupLinkView.kt +++ b/apps/multiplatform/common/src/commonMain/kotlin/chat/simplex/common/views/chat/group/GroupLinkView.kt @@ -52,7 +52,7 @@ fun GroupLinkView( fun addShortLink() { creatingLink = true withBGApi { - val link = chatModel.controller.apiAddShortLinkGroupLink(rhId, groupInfo.groupId) + val link = chatModel.controller.apiAddGroupShortLink(rhId, groupInfo.groupId) if (link != null) { groupLink = link.first groupLinkMemberRole.value = link.second diff --git a/apps/multiplatform/common/src/commonMain/kotlin/chat/simplex/common/views/usersettings/UserAddressView.kt b/apps/multiplatform/common/src/commonMain/kotlin/chat/simplex/common/views/usersettings/UserAddressView.kt index 53237f48ac..d77c4bc7f6 100644 --- a/apps/multiplatform/common/src/commonMain/kotlin/chat/simplex/common/views/usersettings/UserAddressView.kt +++ b/apps/multiplatform/common/src/commonMain/kotlin/chat/simplex/common/views/usersettings/UserAddressView.kt @@ -85,7 +85,7 @@ fun UserAddressView( fun addShortLink() { withBGApi { progressIndicator = true - val userAddress = chatModel.controller.apiAddShortLinkMyAddress(user.value?.remoteHostId) + val userAddress = chatModel.controller.apiAddMyAddressShortLink(user.value?.remoteHostId) if (userAddress != null) { chatModel.userAddress.value = userAddress } diff --git a/apps/simplex-directory-service/src/Directory/Service.hs b/apps/simplex-directory-service/src/Directory/Service.hs index 4909189d40..13510b4d2b 100644 --- a/apps/simplex-directory-service/src/Directory/Service.hs +++ b/apps/simplex-directory-service/src/Directory/Service.hs @@ -713,7 +713,7 @@ directoryServiceEvent st opts@DirectoryOpts {adminUsers, superUsers, serviceName case mRole_ of Nothing -> getGroupLinkRole cc user g >>= \case - Just (_, CCLink gLink _, mRole) -> do + Just (_, CCLink gLink _, _, mRole) -> do let anotherRole = case mRole of GRObserver -> GRMember; _ -> GRObserver sendReply $ initialRole n mRole @@ -1045,7 +1045,7 @@ vr :: ChatController -> VersionRangeChat vr ChatController {config = ChatConfig {chatVRange}} = chatVRange {-# INLINE vr #-} -getGroupLinkRole :: ChatController -> User -> GroupInfo -> IO (Maybe (Int64, CreatedLinkContact, GroupMemberRole)) +getGroupLinkRole :: ChatController -> User -> GroupInfo -> IO (Maybe (Int64, CreatedLinkContact, GroupLinkId, GroupMemberRole)) getGroupLinkRole cc user gInfo = withDB "getGroupLink" cc $ \db -> getGroupLink db user gInfo diff --git a/cabal.project b/cabal.project index 48b75a86cd..c067ba2be0 100644 --- a/cabal.project +++ b/cabal.project @@ -12,7 +12,7 @@ constraints: zip +disable-bzip2 +disable-zstd source-repository-package type: git location: https://github.com/simplex-chat/simplexmq.git - tag: d352d518c2b3a42bc7a298954dde799422e1457f + tag: 18e73b8aa7996562f0f92db3967da02d960cb805 source-repository-package type: git diff --git a/scripts/nix/sha256map.nix b/scripts/nix/sha256map.nix index 68a6054ef0..e25c99ebd1 100644 --- a/scripts/nix/sha256map.nix +++ b/scripts/nix/sha256map.nix @@ -1,5 +1,5 @@ { - "https://github.com/simplex-chat/simplexmq.git"."d352d518c2b3a42bc7a298954dde799422e1457f" = "1rha84pfpaqx3mf218szkfra334vhijqf17hanxqmp1sicfbf1x3"; + "https://github.com/simplex-chat/simplexmq.git"."18e73b8aa7996562f0f92db3967da02d960cb805" = "0sglm2i5gq34fmcm06q13452yapx7k40rc9b4q6qlfzjavq3jgld"; "https://github.com/simplex-chat/hs-socks.git"."a30cc7a79a08d8108316094f8f2f82a0c5e1ac51" = "0yasvnr7g91k76mjkamvzab2kvlb1g5pspjyjn2fr6v83swjhj38"; "https://github.com/simplex-chat/direct-sqlcipher.git"."f814ee68b16a9447fbb467ccc8f29bdd3546bfd9" = "1ql13f4kfwkbaq7nygkxgw84213i0zm7c1a8hwvramayxl38dq5d"; "https://github.com/simplex-chat/sqlcipher-simple.git"."a46bd361a19376c5211f1058908fc0ae6bf42446" = "1z0r78d8f0812kxbgsm735qf6xx8lvaz27k1a0b4a2m0sshpd5gl"; diff --git a/src/Simplex/Chat/Controller.hs b/src/Simplex/Chat/Controller.hs index 5e15c6fb7a..3b59f56021 100644 --- a/src/Simplex/Chat/Controller.hs +++ b/src/Simplex/Chat/Controller.hs @@ -373,7 +373,7 @@ data ChatCommand | APIGroupLinkMemberRole GroupId GroupMemberRole | APIDeleteGroupLink GroupId | APIGetGroupLink GroupId - | APIAddShortLinkGroupLink GroupId + | APIAddGroupShortLink GroupId | APICreateMemberContact GroupId GroupMemberId | APISendMemberContactInvitation {contactId :: ContactId, msgContent_ :: Maybe MsgContent} | GetUserProtoServers AProtocolType @@ -462,7 +462,7 @@ data ChatCommand | DeleteMyAddress | APIShowMyAddress UserId | ShowMyAddress - | APIAddShortLinkMyAddress UserId + | APIAddMyAddressShortLink UserId | APISetProfileAddress UserId Bool | SetProfileAddress Bool | APIAddressAutoAccept UserId (Maybe AutoAccept) diff --git a/src/Simplex/Chat/Library/Commands.hs b/src/Simplex/Chat/Library/Commands.hs index a565d90696..744bb2ba26 100644 --- a/src/Simplex/Chat/Library/Commands.hs +++ b/src/Simplex/Chat/Library/Commands.hs @@ -1812,11 +1812,11 @@ processChatCommand' vr = \case CRUserContactLink user <$> withFastStore (`getUserAddress` user) ShowMyAddress -> withUser' $ \User {userId} -> processChatCommand $ APIShowMyAddress userId - APIAddShortLinkMyAddress userId -> withUserId' userId $ \user -> do + APIAddMyAddressShortLink userId -> withUserId' userId $ \user -> do (ucl@UserContactLink {connLinkContact = CCLink connFullLink sLnk_}, conn) <- withFastStore $ \db -> (,) <$> getUserAddress db user <*> getUserAddressConnection db vr user when (isJust sLnk_) $ throwCmdError "address already has short link" - sLnk <- withAgent $ \a -> setContactShortLink a (aConnId conn) "" + sLnk <- shortenShortLink' =<< withAgent (\a -> setContactShortLink a (aConnId conn) "" Nothing) case entityId conn of Just uclId -> do withFastStore' $ \db -> setUserContactLinkShortLink db uclId sLnk @@ -2401,7 +2401,7 @@ processChatCommand' vr = \case pure $ CRGroupLinkCreated user gInfo ccLink' mRole APIGroupLinkMemberRole groupId mRole' -> withUser $ \user -> withGroupLock "groupLinkMemberRole" groupId $ do gInfo <- withFastStore $ \db -> getGroupInfo db vr user groupId - (groupLinkId, groupLink, mRole) <- withFastStore $ \db -> getGroupLink db user gInfo + (groupLinkId, groupLink, _, mRole) <- withFastStore $ \db -> getGroupLink db user gInfo assertUserGroupRole gInfo GRAdmin when (mRole' > GRMember) $ throwChatError $ CEGroupMemberInitialRole gInfo mRole' when (mRole' /= mRole) $ withFastStore' $ \db -> setGroupLinkMemberRole db user groupLinkId mRole' @@ -2412,16 +2412,17 @@ processChatCommand' vr = \case pure $ CRGroupLinkDeleted user gInfo APIGetGroupLink groupId -> withUser $ \user -> do gInfo <- withFastStore $ \db -> getGroupInfo db vr user groupId - (_, groupLink, mRole) <- withFastStore $ \db -> getGroupLink db user gInfo + (_, groupLink, _, mRole) <- withFastStore $ \db -> getGroupLink db user gInfo pure $ CRGroupLink user gInfo groupLink mRole - APIAddShortLinkGroupLink groupId -> withUser $ \user -> do - (gInfo, (uclId, _gLink@(CCLink connFullLink sLnk_), mRole), conn) <- withFastStore $ \db -> do + APIAddGroupShortLink groupId -> withUser $ \user -> do + (gInfo, (uclId, _gLink@(CCLink connFullLink sLnk_), gLinkId, mRole), conn) <- withFastStore $ \db -> do gInfo <- getGroupInfo db vr user groupId gLink <- getGroupLink db user gInfo conn <- getGroupLinkConnection db vr user gInfo pure (gInfo, gLink, conn) when (isJust sLnk_) $ throwCmdError "group link already has short link" - sLnk <- withAgent $ \a -> setContactShortLink a (aConnId conn) "" + let crClientData = encodeJSON $ CRDataGroup gLinkId + sLnk <- shortenShortLink' =<< toShortGroupLink <$> withAgent (\a -> setContactShortLink a (aConnId conn) "" (Just crClientData)) withFastStore' $ \db -> setUserContactLinkShortLink db uclId sLnk let groupLink' = CCLink connFullLink (Just sLnk) pure $ CRGroupLink user gInfo groupLink' mRole @@ -3295,13 +3296,14 @@ processChatCommand' vr = \case CSLContact _ ct srv linkKey -> CSLContact SLSServer ct srv linkKey restoreShortLink' l = (`restoreShortLink` l) <$> asks (shortLinkPresetServers . config) shortLinkUserData short = if short then Just "" else Nothing + shortenShortLink' :: ConnShortLink m -> CM (ConnShortLink m) + shortenShortLink' l = (`shortenShortLink` l) <$> asks (shortLinkPresetServers . config) shortenCreatedLink :: CreatedConnLink m -> CM (CreatedConnLink m) - shortenCreatedLink (CCLink cReq sLnk) = CCLink cReq <$> mapM (\l -> (`shortenShortLink` l) <$> asks (shortLinkPresetServers . config)) sLnk + shortenCreatedLink (CCLink cReq sLnk) = CCLink cReq <$> mapM shortenShortLink' sLnk createdGroupLink :: CreatedLinkContact -> CreatedLinkContact - createdGroupLink (CCLink cReq shortLink) = CCLink cReq (toGroupLink <$> shortLink) - where - toGroupLink :: ShortLinkContact -> ShortLinkContact - toGroupLink (CSLContact sch _ srv k) = CSLContact sch CCTGroup srv k + createdGroupLink (CCLink cReq shortLink) = CCLink cReq (toShortGroupLink <$> shortLink) + toShortGroupLink :: ShortLinkContact -> ShortLinkContact + toShortGroupLink (CSLContact sch _ srv k) = CSLContact sch CCTGroup srv k updateCIGroupInvitationStatus :: User -> GroupInfo -> CIGroupInvitationStatus -> CM () updateCIGroupInvitationStatus user GroupInfo {groupId} newStatus = do AChatItem _ _ cInfo ChatItem {content, meta = CIMeta {itemId}} <- withFastStore $ \db -> getChatItemByGroupId db vr user groupId @@ -4244,7 +4246,7 @@ chatCommandP = "/_set link role #" *> (APIGroupLinkMemberRole <$> A.decimal <*> memberRole), "/_delete link #" *> (APIDeleteGroupLink <$> A.decimal), "/_get link #" *> (APIGetGroupLink <$> A.decimal), - "/_short link #" *> (APIAddShortLinkGroupLink <$> A.decimal), + "/_short link #" *> (APIAddGroupShortLink <$> A.decimal), "/create link #" *> (CreateGroupLink <$> displayNameP <*> (memberRole <|> pure GRMember) <*> shortP), "/set link role #" *> (GroupLinkMemberRole <$> displayNameP <*> memberRole), "/delete link #" *> (DeleteGroupLink <$> displayNameP), @@ -4300,7 +4302,7 @@ chatCommandP = ("/delete_address" <|> "/da") $> DeleteMyAddress, "/_show_address " *> (APIShowMyAddress <$> A.decimal), ("/show_address" <|> "/sa") $> ShowMyAddress, - "/_short_link_address " *> (APIAddShortLinkMyAddress <$> A.decimal), + "/_short_link_address " *> (APIAddMyAddressShortLink <$> A.decimal), "/_profile_address " *> (APISetProfileAddress <$> A.decimal <* A.space <*> onOffP), ("/profile_address " <|> "/pa ") *> (SetProfileAddress <$> onOffP), "/_auto_accept " *> (APIAddressAutoAccept <$> A.decimal <* A.space <*> autoAcceptP), diff --git a/src/Simplex/Chat/Store/Groups.hs b/src/Simplex/Chat/Store/Groups.hs index 6c66ea0e64..f3661699cb 100644 --- a/src/Simplex/Chat/Store/Groups.hs +++ b/src/Simplex/Chat/Store/Groups.hs @@ -256,12 +256,12 @@ deleteGroupLink db User {userId} GroupInfo {groupId} = do (userId, groupId) DB.execute db "DELETE FROM user_contact_links WHERE user_id = ? AND group_id = ?" (userId, groupId) -getGroupLink :: DB.Connection -> User -> GroupInfo -> ExceptT StoreError IO (Int64, CreatedLinkContact, GroupMemberRole) +getGroupLink :: DB.Connection -> User -> GroupInfo -> ExceptT StoreError IO (Int64, CreatedLinkContact, GroupLinkId, GroupMemberRole) getGroupLink db User {userId} gInfo@GroupInfo {groupId} = ExceptT . firstRow groupLink (SEGroupLinkNotFound gInfo) $ - DB.query db "SELECT user_contact_link_id, conn_req_contact, short_link_contact, group_link_member_role FROM user_contact_links WHERE user_id = ? AND group_id = ? LIMIT 1" (userId, groupId) + DB.query db "SELECT user_contact_link_id, conn_req_contact, short_link_contact, group_link_id, group_link_member_role FROM user_contact_links WHERE user_id = ? AND group_id = ? LIMIT 1" (userId, groupId) where - groupLink (linkId, cReq, shortLink, mRole_) = (linkId, CCLink cReq shortLink, fromMaybe GRMember mRole_) + groupLink (linkId, cReq, shortLink, gLinkId, mRole_) = (linkId, CCLink cReq shortLink, gLinkId, fromMaybe GRMember mRole_) getGroupLinkId :: DB.Connection -> User -> GroupInfo -> IO (Maybe GroupLinkId) getGroupLinkId db User {userId} GroupInfo {groupId} = diff --git a/src/Simplex/Chat/Store/SQLite/Migrations/chat_query_plans.txt b/src/Simplex/Chat/Store/SQLite/Migrations/chat_query_plans.txt index 36833ddd3d..ea91bced4d 100644 --- a/src/Simplex/Chat/Store/SQLite/Migrations/chat_query_plans.txt +++ b/src/Simplex/Chat/Store/SQLite/Migrations/chat_query_plans.txt @@ -5794,7 +5794,7 @@ Query: SELECT user_contact_link_id FROM contact_requests WHERE contact_request_i Plan: SEARCH contact_requests USING INTEGER PRIMARY KEY (rowid=?) -Query: SELECT user_contact_link_id, conn_req_contact, short_link_contact, group_link_member_role FROM user_contact_links WHERE user_id = ? AND group_id = ? LIMIT 1 +Query: SELECT user_contact_link_id, conn_req_contact, short_link_contact, group_link_id, group_link_member_role FROM user_contact_links WHERE user_id = ? AND group_id = ? LIMIT 1 Plan: SEARCH user_contact_links USING INDEX idx_user_contact_links_group_id (group_id=?)