-> nicknames in rooms

-> sync contacts
This commit is contained in:
DaZZZl 2015-05-03 02:44:57 +02:00
parent 995507c27f
commit c716e94c70
4 changed files with 86 additions and 20 deletions

View File

@ -3,7 +3,7 @@ import socket
import struct
import sys
import os
import logging
import google.protobuf
def WRAP(MESSAGE, TYPE):
@ -19,11 +19,12 @@ class SpectrumBackend:
@param host: Host where Spectrum2 NetworkPluginServer runs.
@param port: Port.
"""
def __init__(self):
self.m_pingReceived = False
self.m_data = ""
self.m_init_res = 0
self.logger = logging.getLogger(self.__class__.__name__)
def handleMessage(self, user, legacyName, msg, nickname = "", xhtml = "", timestamp = ""):
m = protocol_pb2.ConversationMessage()
@ -251,6 +252,7 @@ class SpectrumBackend:
def handleConvMessagePayload(self, data):
payload = protocol_pb2.ConversationMessage()
self.logger.error("handleConvMessagePayload")
if (payload.ParseFromString(data) == False):
#TODO: ERROR
return
@ -363,8 +365,10 @@ class SpectrumBackend:
if (len(self.m_data) >= 4):
expected_size = struct.unpack('!I', self.m_data[0:4])[0]
if (len(self.m_data) - 4 < expected_size):
self.logger.error("Expected Data Size Error")
return
else:
self.logger.error("Data too small")
return
@ -378,9 +382,13 @@ class SpectrumBackend:
if (parseFromString == False):
self.m_data = self.m_data[expected_size+4:]
self.logger.error("Parse from String error")
return
self.m_data = self.m_data[4+expected_size:]
#self.logger.error("Data Type: %s",wrapper.type)
if wrapper.type == protocol_pb2.WrapperMessage.TYPE_LOGIN:
self.handleLoginPayload(wrapper.payload)

18
bot.py
View File

@ -48,7 +48,9 @@ class Bot():
"prune": self._prune,
"welcome": self._welcome,
"fortune": self._fortune,
"sync": self._sync
"sync": self._sync,
"groups": self._groups,
"getgroups": self._getgroups
}
def parse(self, message):
@ -173,6 +175,8 @@ class Bot():
\\import [token] import buddies from Google
\\sync sync your imported contacts with WhatsApp
\\fortune [database] give me a quote
\\groups print all attended groups
\\getgroups get current groups from WA
following user commands are available:
\\lastseen request last online timestamp from buddy""")
@ -193,3 +197,15 @@ following user commands are available:
self.session.buddies.prune()
self.session.updateRoster()
self.send("buddy list cleared")
def _groups(self):
for group in self.session.groups:
buddy = self.session.groups[group].owner
try:
nick = self.session.buddies[buddy].nick
except KeyError:
nick = buddy
self.send(self.session.groups[group].id + " " + self.session.groups[group].subject + " Owner: " + nick )
def _getgroups(self):
self.session.call("group_getGroups", ("participating",))

View File

