// Copyright © 2023 OpenIM open source community. All rights reserved. // // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. // You may obtain a copy of the License at // // http://www.apache.org/licenses/LICENSE-2.0 // // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. package chat import ( "context" "time" chatdb "git.imall.cloud/openim/chat/pkg/common/db/table/chat" "git.imall.cloud/openim/chat/pkg/common/mctx" "git.imall.cloud/openim/chat/pkg/protocol/chat" "github.com/openimsdk/tools/errs" ) // ==================== 收藏相关 RPC ==================== // CreateFavorite 创建收藏 func (o *chatSvr) CreateFavorite(ctx context.Context, req *chat.CreateFavoriteReq) (*chat.CreateFavoriteResp, error) { // 获取当前用户ID userID, _, err := mctx.Check(ctx) if err != nil { return nil, err } // 验证收藏类型 if req.Type < 1 || req.Type > 7 { return nil, errs.ErrArgs.WrapMsg("invalid favorite type") } // 创建收藏对象 favorite := &chatdb.Favorite{ UserID: userID, Type: req.Type, Title: req.Title, Content: req.Content, Description: req.Description, Thumbnail: req.Thumbnail, LinkURL: req.LinkURL, FileSize: req.FileSize, Duration: req.Duration, Location: req.Location, Tags: req.Tags, Remark: req.Remark, Status: 1, // 正常状态 CreateTime: time.Now(), UpdateTime: time.Now(), } // 保存到数据库 if err := o.Database.CreateFavorite(ctx, favorite); err != nil { return nil, err } return &chat.CreateFavoriteResp{ FavoriteID: favorite.ID, }, nil } // GetFavorite 获取收藏详情 func (o *chatSvr) GetFavorite(ctx context.Context, req *chat.GetFavoriteReq) (*chat.GetFavoriteResp, error) { // 获取当前用户ID userID, _, err := mctx.Check(ctx) if err != nil { return nil, err } // 获取收藏 favorite, err := o.Database.GetFavorite(ctx, req.FavoriteID) if err != nil { return nil, err } // 验证是否为当前用户的收藏 if favorite.UserID != userID { return nil, errs.ErrNoPermission.WrapMsg("not your favorite") } return &chat.GetFavoriteResp{ Favorite: convertFavoriteToProto(favorite), }, nil } // GetFavorites 获取收藏列表 func (o *chatSvr) GetFavorites(ctx context.Context, req *chat.GetFavoritesReq) (*chat.GetFavoritesResp, error) { // 获取当前用户ID userID, _, err := mctx.Check(ctx) if err != nil { return nil, err } var total int64 var favorites []*chatdb.Favorite if req.Type > 0 { // 按类型查询 total, favorites, err = o.Database.GetFavoritesByUserIDAndType(ctx, userID, req.Type, req.Pagination) } else { // 查询所有 total, favorites, err = o.Database.GetFavoritesByUserID(ctx, userID, req.Pagination) } if err != nil { return nil, err } // 转换为响应格式 favoriteInfos := make([]*chat.FavoriteInfo, 0, len(favorites)) for _, fav := range favorites { favoriteInfos = append(favoriteInfos, convertFavoriteToProto(fav)) } return &chat.GetFavoritesResp{ Total: uint32(total), Favorites: favoriteInfos, }, nil } // SearchFavorites 搜索收藏 func (o *chatSvr) SearchFavorites(ctx context.Context, req *chat.SearchFavoritesReq) (*chat.SearchFavoritesResp, error) { // 获取当前用户ID userID, _, err := mctx.Check(ctx) if err != nil { return nil, err } // 搜索收藏 total, favorites, err := o.Database.SearchFavoritesByKeyword(ctx, userID, req.Keyword, req.Pagination) if err != nil { return nil, err } // 转换为响应格式 favoriteInfos := make([]*chat.FavoriteInfo, 0, len(favorites)) for _, fav := range favorites { favoriteInfos = append(favoriteInfos, convertFavoriteToProto(fav)) } return &chat.SearchFavoritesResp{ Total: uint32(total), Favorites: favoriteInfos, }, nil } // UpdateFavorite 更新收藏 func (o *chatSvr) UpdateFavorite(ctx context.Context, req *chat.UpdateFavoriteReq) (*chat.UpdateFavoriteResp, error) { // 获取当前用户ID userID, _, err := mctx.Check(ctx) if err != nil { return nil, err } // 获取收藏,验证所有权 favorite, err := o.Database.GetFavorite(ctx, req.FavoriteID) if err != nil { return nil, err } if favorite.UserID != userID { return nil, errs.ErrNoPermission.WrapMsg("not your favorite") } // 构建更新数据 updateData := make(map[string]any) if req.Title != "" { updateData["title"] = req.Title } if req.Description != "" { updateData["description"] = req.Description } if req.Remark != "" { updateData["remark"] = req.Remark } if len(req.Tags) > 0 { updateData["tags"] = req.Tags } // 更新收藏 if err := o.Database.UpdateFavorite(ctx, req.FavoriteID, updateData); err != nil { return nil, err } return &chat.UpdateFavoriteResp{}, nil } // DeleteFavorite 删除收藏 func (o *chatSvr) DeleteFavorite(ctx context.Context, req *chat.DeleteFavoriteReq) (*chat.DeleteFavoriteResp, error) { // 获取当前用户ID userID, _, err := mctx.Check(ctx) if err != nil { return nil, err } // 验证所有权(批量验证) for _, favoriteID := range req.FavoriteIDs { favorite, err := o.Database.GetFavorite(ctx, favoriteID) if err != nil { return nil, err } if favorite.UserID != userID { return nil, errs.ErrNoPermission.WrapMsg("not your favorite") } } // 删除收藏 if err := o.Database.DeleteFavorite(ctx, req.FavoriteIDs); err != nil { return nil, err } return &chat.DeleteFavoriteResp{}, nil } // GetFavoritesByTags 根据标签获取收藏 func (o *chatSvr) GetFavoritesByTags(ctx context.Context, req *chat.GetFavoritesByTagsReq) (*chat.GetFavoritesByTagsResp, error) { // 获取当前用户ID userID, _, err := mctx.Check(ctx) if err != nil { return nil, err } if len(req.Tags) == 0 { return nil, errs.ErrArgs.WrapMsg("tags is empty") } // 根据标签查询 total, favorites, err := o.Database.GetFavoritesByTags(ctx, userID, req.Tags, req.Pagination) if err != nil { return nil, err } // 转换为响应格式 favoriteInfos := make([]*chat.FavoriteInfo, 0, len(favorites)) for _, fav := range favorites { favoriteInfos = append(favoriteInfos, convertFavoriteToProto(fav)) } return &chat.GetFavoritesByTagsResp{ Total: uint32(total), Favorites: favoriteInfos, }, nil } // GetFavoriteCount 获取收藏数量 func (o *chatSvr) GetFavoriteCount(ctx context.Context, req *chat.GetFavoriteCountReq) (*chat.GetFavoriteCountResp, error) { // 获取当前用户ID userID, _, err := mctx.Check(ctx) if err != nil { return nil, err } // 获取收藏数量 count, err := o.Database.CountFavoritesByUserID(ctx, userID) if err != nil { return nil, err } return &chat.GetFavoriteCountResp{ Count: count, }, nil } // convertFavoriteToProto 将数据库模型转换为 protobuf 消息 func convertFavoriteToProto(fav *chatdb.Favorite) *chat.FavoriteInfo { return &chat.FavoriteInfo{ Id: fav.ID, UserID: fav.UserID, Type: fav.Type, Title: fav.Title, Content: fav.Content, Description: fav.Description, Thumbnail: fav.Thumbnail, LinkURL: fav.LinkURL, FileSize: fav.FileSize, Duration: fav.Duration, Location: fav.Location, Tags: fav.Tags, Remark: fav.Remark, CreateTime: fav.CreateTime.UnixMilli(), UpdateTime: fav.UpdateTime.UnixMilli(), } }