diff --git a/registersession.py b/registersession.py new file mode 100644 index 0000000..b07b675 --- /dev/null +++ b/registersession.py @@ -0,0 +1,94 @@ +from Spectrum2 import protocol_pb2 + +from yowsupwrapper import YowsupApp +import logging +import threadutils + +class RegisterSession(YowsupApp): + """ + A dummy Session object that is used to register a user to whatsapp + """ + WANT_CC = 0 + WANT_SMS = 1 + def __init__(self, backend, user, legacyName, extra): + self.user = user + self.number = legacyName + self.backend = backend + self.logger = logging.getLogger(self.__class__.__name__) + self.state = self.WANT_CC + + def login(self, password=""): + self.backend.handleConnected(self.user) + self.backend.handleBuddyChanged(self.user, 'bot', 'bot', + ['Admin'], protocol_pb2.STATUS_ONLINE) + self.backend.handleMessage(self.user, 'bot', + 'Please enter your country code') + + def sendMessageToWA(self, buddy, message, ID='', xhtml=''): + if buddy == 'bot' and self.state == self.WANT_CC: + try: + country_code = int(message.strip()) + except ValueError: + self.backend.handleMessage(self.user, 'bot', + 'Country code must be a number') + else: # Succeded in decoding country code + country_code = str(country_code) + if country_code != self.number[:len(country_code)]: + self.backend.handleMessage(self.user, + 'bot', 'Number does not start with provided country code') + else: + self.backend.handleMessage(self.user, 'bot', 'Requesting sms code') + self.logger.debug('Requesting SMS code for %s', self.user) + self._requestSMSCodeNonBlock(country_code) + elif buddy == 'bot' and self.state == self.WANT_SMS: + self.backend.handleMessage(self.user, 'bot', 'Not implemented') + else: + self.logger.warn('Unauthorised user (%s) attempting to send messages', + self.user) + self.backend.handleMessage(self.user, buddy, + 'You are not logged in yet. You can only send messages to bot.') + + def _requestSMSCodeNonBlock(self, country_code): + number = self.number[len(country_code):] + threadFunc = lambda: self.requestSMSCode(country_code, number) + threadutils.runInThread(threadFunc, self._confirmation) + + def _confirmation(self, result): + self.backend.handleMessage(self.user, 'bot', 'SMS Code Sent') + self.state = self.WANT_SMS + self.backend.handleMessage(self.user, 'bot', 'Please enter SMS Code') + + # Dummy methods. Whatsapp backend might call these, but they should have no + # effect + def logout(self): + pass + + def joinRoom(self, room, nickname): + pass + + def leaveRoom(self, room): + pass + + def changeStatusMessage(self, statusMessage): + pass + + def changeStatus(self, status): + pass + + def loadBuddies(self, buddies): + pass + + def updateBuddy(self, buddies): + pass + + def removeBuddy(self, buddies): + pass + + def sendTypingStarted(self, buddy): + pass + + def sendTypingStopped(self, buddy): + pass + + def requestVCard(self, buddy, ID): + pass diff --git a/whatsappbackend.py b/whatsappbackend.py index 233843a..068f1a8 100644 --- a/whatsappbackend.py +++ b/whatsappbackend.py @@ -25,6 +25,7 @@ from Spectrum2.backend import SpectrumBackend from Spectrum2 import protocol_pb2 from session import Session +from registersession import RegisterSession import logging @@ -43,8 +44,13 @@ class WhatsAppBackend(SpectrumBackend): # RequestsHandlers def handleLoginRequest(self, user, legacyName, password, extra): self.logger.debug("handleLoginRequest(user=%s, legacyName=%s)", user, legacyName) - if user not in self.sessions: - self.sessions[user] = Session(self, user, legacyName, extra) + # Key word means we should register + if password == 'register': + if user not in self.sessions: + self.sessions[user] = RegisterSession(self, user, legacyName, extra) + else: + if user not in self.sessions: + self.sessions[user] = Session(self, user, legacyName, extra) self.sessions[user].login(password) diff --git a/yowsupwrapper.py b/yowsupwrapper.py index 2996d22..f6f0116 100644 --- a/yowsupwrapper.py +++ b/yowsupwrapper.py @@ -42,6 +42,11 @@ from yowsup.layers.protocol_profiles.protocolentities import * from yowsup.layers.protocol_receipts.protocolentities import * from yowsup.layers.protocol_media.mediauploader import MediaUploader + +# Registration + +from yowsup.registration.coderequest import WACodeRequest + from functools import partial #from session import MsgIDs @@ -371,6 +376,19 @@ class YowsupApp(object): iq = InfoGroupsIqProtocolEntity(group + '@g.us') self.sendIq(iq, onSuccess = onSuccess, onError = onFailure) + def requestSMSCode(self, countryCode, phoneNumber): + """ + Request an sms regitration code. WARNING: this function is blocking + + Args: + countryCode: The country code of the phone you wish to register + phoneNumber: phoneNumber of the phone you wish to register without + the country code. + """ + request = WACodeRequest(countryCode, phoneNumber) + return request.send() + + def onAuthSuccess(self, status, kind, creation, expiration, props, nonce, t): """ Called when login is successful.