@ -67,6 +67,8 @@ class Session:
self.timer = None
self.password = None
self.initialized = False
self.lastMsgId = None
self.synced = False
self.buddies = BuddyList(legacyName, db)
self.frontend = YowsupConnectionManager()
@ -154,13 +156,21 @@ class Session:
def sendMessageToWA(self, sender, message, ID):
self.logger.info("Message (ID: %s) send from %s to %s: %s", ID, self.legacyName, sender, message)
message = message.encode("utf-8")
if ID == self.lastMsgId:
return
self.lastMsgId = ID
if sender == "bot":
self.bot.parse(message)
elif "-" in sender: # group msg
if "/" in sender:
room, buddy = sender.split("/")
self.call("message_send", (buddy + "@s.whatsapp.net", message))
room, nick2 = sender.split("/")
buddy2 = nick2
for buddy, buddy3 in self.buddies.iteritems():
self.logger.info("Group buddy=%s nick=%s", buddy, buddy3.nick)
if buddy3.nick == nick2:
buddy2 = buddy
self.call("message_send", (buddy2 + "@s.whatsapp.net", message))
else:
room = sender
group = self.groups[room]
@ -177,7 +187,11 @@ class Session:
self.sendMessageToXMPP(buddy, "Fetching Profile Picture")
self.call("contact_getProfilePicture", (buddy + "@s.whatsapp.net",))
else:
waId = self.call("message_send", (buddy + "@s.whatsapp.net", message))
if ("jpg" in message) or ("webp" in message):
#waId = self.call("message_imageSend", (buddy + "@s.whatsapp.net", message, None, 0, None))
waId = self.call("message_send", (buddy + "@s.whatsapp.net", message))
else:
waId = self.call("message_send", (buddy + "@s.whatsapp.net", message))
self.msgIDs[waId] = MsgIDs( ID, waId)
self.logger.info("WA Message send to %s with ID %s", buddy, waId)
@ -196,8 +210,9 @@ class Session:
try:
nick = self.buddies[buddy].nick
except KeyError:
nick = "unknown"
nick = buddy
buddyFull = buddy
if timestamp:
timestamp = time.strftime("%Y%m%dT%H%M%S", time.gmtime(timestamp))
@ -207,10 +222,10 @@ class Session:
if room not in self.groupOfflineQueue:
self.groupOfflineQueue[room] = [ ]
self.groupOfflineQueue[room].append((buddy, messageContent + ": " + nick, timestamp))
self.groupOfflineQueue[room].append((nick, messageContent, timestamp))
else:
self.logger.debug("Group message sent from %s to %s: %s", buddy, room, messageContent)
self.backend.handleMessage(self.user, room, messageContent + ": " + nick, buddy, "", timestamp)
self.backend.handleMessage(self.user, room, messageContent, nick , "", timestamp)
def changeStatus(self, status):
if status != self.status:
@ -258,10 +273,16 @@ class Session:
self.logger.info("Joining room: %s room=%s, nick=%s", self.legacyName, room, nick)
group.nick = nick
try:
ownerNick = self.buddies[group.subjectOwner].nick
except KeyError:
ownerNick = group.subjectOwner
#time.sleep(2)
if init == False:
self.call("group_getParticipants", (room + "@g.us",)) #FIXME
self.backend.handleSubject(self.user, room, group.subject, group.subjectOwner)
self.backend.handleSubject(self.user, room, group.subject, ownerNick)
#self.backend.handleSubject(self.user, room, group.subject, self.user)
self.backend.handleRoomNicknameChanged(self.user,room,group.subject)
else:
self.logger.warn("Room doesn't exist: %s", room)
@ -272,7 +293,13 @@ class Session:
old = self.buddies.keys()
self.buddies.load()
new = self.buddies.keys()
contacts = new
#self.logger.info("Roster: %s", str(list(new)))
if self.synced == False:
self.call("sync_sendSync", (contacts,))
self.synced = True
#self.call("sync_sendContacts", (contacts,))
add = set(new) - set(old)
remove = set(old) - set(new)
@ -340,7 +367,7 @@ class Session:
#if receiptRequested:
self.call("message_ack", (jid, messageId))
def onMediaReceived(self, messageId, jid, preview, url, size, receiptRequested, isBroadcast):
def onMediaReceived(self, messageId, jid, preview, url, size, caption, timestamp, receiptRequested, pushName, isBroadcast):
buddy = jid.split("@")[0]
self.logger.info("Media received from %s: %s", buddy, url)
@ -349,7 +376,7 @@ class Session:
#if receiptRequested:
self.call("message_ack", (jid, messageId))
def onGroupMediaReceived(self, messageId, gjid, jid, preview, url, size, receiptRequested):
def onGroupMediaReceived(self, messageId, gjid, jid, preview, url, size, caption, timestamp, receiptRequested, pushName):
buddy = jid.split("@")[0]
room = gjid.split("@")[0]
@ -362,31 +389,35 @@ class Session:
def onLocationReceived(self, messageId, jid, name, preview, latitude, longitude, receiptRequested, isBroadcast):
def onLocationReceived(self, messageId, jid, name, preview, latitude, longitude, timestamp, receiptRequested, pushName, isBroadcast):
buddy = jid.split("@")[0]
self.logger.info("Location received from %s: %s, %s", buddy, latitude, longitude)
url = "http://maps.google.de?%s" % urllib.urlencode({ "q": "%s %s" % (latitude, longitude) })
geo = "geo:"+latitude+","+longitude
# self.sendMessageToXMPP(buddy, utils.shorten(url))
self.sendMessageToXMPP(buddy, url)
self.sendMessageToXMPP(buddy, geo)
#if receiptRequested:
self.call("message_ack", (jid, messageId))
def onGroupLocationReceived(self, messageId, gjid, jid, name, preview, latitude, longitude, receiptRequested):
def onGroupLocationReceived(self, messageId, gjid, jid, name, preview, latitude, longitude, timestamp, receiptRequested, pushName):
buddy = jid.split("@")[0]
room = gjid.split("@")[0]
url = "http://maps.google.de?%s" % urllib.urlencode({ "q": "%s %s" % (latitude, longitude) })
geo = "geo:"+latitude+","+longitude
# self.sendMessageToXMPP(buddy, utils.shorten(url))
self.sendGroupMessageToXMPP(room, buddy, url)
self.sendGroupMessageToXMPP(room, buddy, geo)
#if receiptRequested:
self.call("message_ack", (gjid, messageId))
def onVcardReceived(self, messageId, jid, name, data, receiptRequested, isBroadcast): # TODO
def onVcardReceived(self, messageId, jid, name, data, timestamp, receiptRequested, pushName, isBroadcast): # TODO
buddy = jid.split("@")[0]
self.logger.info("VCard received from %s", buddy)
self.sendMessageToXMPP(buddy, "Received VCard (not implemented yet)")
@ -469,14 +500,25 @@ class Session:
for jid in jids:
buddy = jid.split("@")[0]
self.logger.info("Added %s to room %s", buddy, room)
try:
nick = self.buddies[buddy].nick
except KeyError:
nick = buddy
#nick = ""
#nick = ""
buddyFull = buddy
if buddy == group.owner:
flags = protocol_pb2.PARTICIPANT_FLAG_MODERATOR
else:
flags = protocol_pb2.PARTICIPANT_FLAG_NONE
if buddy == self.legacyName:
nick = group.nick
flags = protocol_pb2.PARTICIPANT_FLAG_ME
buddyFull = self.user
self.backend.handleParticipantChanged(self.user, buddy, room, flags, protocol_pb2.STATUS_ONLINE,"Nici","") # TODO check status
self.backend.handleParticipantChanged(self.user, buddyFull, room, flags, protocol_pb2.STATUS_ONLINE, buddy, nick) # TODO check status
#self.backend.handleParticipantChanged(self.user, buddy , room, flags, protocol_pb2.STATUS_ONLINE, buddy, nick) # TODO check sta
if room in self.groupOfflineQueue:
while self.groupOfflineQueue[room]:
msg = self.groupOfflineQueue[room].pop(0)
@ -552,7 +594,7 @@ class Session:
self.db.commit()
# if receiptRequested: self.call("notification_ack", (jid, messageId))
#if receiptRequested: self.call("notification_ack", (jid, messageId))
def onReceiptMessageDeliverd(self, jid, msgId):
buddy = jid.split("@")[0]

View File

@ -63,7 +63,7 @@ class WhatsAppBackend(SpectrumBackend):
del self.sessions[user]
def handleMessageSendRequest(self, user, buddy, message, xhtml = "", ID = 0):
self.logger.debug("handleMessageSendRequest(user=%s, buddy=%s, message=%s, id=%d)", user, buddy, message, ID)
self.logger.info("handleMessageSendRequest(user=%s, buddy=%s, message=%s, id=%s)", user, buddy, message, ID)
if user not in self.sessions:
return;
self.sessions[user].sendMessageToWA(buddy, message, ID)