From b2471e801f8e0ca9650eadfe010e39bbeeb4e951 Mon Sep 17 00:00:00 2001 From: zhaoYangguang <1163765691@qq.com> Date: Fri, 27 Nov 2020 12:17:47 +0800 Subject: [PATCH] Remove irrelevant code --- commands.go | 14 +- go.mod | 3 - portal.go | 379 +++++++++-------------------------- puppet.go | 10 +- skype-ext/chat.go | 5 +- skype-ext/cmd.go | 5 +- user.go | 242 +++++++++++----------- whatsapp-ext/call.go | 72 ------- whatsapp-ext/chat.go | 174 ---------------- whatsapp-ext/cmd.go | 69 ------- whatsapp-ext/conn.go | 65 ------ whatsapp-ext/jsonmessage.go | 105 ---------- whatsapp-ext/msginfo.go | 95 --------- whatsapp-ext/presence.go | 67 ------- whatsapp-ext/props.go | 73 ------- whatsapp-ext/protomessage.go | 59 ------ whatsapp-ext/stream.go | 68 ------- whatsapp-ext/whatsapp.go | 206 ------------------- 18 files changed, 224 insertions(+), 1487 deletions(-) delete mode 100644 whatsapp-ext/call.go delete mode 100644 whatsapp-ext/chat.go delete mode 100644 whatsapp-ext/cmd.go delete mode 100644 whatsapp-ext/conn.go delete mode 100644 whatsapp-ext/jsonmessage.go delete mode 100644 whatsapp-ext/msginfo.go delete mode 100644 whatsapp-ext/presence.go delete mode 100644 whatsapp-ext/props.go delete mode 100644 whatsapp-ext/protomessage.go delete mode 100644 whatsapp-ext/stream.go delete mode 100644 whatsapp-ext/whatsapp.go diff --git a/commands.go b/commands.go index 72e7b93..2df83ca 100644 --- a/commands.go +++ b/commands.go @@ -8,11 +8,9 @@ import ( "math" "time" - //"math" "sort" "strconv" "strings" - //"time" "maunium.net/go/maulogger/v2" @@ -21,8 +19,6 @@ import ( "maunium.net/go/mautrix/event" "maunium.net/go/mautrix/format" "maunium.net/go/mautrix/id" - - "github.com/kelaresg/matrix-skype/whatsapp-ext" ) type CommandHandler struct { @@ -697,7 +693,7 @@ func (handler *CommandHandler) CommandOpen(ce *CommandEvent) { jid := ce.Args[0] if strings.HasSuffix(jid, skypeExt.NewUserSuffix) { - ce.Reply("That looks like a user ID. Did you mean `pm %s`?", jid[:len(jid)-len(whatsappExt.NewUserSuffix)]) + ce.Reply("That looks like a user ID. Did you mean `pm %s`?", jid[:len(jid)-len(skypeExt.NewUserSuffix)]) return } ce.User.Conn.GetConversations("", handler.bridge.Config.Bridge.InitialChatSync) @@ -977,7 +973,7 @@ func (handler *CommandHandler) CommandKick(ce *CommandEvent) { // reason = ce.Args[0] //} - if strings.HasSuffix(converationId, whatsappExt.NewUserSuffix) { + if strings.HasSuffix(converationId, skypeExt.NewUserSuffix) { ce.Reply("**Usage:** `kick ,... reason`") return } @@ -995,8 +991,8 @@ func (handler *CommandHandler) CommandKick(ce *CommandEvent) { portal := user.bridge.GetPortalByJID(database.GroupPortalKey(converationId)) for i, number := range userNumbers { - userNumbers[i] = number // + whatsappExt.NewUserSuffix - member := portal.bridge.GetPuppetByJID(number + whatsappExt.NewUserSuffix) + userNumbers[i] = number // + skypeExt.NewUserSuffix + member := portal.bridge.GetPuppetByJID(number + skypeExt.NewUserSuffix) if member == nil { portal.log.Errorln("%s is not a puppet", number) @@ -1025,7 +1021,7 @@ func (handler *CommandHandler) CommandLeave(ce *CommandEvent) { user := ce.User groupId := ce.Args[0] - if strings.HasSuffix(groupId, whatsappExt.NewUserSuffix) { + if strings.HasSuffix(groupId, skypeExt.NewUserSuffix) { ce.Reply("**Usage:** `leave `") return } diff --git a/go.mod b/go.mod index d59b3e1..ac80bb8 100644 --- a/go.mod +++ b/go.mod @@ -3,7 +3,6 @@ module github.com/kelaresg/matrix-skype go 1.14 require ( - github.com/Rhymen/go-whatsapp v0.1.0 github.com/chai2010/webp v1.1.0 github.com/gorilla/websocket v1.4.2 github.com/kelaresg/go-skypeapi v0.1.2-0.20201126103218-226d1ec92858 @@ -19,6 +18,4 @@ require ( maunium.net/go/mautrix v0.8.0-rc.4 ) -replace github.com/Rhymen/go-whatsapp => github.com/tulir/go-whatsapp v0.2.8 - replace maunium.net/go/mautrix => github.com/pidongqianqian/mautrix-go v0.8.0-rc.4.0.20201126070406-7b13ac473bcc diff --git a/portal.go b/portal.go index d1dfedc..d818c28 100644 --- a/portal.go +++ b/portal.go @@ -2,13 +2,16 @@ package main import ( "bytes" - "encoding/gob" + //whatsappExt "github.com/kelaresg/matrix-skype/whatsapp-ext" + + //"encoding/gob" "encoding/hex" "encoding/json" "encoding/xml" "fmt" skype "github.com/kelaresg/go-skypeapi" skypeExt "github.com/kelaresg/matrix-skype/skype-ext" + //whatsappExt "github.com/kelaresg/matrix-skype/whatsapp-ext" "html" "image" "image/gif" @@ -28,8 +31,8 @@ import ( "maunium.net/go/mautrix/crypto/attachment" - "github.com/Rhymen/go-whatsapp" - waProto "github.com/Rhymen/go-whatsapp/binary/proto" + //"github.com/Rhymen/go-whatsapp" + //waProto "github.com/Rhymen/go-whatsapp/binary/proto" "maunium.net/go/mautrix" "maunium.net/go/mautrix/appservice" @@ -40,7 +43,7 @@ import ( "github.com/kelaresg/matrix-skype/database" "github.com/kelaresg/matrix-skype/types" - "github.com/kelaresg/matrix-skype/whatsapp-ext" + //"github.com/kelaresg/matrix-skype/whatsapp-ext" ) func (bridge *Bridge) GetPortalByMXID(mxid id.RoomID) *Portal { @@ -251,36 +254,36 @@ func (portal *Portal) isDuplicate(clientMessageId types.SkypeMessageID, id strin return false } -func init() { - gob.Register(&waProto.Message{}) -} +//func init() { +// gob.Register(&waProto.Message{}) +//} -func (portal *Portal) markHandled(source *User, message *waProto.WebMessageInfo, mxid id.EventID) { - msg := portal.bridge.DB.Message.New() - msg.Chat = portal.Key - msg.JID = message.GetKey().GetId() - msg.MXID = mxid - msg.Timestamp = message.GetMessageTimestamp() - if message.GetKey().GetFromMe() { - msg.Sender = source.JID - } else if portal.IsPrivateChat() { - msg.Sender = portal.Key.JID - } else { - msg.Sender = message.GetKey().GetParticipant() - if len(msg.Sender) == 0 { - msg.Sender = message.GetParticipant() - } - } - //msg.Content = message.Message - msg.Content = &skype.Resource{} - msg.Insert() - - portal.recentlyHandledLock.Lock() - index := portal.recentlyHandledIndex - portal.recentlyHandledIndex = (portal.recentlyHandledIndex + 1) % recentlyHandledLength - portal.recentlyHandledLock.Unlock() - portal.recentlyHandled[index] = msg.JID -} +//func (portal *Portal) markHandled(source *User, message *waProto.WebMessageInfo, mxid id.EventID) { +// msg := portal.bridge.DB.Message.New() +// msg.Chat = portal.Key +// msg.JID = message.GetKey().GetId() +// msg.MXID = mxid +// msg.Timestamp = message.GetMessageTimestamp() +// if message.GetKey().GetFromMe() { +// msg.Sender = source.JID +// } else if portal.IsPrivateChat() { +// msg.Sender = portal.Key.JID +// } else { +// msg.Sender = message.GetKey().GetParticipant() +// if len(msg.Sender) == 0 { +// msg.Sender = message.GetParticipant() +// } +// } +// //msg.Content = message.Message +// msg.Content = &skype.Resource{} +// msg.Insert() +// +// portal.recentlyHandledLock.Lock() +// index := portal.recentlyHandledIndex +// portal.recentlyHandledIndex = (portal.recentlyHandledIndex + 1) % recentlyHandledLength +// portal.recentlyHandledLock.Unlock() +// portal.recentlyHandled[index] = msg.JID +//} func (portal *Portal) markHandledSkype(source *User, message *skype.Resource, mxid id.EventID) { msg := portal.bridge.DB.Message.New() @@ -312,20 +315,20 @@ fmt.Println("markHandledSkype2", msg.JID) portal.recentlyHandled[index] = msg.JID } -func (portal *Portal) getMessageIntent(user *User, info whatsapp.MessageInfo) *appservice.IntentAPI { - if info.FromMe { - return portal.bridge.GetPuppetByJID(user.JID).IntentFor(portal) - } else if portal.IsPrivateChat() { - return portal.MainIntent() - } else if len(info.SenderJid) == 0 { - if len(info.Source.GetParticipant()) != 0 { - info.SenderJid = info.Source.GetParticipant() - } else { - return nil - } - } - return portal.bridge.GetPuppetByJID(info.SenderJid).IntentFor(portal) -} +//func (portal *Portal) getMessageIntent(user *User, info whatsapp.MessageInfo) *appservice.IntentAPI { +// if info.FromMe { +// return portal.bridge.GetPuppetByJID(user.JID).IntentFor(portal) +// } else if portal.IsPrivateChat() { +// return portal.MainIntent() +// } else if len(info.SenderJid) == 0 { +// if len(info.Source.GetParticipant()) != 0 { +// info.SenderJid = info.Source.GetParticipant() +// } else { +// return nil +// } +// } +// return portal.bridge.GetPuppetByJID(info.SenderJid).IntentFor(portal) +//} func (portal *Portal) getMessageIntentSkype(user *User, info skype.Resource) *appservice.IntentAPI { if info.GetFromMe(user.Conn.Conn) { @@ -385,11 +388,11 @@ func (portal *Portal) startHandlingSkype(source *User, info skype.Resource) (*ap return nil, nil } -func (portal *Portal) finishHandling(source *User, message *waProto.WebMessageInfo, mxid id.EventID) { - portal.markHandled(source, message, mxid) - portal.sendDeliveryReceipt(mxid) - portal.log.Debugln("Handled message", message.GetKey().GetId(), "->", mxid) -} +//func (portal *Portal) finishHandling(source *User, message *waProto.WebMessageInfo, mxid id.EventID) { +// portal.markHandled(source, message, mxid) +// portal.sendDeliveryReceipt(mxid) +// portal.log.Debugln("Handled message", message.GetKey().GetId(), "->", mxid) +//} func (portal *Portal) finishHandlingSkype(source *User, message *skype.Resource, mxid id.EventID) { portal.markHandledSkype(source, message, mxid) @@ -1291,21 +1294,21 @@ func (portal *Portal) MainIntent() *appservice.IntentAPI { return portal.bridge.Bot } -func (portal *Portal) SetReply(content *event.MessageEventContent, info whatsapp.ContextInfo) { - if len(info.QuotedMessageID) == 0 { - return - } - message := portal.bridge.DB.Message.GetByJID(portal.Key, info.QuotedMessageID) - if message != nil { - evt, err := portal.MainIntent().GetEvent(portal.MXID, message.MXID) - if err != nil { - portal.log.Warnln("Failed to get reply target:", err) - return - } - content.SetReply(evt) - } - return -} +//func (portal *Portal) SetReply(content *event.MessageEventContent, info whatsapp.ContextInfo) { +// if len(info.QuotedMessageID) == 0 { +// return +// } +// message := portal.bridge.DB.Message.GetByJID(portal.Key, info.QuotedMessageID) +// if message != nil { +// evt, err := portal.MainIntent().GetEvent(portal.MXID, message.MXID) +// if err != nil { +// portal.log.Warnln("Failed to get reply target:", err) +// return +// } +// content.SetReply(evt) +// } +// return +//} func (portal *Portal) SetReplySkype(content *event.MessageEventContent, info skype.Resource) { if len(info.Id) == 0 { @@ -1347,32 +1350,31 @@ func (portal *Portal) HandleMessageRevokeSkype(user *User, message skype.Resourc msg.Delete() } - -func (portal *Portal) HandleMessageRevoke(user *User, message whatsappExt.MessageRevocation) { - msg := portal.bridge.DB.Message.GetByJID(portal.Key, message.Id) - if msg == nil { - return - } - var intent *appservice.IntentAPI - if message.FromMe { - if portal.IsPrivateChat() { - intent = portal.bridge.GetPuppetByJID(user.JID).CustomIntent() - } else { - intent = portal.bridge.GetPuppetByJID(user.JID).IntentFor(portal) - } - } else if len(message.Participant) > 0 { - intent = portal.bridge.GetPuppetByJID(message.Participant).IntentFor(portal) - } - if intent == nil { - intent = portal.MainIntent() - } - _, err := intent.RedactEvent(portal.MXID, msg.MXID) - if err != nil { - portal.log.Errorln("Failed to redact %s: %v", msg.JID, err) - return - } - msg.Delete() -} +//func (portal *Portal) HandleMessageRevoke(user *User, message whatsappExt.MessageRevocation) { +// msg := portal.bridge.DB.Message.GetByJID(portal.Key, message.Id) +// if msg == nil { +// return +// } +// var intent *appservice.IntentAPI +// if message.FromMe { +// if portal.IsPrivateChat() { +// intent = portal.bridge.GetPuppetByJID(user.JID).CustomIntent() +// } else { +// intent = portal.bridge.GetPuppetByJID(user.JID).IntentFor(portal) +// } +// } else if len(message.Participant) > 0 { +// intent = portal.bridge.GetPuppetByJID(message.Participant).IntentFor(portal) +// } +// if intent == nil { +// intent = portal.MainIntent() +// } +// _, err := intent.RedactEvent(portal.MXID, msg.MXID) +// if err != nil { +// portal.log.Errorln("Failed to redact %s: %v", msg.JID, err) +// return +// } +// msg.Delete() +//} func (portal *Portal) HandleFakeMessage(source *User, message FakeMessage) { if portal.isRecentlyHandled(message.ID) { @@ -1579,7 +1581,7 @@ func (portal *Portal) HandleMediaMessageSkype(source *User, download func(conn * } data, mediaMessage, err := download(source.Conn.Conn, mediaType) - if err == whatsapp.ErrMediaDownloadFailedWith404 || err == whatsapp.ErrMediaDownloadFailedWith410 { + if err == skype.ErrMediaDownloadFailedWith404 || err == skype.ErrMediaDownloadFailedWith410 { portal.log.Warnfln("Failed to download media for %s: %v. Calling LoadMediaInfo and retrying download...", info.Id, err) //_, err = source.Conn.LoadMediaInfo(info.RemoteJid, info.Id, info.FromMe) //if err != nil { @@ -1588,7 +1590,7 @@ func (portal *Portal) HandleMediaMessageSkype(source *User, download func(conn * //} data, mediaMessage, err = download(source.Conn.Conn, mediaType) } - if err == whatsapp.ErrNoURLPresent { + if err == skype.ErrNoURLPresent { portal.log.Debugfln("No URL present error for media message %s, ignoring...", info.Id) return } else if err != nil { @@ -1819,54 +1821,6 @@ func (portal *Portal) preprocessMatrixMediaSkype(relaybotFormatted bool, content return caption, uint64(len(data)), data } -func (portal *Portal) preprocessMatrixMedia(sender *User, relaybotFormatted bool, content *event.MessageEventContent, eventID id.EventID, mediaType whatsapp.MediaType) *MediaUpload { - //var caption string - //if relaybotFormatted { - // caption = portal.bridge.Formatter.ParseMatrix(content.FormattedBody) - //} - - var file *event.EncryptedFileInfo - rawMXC := content.URL - if content.File != nil { - file = content.File - rawMXC = file.URL - } - mxc, err := rawMXC.Parse() - if err != nil { - portal.log.Errorln("Malformed content URL in %s: %v", eventID, err) - return nil - } - data, err := portal.MainIntent().DownloadBytes(mxc) - if err != nil { - portal.log.Errorfln("Failed to download media in %s: %v", eventID, err) - return nil - } - if file != nil { - data, err = file.Decrypt(data) - if err != nil { - portal.log.Errorfln("Failed to decrypt media in %s: %v", eventID, err) - return nil - } - } - - //url, mediaKey, fileEncSHA256, fileSHA256, fileLength, err := sender.Conn.Upload(bytes.NewReader(data), mediaType) - //if err != nil { - // portal.log.Errorfln("Failed to upload media in %s: %v", eventID, err) - // return nil - //} - // - //return &MediaUpload{ - // Caption: caption, - // URL: url, - // MediaKey: mediaKey, - // FileEncSHA256: fileEncSHA256, - // FileSHA256: fileSHA256, - // FileLength: fileLength, - // Thumbnail: portal.downloadThumbnail(content, eventID), - //} - return nil -} - type MediaUpload struct { Caption string URL string @@ -2098,145 +2052,6 @@ func (portal *Portal) convertMatrixMessageSkype(sender *User, evt *event.Event) return info, sender, content } -func (portal *Portal) convertMatrixMessage(sender *User, evt *event.Event) (*waProto.WebMessageInfo, *User, *event.MessageEventContent) { - content, ok := evt.Content.Parsed.(*event.MessageEventContent) - if !ok { - portal.log.Debugfln("Failed to handle event %s: unexpected parsed content type %T", evt.ID, evt.Content.Parsed) - return nil, sender, content - } - - ts := uint64(evt.Timestamp / 1000) - status := waProto.WebMessageInfo_ERROR - fromMe := true - info := &waProto.WebMessageInfo{ - Key: &waProto.MessageKey{ - FromMe: &fromMe, - Id: makeMessageID(), - RemoteJid: &portal.Key.JID, - }, - MessageTimestamp: &ts, - Message: &waProto.Message{}, - Status: &status, - } - //ctxInfo := &waProto.ContextInfo{} - replyToID := content.GetReplyTo() - if len(replyToID) > 0 { - content.RemoveReplyFallback() - msg := portal.bridge.DB.Message.GetByMXID(replyToID) - //if msg != nil && msg.Content != nil { - if msg != nil { - //ctxInfo.StanzaId = &msg.JID - //ctxInfo.Participant = &msg.Sender - //ctxInfo.QuotedMessage = msg.Content - } - } - relaybotFormatted := false - if sender.NeedsRelaybot(portal) { - if !portal.HasRelaybot() { - if sender.HasSession() { - portal.log.Debugln("Database says", sender.MXID, "not in chat and no relaybot, but trying to send anyway") - } else { - portal.log.Debugln("Ignoring message from", sender.MXID, "in chat with no relaybot") - return nil, sender, content - } - } else { - relaybotFormatted = portal.addRelaybotFormat(sender, content) - sender = portal.bridge.Relaybot - } - } - if evt.Type == event.EventSticker { - content.MsgType = event.MsgImage - } -fmt.Println("convertMatrixMessage content.MsgType: ", content.MsgType) - switch content.MsgType { - case event.MsgText, event.MsgEmote, event.MsgNotice: - text := content.Body - if content.Format == event.FormatHTML { - text = portal.bridge.Formatter.ParseMatrix(content.FormattedBody) - } - if content.MsgType == event.MsgEmote && !relaybotFormatted { - text = "/me " + text - } - //ctxInfo.MentionedJid = mentionRegex.FindAllString(text, -1) - //for index, mention := range ctxInfo.MentionedJid { - // ctxInfo.MentionedJid[index] = mention[1:] + whatsappExt.NewUserSuffix - //} - //if ctxInfo.StanzaId != nil || ctxInfo.MentionedJid != nil { - // info.Message.ExtendedTextMessage = &waProto.ExtendedTextMessage{ - // Text: &text, - // ContextInfo: ctxInfo, - // } - //} else { - // info.Message.Conversation = &text - //} - case event.MsgImage: - media := portal.preprocessMatrixMedia(sender, relaybotFormatted, content, evt.ID, whatsapp.MediaImage) - if media == nil { - return nil, sender, content - } - info.Message.ImageMessage = &waProto.ImageMessage{ - Caption: &media.Caption, - JpegThumbnail: media.Thumbnail, - Url: &media.URL, - MediaKey: media.MediaKey, - Mimetype: &content.GetInfo().MimeType, - FileEncSha256: media.FileEncSHA256, - FileSha256: media.FileSHA256, - FileLength: &media.FileLength, - } - case event.MsgVideo: - media := portal.preprocessMatrixMedia(sender, relaybotFormatted, content, evt.ID, whatsapp.MediaVideo) - if media == nil { - return nil, sender, content - } - duration := uint32(content.GetInfo().Duration) - info.Message.VideoMessage = &waProto.VideoMessage{ - Caption: &media.Caption, - JpegThumbnail: media.Thumbnail, - Url: &media.URL, - MediaKey: media.MediaKey, - Mimetype: &content.GetInfo().MimeType, - Seconds: &duration, - FileEncSha256: media.FileEncSHA256, - FileSha256: media.FileSHA256, - FileLength: &media.FileLength, - } - case event.MsgAudio: - media := portal.preprocessMatrixMedia(sender, relaybotFormatted, content, evt.ID, whatsapp.MediaAudio) - if media == nil { - return nil, sender, content - } - duration := uint32(content.GetInfo().Duration) - info.Message.AudioMessage = &waProto.AudioMessage{ - Url: &media.URL, - MediaKey: media.MediaKey, - Mimetype: &content.GetInfo().MimeType, - Seconds: &duration, - FileEncSha256: media.FileEncSHA256, - FileSha256: media.FileSHA256, - FileLength: &media.FileLength, - } - case event.MsgFile: - media := portal.preprocessMatrixMedia(sender, relaybotFormatted, content, evt.ID, whatsapp.MediaDocument) - if media == nil { - return nil, sender, content - } - info.Message.DocumentMessage = &waProto.DocumentMessage{ - Url: &media.URL, - FileName: &content.Body, - MediaKey: media.MediaKey, - Mimetype: &content.GetInfo().MimeType, - FileEncSha256: media.FileEncSHA256, - FileSha256: media.FileSHA256, - FileLength: &media.FileLength, - } - default: - portal.log.Debugln("Unhandled Matrix event %s: unknown msgtype %s", evt.ID, content.MsgType) - return nil, sender, content - } - return info, sender, content -} - func (portal *Portal) wasMessageSent(sender *User, id string) bool { //_, err := sender.Conn.LoadMessagesAfter(portal.Key.JID, id, true, 0) //if err != nil { diff --git a/puppet.go b/puppet.go index 31543dd..15bdfdc 100644 --- a/puppet.go +++ b/puppet.go @@ -15,7 +15,7 @@ import ( "github.com/kelaresg/matrix-skype/database" "github.com/kelaresg/matrix-skype/types" - "github.com/kelaresg/matrix-skype/whatsapp-ext" + //"github.com/kelaresg/matrix-skype/whatsapp-ext" ) func (bridge *Bridge) ParsePuppetMXID(mxid id.UserID) (types.SkypeID, bool) { @@ -134,10 +134,8 @@ func (bridge *Bridge) NewPuppet(dbPuppet *database.Puppet) *Puppet { MXID: id.NewUserID( bridge.Config.Bridge.FormatUsername( - // dbPuppet.JID, - //), strings.Replace( - strings.Replace(dbPuppet.JID, whatsappExt.NewUserSuffix, "", 1), + strings.Replace(dbPuppet.JID, skypeExt.NewUserSuffix, "", 1), ":", "-", -1, @@ -164,7 +162,7 @@ type Puppet struct { } func (puppet *Puppet) PhoneNumber() string { - return strings.Replace(puppet.JID, whatsappExt.NewUserSuffix, "", 1) + return strings.Replace(puppet.JID, skypeExt.NewUserSuffix, "", 1) } func (puppet *Puppet) IntentFor(portal *Portal) *appservice.IntentAPI { @@ -272,7 +270,7 @@ func (puppet *Puppet) UpdateName(source *User, contact skype.Contact) bool { func (puppet *Puppet) updatePortalMeta(meta func(portal *Portal)) { if puppet.bridge.Config.Bridge.PrivateChatPortalMeta { - jid := strings.Replace(puppet.JID, whatsappExt.NewUserSuffix, "", 1) + jid := strings.Replace(puppet.JID, skypeExt.NewUserSuffix, "", 1) for _, portal := range puppet.bridge.GetAllPortalsByJID(jid) { meta(portal) } diff --git a/skype-ext/chat.go b/skype-ext/chat.go index 70453dd..28845e4 100644 --- a/skype-ext/chat.go +++ b/skype-ext/chat.go @@ -18,9 +18,8 @@ package skypeExt import ( "encoding/json" + skype "github.com/kelaresg/go-skypeapi" "strings" - - "github.com/Rhymen/go-whatsapp" ) type ChatUpdateCommand string @@ -155,7 +154,7 @@ func (cud *ChatUpdateData) UnmarshalJSON(data []byte) error { } type ChatUpdateHandler interface { - whatsapp.Handler + skype.Handler HandleChatUpdate(ChatUpdate) } diff --git a/skype-ext/cmd.go b/skype-ext/cmd.go index fcbda17..75ef250 100644 --- a/skype-ext/cmd.go +++ b/skype-ext/cmd.go @@ -18,9 +18,8 @@ package skypeExt import ( "encoding/json" + skype "github.com/kelaresg/go-skypeapi" "strings" - - "github.com/Rhymen/go-whatsapp" ) type CommandType string @@ -41,7 +40,7 @@ type Command struct { } type CommandHandler interface { - whatsapp.Handler + skype.Handler HandleCommand(Command) } diff --git a/user.go b/user.go index 89bed9d..216e94d 100644 --- a/user.go +++ b/user.go @@ -12,20 +12,20 @@ import ( "sync" "time" - "github.com/pkg/errors" + //"github.com/pkg/errors" "github.com/skip2/go-qrcode" log "maunium.net/go/maulogger/v2" "maunium.net/go/mautrix" - "github.com/Rhymen/go-whatsapp" - waProto "github.com/Rhymen/go-whatsapp/binary/proto" + //"github.com/Rhymen/go-whatsapp" + //waProto "github.com/Rhymen/go-whatsapp/binary/proto" "maunium.net/go/mautrix/event" "maunium.net/go/mautrix/id" "github.com/kelaresg/matrix-skype/database" "github.com/kelaresg/matrix-skype/types" - "github.com/kelaresg/matrix-skype/whatsapp-ext" + //"github.com/kelaresg/matrix-skype/whatsapp-ext" ) type User struct { @@ -587,13 +587,13 @@ func (user *User) syncPortals(chatMap map[string]skype.Conversation, createAll b } } -func (user *User) HandleContactList(contacts []whatsapp.Contact) { - contactMap := make(map[string]whatsapp.Contact) - for _, contact := range contacts { - contactMap[contact.Jid] = contact - } - // go user.syncPuppets(contactMap) -} +//func (user *User) HandleContactList(contacts []whatsapp.Contact) { +// contactMap := make(map[string]whatsapp.Contact) +// for _, contact := range contacts { +// contactMap[contact.Jid] = contact +// } +// // go user.syncPuppets(contactMap) +//} func (user *User) syncPuppets(contacts map[string]skype.Contact) { if contacts == nil { @@ -636,20 +636,6 @@ func (user *User) updateLastConnectionIfNecessary() { } func (user *User) HandleError(err error) { - if errors.Cause(err) != whatsapp.ErrInvalidWsData { - user.log.Errorfln("WhatsApp error: %v", err) - } - if closed, ok := err.(*whatsapp.ErrConnectionClosed); ok { - if closed.Code == 1000 && user.cleanDisconnection { - user.cleanDisconnection = false - user.log.Infoln("Clean disconnection by server") - return - } - go user.tryReconnect(fmt.Sprintf("Your WhatsApp connection was closed with websocket status code %d", closed.Code)) - } else if failed, ok := err.(*whatsapp.ErrConnectionFailed); ok { - user.ConnectionErrors++ - go user.tryReconnect(fmt.Sprintf("Your WhatsApp connection failed: %v", failed.Err)) - } // Otherwise unknown error, probably mostly harmless } @@ -762,21 +748,21 @@ func (user *User) HandleImageMessage(message skype.Resource) { user.putMessage(PortalMessage{message.Jid, user, message, uint64(message.Timestamp)}) } -func (user *User) HandleStickerMessage(message whatsapp.StickerMessage) { - user.putMessage(PortalMessage{message.Info.RemoteJid, user, message, message.Info.Timestamp}) -} - -func (user *User) HandleVideoMessage(message whatsapp.VideoMessage) { - user.putMessage(PortalMessage{message.Info.RemoteJid, user, message, message.Info.Timestamp}) -} - -func (user *User) HandleAudioMessage(message whatsapp.AudioMessage) { - user.putMessage(PortalMessage{message.Info.RemoteJid, user, message, message.Info.Timestamp}) -} - -func (user *User) HandleDocumentMessage(message whatsapp.DocumentMessage) { - user.putMessage(PortalMessage{message.Info.RemoteJid, user, message, message.Info.Timestamp}) -} +//func (user *User) HandleStickerMessage(message whatsapp.StickerMessage) { +// user.putMessage(PortalMessage{message.Info.RemoteJid, user, message, message.Info.Timestamp}) +//} +// +//func (user *User) HandleVideoMessage(message whatsapp.VideoMessage) { +// user.putMessage(PortalMessage{message.Info.RemoteJid, user, message, message.Info.Timestamp}) +//} +// +//func (user *User) HandleAudioMessage(message whatsapp.AudioMessage) { +// user.putMessage(PortalMessage{message.Info.RemoteJid, user, message, message.Info.Timestamp}) +//} +// +//func (user *User) HandleDocumentMessage(message whatsapp.DocumentMessage) { +// user.putMessage(PortalMessage{message.Info.RemoteJid, user, message, message.Info.Timestamp}) +//} func (user *User) HandleContactMessage(message skype.Resource) { user.log.Debugf("HandleContactMessage: ", message) @@ -798,40 +784,40 @@ type FakeMessage struct { Alert bool } -func (user *User) HandleCallInfo(info whatsappExt.CallInfo) { - if info.Data != nil { - return - } - data := FakeMessage{ - ID: info.ID, - } - switch info.Type { - case whatsappExt.CallOffer: - if !user.bridge.Config.Bridge.CallNotices.Start { - return - } - data.Text = "Incoming call" - data.Alert = true - case whatsappExt.CallOfferVideo: - if !user.bridge.Config.Bridge.CallNotices.Start { - return - } - data.Text = "Incoming video call" - data.Alert = true - case whatsappExt.CallTerminate: - if !user.bridge.Config.Bridge.CallNotices.End { - return - } - data.Text = "Call ended" - data.ID += "E" - default: - return - } - portal := user.GetPortalByJID(info.From) - if portal != nil { - portal.messages <- PortalMessage{info.From, user, data, 0} - } -} +//func (user *User) HandleCallInfo(info whatsappExt.CallInfo) { +// if info.Data != nil { +// return +// } +// data := FakeMessage{ +// ID: info.ID, +// } +// switch info.Type { +// case whatsappExt.CallOffer: +// if !user.bridge.Config.Bridge.CallNotices.Start { +// return +// } +// data.Text = "Incoming call" +// data.Alert = true +// case whatsappExt.CallOfferVideo: +// if !user.bridge.Config.Bridge.CallNotices.Start { +// return +// } +// data.Text = "Incoming video call" +// data.Alert = true +// case whatsappExt.CallTerminate: +// if !user.bridge.Config.Bridge.CallNotices.End { +// return +// } +// data.Text = "Call ended" +// data.ID += "E" +// default: +// return +// } +// portal := user.GetPortalByJID(info.From) +// if portal != nil { +// portal.messages <- PortalMessage{info.From, user, data, 0} +// } +//} func (user *User) HandleTypingStatus(info skype.Resource) { sendId := info.SendId + skypeExt.NewUserSuffix @@ -904,62 +890,62 @@ func (user *User) HandlePresence(info skype.Resource) { } } -func (user *User) HandlePresenceWA(info whatsappExt.Presence) { - puppet := user.bridge.GetPuppetByJID(info.SenderJID) - switch info.Status { - case whatsapp.PresenceUnavailable: - _ = puppet.DefaultIntent().SetPresence("offline") - case whatsapp.PresenceAvailable: - if len(puppet.typingIn) > 0 && puppet.typingAt+15 > time.Now().Unix() { - portal := user.bridge.GetPortalByMXID(puppet.typingIn) - _, _ = puppet.IntentFor(portal).UserTyping(puppet.typingIn, false, 0) - puppet.typingIn = "" - puppet.typingAt = 0 - } - _ = puppet.DefaultIntent().SetPresence("online") - case whatsapp.PresenceComposing: - portal := user.GetPortalByJID(info.JID) - if len(puppet.typingIn) > 0 && puppet.typingAt+15 > time.Now().Unix() { - if puppet.typingIn == portal.MXID { - return - } - _, _ = puppet.IntentFor(portal).UserTyping(puppet.typingIn, false, 0) - } - puppet.typingIn = portal.MXID - puppet.typingAt = time.Now().Unix() - _, _ = puppet.IntentFor(portal).UserTyping(portal.MXID, true, 15*1000) - _ = puppet.DefaultIntent().SetPresence("online") - } -} +//func (user *User) HandlePresenceWA(info whatsappExt.Presence) { +// puppet := user.bridge.GetPuppetByJID(info.SenderJID) +// switch info.Status { +// case whatsapp.PresenceUnavailable: +// _ = puppet.DefaultIntent().SetPresence("offline") +// case whatsapp.PresenceAvailable: +// if len(puppet.typingIn) > 0 && puppet.typingAt+15 > time.Now().Unix() { +// portal := user.bridge.GetPortalByMXID(puppet.typingIn) +// _, _ = puppet.IntentFor(portal).UserTyping(puppet.typingIn, false, 0) +// puppet.typingIn = "" +// puppet.typingAt = 0 +// } +// _ = puppet.DefaultIntent().SetPresence("online") +// case whatsapp.PresenceComposing: +// portal := user.GetPortalByJID(info.JID) +// if len(puppet.typingIn) > 0 && puppet.typingAt+15 > time.Now().Unix() { +// if puppet.typingIn == portal.MXID { +// return +// } +// _, _ = puppet.IntentFor(portal).UserTyping(puppet.typingIn, false, 0) +// } +// puppet.typingIn = portal.MXID +// puppet.typingAt = time.Now().Unix() +// _, _ = puppet.IntentFor(portal).UserTyping(portal.MXID, true, 15*1000) +// _ = puppet.DefaultIntent().SetPresence("online") +// } +//} -func (user *User) HandleMsgInfo(info whatsappExt.MsgInfo) { - if (info.Command == whatsappExt.MsgInfoCommandAck || info.Command == whatsappExt.MsgInfoCommandAcks) && info.Acknowledgement == whatsappExt.AckMessageRead { - portal := user.GetPortalByJID(info.ToJID) - if len(portal.MXID) == 0 { - return - } - - go func() { - intent := user.bridge.GetPuppetByJID(info.SenderJID).IntentFor(portal) - for _, id := range info.IDs { - msg := user.bridge.DB.Message.GetByJID(portal.Key, id) - if msg == nil { - continue - } - - err := intent.MarkRead(portal.MXID, msg.MXID) - if err != nil { - user.log.Warnln("Failed to mark message %s as read by %s: %v", msg.MXID, info.SenderJID, err) - } - } - }() - } -} +//func (user *User) HandleMsgInfo(info whatsappExt.MsgInfo) { +// if (info.Command == whatsappExt.MsgInfoCommandAck || info.Command == whatsappExt.MsgInfoCommandAcks) && info.Acknowledgement == whatsappExt.AckMessageRead { +// portal := user.GetPortalByJID(info.ToJID) +// if len(portal.MXID) == 0 { +// return +// } +// +// go func() { +// intent := user.bridge.GetPuppetByJID(info.SenderJID).IntentFor(portal) +// for _, id := range info.IDs { +// msg := user.bridge.DB.Message.GetByJID(portal.Key, id) +// if msg == nil { +// continue +// } +// +// err := intent.MarkRead(portal.MXID, msg.MXID) +// if err != nil { +// user.log.Warnln("Failed to mark message %s as read by %s: %v", msg.MXID, info.SenderJID, err) +// } +// } +// }() +// } +//} func (user *User) HandleCommand(cmd skypeExt.Command) { switch cmd.Type { case skypeExt.CommandPicture: - if strings.HasSuffix(cmd.JID, whatsappExt.NewUserSuffix) { + if strings.HasSuffix(cmd.JID, skypeExt.NewUserSuffix) { puppet := user.bridge.GetPuppetByJID(cmd.JID) go puppet.UpdateAvatar(user, cmd.ProfilePicInfo) } else { @@ -1145,9 +1131,9 @@ func (user *User) HandleJsonMessage(message string) { user.updateLastConnectionIfNecessary() } -func (user *User) HandleRawMessage(message *waProto.WebMessageInfo) { - user.updateLastConnectionIfNecessary() -} +//func (user *User) HandleRawMessage(message *waProto.WebMessageInfo) { +// user.updateLastConnectionIfNecessary() +//} func (user *User) NeedsRelaybot(portal *Portal) bool { return false diff --git a/whatsapp-ext/call.go b/whatsapp-ext/call.go deleted file mode 100644 index 29575c3..0000000 --- a/whatsapp-ext/call.go +++ /dev/null @@ -1,72 +0,0 @@ -// matrix-skype - A Matrix-WhatsApp puppeting bridge. -// Copyright (C) 2019 Tulir Asokan -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU Affero General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU Affero General Public License for more details. -// -// You should have received a copy of the GNU Affero General Public License -// along with this program. If not, see . - -package whatsappExt - -import ( - "encoding/json" - "strings" - - "github.com/Rhymen/go-whatsapp" -) - -type CallInfoType string - -const ( - CallOffer CallInfoType = "offer" - CallOfferVideo CallInfoType = "offer_video" - CallTransport CallInfoType = "transport" - CallRelayLatency CallInfoType = "relaylatency" - CallTerminate CallInfoType = "terminate" -) - -type CallInfo struct { - ID string `json:"id"` - Type CallInfoType `json:"type"` - From string `json:"from"` - - Platform string `json:"platform"` - Version []int `json:"version"` - - Data [][]interface{} `json:"data"` -} - -type CallInfoHandler interface { - whatsapp.Handler - HandleCallInfo(CallInfo) -} - -func (ext *ExtendedConn) handleMessageCall(message []byte) { - var event CallInfo - err := json.Unmarshal(message, &event) - if err != nil { - ext.jsonParseError(err) - return - } - event.From = strings.Replace(event.From, OldUserSuffix, NewUserSuffix, 1) - for _, handler := range ext.handlers { - callInfoHandler, ok := handler.(CallInfoHandler) - if !ok { - continue - } - - if ext.shouldCallSynchronously(callInfoHandler) { - callInfoHandler.HandleCallInfo(event) - } else { - go callInfoHandler.HandleCallInfo(event) - } - } -} diff --git a/whatsapp-ext/chat.go b/whatsapp-ext/chat.go deleted file mode 100644 index 8de0a99..0000000 --- a/whatsapp-ext/chat.go +++ /dev/null @@ -1,174 +0,0 @@ -// matrix-skype - A Matrix-WhatsApp puppeting bridge. -// Copyright (C) 2019 Tulir Asokan -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU Affero General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU Affero General Public License for more details. -// -// You should have received a copy of the GNU Affero General Public License -// along with this program. If not, see . - -package whatsappExt - -import ( - "encoding/json" - "strings" - - "github.com/Rhymen/go-whatsapp" -) - -type ChatUpdateCommand string - -const ( - ChatUpdateCommandAction ChatUpdateCommand = "action" -) - -type ChatUpdate struct { - JID string `json:"id"` - Command ChatUpdateCommand `json:"cmd"` - Data ChatUpdateData `json:"data"` -} - -type ChatActionType string - -const ( - ChatActionNameChange ChatActionType = "subject" - ChatActionAddTopic ChatActionType = "desc_add" - ChatActionRemoveTopic ChatActionType = "desc_remove" - ChatActionRestrict ChatActionType = "restrict" - ChatActionAnnounce ChatActionType = "announce" - ChatActionPromote ChatActionType = "promote" - ChatActionDemote ChatActionType = "demote" - ChatActionRemove ChatActionType = "remove" - ChatActionAdd ChatActionType = "add" - ChatActionIntroduce ChatActionType = "introduce" - ChatActionCreate ChatActionType = "create" -) - -type ChatUpdateData struct { - Action ChatActionType - SenderJID string - - NameChange struct { - Name string `json:"subject"` - SetAt int64 `json:"s_t"` - SetBy string `json:"s_o"` - } - - AddTopic struct { - Topic string `json:"desc"` - ID string `json:"descId"` - SetAt int64 `json:"descTime"` - } - - RemoveTopic struct { - ID string `json:"descId"` - } - - Restrict bool - - Announce bool - - PermissionChange struct { - JIDs []string `json:"participants"` - } - - MemberAction struct { - JIDs []string `json:"participants"` - } - - Create struct { - Creation int64 `json:"creation"` - Name string `json:"subject"` - SetAt int64 `json:"s_t"` - SetBy string `json:"s_o"` - Admins []string `json:"admins"` - SuperAdmins []string `json:"superadmins"` - Regulars []string `json:"regulars"` - } -} - -func (cud *ChatUpdateData) UnmarshalJSON(data []byte) error { - var arr []json.RawMessage - err := json.Unmarshal(data, &arr) - if err != nil { - return err - } else if len(arr) < 3 { - return nil - } - - err = json.Unmarshal(arr[0], &cud.Action) - if err != nil { - return err - } - - err = json.Unmarshal(arr[1], &cud.SenderJID) - if err != nil { - return err - } - cud.SenderJID = strings.Replace(cud.SenderJID, OldUserSuffix, NewUserSuffix, 1) - - var unmarshalTo interface{} - switch cud.Action { - case ChatActionNameChange: - unmarshalTo = &cud.NameChange - case ChatActionAddTopic: - unmarshalTo = &cud.AddTopic - case ChatActionRemoveTopic: - unmarshalTo = &cud.RemoveTopic - case ChatActionRestrict: - unmarshalTo = &cud.Restrict - case ChatActionAnnounce: - unmarshalTo = &cud.Announce - case ChatActionPromote, ChatActionDemote: - unmarshalTo = &cud.PermissionChange - case ChatActionAdd, ChatActionRemove: - unmarshalTo = &cud.MemberAction - case ChatActionCreate: - unmarshalTo = &cud.Create - default: - return nil - } - err = json.Unmarshal(arr[2], unmarshalTo) - if err != nil { - return err - } - cud.NameChange.SetBy = strings.Replace(cud.NameChange.SetBy, OldUserSuffix, NewUserSuffix, 1) - for index, jid := range cud.PermissionChange.JIDs { - cud.PermissionChange.JIDs[index] = strings.Replace(jid, OldUserSuffix, NewUserSuffix, 1) - } - return nil -} - -type ChatUpdateHandler interface { - whatsapp.Handler - HandleChatUpdate(ChatUpdate) -} - -func (ext *ExtendedConn) handleMessageChatUpdate(message []byte) { - var event ChatUpdate - err := json.Unmarshal(message, &event) - if err != nil { - ext.jsonParseError(err) - return - } - event.JID = strings.Replace(event.JID, OldUserSuffix, NewUserSuffix, 1) - for _, handler := range ext.handlers { - chatUpdateHandler, ok := handler.(ChatUpdateHandler) - if !ok { - continue - } - - if ext.shouldCallSynchronously(chatUpdateHandler) { - chatUpdateHandler.HandleChatUpdate(event) - } else { - go chatUpdateHandler.HandleChatUpdate(event) - } - } -} diff --git a/whatsapp-ext/cmd.go b/whatsapp-ext/cmd.go deleted file mode 100644 index 0954df3..0000000 --- a/whatsapp-ext/cmd.go +++ /dev/null @@ -1,69 +0,0 @@ -// matrix-skype - A Matrix-WhatsApp puppeting bridge. -// Copyright (C) 2019 Tulir Asokan -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU Affero General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU Affero General Public License for more details. -// -// You should have received a copy of the GNU Affero General Public License -// along with this program. If not, see . - -package whatsappExt - -import ( - "encoding/json" - "strings" - - "github.com/Rhymen/go-whatsapp" -) - -type CommandType string - -const ( - CommandPicture CommandType = "picture" - CommandDisconnect CommandType = "disconnect" -) - -type Command struct { - Type CommandType `json:"type"` - JID string `json:"jid"` - - *ProfilePicInfo - Kind string `json:"kind"` - - Raw json.RawMessage `json:"-"` -} - -type CommandHandler interface { - whatsapp.Handler - HandleCommand(Command) -} - -func (ext *ExtendedConn) handleMessageCommand(message []byte) { - var event Command - err := json.Unmarshal(message, &event) - if err != nil { - ext.jsonParseError(err) - return - } - event.Raw = message - event.JID = strings.Replace(event.JID, OldUserSuffix, NewUserSuffix, 1) - for _, handler := range ext.handlers { - commandHandler, ok := handler.(CommandHandler) - if !ok { - continue - } - - if ext.shouldCallSynchronously(commandHandler) { - commandHandler.HandleCommand(event) - } else { - go commandHandler.HandleCommand(event) - } - } -} diff --git a/whatsapp-ext/conn.go b/whatsapp-ext/conn.go deleted file mode 100644 index 8ce4345..0000000 --- a/whatsapp-ext/conn.go +++ /dev/null @@ -1,65 +0,0 @@ -// matrix-skype - A Matrix-WhatsApp puppeting bridge. -// Copyright (C) 2019 Tulir Asokan -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU Affero General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU Affero General Public License for more details. -// -// You should have received a copy of the GNU Affero General Public License -// along with this program. If not, see . - -package whatsappExt - -import ( - "encoding/json" - - "github.com/Rhymen/go-whatsapp" -) - -type ConnInfo struct { - ProtocolVersion []int `json:"protoVersion"` - BinaryVersion int `json:"binVersion"` - Phone struct { - WhatsAppVersion string `json:"wa_version"` - MCC string `json:"mcc"` - MNC string `json:"mnc"` - OSVersion string `json:"os_version"` - DeviceManufacturer string `json:"device_manufacturer"` - DeviceModel string `json:"device_model"` - OSBuildNumber string `json:"os_build_number"` - } `json:"phone"` - Features map[string]interface{} `json:"features"` - PushName string `json:"pushname"` -} - -type ConnInfoHandler interface { - whatsapp.Handler - HandleConnInfo(ConnInfo) -} - -func (ext *ExtendedConn) handleMessageConn(message []byte) { - var event ConnInfo - err := json.Unmarshal(message, &event) - if err != nil { - ext.jsonParseError(err) - return - } - for _, handler := range ext.handlers { - connInfoHandler, ok := handler.(ConnInfoHandler) - if !ok { - continue - } - - if ext.shouldCallSynchronously(connInfoHandler) { - connInfoHandler.HandleConnInfo(event) - } else { - go connInfoHandler.HandleConnInfo(event) - } - } -} diff --git a/whatsapp-ext/jsonmessage.go b/whatsapp-ext/jsonmessage.go deleted file mode 100644 index e0ac474..0000000 --- a/whatsapp-ext/jsonmessage.go +++ /dev/null @@ -1,105 +0,0 @@ -// matrix-skype - A Matrix-WhatsApp puppeting bridge. -// Copyright (C) 2019 Tulir Asokan -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU Affero General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU Affero General Public License for more details. -// -// You should have received a copy of the GNU Affero General Public License -// along with this program. If not, see . - -package whatsappExt - -import ( - "encoding/json" - - "github.com/Rhymen/go-whatsapp" -) - -type JSONMessage []json.RawMessage - -type JSONMessageType string - -const ( - MessageMsgInfo JSONMessageType = "MsgInfo" - MessageMsg JSONMessageType = "Msg" - MessagePresence JSONMessageType = "Presence" - MessageStream JSONMessageType = "Stream" - MessageConn JSONMessageType = "Conn" - MessageProps JSONMessageType = "Props" - MessageCmd JSONMessageType = "Cmd" - MessageChat JSONMessageType = "Chat" - MessageCall JSONMessageType = "Call" -) - -func (ext *ExtendedConn) HandleError(error) {} - -type UnhandledJSONMessageHandler interface { - whatsapp.Handler - HandleUnhandledJSONMessage(string) -} - -type JSONParseErrorHandler interface { - whatsapp.Handler - HandleJSONParseError(error) -} - -func (ext *ExtendedConn) jsonParseError(err error) { - for _, handler := range ext.handlers { - errorHandler, ok := handler.(JSONParseErrorHandler) - if !ok { - continue - } - errorHandler.HandleJSONParseError(err) - } -} - -func (ext *ExtendedConn) HandleJsonMessage(message string) { - msg := JSONMessage{} - err := json.Unmarshal([]byte(message), &msg) - if err != nil || len(msg) < 2 { - ext.jsonParseError(err) - return - } - - var msgType JSONMessageType - json.Unmarshal(msg[0], &msgType) - - switch msgType { - case MessagePresence: - ext.handleMessagePresence(msg[1]) - case MessageStream: - ext.handleMessageStream(msg[1:]) - case MessageConn: - ext.handleMessageConn(msg[1]) - case MessageProps: - ext.handleMessageProps(msg[1]) - case MessageMsgInfo, MessageMsg: - ext.handleMessageMsgInfo(msgType, msg[1]) - case MessageCmd: - ext.handleMessageCommand(msg[1]) - case MessageChat: - ext.handleMessageChatUpdate(msg[1]) - case MessageCall: - ext.handleMessageCall(msg[1]) - default: - for _, handler := range ext.handlers { - ujmHandler, ok := handler.(UnhandledJSONMessageHandler) - if !ok { - continue - } - - if ext.shouldCallSynchronously(ujmHandler) { - ujmHandler.HandleUnhandledJSONMessage(message) - } else { - go ujmHandler.HandleUnhandledJSONMessage(message) - } - } - } -} diff --git a/whatsapp-ext/msginfo.go b/whatsapp-ext/msginfo.go deleted file mode 100644 index 702c322..0000000 --- a/whatsapp-ext/msginfo.go +++ /dev/null @@ -1,95 +0,0 @@ -// matrix-skype - A Matrix-WhatsApp puppeting bridge. -// Copyright (C) 2019 Tulir Asokan -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU Affero General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU Affero General Public License for more details. -// -// You should have received a copy of the GNU Affero General Public License -// along with this program. If not, see . - -package whatsappExt - -import ( - "encoding/json" - "strings" - - "github.com/Rhymen/go-whatsapp" -) - -type MsgInfoCommand string - -const ( - MsgInfoCommandAck MsgInfoCommand = "ack" - MsgInfoCommandAcks MsgInfoCommand = "acks" -) - -type Acknowledgement int - -const ( - AckMessageSent Acknowledgement = 1 - AckMessageDelivered Acknowledgement = 2 - AckMessageRead Acknowledgement = 3 -) - -type JSONStringOrArray []string - -func (jsoa *JSONStringOrArray) UnmarshalJSON(data []byte) error { - var str string - if json.Unmarshal(data, &str) == nil { - *jsoa = []string{str} - return nil - } - var strs []string - json.Unmarshal(data, &strs) - *jsoa = strs - return nil -} - -type MsgInfo struct { - Command MsgInfoCommand `json:"cmd"` - IDs JSONStringOrArray `json:"id"` - Acknowledgement Acknowledgement `json:"ack"` - MessageFromJID string `json:"from"` - SenderJID string `json:"participant"` - ToJID string `json:"to"` - Timestamp int64 `json:"t"` -} - -type MsgInfoHandler interface { - whatsapp.Handler - HandleMsgInfo(MsgInfo) -} - -func (ext *ExtendedConn) handleMessageMsgInfo(msgType JSONMessageType, message []byte) { - var event MsgInfo - err := json.Unmarshal(message, &event) - if err != nil { - ext.jsonParseError(err) - return - } - event.MessageFromJID = strings.Replace(event.MessageFromJID, OldUserSuffix, NewUserSuffix, 1) - event.SenderJID = strings.Replace(event.SenderJID, OldUserSuffix, NewUserSuffix, 1) - event.ToJID = strings.Replace(event.ToJID, OldUserSuffix, NewUserSuffix, 1) - if msgType == MessageMsg { - event.SenderJID = event.ToJID - } - for _, handler := range ext.handlers { - msgInfoHandler, ok := handler.(MsgInfoHandler) - if !ok { - continue - } - - if ext.shouldCallSynchronously(msgInfoHandler) { - msgInfoHandler.HandleMsgInfo(event) - } else { - go msgInfoHandler.HandleMsgInfo(event) - } - } -} diff --git a/whatsapp-ext/presence.go b/whatsapp-ext/presence.go deleted file mode 100644 index 01365d2..0000000 --- a/whatsapp-ext/presence.go +++ /dev/null @@ -1,67 +0,0 @@ -// matrix-skype - A Matrix-WhatsApp puppeting bridge. -// Copyright (C) 2019 Tulir Asokan -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU Affero General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU Affero General Public License for more details. -// -// You should have received a copy of the GNU Affero General Public License -// along with this program. If not, see . - -package whatsappExt - -import ( - "encoding/json" - "strings" - - "github.com/Rhymen/go-whatsapp" -) - -type Presence struct { - JID string `json:"id"` - SenderJID string `json:"participant"` - Status whatsapp.Presence `json:"type"` - Timestamp int64 `json:"t"` - Deny bool `json:"deny"` -} - -type PresenceHandler interface { - whatsapp.Handler - HandlePresence(Presence) -} - -func (ext *ExtendedConn) handleMessagePresence(message []byte) { - var event Presence - err := json.Unmarshal(message, &event) - if err != nil { - ext.jsonParseError(err) - return - } - event.JID = strings.Replace(event.JID, OldUserSuffix, NewUserSuffix, 1) - if len(event.SenderJID) == 0 { - if strings.Index(event.JID,"@g.us") > -1 { - return - } - event.SenderJID = event.JID - } else { - event.SenderJID = strings.Replace(event.SenderJID, OldUserSuffix, NewUserSuffix, 1) - } - for _, handler := range ext.handlers { - presenceHandler, ok := handler.(PresenceHandler) - if !ok { - continue - } - - if ext.shouldCallSynchronously(presenceHandler) { - presenceHandler.HandlePresence(event) - } else { - go presenceHandler.HandlePresence(event) - } - } -} diff --git a/whatsapp-ext/props.go b/whatsapp-ext/props.go deleted file mode 100644 index 4245683..0000000 --- a/whatsapp-ext/props.go +++ /dev/null @@ -1,73 +0,0 @@ -// matrix-skype - A Matrix-WhatsApp puppeting bridge. -// Copyright (C) 2019 Tulir Asokan -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU Affero General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU Affero General Public License for more details. -// -// You should have received a copy of the GNU Affero General Public License -// along with this program. If not, see . - -package whatsappExt - -import ( - "encoding/json" - - "github.com/Rhymen/go-whatsapp" -) - -type ProtocolProps struct { - WebPresence bool `json:"webPresence"` - NotificationQuery bool `json:"notificationQuery"` - FacebookCrashLog bool `json:"fbCrashlog"` - Bucket string `json:"bucket"` - GIFSearch string `json:"gifSearch"` - Spam bool `json:"SPAM"` - SetBlock bool `json:"SET_BLOCK"` - MessageInfo bool `json:"MESSAGE_INFO"` - MaxFileSize int `json:"maxFileSize"` - Media int `json:"media"` - GroupNameLength int `json:"maxSubject"` - GroupDescriptionLength int `json:"groupDescLength"` - MaxParticipants int `json:"maxParticipants"` - VideoMaxEdge int `json:"videoMaxEdge"` - ImageMaxEdge int `json:"imageMaxEdge"` - ImageMaxKilobytes int `json:"imageMaxKBytes"` - Edit int `json:"edit"` - FwdUIStartTimestamp int `json:"fwdUiStartTs"` - GroupsV3 int `json:"groupsV3"` - RestrictGroups int `json:"restrictGroups"` - AnnounceGroups int `json:"announceGroups"` -} - -type ProtocolPropsHandler interface { - whatsapp.Handler - HandleProtocolProps(ProtocolProps) -} - -func (ext *ExtendedConn) handleMessageProps(message []byte) { - var event ProtocolProps - err := json.Unmarshal(message, &event) - if err != nil { - ext.jsonParseError(err) - return - } - for _, handler := range ext.handlers { - protocolPropsHandler, ok := handler.(ProtocolPropsHandler) - if !ok { - continue - } - - if ext.shouldCallSynchronously(protocolPropsHandler) { - protocolPropsHandler.HandleProtocolProps(event) - } else { - go protocolPropsHandler.HandleProtocolProps(event) - } - } -} diff --git a/whatsapp-ext/protomessage.go b/whatsapp-ext/protomessage.go deleted file mode 100644 index ca00f05..0000000 --- a/whatsapp-ext/protomessage.go +++ /dev/null @@ -1,59 +0,0 @@ -// matrix-skype - A Matrix-WhatsApp puppeting bridge. -// Copyright (C) 2019 Tulir Asokan -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU Affero General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU Affero General Public License for more details. -// -// You should have received a copy of the GNU Affero General Public License -// along with this program. If not, see . - -package whatsappExt - -import ( - "github.com/Rhymen/go-whatsapp" - "github.com/Rhymen/go-whatsapp/binary/proto" -) - -type MessageRevokeHandler interface { - whatsapp.Handler - HandleMessageRevoke(key MessageRevocation) -} - -type MessageRevocation struct { - Id string - RemoteJid string - FromMe bool - Participant string -} - -func (ext *ExtendedConn) HandleRawMessage(message *proto.WebMessageInfo) { - protoMsg := message.GetMessage().GetProtocolMessage() - if protoMsg != nil && protoMsg.GetType() == proto.ProtocolMessage_REVOKE { - key := protoMsg.GetKey() - deletedMessage := MessageRevocation{ - Id: key.GetId(), - RemoteJid: key.GetRemoteJid(), - FromMe: key.GetFromMe(), - Participant: key.GetParticipant(), - } - for _, handler := range ext.handlers { - mrHandler, ok := handler.(MessageRevokeHandler) - if !ok { - continue - } - - if ext.shouldCallSynchronously(mrHandler) { - mrHandler.HandleMessageRevoke(deletedMessage) - } else { - go mrHandler.HandleMessageRevoke(deletedMessage) - } - } - } -} diff --git a/whatsapp-ext/stream.go b/whatsapp-ext/stream.go deleted file mode 100644 index bd82672..0000000 --- a/whatsapp-ext/stream.go +++ /dev/null @@ -1,68 +0,0 @@ -// matrix-skype - A Matrix-WhatsApp puppeting bridge. -// Copyright (C) 2019 Tulir Asokan -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU Affero General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU Affero General Public License for more details. -// -// You should have received a copy of the GNU Affero General Public License -// along with this program. If not, see . - -package whatsappExt - -import ( - "encoding/json" - - "github.com/Rhymen/go-whatsapp" -) - -type StreamType string - -const ( - StreamUpdate = "update" - StreamSleep = "asleep" -) - -type StreamEvent struct { - Type StreamType - Boolean bool - Version string -} - -type StreamEventHandler interface { - whatsapp.Handler - HandleStreamEvent(StreamEvent) -} - -func (ext *ExtendedConn) handleMessageStream(message []json.RawMessage) { - var event StreamEvent - err := json.Unmarshal(message[0], &event.Type) - if err != nil { - ext.jsonParseError(err) - return - } - - if event.Type == StreamUpdate && len(message) > 4 { - json.Unmarshal(message[1], event.Boolean) - json.Unmarshal(message[2], event.Version) - } - - for _, handler := range ext.handlers { - streamHandler, ok := handler.(StreamEventHandler) - if !ok { - continue - } - - if ext.shouldCallSynchronously(streamHandler) { - streamHandler.HandleStreamEvent(event) - } else { - go streamHandler.HandleStreamEvent(event) - } - } -} diff --git a/whatsapp-ext/whatsapp.go b/whatsapp-ext/whatsapp.go deleted file mode 100644 index 5c356c3..0000000 --- a/whatsapp-ext/whatsapp.go +++ /dev/null @@ -1,206 +0,0 @@ -// matrix-skype - A Matrix-WhatsApp puppeting bridge. -// Copyright (C) 2019 Tulir Asokan -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU Affero General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU Affero General Public License for more details. -// -// You should have received a copy of the GNU Affero General Public License -// along with this program. If not, see . - -package whatsappExt - -import ( - "encoding/json" - "fmt" - "io" - "io/ioutil" - "net/http" - "strings" - - "github.com/Rhymen/go-whatsapp" -) - -const ( - OldUserSuffix = "@c.us" - //NewUserSuffix = "@s.whatsapp.net" - NewUserSuffix = "@s.skype.net" -) - -type ExtendedConn struct { - *whatsapp.Conn - - handlers []whatsapp.Handler -} - -func ExtendConn(conn *whatsapp.Conn) *ExtendedConn { - ext := &ExtendedConn{ - Conn: conn, - } - ext.Conn.AddHandler(ext) - return ext -} - -func (ext *ExtendedConn) AddHandler(handler whatsapp.Handler) { - ext.Conn.AddHandler(handler) - ext.handlers = append(ext.handlers, handler) -} - - -func (ext *ExtendedConn) RemoveHandler(handler whatsapp.Handler) bool { - ext.Conn.RemoveHandler(handler) - for i, v := range ext.handlers { - if v == handler { - ext.handlers = append(ext.handlers[:i], ext.handlers[i+1:]...) - return true - } - } - return false -} - -func (ext *ExtendedConn) RemoveHandlers() { - ext.Conn.RemoveHandlers() - ext.handlers = make([]whatsapp.Handler, 0) -} - -func (ext *ExtendedConn) shouldCallSynchronously(handler whatsapp.Handler) bool { - sh, ok := handler.(whatsapp.SyncHandler) - return ok && sh.ShouldCallSynchronously() -} - -func (ext *ExtendedConn) ShouldCallSynchronously() bool { - return true -} - -type GroupInfo struct { - JID string `json:"jid"` - OwnerJID string `json:"owner"` - - Name string `json:"subject"` - NameSetTime int64 `json:"subjectTime"` - NameSetBy string `json:"subjectOwner"` - - Topic string `json:"desc"` - TopicID string `json:"descId"` - TopicSetAt int64 `json:"descTime"` - TopicSetBy string `json:"descOwner"` - - GroupCreated int64 `json:"creation"` - - Status int16 `json:"status"` - - Participants []struct { - JID string `json:"id"` - IsAdmin bool `json:"isAdmin"` - IsSuperAdmin bool `json:"isSuperAdmin"` - } `json:"participants"` -} - -func (ext *ExtendedConn) GetGroupMetaData(jid string) (*GroupInfo, error) { - data, err := ext.Conn.GetGroupMetaData(jid) - if err != nil { - return nil, fmt.Errorf("failed to get group metadata: %v", err) - } - content := <-data - - info := &GroupInfo{} - err = json.Unmarshal([]byte(content), info) - if err != nil { - return info, fmt.Errorf("failed to unmarshal group metadata: %v", err) - } - - for index, participant := range info.Participants { - info.Participants[index].JID = strings.Replace(participant.JID, OldUserSuffix, NewUserSuffix, 1) - } - info.NameSetBy = strings.Replace(info.NameSetBy, OldUserSuffix, NewUserSuffix, 1) - info.TopicSetBy = strings.Replace(info.TopicSetBy, OldUserSuffix, NewUserSuffix, 1) - - return info, nil -} - -type ProfilePicInfo struct { - URL string `json:"eurl"` - Tag string `json:"tag"` - - Status int16 `json:"status"` -} - -func (ppi *ProfilePicInfo) Download() (io.ReadCloser, error) { - resp, err := http.Get(ppi.URL) - if err != nil { - return nil, err - } - return resp.Body, nil -} - -func (ppi *ProfilePicInfo) DownloadBytes() ([]byte, error) { - body, err := ppi.Download() - if err != nil { - return nil, err - } - defer body.Close() - data, err := ioutil.ReadAll(body) - return data, err -} - -func (ext *ExtendedConn) GetProfilePicThumb(jid string) (*ProfilePicInfo, error) { - data, err := ext.Conn.GetProfilePicThumb(jid) - if err != nil { - return nil, fmt.Errorf("failed to get avatar: %v", err) - } - content := <-data - info := &ProfilePicInfo{} - err = json.Unmarshal([]byte(content), info) - if err != nil { - return info, fmt.Errorf("failed to unmarshal avatar info: %v", err) - } - return info, nil -} - -func (ext *ExtendedConn) HandleGroupInvite(groupJid string, numbers[]string) (err error) { - var parts []string - parts = append(parts, numbers...) - _, err = ext.Conn.AddMember(groupJid, parts) - if err != nil { - fmt.Printf("%s Handle Invite err", err) - } - return -} - -func (ext *ExtendedConn) HandleGroupJoin(code string) (jid string, err error) { - return ext.Conn.GroupAcceptInviteCode(code) -} - -func (ext *ExtendedConn) HandleGroupKick(groupJid string, numbers[]string) (err error) { - var parts []string - parts = append(parts, numbers...) - _, err = ext.Conn.RemoveMember(groupJid, parts) - if err != nil { - fmt.Printf("%s Handle kick err", err) - } - return -} - -func (ext *ExtendedConn) HandleGroupCreate(subject string, numbers[]string) (err error) { - var parts []string - parts = append(parts, numbers...) - _, err = ext.Conn.CreateGroup(subject, parts) - if err != nil { - fmt.Printf("%s HandleGroupCreate err", err) - } - return -} - -func (ext *ExtendedConn) HandleGroupLeave(groupJid string) (err error) { - _, err = ext.Conn.LeaveGroup(groupJid) - if err != nil { - fmt.Printf("%s HandleGroupLeave err", err) - } - return -}