From 93f467247822816b214c57c166f15b70b8242673 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?=E7=8E=8B=E6=9E=97?= <576101059@qq.com>
Date: Fri, 5 Nov 2021 17:38:07 +0800
Subject: [PATCH] =?UTF-8?q?=E4=BF=AE=E5=A4=8DBUG&=E6=96=B0=E5=A2=9E?=
=?UTF-8?q?=E6=8E=A5=E5=8F=A3?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
README.md | 26 +++++++-
group/api.go | 172 +++++++++++++++++++++++++++++++++++++++----------
group/group.go | 18 +++---
group/types.go | 69 ++++++++++++--------
im_test.go | 145 +++++++++++++++++++++++++++--------------
5 files changed, 311 insertions(+), 119 deletions(-)
diff --git a/README.md b/README.md
index 3d345a0..9bb0f35 100644
--- a/README.md
+++ b/README.md
@@ -669,7 +669,7 @@ func main() {
获取直播群在线人数
diff --git a/group/api.go b/group/api.go
index 7822d61..b65fb6a 100644
--- a/group/api.go
+++ b/group/api.go
@@ -89,6 +89,13 @@ type API interface {
// https://cloud.tencent.com/document/product/269/1617
FetchMembers(groupId string, limit, offset int, filter ...*Filter) (ret *FetchMembersRet, err error)
+ // PullMembers 续拉取群成员详细资料
+ // 本方法由“拉取群成员详细资料(FetchMembers)”拓展而来
+ // App管理员可以根据群组ID获取群组成员的资料。
+ // 点击查看详细文档:
+ // https://cloud.tencent.com/document/product/269/1617
+ PullMembers(arg *PullMembersArg, fn func(ret *FetchMembersRet)) (err error)
+
// UpdateGroup 修改群基础资料
// App管理员可以通过该接口修改指定群组的基础信息。
// 点击查看详细文档:
@@ -123,7 +130,14 @@ type API interface {
// App管理员可以通过本接口获取某一用户加入的群信息。默认不获取用户已加入但未激活好友工作群(Work)以及直播群(AVChatRoom)群信息。
// 点击查看详细文档:
// https://cloud.tencent.com/document/product/269/1625
- FetchMemberGroups(arg FetchMemberGroupsArg) (ret *FetchMemberGroupsRet, err error)
+ FetchMemberGroups(arg *FetchMemberGroupsArg) (ret *FetchMemberGroupsRet, err error)
+
+ // PullMemberGroups 续拉取用户所加入的群组
+ // 本方法由“拉取用户所加入的群组(FetchMemberGroups)”拓展而来
+ // App管理员可以通过本接口获取某一用户加入的群信息。默认不获取用户已加入但未激活好友工作群(Work)以及直播群(AVChatRoom)群信息。
+ // 点击查看详细文档:
+ // https://cloud.tencent.com/document/product/269/1625
+ PullMemberGroups(arg *PullMemberGroupsArg, fn func(ret *FetchMemberGroupsRet)) (err error)
// GetRolesInGroup 查询用户在群组中的身份
// App管理员可以通过该接口获取一批用户在群内的身份,即“成员角色”。
@@ -224,6 +238,15 @@ type API interface {
// https://cloud.tencent.com/document/product/269/2738
FetchMessages(groupId string, limit int, msgSeq ...int) (ret *FetchMessagesRet, err error)
+ // PullMessages 续拉取群历史消息
+ // 本方法由“拉取群历史消息(FetchMessages)”拓展而来
+ // 即时通信 IM 的群消息是按 Seq 排序的,按照 server 收到群消息的顺序分配 Seq,先发的群消息 Seq 小,后发的 Seq 大。
+ // 如果用户想拉取一个群的全量消息,首次拉取时不用填拉取 Seq,Server 会自动返回最新的消息,以后拉取时拉取 Seq 填上次返回的最小 Seq 减1。
+ // 如果返回消息的 IsPlaceMsg 为1,表示这个 Seq 的消息或者过期、或者存储失败、或者被删除了。
+ // 点击查看详细文档:
+ // https://cloud.tencent.com/document/product/269/2738
+ PullMessages(groupId string, limit int, fn func(ret *FetchMessagesRet)) (err error)
+
// GetOnlineMemberNum 获取直播群在线人数
// App 管理员可以根据群组 ID 获取直播群在线人数。
// 点击查看详细文档:
@@ -356,7 +379,7 @@ func (a *api) CreateGroup(group *Group) (groupId string, err error) {
req := &createGroupReq{}
req.GroupId = group.id
req.OwnerUserId = group.owner
- req.Type = group.types
+ req.GroupType = group.groupType
req.Name = group.name
req.FaceUrl = group.avatar
req.Introduction = group.introduction
@@ -374,8 +397,8 @@ func (a *api) CreateGroup(group *Group) (groupId string, err error) {
}
}
- if len(group.members) > 0 {
- req.MemberList = make([]*memberItem, 0, len(group.members))
+ if c := len(group.members); c > 0 {
+ req.MemberList = make([]*memberItem, 0, c)
var item *memberItem
for _, member := range group.members {
@@ -424,7 +447,7 @@ func (a *api) GetGroup(groupId string, filter ...*Filter) (group *Group, err err
return
}
- if groups != nil && len(groups) > 0 {
+ if len(groups) > 0 {
if err = groups[0].err; err != nil {
return
}
@@ -473,7 +496,7 @@ func (a *api) GetGroups(groupIds []string, filters ...*Filter) (groups []*Group,
if group.err == nil {
group.id = item.GroupId
group.name = item.Name
- group.types = item.Type
+ group.groupType = item.GroupType
group.owner = item.OwnerUserId
group.avatar = item.FaceUrl
group.memberNum = item.MemberNum
@@ -525,10 +548,7 @@ func (a *api) GetGroups(groupIds []string, filters ...*Filter) (groups []*Group,
// 点击查看详细文档:
// https://cloud.tencent.com/document/product/269/1617
func (a *api) FetchMembers(groupId string, limit, offset int, filters ...*Filter) (ret *FetchMembersRet, err error) {
- req := &fetchMembersReq{}
- req.GroupId = groupId
- req.Limit = limit
- req.Offset = offset
+ req := &fetchMembersReq{GroupId: groupId, Limit: limit, Offset: offset}
if len(filters) > 0 {
if filter := filters[0]; filter != nil {
@@ -547,7 +567,7 @@ func (a *api) FetchMembers(groupId string, limit, offset int, filters ...*Filter
ret = &FetchMembersRet{}
ret.Total = resp.MemberNum
ret.List = make([]*Member, 0, len(resp.MemberList))
- ret.HasMore = resp.MemberNum > limit*(offset+1)
+ ret.HasMore = resp.MemberNum > limit+offset
for _, m := range resp.MemberList {
member := &Member{
@@ -572,6 +592,33 @@ func (a *api) FetchMembers(groupId string, limit, offset int, filters ...*Filter
return
}
+// PullMembers 续拉取群成员详细资料
+// 本方法由“拉取群成员详细资料(FetchMembers)”拓展而来
+// App管理员可以根据群组ID获取群组成员的资料。
+// 点击查看详细文档:
+// https://cloud.tencent.com/document/product/269/1617
+func (a *api) PullMembers(arg *PullMembersArg, fn func(ret *FetchMembersRet)) (err error) {
+ var (
+ offset int
+ ret *FetchMembersRet
+ )
+
+ for ret == nil || ret.HasMore {
+ ret, err = a.FetchMembers(arg.GroupId, arg.Limit, offset, arg.Filter)
+ if err != nil {
+ return
+ }
+
+ fn(ret)
+
+ if ret.HasMore {
+ offset += arg.Limit
+ }
+ }
+
+ return
+}
+
// UpdateGroup 修改群基础资料
// App管理员可以通过该接口修改指定群组的基础信息。
// 点击查看详细文档:
@@ -721,12 +768,8 @@ func (a *api) DestroyGroup(groupId string) (err error) {
// App管理员可以通过本接口获取某一用户加入的群信息。默认不获取用户已加入但未激活好友工作群(Work)以及直播群(AVChatRoom)群信息。
// 点击查看详细文档:
// https://cloud.tencent.com/document/product/269/1625
-func (a *api) FetchMemberGroups(arg FetchMemberGroupsArg) (ret *FetchMemberGroupsRet, err error) {
- req := &fetchMemberGroupsReq{}
- req.UserId = arg.UserId
- req.Limit = arg.Limit
- req.Offset = arg.Offset
- req.GroupType = string(arg.GroupType)
+func (a *api) FetchMemberGroups(arg *FetchMemberGroupsArg) (ret *FetchMemberGroupsRet, err error) {
+ req := &fetchMemberGroupsReq{UserId: arg.UserId, Limit: arg.Limit, Offset: arg.Offset, GroupType: arg.GroupType}
if arg.Filter != nil {
req.ResponseFilter = &responseFilter{
@@ -756,14 +799,14 @@ func (a *api) FetchMemberGroups(arg FetchMemberGroupsArg) (ret *FetchMemberGroup
if arg.Limit == 0 {
ret.HasMore = false
} else {
- ret.HasMore = arg.Limit*(1+arg.Offset) < resp.TotalCount
+ ret.HasMore = arg.Limit+arg.Offset < resp.TotalCount
}
for _, item := range resp.GroupList {
group := NewGroup()
group.id = item.GroupId
group.name = item.Name
- group.types = item.Type
+ group.groupType = item.GroupType
group.owner = item.OwnerUserId
group.avatar = item.FaceUrl
group.memberNum = item.MemberNum
@@ -807,21 +850,55 @@ func (a *api) FetchMemberGroups(arg FetchMemberGroupsArg) (ret *FetchMemberGroup
return
}
+// PullMemberGroups 续拉取用户所加入的群组
+// 本方法由“拉取用户所加入的群组(FetchMemberGroups)”拓展而来
+// App管理员可以通过本接口获取某一用户加入的群信息。默认不获取用户已加入但未激活好友工作群(Work)以及直播群(AVChatRoom)群信息。
+// 点击查看详细文档:
+// https://cloud.tencent.com/document/product/269/1625
+func (a *api) PullMemberGroups(arg *PullMemberGroupsArg, fn func(ret *FetchMemberGroupsRet)) (err error) {
+ var (
+ ret *FetchMemberGroupsRet
+ req = &FetchMemberGroupsArg{
+ UserId: arg.UserId,
+ Limit: arg.Limit,
+ GroupType: arg.GroupType,
+ Filter: arg.Filter,
+ IsWithNoActiveGroups: arg.IsWithNoActiveGroups,
+ IsWithLiveRoomGroups: arg.IsWithLiveRoomGroups,
+ }
+ )
+
+ for ret == nil || ret.HasMore {
+ ret, err = a.FetchMemberGroups(req)
+ if err != nil {
+ return
+ }
+
+ fn(ret)
+
+ if ret.HasMore {
+ req.Offset += arg.Limit
+ }
+ }
+
+ return
+}
+
// GetRolesInGroup 查询用户在群组中的身份
// App管理员可以通过该接口获取一批用户在群内的身份,即“成员角色”。
// 点击查看详细文档:
// https://cloud.tencent.com/document/product/269/1626
-func (a *api) GetRolesInGroup(groupId string, userIds []string) (memberRoles map[string]string, err error) {
- req := getRolesInGroupReq{GroupId: groupId, UserIds: userIds}
+func (a *api) GetRolesInGroup(groupId string, userIds []string) (roles map[string]string, err error) {
+ req := &getRolesInGroupReq{GroupId: groupId, UserIds: userIds}
resp := &getRolesInGroupResp{}
if err = a.client.Post(serviceGroup, commandGetRoleInGroup, req, resp); err != nil {
return
}
- memberRoles = make(map[string]string)
+ roles = make(map[string]string, len(resp.MemberRoleList))
for _, item := range resp.MemberRoleList {
- memberRoles[item.UserId] = item.Role
+ roles[item.UserId] = item.Role
}
return
@@ -834,7 +911,7 @@ func (a *api) GetRolesInGroup(groupId string, userIds []string) (memberRoles map
// 点击查看详细文档:
// https://cloud.tencent.com/document/product/269/1627
func (a *api) ForbidSendMessage(groupId string, userIds []string, shutUpTime int64) (err error) {
- req := forbidSendMessageReq{
+ req := &forbidSendMessageReq{
GroupId: groupId,
UserIds: userIds,
ShutUpTime: shutUpTime,
@@ -860,7 +937,7 @@ func (a *api) AllowSendMessage(groupId string, userIds []string) (err error) {
// 点击查看详细文档:
// https://cloud.tencent.com/document/product/269/2925
func (a *api) GetShuttedUpMembers(groupId string) (shuttedUps map[string]int64, err error) {
- req := getShuttedUpMembersReq{GroupId: groupId}
+ req := &getShuttedUpMembersReq{GroupId: groupId}
resp := &getShuttedUpMembersResp{}
if err = a.client.Post(serviceGroup, commandGetGroupShuttedUin, req, resp); err != nil {
@@ -884,7 +961,7 @@ func (a *api) SendMessage(groupId string, message *Message) (ret *SendMessageRet
return
}
- req := sendMessageReq{}
+ req := &sendMessageReq{}
req.GroupId = groupId
req.FromUserId = message.GetSender()
req.OfflinePushInfo = message.GetOfflinePushInfo()
@@ -931,8 +1008,8 @@ func (a *api) SendMessage(groupId string, message *Message) (ret *SendMessageRet
// App 管理员可以通过该接口在群组中发送系统通知。
// 点击查看详细文档:
// https://cloud.tencent.com/document/product/269/1630
-func (a *api) SendNotification(groupId, content string, userId ...string) (err error) {
- req := sendNotificationReq{GroupId: groupId, Content: content, UserIds: userId}
+func (a *api) SendNotification(groupId, content string, userIds ...string) (err error) {
+ req := &sendNotificationReq{GroupId: groupId, Content: content, UserIds: userIds}
if err = a.client.Post(serviceGroup, commandSendGroupSystemNotification, req, &types.ActionBaseResp{}); err != nil {
return
@@ -948,7 +1025,7 @@ func (a *api) SendNotification(groupId, content string, userId ...string) (err e
// 点击查看详细文档:
// https://cloud.tencent.com/document/product/269/1633
func (a *api) ChangeGroupOwner(groupId, userId string) (err error) {
- req := changeGroupOwnerReq{GroupId: groupId, OwnerUserId: userId}
+ req := &changeGroupOwnerReq{GroupId: groupId, OwnerUserId: userId}
if err = a.client.Post(serviceGroup, commandChangeGroupOwner, req, &types.ActionBaseResp{}); err != nil {
return
@@ -1013,10 +1090,10 @@ func (a *api) ImportGroup(group *Group) (groupId string, err error) {
return
}
- req := importGroupReq{}
+ req := &importGroupReq{}
req.GroupId = group.id
req.OwnerUserId = group.owner
- req.Type = group.types
+ req.GroupType = group.groupType
req.Name = group.name
req.FaceUrl = group.avatar
req.Introduction = group.introduction
@@ -1026,9 +1103,9 @@ func (a *api) ImportGroup(group *Group) (groupId string, err error) {
req.CreateTime = group.createTime
if data := group.GetAllCustomData(); data != nil {
- req.AppDefinedData = make([]customDataItem, 0, len(data))
+ req.AppDefinedData = make([]*customDataItem, 0, len(data))
for key, val := range data {
- req.AppDefinedData = append(req.AppDefinedData, customDataItem{
+ req.AppDefinedData = append(req.AppDefinedData, &customDataItem{
Key: key,
Value: val,
})
@@ -1191,6 +1268,35 @@ func (a *api) FetchMessages(groupId string, limit int, msgSeq ...int) (ret *Fetc
return
}
+// PullMessages 续拉取群历史消息
+// 本方法由“拉取群历史消息(FetchMessages)”拓展而来
+// 即时通信 IM 的群消息是按 Seq 排序的,按照 server 收到群消息的顺序分配 Seq,先发的群消息 Seq 小,后发的 Seq 大。
+// 如果用户想拉取一个群的全量消息,首次拉取时不用填拉取 Seq,Server 会自动返回最新的消息,以后拉取时拉取 Seq 填上次返回的最小 Seq 减1。
+// 如果返回消息的 IsPlaceMsg 为1,表示这个 Seq 的消息或者过期、或者存储失败、或者被删除了。
+// 点击查看详细文档:
+// https://cloud.tencent.com/document/product/269/2738
+func (a *api) PullMessages(groupId string, limit int, fn func(ret *FetchMessagesRet)) (err error) {
+ var (
+ ret *FetchMessagesRet
+ msgSeq int
+ )
+
+ for ret == nil || ret.HasMore {
+ ret, err = a.FetchMessages(groupId, limit, msgSeq)
+ if err != nil {
+ return
+ }
+
+ fn(ret)
+
+ if ret.HasMore {
+ msgSeq = ret.NextSeq
+ }
+ }
+
+ return
+}
+
// GetOnlineMemberNum 获取直播群在线人数
// App 管理员可以根据群组 ID 获取直播群在线人数。
// 点击查看详细文档:
diff --git a/group/group.go b/group/group.go
index 8093c55..f8e57ca 100644
--- a/group/group.go
+++ b/group/group.go
@@ -52,7 +52,7 @@ type Group struct {
err error
id string // 群ID
name string // 群名称
- types string // 群类型
+ groupType GroupType // 群类型
owner string // 群主ID
introduction string // 群简介
notification string // 群公告
@@ -107,14 +107,14 @@ func (g *Group) GetName() string {
return g.name
}
-// SetType 设置群类型
-func (g *Group) SetType(types GroupType) {
- g.types = string(types)
+// SetGroupType 设置群类型
+func (g *Group) SetGroupType(groupType GroupType) {
+ g.groupType = groupType
}
-// GetType 获取群类型
-func (g *Group) GetType() GroupType {
- return GroupType(g.types)
+// GetGroupType 获取群类型
+func (g *Group) GetGroupType() GroupType {
+ return g.groupType
}
// SetIntroduction 设置群简介
@@ -351,11 +351,11 @@ func (g *Group) checkNameArgError() error {
// 检测群类型参数错误
func (g *Group) checkTypeArgError() error {
- if g.types == "" {
+ if g.groupType == "" {
return errNotSetGroupType
}
- switch GroupType(g.types) {
+ switch GroupType(g.groupType) {
case TypePublic, TypePrivate, TypeChatRoom, TypeLiveRoom:
default:
return errInvalidGroupType
diff --git a/group/types.go b/group/types.go
index 6676212..03743e8 100644
--- a/group/types.go
+++ b/group/types.go
@@ -63,7 +63,7 @@ type (
createGroupReq struct {
OwnerUserId string `json:"Owner_Account,omitempty"` // (选填)群主 ID(需是 已导入 的账号)。填写后自动添加到群成员中;如果不填,群没有群主
GroupId string `json:"GroupId,omitempty"` // (选填)为了使得群组 ID 更加简单,便于记忆传播,腾讯云支持 App 在通过 REST API 创建群组时 自定义群组 ID
- Type string `json:"Type"` // (必填)群组形态,包括 Public(陌生人社交群),Private(即 Work,好友工作群),ChatRoom(即 Meeting,会议群),AVChatRoom(直播群)
+ GroupType GroupType `json:"Type"` // (必填)群组形态,包括 Public(陌生人社交群),Private(即 Work,好友工作群),ChatRoom(即 Meeting,会议群),AVChatRoom(直播群)
Name string `json:"Name"` // (必填)群名称,最长30字节,使用 UTF-8 编码,1个汉字占3个字节
Introduction string `json:"Introduction,omitempty"` // (选填)群简介,最长240字节,使用 UTF-8 编码,1个汉字占3个字节
Notification string `json:"Notification,omitempty"` // (选填)群公告,最长300字节,使用 UTF-8 编码,1个汉字占3个字节
@@ -124,7 +124,7 @@ type (
GroupId string `json:"GroupId"`
ErrorCode int `json:"ErrorCode"`
ErrorInfo string `json:"ErrorInfo"`
- Type string `json:"GroupType"`
+ GroupType GroupType `json:"Type"`
Name string `json:"Name"`
AppId int `json:"Appid"`
Introduction string `json:"Introduction"`
@@ -146,19 +146,19 @@ type (
// 获取群成员详细资料(请求)
fetchMembersReq struct {
- GroupId string `json:"GroupId"`
- Limit int `json:"Limit"`
- Offset int `json:"Offset"`
- MemberInfoFilter []string `json:"MemberInfoFilter"`
- MemberRoleFilter []string `json:"MemberRoleFilter"`
- MemberCustomDataFilter []string `json:"AppDefinedDataFilter_GroupMember"`
+ GroupId string `json:"GroupId"` // (必填)需要拉取成员信息的群组的 ID
+ Limit int `json:"Limit"` // (选填)一次最多获取多少个成员的资料,不得超过6000。如果不填,则获取群内全部成员的信息
+ Offset int `json:"Offset"` // (选填)从第几个成员开始获取,如果不填则默认为0,表示从第一个成员开始获取
+ MemberInfoFilter []string `json:"MemberInfoFilter"` // (选填)需要获取哪些信息, 如果没有该字段则为群成员全部资料,成员信息字段详情请参阅 群成员资料
+ MemberRoleFilter []string `json:"MemberRoleFilter"` // (选填)拉取指定身份的群成员资料。如没有填写该字段,默认为所有身份成员资料,成员身份可以为:“Owner”,“Admin”,“Member”
+ MemberCustomDataFilter []string `json:"AppDefinedDataFilter_GroupMember"` // (选填)默认情况是没有的。该字段用来群成员维度的自定义字段过滤器,指定需要获取的群成员维度的自定义字段,群成员维度的自定义字段详情请参阅 自定义字段
}
// 获取群成员详细资料(响应)
fetchMembersResp struct {
types.ActionBaseResp
- MemberNum int `json:"MemberNum"`
- MemberList []memberItem `json:"MemberList"`
+ MemberNum int `json:"MemberNum"` // 本群组的群成员总数
+ MemberList []memberItem `json:"MemberList"` // 获取到的群成员列表,其中包含了全部或者指定的群成员信息,成员信息字段详情请参阅 群成员资料
}
// FetchMembersRet 拉取群成员结果
@@ -168,6 +168,13 @@ type (
List []*Member // 成员列表
}
+ // PullMembersArg 续拉取群成员(参数)
+ PullMembersArg struct {
+ GroupId string // (必填)需要拉取成员信息的群组的 ID
+ Limit int // (选填)一次最多获取多少个成员的资料,不得超过6000。如果不填,则获取群内全部成员的信息
+ Filter *Filter // (选填)返回过滤器
+ }
+
// 修改群基础资料(请求)
updateGroupReq struct {
GroupId string `json:"GroupId"`
@@ -241,12 +248,22 @@ type (
List []*Group // 列表
}
+ // PullMemberGroupsArg 续拉取用户所加入的群组(参数)
+ PullMemberGroupsArg struct {
+ UserId string // (必填)用户ID
+ Limit int // (选填)单次拉取的群组数量,如果不填代表所有群组
+ GroupType GroupType // (选填)拉取哪种群组类型
+ Filter *Filter // (选填)过滤器
+ IsWithNoActiveGroups bool // (选填)是否获取用户已加入但未激活的 Private(即新版本中 Work,好友工作群) 群信息
+ IsWithLiveRoomGroups bool // (选填)是否获取用户加入的 AVChatRoom(直播群)
+ }
+
// 拉取用户所加入的群组(请求)
fetchMemberGroupsReq struct {
UserId string `json:"Member_Account"` // (必填)用户ID
Limit int `json:"Limit,omitempty"` // (选填)单次拉取的群组数量,如果不填代表所有群组
Offset int `json:"Offset,omitempty"` // (选填)从第多少个群组开始拉取
- GroupType string `json:"GroupType,omitempty"` // (选填)拉取哪种群组类型
+ GroupType GroupType `json:"GroupType,omitempty"` // (选填)拉取哪种群组类型
WithHugeGroups int `json:"WithHugeGroups,omitempty"`
WithNoActiveGroups int `json:"WithNoActiveGroups,omitempty"`
ResponseFilter *responseFilter `json:"ResponseFilter,omitempty"` // (选填)响应过滤
@@ -256,7 +273,7 @@ type (
fetchMemberGroupsResp struct {
types.ActionBaseResp
TotalCount int `json:"TotalCount"`
- GroupList []groupInfo `json:"GroupIds"`
+ GroupList []groupInfo `json:"GroupIdList"`
}
// 获取
@@ -334,9 +351,9 @@ type (
// 在群组中发送系统通知(请求)
sendNotificationReq struct {
- GroupId string `json:"GroupId"`
- Content string `json:"Content"`
- UserIds []string `json:"ToMembers_Account"`
+ GroupId string `json:"GroupId"` // (必填)向哪个群组发送系统通知
+ Content string `json:"Content"` // (必填)系统通知的内容
+ UserIds []string `json:"ToMembers_Account,omitempty"` // (选填)接收者群成员列表,请填写接收者 UserID,不填或为空表示全员下发
}
// 转让群主(请求)
@@ -369,17 +386,17 @@ type (
// 导入群基础资料(请求)
importGroupReq struct {
- OwnerUserId string `json:"Owner_Account,omitempty"` // (选填)群主 ID(需是 已导入 的账号)。填写后自动添加到群成员中;如果不填,群没有群主
- GroupId string `json:"GroupId,omitempty"` // (选填)为了使得群组 ID 更加简单,便于记忆传播,腾讯云支持 App 在通过 REST API 创建群组时 自定义群组 ID
- Type string `json:"GroupType"` // (必填)群组形态,包括 Public(陌生人社交群),Private(即 Work,好友工作群),ChatRoom(即 Meeting,会议群),AVChatRoom(直播群)
- Name string `json:"Name"` // (必填)群名称,最长30字节,使用 UTF-8 编码,1个汉字占3个字节
- Introduction string `json:"Introduction,omitempty"` // (选填)群简介,最长240字节,使用 UTF-8 编码,1个汉字占3个字节
- Notification string `json:"Notification,omitempty"` // (选填)群公告,最长300字节,使用 UTF-8 编码,1个汉字占3个字节
- FaceUrl string `json:"FaceUrl,omitempty"` // (选填)群头像 URL,最长100字节
- MaxMemberNum uint `json:"MaxMemberCount,omitempty"` // (选填)最大群成员数量,缺省时的默认值:付费套餐包上限,例如体验版是20,如果升级套餐包,需按照修改群基础资料修改这个字段
- ApplyJoinOption string `json:"ApplyJoinOption,omitempty"` // (选填)申请加群处理方式。包含 FreeAccess(自由加入),NeedPermission(需要验证),DisableApply(禁止加群),不填默认为 NeedPermission(需要验证) 仅当创建支持申请加群的 群组 时,该字段有效
- AppDefinedData []customDataItem `json:"AppDefinedData,omitempty"` // (选填)群组维度的自定义字段,默认情况是没有的,可以通过 即时通信 IM 控制台 进行配置,详情请参阅 自定义字段
- CreateTime int64 `json:"CreateTime"` // (选填)群组的创建时间
+ OwnerUserId string `json:"Owner_Account,omitempty"` // (选填)群主 ID(需是 已导入 的账号)。填写后自动添加到群成员中;如果不填,群没有群主
+ GroupId string `json:"GroupId,omitempty"` // (选填)为了使得群组 ID 更加简单,便于记忆传播,腾讯云支持 App 在通过 REST API 创建群组时 自定义群组 ID
+ GroupType GroupType `json:"Type"` // (必填)群组形态,包括 Public(陌生人社交群),Private(即 Work,好友工作群),ChatRoom(即 Meeting,会议群),AVChatRoom(直播群)
+ Name string `json:"Name"` // (必填)群名称,最长30字节,使用 UTF-8 编码,1个汉字占3个字节
+ Introduction string `json:"Introduction,omitempty"` // (选填)群简介,最长240字节,使用 UTF-8 编码,1个汉字占3个字节
+ Notification string `json:"Notification,omitempty"` // (选填)群公告,最长300字节,使用 UTF-8 编码,1个汉字占3个字节
+ FaceUrl string `json:"FaceUrl,omitempty"` // (选填)群头像 URL,最长100字节
+ MaxMemberNum uint `json:"MaxMemberCount,omitempty"` // (选填)最大群成员数量,缺省时的默认值:付费套餐包上限,例如体验版是20,如果升级套餐包,需按照修改群基础资料修改这个字段
+ ApplyJoinOption string `json:"ApplyJoinOption,omitempty"` // (选填)申请加群处理方式。包含 FreeAccess(自由加入),NeedPermission(需要验证),DisableApply(禁止加群),不填默认为 NeedPermission(需要验证) 仅当创建支持申请加群的 群组 时,该字段有效
+ AppDefinedData []*customDataItem `json:"AppDefinedData,omitempty"` // (选填)群组维度的自定义字段,默认情况是没有的,可以通过 即时通信 IM 控制台 进行配置,详情请参阅 自定义字段
+ CreateTime int64 `json:"CreateTime"` // (选填)群组的创建时间
}
// 导入群基础资料(响应)
diff --git a/im_test.go b/im_test.go
index 9c6d5ec..85410f1 100644
--- a/im_test.go
+++ b/im_test.go
@@ -1016,8 +1016,8 @@ func TestIm_Private_GetUnreadMessageNum(t *testing.T) {
// 创建群组
func TestIm_Group_CreateGroup(t *testing.T) {
g := group.NewGroup()
- g.SetName("测试群1")
- g.SetType(group.TypeLiveRoom)
+ g.SetName("测试群2")
+ g.SetGroupType(group.TypePrivate)
g.SetMaxMemberNum(30)
g.SetAvatar("http://www.baidu.com")
g.SetGroupId("test_group2")
@@ -1040,7 +1040,7 @@ func TestIm_Group_CreateGroup(t *testing.T) {
// 解散单个群
func TestIm_Group_DestroyGroup(t *testing.T) {
- err := NewIM().Group().DestroyGroup("test_group1")
+ err := NewIM().Group().DestroyGroup("test_group2")
if err != nil {
handleError(t, "group.DestroyGroup", err)
}
@@ -1050,15 +1050,15 @@ func TestIm_Group_DestroyGroup(t *testing.T) {
// 获取单个群详细资料
func TestIm_Group_GetGroup(t *testing.T) {
- g, err := NewIM().Group().GetGroup("test_group1")
+ g, err := NewIM().Group().GetGroup("test_group2")
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.GetGroup", err)
}
if g != nil {
t.Log(g.GetGroupId())
t.Log(g.GetName())
- t.Log(g.GetType())
+ t.Log(g.GetGroupType())
t.Log(g.GetOwner())
t.Log(g.GetAvatar())
}
@@ -1067,10 +1067,10 @@ func TestIm_Group_GetGroup(t *testing.T) {
// 获取多个群详细资料
func TestIm_Group_GetGroups(t *testing.T) {
groups, err := NewIM().Group().GetGroups([]string{
- "test_group1",
+ "test_group2",
})
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.GetGroups", err)
}
for _, g := range groups {
@@ -1079,7 +1079,7 @@ func TestIm_Group_GetGroups(t *testing.T) {
} else {
t.Log(g.GetGroupId())
t.Log(g.GetName())
- t.Log(g.GetType())
+ t.Log(g.GetGroupType())
t.Log(g.GetOwner())
t.Log(g.GetAvatar())
}
@@ -1088,12 +1088,12 @@ func TestIm_Group_GetGroups(t *testing.T) {
// 添加群成员
func TestIm_Group_AddGroupMembers(t *testing.T) {
- results, err := NewIM().Group().AddMembers("test_group1", []string{
+ results, err := NewIM().Group().AddMembers("test_group2", []string{
test1,
test2,
}, true)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.AddMembers", err)
}
t.Log(results)
@@ -1101,13 +1101,13 @@ func TestIm_Group_AddGroupMembers(t *testing.T) {
// 删除群成员
func TestIm_Group_DeleteGroupMembers(t *testing.T) {
- err := NewIM().Group().DeleteMembers("test_group1", []string{
+ err := NewIM().Group().DeleteMembers("test_group2", []string{
test1,
test2,
test3,
}, "测试删除", true)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.DeleteMembers", err)
}
t.Log("Success")
@@ -1115,9 +1115,9 @@ func TestIm_Group_DeleteGroupMembers(t *testing.T) {
// 转让群组
func TestIm_Group_ChangeGroupOwner(t *testing.T) {
- err := NewIM().Group().ChangeGroupOwner("test_group1", test1)
+ err := NewIM().Group().ChangeGroupOwner("test_group2", test1)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.ChangeGroupOwner", err)
}
t.Log("Success")
@@ -1127,16 +1127,16 @@ func TestIm_Group_ChangeGroupOwner(t *testing.T) {
func TestIm_Group_UpdateGroup(t *testing.T) {
g := group.NewGroup()
g.SetName("测试群1")
- g.SetType(group.TypePublic)
+ g.SetGroupType(group.TypePublic)
g.SetMaxMemberNum(30)
g.SetAvatar("http://www.baidu.com")
- g.SetGroupId("test_group1")
+ g.SetGroupId("test_group2")
g.SetIntroduction("这是一个测试群")
g.SetNotification("这是一个测试群公告")
err := NewIM().Group().UpdateGroup(g)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.UpdateGroup", err)
}
t.Log("Success")
@@ -1144,13 +1144,13 @@ func TestIm_Group_UpdateGroup(t *testing.T) {
// 查询用户在群组中的身份
func TestIm_Group_GetRolesInGroup(t *testing.T) {
- ret, err := NewIM().Group().GetRolesInGroup("test_group1", []string{
+ ret, err := NewIM().Group().GetRolesInGroup("test_group2", []string{
test1,
test2,
test3,
})
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.GetRolesInGroup", err)
}
t.Log(ret)
@@ -1160,7 +1160,7 @@ func TestIm_Group_GetRolesInGroup(t *testing.T) {
func TestIm_Group_FetchGroupMembers(t *testing.T) {
ret, err := NewIM().Group().FetchMembers("test_group1", 3, 2)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.FetchMembers", err)
}
t.Log(ret.HasMore)
@@ -1171,6 +1171,24 @@ func TestIm_Group_FetchGroupMembers(t *testing.T) {
}
}
+// 拉取群成员详细资料
+func TestIm_Group_PullGroupMembers(t *testing.T) {
+ err := NewIM().Group().PullMembers(&group.PullMembersArg{
+ GroupId: "test_group2",
+ Limit: 3,
+ }, func(ret *group.FetchMembersRet) {
+ t.Log(ret.HasMore)
+ t.Log(ret.Total)
+
+ for _, member := range ret.List {
+ t.Log(member.GetUserId())
+ }
+ })
+ if err != nil {
+ handleError(t, "group.PullMembers", err)
+ }
+}
+
// 拉取App中的所有群组
func TestIm_Group_FetchGroupIds(t *testing.T) {
ret, err := NewIM().Group().FetchGroupIds(3, 7964653962)
@@ -1229,9 +1247,9 @@ func TestIm_Group_UpdateGroupMember(t *testing.T) {
member.SetNameCard("这是一个测试名片信息")
member.SetMsgFlag(group.MsgFlagAcceptAndNotify)
- err := NewIM().Group().UpdateMember("test_group1", member)
+ err := NewIM().Group().UpdateMember("test_group2", member)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.UpdateMember", err)
}
t.Log("Success")
@@ -1239,15 +1257,15 @@ func TestIm_Group_UpdateGroupMember(t *testing.T) {
// 拉取用户所加入的群组
func TestIm_Group_FetchMemberGroups(t *testing.T) {
- ret, err := NewIM().Group().FetchMemberGroups(group.FetchMemberGroupsArg{
+ ret, err := NewIM().Group().FetchMemberGroups(&group.FetchMemberGroupsArg{
UserId: test1,
Limit: 3,
- Offset: 2,
+ Offset: 0,
IsWithLiveRoomGroups: true,
IsWithNoActiveGroups: true,
})
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.FetchMemberGroups", err)
}
t.Log(ret.Total)
@@ -1255,13 +1273,30 @@ func TestIm_Group_FetchMemberGroups(t *testing.T) {
t.Log(ret.List)
}
+// 续拉取用户所加入的群组
+func TestIm_Group_PullMemberGroups(t *testing.T) {
+ err := NewIM().Group().PullMemberGroups(&group.PullMemberGroupsArg{
+ UserId: test1,
+ Limit: 3,
+ IsWithLiveRoomGroups: true,
+ IsWithNoActiveGroups: true,
+ }, func(ret *group.FetchMemberGroupsRet) {
+ t.Log(ret.Total)
+ t.Log(ret.HasMore)
+ t.Log(ret.List)
+ })
+ if err != nil {
+ handleError(t, "group.PullMemberGroups", err)
+ }
+}
+
// 批量禁言
func TestIm_Group_ForbidSendMessage(t *testing.T) {
err := NewIM().Group().ForbidSendMessage("test_group1", []string{
test1,
}, 1000)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.ForbidSendMessage", err)
}
t.Log("Success")
@@ -1269,7 +1304,7 @@ func TestIm_Group_ForbidSendMessage(t *testing.T) {
// 取消禁言
func TestIm_Group_AllowSendMessage(t *testing.T) {
- err := NewIM().Group().AllowSendMessage("test_group1", []string{
+ err := NewIM().Group().AllowSendMessage("test_group2", []string{
test1,
test2,
})
@@ -1282,9 +1317,9 @@ func TestIm_Group_AllowSendMessage(t *testing.T) {
// 获取被禁言群成员列表
func TestIm_Group_GetShuttedUpMembers(t *testing.T) {
- shuttedUps, err := NewIM().Group().GetShuttedUpMembers("test_group1")
+ shuttedUps, err := NewIM().Group().GetShuttedUpMembers("test_group2")
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.GetShuttedUpMembers", err)
}
t.Log(shuttedUps)
@@ -1292,9 +1327,9 @@ func TestIm_Group_GetShuttedUpMembers(t *testing.T) {
// 撤回单条群消息
func TestIm_Group_RevokeMessage(t *testing.T) {
- err := NewIM().Group().RevokeMessage("test_group1", 100)
+ err := NewIM().Group().RevokeMessage("test_group2", 100)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.RevokeMessage", err)
}
t.Log("Success")
@@ -1302,9 +1337,9 @@ func TestIm_Group_RevokeMessage(t *testing.T) {
// 撤回多条群消息
func TestIm_Group_RevokeMessages(t *testing.T) {
- results, err := NewIM().Group().RevokeMessages("test_group1", 100)
+ results, err := NewIM().Group().RevokeMessages("test_group2", 100)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.RevokeMessages", err)
}
t.Log(results)
@@ -1312,9 +1347,9 @@ func TestIm_Group_RevokeMessages(t *testing.T) {
// 设置成员未读消息计数
func TestIm_Group_SetMemberUnreadMsgNum(t *testing.T) {
- err := NewIM().Group().SetMemberUnreadMsgNum("test_group1", test1, 100)
+ err := NewIM().Group().SetMemberUnreadMsgNum("test_group2", test1, 100)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.SetMemberUnreadMsgNum", err)
}
t.Log("Success")
@@ -1322,9 +1357,9 @@ func TestIm_Group_SetMemberUnreadMsgNum(t *testing.T) {
// 撤回指定用户发送的消息
func TestIm_Group_RevokeMemberMessages(t *testing.T) {
- err := NewIM().Group().RevokeMemberMessages("test_group1", test1)
+ err := NewIM().Group().RevokeMemberMessages("test_group2", test1)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.RevokeMemberMessages", err)
}
t.Log("Success")
@@ -1352,9 +1387,9 @@ func TestIm_Group_SendMessage(t *testing.T) {
message.AtMembers(test2)
message.ClearAtMembers()
- ret, err := NewIM().Group().SendMessage("test_group1", message)
+ ret, err := NewIM().Group().SendMessage("test_group2", message)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.SendMessage", err)
}
t.Log(ret.MsgSeq)
@@ -1363,9 +1398,9 @@ func TestIm_Group_SendMessage(t *testing.T) {
// 在群组中发送普通消息
func TestIm_Group_SendNotification(t *testing.T) {
- err := NewIM().Group().SendNotification("test_group1", "Hello welcome to the test group", test1)
+ err := NewIM().Group().SendNotification("test_group2", "Hello welcome to the test group", test1)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.SendNotification", err)
}
t.Log("Success")
@@ -1375,7 +1410,7 @@ func TestIm_Group_SendNotification(t *testing.T) {
func TestIm_Group_ImportGroup(t *testing.T) {
g := group.NewGroup()
g.SetName("测试群1")
- g.SetType(group.TypePublic)
+ g.SetGroupType(group.TypePublic)
g.SetMaxMemberNum(30)
g.SetAvatar("http://www.baidu.com")
g.SetIntroduction("这是一个测试群")
@@ -1383,7 +1418,7 @@ func TestIm_Group_ImportGroup(t *testing.T) {
groupId, err := NewIM().Group().ImportGroup(g)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.ImportGroup", err)
}
t.Log(groupId)
@@ -1399,9 +1434,9 @@ func TestIm_Group_ImportMessages(t *testing.T) {
Text: "Hello world",
})
- results, err := NewIM().Group().ImportMessages("test_group1", message)
+ results, err := NewIM().Group().ImportMessages("test_group2", message)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.ImportMessages", err)
}
t.Log(results)
@@ -1419,9 +1454,9 @@ func TestIm_Group_ImportMembers(t *testing.T) {
members = append(members, member)
}
- results, err := NewIM().Group().ImportMembers("@TGS#25J4AWNHA", members...)
+ results, err := NewIM().Group().ImportMembers("test_group2", members...)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.ImportMembers", err)
}
t.Log(results)
@@ -1429,14 +1464,24 @@ func TestIm_Group_ImportMembers(t *testing.T) {
// 拉取群历史消息
func TestIm_Group_FetchMessages(t *testing.T) {
- ret, err := NewIM().Group().FetchMessages("test_group1", 5)
+ ret, err := NewIM().Group().FetchMessages("test_group2", 5)
if err != nil {
- t.Fatal(err)
+ handleError(t, "group.FetchMessages", err)
}
t.Log(ret)
}
+// 续拉取群历史消息
+func TestIm_Group_PullMessages(t *testing.T) {
+ err := NewIM().Group().PullMessages("test_group2", 5, func(ret *group.FetchMessagesRet) {
+ t.Log(ret)
+ })
+ if err != nil {
+ handleError(t, "group.PullMessages", err)
+ }
+}
+
// 拉取会话列表
func TestIm_RecentContact_FetchSessions(t *testing.T) {
ret, err := NewIM().RecentContact().FetchSessions(&recentcontact.FetchSessionsArg{
|