Fix conversation context topic fallback
This commit is contained in:
+36
-1
@@ -4088,7 +4088,11 @@ func serveIMConversationContext(wrt http.ResponseWriter, req *http.Request) {
|
|||||||
writeIMError(wrt, req, http.StatusMethodNotAllowed, 30002, imReasonMethodNotAllowed, "method not allowed", nil)
|
writeIMError(wrt, req, http.StatusMethodNotAllowed, 30002, imReasonMethodNotAllowed, "method not allowed", nil)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
topic, peer := normalizeP2PConversationTopic(topic, principal.Uid)
|
topic, peer, err := resolveConversationContextTopic(principal, topic)
|
||||||
|
if err != nil {
|
||||||
|
writeIMRelationError(wrt, req, err)
|
||||||
|
return
|
||||||
|
}
|
||||||
if topic == "" || peer.IsZero() {
|
if topic == "" || peer.IsZero() {
|
||||||
writeIMError(wrt, req, http.StatusBadRequest, 30000, imReasonMalformedRequest, "malformed request", map[string]any{"field": "topic"})
|
writeIMError(wrt, req, http.StatusBadRequest, 30000, imReasonMalformedRequest, "malformed request", map[string]any{"field": "topic"})
|
||||||
return
|
return
|
||||||
@@ -9996,6 +10000,37 @@ func normalizeP2PConversationTopic(topic string, uid types.Uid) (string, types.U
|
|||||||
return topic, peer
|
return topic, peer
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func resolveConversationContextTopic(principal *imPrincipal, topic string) (string, types.Uid, error) {
|
||||||
|
normalized, peer := normalizeP2PConversationTopic(topic, principal.Uid)
|
||||||
|
if normalized != "" && !peer.IsZero() {
|
||||||
|
return normalized, peer, nil
|
||||||
|
}
|
||||||
|
topic = strings.TrimSpace(topic)
|
||||||
|
if types.GetTopicCat(topic) != types.TopicCatP2P {
|
||||||
|
return "", types.ZeroUid, nil
|
||||||
|
}
|
||||||
|
if _, _, err := types.ParseP2P(topic); err != nil {
|
||||||
|
return "", types.ZeroUid, nil
|
||||||
|
}
|
||||||
|
cursor := ""
|
||||||
|
for {
|
||||||
|
items, nextCursor, err := store.Relations.ListFriends(principal.TenantID, principal.Uid, "", "", cursor, 100)
|
||||||
|
if err != nil {
|
||||||
|
return "", types.ZeroUid, err
|
||||||
|
}
|
||||||
|
for _, item := range items {
|
||||||
|
if strings.TrimSpace(item.Friendship.Topic) == topic && !item.Friendship.PeerID.IsZero() {
|
||||||
|
return topic, item.Friendship.PeerID, nil
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if nextCursor == "" {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
cursor = nextCursor
|
||||||
|
}
|
||||||
|
return "", types.ZeroUid, nil
|
||||||
|
}
|
||||||
|
|
||||||
func normalizeConversationSettingsTopic(topic string, uid types.Uid) string {
|
func normalizeConversationSettingsTopic(topic string, uid types.Uid) string {
|
||||||
if normalized, peer := normalizeP2PConversationTopic(topic, uid); !peer.IsZero() {
|
if normalized, peer := normalizeP2PConversationTopic(topic, uid); !peer.IsZero() {
|
||||||
return normalized
|
return normalized
|
||||||
|
|||||||
@@ -5736,6 +5736,39 @@ func TestServeIMConversationContextAcceptsUserTopic(t *testing.T) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestServeIMConversationContextAcceptsFriendListTopicFallback(t *testing.T) {
|
||||||
|
ctrl := gomock.NewController(t)
|
||||||
|
defer ctrl.Finish()
|
||||||
|
expectIMBearer(t, ctrl, "token-1", 7, 1)
|
||||||
|
oldRelations := store.Relations
|
||||||
|
peer := types.Uid(2)
|
||||||
|
legacyTopic := types.Uid(2).P2PName(types.Uid(3))
|
||||||
|
store.Relations = &testRelationsStore{friends: []types.FriendListItem{{
|
||||||
|
Friendship: types.Friendship{
|
||||||
|
TenantID: 7,
|
||||||
|
UserID: types.Uid(1),
|
||||||
|
PeerID: peer,
|
||||||
|
Status: types.RelationshipFriend,
|
||||||
|
Topic: legacyTopic,
|
||||||
|
},
|
||||||
|
}}}
|
||||||
|
defer func() { store.Relations = oldRelations }()
|
||||||
|
|
||||||
|
req := httptest.NewRequest(http.MethodGet, "/v1/im/conversations/"+legacyTopic+"/context", nil)
|
||||||
|
req.Header.Set("Authorization", "Bearer token-1")
|
||||||
|
rec := httptest.NewRecorder()
|
||||||
|
|
||||||
|
serveIMConversationContext(rec, req)
|
||||||
|
|
||||||
|
if rec.Code != http.StatusOK {
|
||||||
|
t.Fatalf("status: got %d, want %d; body=%s", rec.Code, http.StatusOK, rec.Body.String())
|
||||||
|
}
|
||||||
|
data := decodeIMHTTPResponse(t, rec).Data.(map[string]any)
|
||||||
|
if data["topic"] != legacyTopic || data["peer_user_id"] != peer.UserId() {
|
||||||
|
t.Fatalf("unexpected context response: %#v", data)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
func TestNormalizeP2PConversationTopicParsesTinodeTopic(t *testing.T) {
|
func TestNormalizeP2PConversationTopicParsesTinodeTopic(t *testing.T) {
|
||||||
user := types.Uid(1)
|
user := types.Uid(1)
|
||||||
peer := types.Uid(2)
|
peer := types.Uid(2)
|
||||||
|
|||||||
Reference in New Issue
Block a user