From 7ddcde9ab64560b4f2e90f4093df3cd3ea223642 Mon Sep 17 00:00:00 2001 From: eatMoreApple <15055461510@163.com> Date: Tue, 27 Apr 2021 11:02:20 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BC=98=E5=8C=96=E5=BA=95=E5=B1=82=E9=80=BB?= =?UTF-8?q?=E8=BE=91=E5=92=8C=E5=A2=9E=E5=8A=A0self=E7=9A=84=E8=A1=8C?= =?UTF-8?q?=E4=B8=BA?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- relations.go | 443 ++++++++++++++++---------------- user.go | 707 ++++++++++++++++++++++++++++++--------------------- 2 files changed, 634 insertions(+), 516 deletions(-) diff --git a/relations.go b/relations.go index 0206217..c415c9a 100644 --- a/relations.go +++ b/relations.go @@ -1,381 +1,364 @@ package openwechat import ( - "errors" - "fmt" - "os" - "strings" - "time" + "fmt" + "os" + "strings" + "time" ) type Friend struct{ *User } // implement fmt.Stringer func (f Friend) String() string { - return fmt.Sprintf("", f.NickName) + return fmt.Sprintf("", f.NickName) } // 重命名当前好友 func (f *Friend) SetRemarkName(name string) error { - return f.setRemarkName(name) + return f.Self.SetRemarkNameToFriend(f, name) } // 发送自定义消息 func (f *Friend) SendMsg(msg *SendMessage) error { - return f.sendMsg(msg) + return f.Self.SendMessageToFriend(f, msg) } // 发送文本消息 func (f *Friend) SendText(content string) error { - return f.sendText(content) + return f.Self.SendTextToFriend(f, content) } // 发送图片消息 func (f *Friend) SendImage(file *os.File) error { - return f.sendImage(file) + return f.Self.SendImageToFriend(f, file) } // 拉该好友入群 func (f *Friend) AddIntoGroup(groups ...*Group) error { - for _, group := range groups { - if err := group.AddFriendsIn(f); err != nil { - return err - } - } - return nil + return f.Self.AddFriendIntoManyGroups(f, groups...) } type Friends []*Friend // 获取好友的数量 func (f Friends) Count() int { - return len(f) + return len(f) } // 获取第一个好友 func (f Friends) First() *Friend { - if f.Count() > 0 { - return f[0] - } - return nil + if f.Count() > 0 { + return f[0] + } + return nil } // 获取最后一个好友 func (f Friends) Last() *Friend { - if f.Count() > 0 { - return f[f.Count()-1] - } - return nil + if f.Count() > 0 { + return f[f.Count()-1] + } + return nil } // 根据用户名查找好友 func (f Friends) SearchByUserName(limit int, username string) (results Friends) { - return f.Search(limit, func(friend *Friend) bool { return friend.User.UserName == username }) + return f.Search(limit, func(friend *Friend) bool { return friend.User.UserName == username }) } // 根据昵称查找好友 func (f Friends) SearchByNickName(limit int, nickName string) (results Friends) { - return f.Search(limit, func(friend *Friend) bool { return friend.User.NickName == nickName }) + return f.Search(limit, func(friend *Friend) bool { return friend.User.NickName == nickName }) } // 根据备注查找好友 func (f Friends) SearchByRemarkName(limit int, remarkName string) (results Friends) { - return f.Search(limit, func(friend *Friend) bool { return friend.User.RemarkName == remarkName }) + return f.Search(limit, func(friend *Friend) bool { return friend.User.RemarkName == remarkName }) } // 根据自定义条件查找好友 func (f Friends) Search(limit int, condFuncList ...func(friend *Friend) bool) (results Friends) { - if condFuncList == nil { - return f - } - if limit <= 0 { - limit = f.Count() - } - for _, member := range f { - if results.Count() == limit { - break - } - var passCount int - for _, condFunc := range condFuncList { - if condFunc(member) { - passCount++ - } - } - if passCount == len(condFuncList) { - results = append(results, member) - } - } - return + if condFuncList == nil { + return f + } + if limit <= 0 { + limit = f.Count() + } + for _, member := range f { + if results.Count() == limit { + break + } + var passCount int + for _, condFunc := range condFuncList { + if condFunc(member) { + passCount++ + } + } + if passCount == len(condFuncList) { + results = append(results, member) + } + } + return } // 向slice的好友依次发送消息 func (f Friends) SendMsg(msg *SendMessage, delay ...time.Duration) error { - for _, friend := range f { - if len(delay) != 0 { - time.Sleep(delay[0]) - } - if err := friend.SendMsg(msg); err != nil { - return err - } - } - return nil + for _, friend := range f { + if len(delay) != 0 { + time.Sleep(delay[0]) + } + if err := friend.SendMsg(msg); err != nil { + return err + } + } + return nil } // 向slice的好友依次发送文本消息 func (f Friends) SendText(text string, delay ...time.Duration) error { - for _, friend := range f { - if len(delay) != 0 { - time.Sleep(delay[0]) - } - if err := friend.SendText(text); err != nil { - return err - } - } - return nil + for _, friend := range f { + if len(delay) != 0 { + time.Sleep(delay[0]) + } + if err := friend.SendText(text); err != nil { + return err + } + } + return nil } +// 向slice的好友依次发送图片消息 func (f Friends) SendImage(file *os.File, delay ...time.Duration) error { - for _, friend := range f { - if len(delay) != 0 { - time.Sleep(delay[0]) - } - if err := friend.SendImage(file); err != nil { - return err - } - } - return nil + for _, friend := range f { + if len(delay) != 0 { + time.Sleep(delay[0]) + } + if err := friend.SendImage(file); err != nil { + return err + } + } + return nil } type Group struct{ *User } // implement fmt.Stringer func (g Group) String() string { - return fmt.Sprintf("", g.NickName) + return fmt.Sprintf("", g.NickName) } +// 发行消息给当前的群组 func (g *Group) SendMsg(msg *SendMessage) error { - return g.sendMsg(msg) + return g.Self.SendMessageToGroup(g, msg) } +// 发行文本消息给当前的群组 func (g *Group) SendText(content string) error { - return g.sendText(content) + return g.Self.SendTextToGroup(g, content) } +// 发行图片消息给当前的群组 func (g *Group) SendImage(file *os.File) error { - return g.sendImage(file) + return g.Self.SendImageToGroup(g, file) } // 获取所有的群成员 func (g *Group) Members() (Members, error) { - group, err := g.Detail() - if err != nil { - return nil, err - } - return group.MemberList, nil + group, err := g.Detail() + if err != nil { + return nil, err + } + return group.MemberList, nil } // 拉好友入群 func (g *Group) AddFriendsIn(friends ...*Friend) error { - if len(friends) == 0 { - return nil - } - groupMembers, err := g.Members() - if err != nil { - return err - } - for _, friend := range friends { - for _, member := range groupMembers { - if member.UserName == friend.UserName { - return fmt.Errorf("user %s has alreay in this group", friend.String()) - } - } - } - req := g.Self.Bot.storage.Request - info := g.Self.Bot.storage.LoginInfo - return g.Self.Bot.Caller.AddFriendIntoChatRoom(req, info, g, friends...) + return g.Self.AddFriendsIntoGroup(g, friends...) } // 从群聊中移除用户 // Deprecated // 无论是网页版,还是程序上都不起作用 func (g *Group) RemoveMembers(members Members) error { - if len(members) == 0 { - return nil - } - if g.IsOwner == 0 { - return errors.New("group owner required") - } - groupMembers, err := g.Members() - if err != nil { - return err - } - // 判断用户是否在群聊中 - var count int - for _, member := range members { - for _, gm := range groupMembers { - if gm.UserName == member.UserName { - count++ - } - } - } - if count != len(members) { - return errors.New("invalid members") - } - req := g.Self.Bot.storage.Request - info := g.Self.Bot.storage.LoginInfo - return g.Self.Bot.Caller.RemoveFriendFromChatRoom(req, info, g, members...) + return g.Self.RemoveMemberFromGroup(g, members) } type Groups []*Group +// 获取群组数量 func (g Groups) Count() int { - return len(g) + return len(g) } +// 获取第一个群组 func (g Groups) First() *Group { - if g.Count() > 0 { - return g[0] - } - return nil + if g.Count() > 0 { + return g[0] + } + return nil } +// 获取最后一个群组 func (g Groups) Last() *Group { - if g.Count() > 0 { - return g[g.Count()-1] - } - return nil + if g.Count() > 0 { + return g[g.Count()-1] + } + return nil } +// 向群组依次发送消息, 支持发送延迟 func (g Groups) SendMsg(msg *SendMessage, delay ...time.Duration) error { - for _, group := range g { - if len(delay) != 0 { - time.Sleep(delay[0]) - } - if err := group.SendMsg(msg); err != nil { - return err - } - } - return nil + var total time.Duration + for _, d := range delay { + total += d + } + for _, group := range g { + time.Sleep(total) + if err := group.SendMsg(msg); err != nil { + return err + } + } + return nil } +// 向群组依次发送文本消息, 支持发送延迟 func (g Groups) SendText(text string, delay ...time.Duration) error { - for _, group := range g { - if len(delay) != 0 { - time.Sleep(delay[0]) - } - if err := group.SendText(text); err != nil { - return err - } - } - return nil + var total time.Duration + for _, d := range delay { + total += d + } + for _, group := range g { + time.Sleep(total) + if err := group.SendText(text); err != nil { + return err + } + } + return nil } +// 向群组依次发送图片消息, 支持发送延迟 func (g Groups) SendImage(file *os.File, delay ...time.Duration) error { - for _, group := range g { - if len(delay) != 0 { - time.Sleep(delay[0]) - } - if err := group.SendImage(file); err != nil { - return err - } - } - return nil + var total time.Duration + for _, d := range delay { + total += d + } + for _, group := range g { + time.Sleep(total) + if err := group.SendImage(file); err != nil { + return err + } + } + return nil } +// 根据用户名查找群组 func (g Groups) SearchByUserName(limit int, username string) (results Groups) { - return g.Search(limit, func(group *Group) bool { return group.UserName == username }) + return g.Search(limit, func(group *Group) bool { return group.UserName == username }) } +// 根据昵称查找群组 func (g Groups) SearchByNickName(limit int, nickName string) (results Groups) { - return g.Search(limit, func(group *Group) bool { return group.NickName == nickName }) + return g.Search(limit, func(group *Group) bool { return group.NickName == nickName }) } +// 根据备注查找群组 func (g Groups) SearchByRemarkName(limit int, remarkName string) (results Groups) { - return g.Search(limit, func(group *Group) bool { return group.RemarkName == remarkName }) + return g.Search(limit, func(group *Group) bool { return group.RemarkName == remarkName }) } +// 根据自定义条件查找群组 func (g Groups) Search(limit int, condFuncList ...func(group *Group) bool) (results Groups) { - if condFuncList == nil { - return g - } - if limit <= 0 { - limit = g.Count() - } - for _, member := range g { - if results.Count() == limit { - break - } - var passCount int - for _, condFunc := range condFuncList { - if condFunc(member) { - passCount++ - } - } - if passCount == len(condFuncList) { - results = append(results, member) - } - } - return -} - -func isFriend(user User) bool { - return !isGroup(user) && strings.HasPrefix(user.UserName, "@") && user.VerifyFlag == 0 -} - -func isGroup(user User) bool { - return strings.HasPrefix(user.UserName, "@@") && user.VerifyFlag == 0 -} - -func isMP(user User) bool { - return user.VerifyFlag == 8 || user.VerifyFlag == 24 || user.VerifyFlag == 136 + if condFuncList == nil { + return g + } + if limit <= 0 { + limit = g.Count() + } + for _, member := range g { + if results.Count() == limit { + break + } + var passCount int + for _, condFunc := range condFuncList { + if condFunc(member) { + passCount++ + } + } + if passCount == len(condFuncList) { + results = append(results, member) + } + } + return } +// 公众号对象 type Mp struct{ *User } func (m Mp) String() string { - return fmt.Sprintf("", m.NickName) + return fmt.Sprintf("", m.NickName) } +// 公众号组对象 type Mps []*Mp +// 数量统计 func (m Mps) Count() int { - return len(m) + return len(m) } +// 获取第一个 func (m Mps) First() *Mp { - if m.Count() > 0 { - return m[0] - } - return nil + if m.Count() > 0 { + return m[0] + } + return nil } +// 获取最后一个 func (m Mps) Last() *Mp { - if m.Count() > 0 { - return m[m.Count()-1] - } - return nil + if m.Count() > 0 { + return m[m.Count()-1] + } + return nil } +// 根据自定义条件查找 func (m Mps) Search(limit int, condFuncList ...func(group *Mp) bool) (results Mps) { - if condFuncList == nil { - return m - } - if limit <= 0 { - limit = m.Count() - } - for _, member := range m { - if results.Count() == limit { - break - } - var passCount int - for _, condFunc := range condFuncList { - if condFunc(member) { - passCount++ - } - } - if passCount == len(condFuncList) { - results = append(results, member) - } - } - return + if condFuncList == nil { + return m + } + if limit <= 0 { + limit = m.Count() + } + for _, member := range m { + if results.Count() == limit { + break + } + var passCount int + for _, condFunc := range condFuncList { + if condFunc(member) { + passCount++ + } + } + if passCount == len(condFuncList) { + results = append(results, member) + } + } + return +} + +// 判断是否为好友 +func isFriend(user User) bool { + return !isGroup(user) && strings.HasPrefix(user.UserName, "@") && user.VerifyFlag == 0 +} + +// 判断是否为群组 +func isGroup(user User) bool { + return strings.HasPrefix(user.UserName, "@@") && user.VerifyFlag == 0 +} + +// 判断是否为公众号 +func isMP(user User) bool { + return user.VerifyFlag == 8 || user.VerifyFlag == 24 || user.VerifyFlag == 136 } diff --git a/user.go b/user.go index e936dd8..937c3b1 100644 --- a/user.go +++ b/user.go @@ -1,391 +1,526 @@ package openwechat import ( - "bytes" - "fmt" - "net/http" - "os" + "bytes" + "errors" + "fmt" + "net/http" + "os" ) type User struct { - Uin int - HideInputBarFlag int - StarFriend int - Sex int - AppAccountFlag int - VerifyFlag int - ContactFlag int - WebWxPluginSwitch int - HeadImgFlag int - SnsFlag int - UserName string - NickName string - HeadImgUrl string - RemarkName string - PYInitial string - PYQuanPin string - RemarkPYInitial string - RemarkPYQuanPin string - Signature string - MemberCount int - MemberList Members - OwnerUin int - Statues int - AttrStatus int - Province string - City string - Alias string - UniFriend int - DisplayName string - ChatRoomId int - KeyWord string - EncryChatRoomId string - IsOwner int + Uin int + HideInputBarFlag int + StarFriend int + Sex int + AppAccountFlag int + VerifyFlag int + ContactFlag int + WebWxPluginSwitch int + HeadImgFlag int + SnsFlag int + IsOwner int + MemberCount int + ChatRoomId int + UniFriend int + OwnerUin int + Statues int + AttrStatus int + Province string + City string + Alias string + DisplayName string + KeyWord string + EncryChatRoomId string + UserName string + NickName string + HeadImgUrl string + RemarkName string + PYInitial string + PYQuanPin string + RemarkPYInitial string + RemarkPYQuanPin string + Signature string - Self *Self + MemberList Members + + Self *Self } // implement fmt.Stringer func (u *User) String() string { - return fmt.Sprintf("", u.NickName) + return fmt.Sprintf("", u.NickName) } // 获取用户头像 func (u *User) GetAvatarResponse() (*http.Response, error) { - return u.Self.Bot.Caller.Client.WebWxGetHeadImg(u.HeadImgUrl) + return u.Self.Bot.Caller.Client.WebWxGetHeadImg(u.HeadImgUrl) } // 下载用户头像 func (u *User) SaveAvatar(filename string) error { - resp, err := u.GetAvatarResponse() - if err != nil { - return err - } - defer resp.Body.Close() - buffer := bytes.Buffer{} - if _, err := buffer.ReadFrom(resp.Body); err != nil { - return err - } - file, err := os.Create(filename) - if err != nil { - return err - } - defer file.Close() - _, err = file.Write(buffer.Bytes()) - return err + resp, err := u.GetAvatarResponse() + if err != nil { + return err + } + defer resp.Body.Close() + buffer := bytes.Buffer{} + if _, err := buffer.ReadFrom(resp.Body); err != nil { + return err + } + file, err := os.Create(filename) + if err != nil { + return err + } + defer file.Close() + _, err = file.Write(buffer.Bytes()) + return err } +// Deprecated func (u *User) sendMsg(msg *SendMessage) error { - msg.FromUserName = u.Self.UserName - msg.ToUserName = u.UserName - info := u.Self.Bot.storage.LoginInfo - request := u.Self.Bot.storage.Request - return u.Self.Bot.Caller.WebWxSendMsg(msg, info, request) + msg.FromUserName = u.Self.UserName + msg.ToUserName = u.UserName + info := u.Self.Bot.storage.LoginInfo + request := u.Self.Bot.storage.Request + return u.Self.Bot.Caller.WebWxSendMsg(msg, info, request) } +// Deprecated func (u *User) sendText(content string) error { - msg := NewTextSendMessage(content, u.Self.UserName, u.UserName) - return u.sendMsg(msg) + msg := NewTextSendMessage(content, u.Self.UserName, u.UserName) + return u.sendMsg(msg) } +// Deprecated func (u *User) sendImage(file *os.File) error { - request := u.Self.Bot.storage.Request - info := u.Self.Bot.storage.LoginInfo - return u.Self.Bot.Caller.WebWxSendImageMsg(file, request, info, u.Self.UserName, u.UserName) + request := u.Self.Bot.storage.Request + info := u.Self.Bot.storage.LoginInfo + return u.Self.Bot.Caller.WebWxSendImageMsg(file, request, info, u.Self.UserName, u.UserName) } +// Deprecated func (u *User) setRemarkName(remarkName string) error { - request := u.Self.Bot.storage.Request - return u.Self.Bot.Caller.WebWxOplog(request, remarkName, u.UserName) + request := u.Self.Bot.storage.Request + return u.Self.Bot.Caller.WebWxOplog(request, remarkName, u.UserName) } // 获取用户的详情 func (u *User) Detail() (*User, error) { - members := Members{u} - request := u.Self.Bot.storage.Request - newMembers, err := u.Self.Bot.Caller.WebWxBatchGetContact(members, request) - if err != nil { - return nil, err - } - user := newMembers.First() - user.Self = u.Self - return user, nil + members := Members{u} + request := u.Self.Bot.storage.Request + newMembers, err := u.Self.Bot.Caller.WebWxBatchGetContact(members, request) + if err != nil { + return nil, err + } + user := newMembers.First() + user.Self = u.Self + return user, nil } +// 自己,当前登录用户对象 type Self struct { - *User - Bot *Bot - fileHelper *Friend - members Members - friends Friends - groups Groups - mps Mps + *User + Bot *Bot + fileHelper *Friend + members Members + friends Friends + groups Groups + mps Mps } // 获取所有的好友、群组、公众号信息 func (s *Self) Members(update ...bool) (Members, error) { - // 首先判断缓存里有没有,如果没有则去更新缓存 - if s.members == nil { - if err := s.updateMembers(); err != nil { - return nil, err - } - return s.members, nil - } - // 判断是否需要更新,如果传入的参数不为nil,则取最后一个 - var isUpdate bool - if len(update) > 0 { - isUpdate = update[len(update)-1] - } - // 如果需要更新,则直接更新缓存 - if isUpdate { - if err := s.updateMembers(); err != nil { - return nil, err - } - } - return s.members, nil + // 首先判断缓存里有没有,如果没有则去更新缓存 + if s.members == nil { + if err := s.updateMembers(); err != nil { + return nil, err + } + return s.members, nil + } + // 判断是否需要更新,如果传入的参数不为nil,则取最后一个 + var isUpdate bool + if len(update) > 0 { + isUpdate = update[len(update)-1] + } + // 如果需要更新,则直接更新缓存 + if isUpdate { + if err := s.updateMembers(); err != nil { + return nil, err + } + } + return s.members, nil } // 更新联系人处理 func (s *Self) updateMembers() error { - info := s.Bot.storage.LoginInfo - members, err := s.Bot.Caller.WebWxGetContact(info) - if err != nil { - return err - } - members.SetOwner(s) - s.members = members - return nil + info := s.Bot.storage.LoginInfo + members, err := s.Bot.Caller.WebWxGetContact(info) + if err != nil { + return err + } + members.SetOwner(s) + s.members = members + return nil } // 获取文件传输助手对象,封装成Friend返回 func (s *Self) FileHelper() (*Friend, error) { - // 如果缓存里有,直接返回,否则去联系人里面找 - if s.fileHelper != nil { - return s.fileHelper, nil - } - members, err := s.Members() - if err != nil { - return nil, err - } - users := members.SearchByUserName(1, "filehelper") - if users == nil { - return nil, noSuchUserFoundError - } - s.fileHelper = &Friend{users.First()} - return s.fileHelper, nil + // 如果缓存里有,直接返回,否则去联系人里面找 + if s.fileHelper != nil { + return s.fileHelper, nil + } + members, err := s.Members() + if err != nil { + return nil, err + } + users := members.SearchByUserName(1, "filehelper") + if users == nil { + return nil, noSuchUserFoundError + } + s.fileHelper = &Friend{users.First()} + return s.fileHelper, nil } // 获取所有的好友 func (s *Self) Friends(update ...bool) (Friends, error) { - if s.friends == nil { - if err := s.updateFriends(update...); err != nil { - return nil, err - } - } - return s.friends, nil + if s.friends == nil { + if err := s.updateFriends(update...); err != nil { + return nil, err + } + } + return s.friends, nil } // 获取所有的群组 func (s *Self) Groups(update ...bool) (Groups, error) { - if s.groups == nil { - if err := s.updateGroups(update...); err != nil { - return nil, err - } - } - return s.groups, nil + if s.groups == nil { + if err := s.updateGroups(update...); err != nil { + return nil, err + } + } + return s.groups, nil } // 获取所有的公众号 func (s *Self) Mps(update ...bool) (Mps, error) { - if s.mps == nil { - if err := s.updateMps(update...); err != nil { - return nil, err - } - } - return s.mps, nil + if s.mps == nil { + if err := s.updateMps(update...); err != nil { + return nil, err + } + } + return s.mps, nil } // 更新好友处理 func (s *Self) updateFriends(update ...bool) error { - var isUpdate bool - if len(update) > 0 { - isUpdate = update[len(update)-1] - } - if isUpdate || s.members == nil { - if err := s.updateMembers(); err != nil { - return err - } - } - var friends Friends - for _, member := range s.members { - if isFriend(*member) { - friend := &Friend{member} - friend.Self = s - friends = append(friends, friend) - } - } - s.friends = friends - return nil + var isUpdate bool + if len(update) > 0 { + isUpdate = update[len(update)-1] + } + if isUpdate || s.members == nil { + if err := s.updateMembers(); err != nil { + return err + } + } + var friends Friends + for _, member := range s.members { + if isFriend(*member) { + friend := &Friend{member} + friend.Self = s + friends = append(friends, friend) + } + } + s.friends = friends + return nil } // 更新群组处理 func (s *Self) updateGroups(update ...bool) error { - var isUpdate bool - if len(update) > 0 { - isUpdate = update[len(update)-1] - } - if isUpdate || s.members == nil { - if err := s.updateMembers(); err != nil { - return err - } - } - var groups Groups - for _, member := range s.members { - if isGroup(*member) { - group := &Group{member} - groups = append(groups, group) - } - } - s.groups = groups - return nil + var isUpdate bool + if len(update) > 0 { + isUpdate = update[len(update)-1] + } + if isUpdate || s.members == nil { + if err := s.updateMembers(); err != nil { + return err + } + } + var groups Groups + for _, member := range s.members { + if isGroup(*member) { + group := &Group{member} + groups = append(groups, group) + } + } + s.groups = groups + return nil } +// 更新公众号处理 func (s *Self) updateMps(update ...bool) error { - var isUpdate bool - if len(update) > 0 { - isUpdate = update[len(update)-1] - } - if isUpdate || s.members == nil { - if err := s.updateMembers(); err != nil { - return err - } - } - var mps Mps - for _, member := range s.members { - if isMP(*member) { - mp := &Mp{member} - mps = append(mps, mp) - } - } - s.mps = mps - return nil + var isUpdate bool + if len(update) > 0 { + isUpdate = update[len(update)-1] + } + if isUpdate || s.members == nil { + if err := s.updateMembers(); err != nil { + return err + } + } + var mps Mps + for _, member := range s.members { + if isMP(*member) { + mp := &Mp{member} + mps = append(mps, mp) + } + } + s.mps = mps + return nil } // 更新所有的联系人信息 func (s *Self) UpdateMembersDetail() error { - // 先获取所有的联系人 - members, err := s.Members() - if err != nil { - return err - } - // 获取他们的数量 - count := members.Count() - // 一次更新50个,分情况讨论 + // 先获取所有的联系人 + members, err := s.Members() + if err != nil { + return err + } + // 获取他们的数量 + count := members.Count() + // 一次更新50个,分情况讨论 - // 获取总的需要更新的次数 - var times int - if count < 50 { - times = 1 - } else { - times = count / 50 - } - var newMembers Members - request := s.Bot.storage.Request - var pMembers Members - // 分情况依次更新 - for i := 1; i <= times; i++ { - if times == 1 { - pMembers = members - } else { - pMembers = members[(i-1)*50 : i*50] - } - nMembers, err := s.Bot.Caller.WebWxBatchGetContact(pMembers, request) - if err != nil { - return err - } - newMembers = append(newMembers, nMembers...) - } - // 最后判断是否全部更新完毕 - total := times * 50 - if total < count { - // 将全部剩余的更新完毕 - left := count - total - pMembers = members[total : total+left] - nMembers, err := s.Bot.Caller.WebWxBatchGetContact(pMembers, request) - if err != nil { - return err - } - newMembers = append(newMembers, nMembers...) - } - if len(newMembers) != 0 { - newMembers.SetOwner(s) - s.members = newMembers - } - return nil + // 获取总的需要更新的次数 + var times int + if count < 50 { + times = 1 + } else { + times = count / 50 + } + var newMembers Members + request := s.Bot.storage.Request + var pMembers Members + // 分情况依次更新 + for i := 1; i <= times; i++ { + if times == 1 { + pMembers = members + } else { + pMembers = members[(i-1)*50 : i*50] + } + nMembers, err := s.Bot.Caller.WebWxBatchGetContact(pMembers, request) + if err != nil { + return err + } + newMembers = append(newMembers, nMembers...) + } + // 最后判断是否全部更新完毕 + total := times * 50 + if total < count { + // 将全部剩余的更新完毕 + left := count - total + pMembers = members[total : total+left] + nMembers, err := s.Bot.Caller.WebWxBatchGetContact(pMembers, request) + if err != nil { + return err + } + newMembers = append(newMembers, nMembers...) + } + if len(newMembers) != 0 { + newMembers.SetOwner(s) + s.members = newMembers + } + return nil } +// 抽象发送消息接口 +func (s *Self) sendMessageToUser(user *User, msg *SendMessage) error { + msg.FromUserName = s.UserName + msg.ToUserName = user.UserName + info := s.Bot.storage.LoginInfo + request := s.Bot.storage.Request + return s.Bot.Caller.WebWxSendMsg(msg, info, request) +} + +// 发送消息给好友 +func (s *Self) SendMessageToFriend(friend *Friend, msg *SendMessage) error { + return s.sendMessageToUser(friend.User, msg) +} + +// 发送文本消息给好友 +func (s *Self) SendTextToFriend(friend *Friend, text string) error { + msg := NewTextSendMessage(text, s.UserName, friend.UserName) + return s.SendMessageToFriend(friend, msg) +} + +// 发送图片消息给好友 +func (s *Self) SendImageToFriend(friend *Friend, file *os.File) error { + req := s.Bot.storage.Request + info := s.Bot.storage.LoginInfo + return s.Bot.Caller.WebWxSendImageMsg(file, req, info, s.UserName, friend.UserName) +} + +// 设置好友备注 +func (s *Self) SetRemarkNameToFriend(friend *Friend, remarkName string) error { + req := s.Bot.storage.Request + return s.Bot.Caller.WebWxOplog(req, remarkName, friend.UserName) +} + +// 拉多名好友进群 +// 最好自己是群主,成功率高一点,因为有的群允许非群组拉人,而有的群不允许 +func (s *Self) AddFriendsIntoGroup(group *Group, friends ...*Friend) error { + if len(friends) == 0 { + return nil + } + // 获取群的所有的群员 + groupMembers, err := group.Members() + if err != nil { + return err + } + // 判断当前的成员在不在群里面 + for _, friend := range friends { + for _, member := range groupMembers { + if member.UserName == friend.UserName { + return fmt.Errorf("user %s has alreay in this group", friend.String()) + } + } + } + req := s.Bot.storage.Request + info := s.Bot.storage.LoginInfo + return s.Bot.Caller.AddFriendIntoChatRoom(req, info, group, friends...) +} + +// 从群聊中移除用户 +// Deprecated +// 无论是网页版,还是程序上都不起作用 +func (s *Self) RemoveMemberFromGroup(group *Group, members Members) error { + if len(members) == 0 { + return nil + } + if group.IsOwner == 0 { + return errors.New("group owner required") + } + groupMembers, err := group.Members() + if err != nil { + return err + } + // 判断用户是否在群聊中 + var count int + for _, member := range members { + for _, gm := range groupMembers { + if gm.UserName == member.UserName { + count++ + } + } + } + if count != len(members) { + return errors.New("invalid members") + } + req := s.Bot.storage.Request + info := s.Bot.storage.LoginInfo + return s.Bot.Caller.RemoveFriendFromChatRoom(req, info, group, members...) +} + +// 拉好友进多个群聊 +// AddFriendIntoGroups, 名字和上面的有点像 +func (s *Self) AddFriendIntoManyGroups(friend *Friend, groups ...*Group) error { + for _, group := range groups { + if err := s.AddFriendsIntoGroup(group, friend); err != nil { + return err + } + } + return nil +} + +// 发送消息给群组 +func (s *Self) SendMessageToGroup(group *Group, msg *SendMessage) error { + return s.sendMessageToUser(group.User, msg) +} + +// 发送文本消息给群组 +func (s *Self) SendTextToGroup(group *Group, text string) error { + msg := NewTextSendMessage(text, s.UserName, group.UserName) + return s.SendMessageToGroup(group, msg) +} + +// 发送图片消息给群组 +func (s *Self) SendImageToGroup(group *Group, file *os.File) error { + req := s.Bot.storage.Request + info := s.Bot.storage.LoginInfo + return s.Bot.Caller.WebWxSendImageMsg(file, req, info, s.UserName, group.UserName) +} + +// 抽象的用户组 type Members []*User +// 统计数量 func (m Members) Count() int { - return len(m) + return len(m) } +// 获取第一个 func (m Members) First() *User { - if m.Count() > 0 { - u := m[0] - return u - } - return nil + if m.Count() > 0 { + u := m[0] + return u + } + return nil } +// 获取最后一个 func (m Members) Last() *User { - if m.Count() > 0 { - u := m[m.Count()-1] - return u - } - return nil + if m.Count() > 0 { + u := m[m.Count()-1] + return u + } + return nil } +// 设置owner +// 请不要随意设置 func (m Members) SetOwner(s *Self) { - for _, member := range m { - member.Self = s - } + for _, member := range m { + member.Self = s + } } +// 根据用户名查找 func (m Members) SearchByUserName(limit int, username string) (results Members) { - return m.Search(limit, func(user *User) bool { return user.UserName == username }) + return m.Search(limit, func(user *User) bool { return user.UserName == username }) } +// 根据昵称查找 func (m Members) SearchByNickName(limit int, nickName string) (results Members) { - return m.Search(limit, func(user *User) bool { return user.NickName == nickName }) + return m.Search(limit, func(user *User) bool { return user.NickName == nickName }) } +// 根据备注查找 func (m Members) SearchByRemarkName(limit int, remarkName string) (results Members) { - return m.Search(limit, func(user *User) bool { return user.RemarkName == remarkName }) + return m.Search(limit, func(user *User) bool { return user.RemarkName == remarkName }) } +// 根据自定义条件查找 func (m Members) Search(limit int, condFuncList ...func(user *User) bool) (results Members) { - if condFuncList == nil { - return m - } - if limit <= 0 { - limit = m.Count() - } - for _, member := range m { - if count := len(results); count == limit { - break - } - var passCount int - for _, condFunc := range condFuncList { - if condFunc(member) { - passCount++ - } else { - break - } - } - if passCount == len(condFuncList) { - results = append(results, member) - } - } - return + if condFuncList == nil { + return m + } + if limit <= 0 { + limit = m.Count() + } + for _, member := range m { + if count := len(results); count == limit { + break + } + var passCount int + for _, condFunc := range condFuncList { + if condFunc(member) { + passCount++ + } else { + break + } + } + if passCount == len(condFuncList) { + results = append(results, member) + } + } + return }