Example #1
0
    def connect(self):
        self.reader = Reader()
        self.writer = Writer()

        self._connect()

        buf = self.writer.start_stream(
            self.SERVER,
            "%s-%s-%d" % (PROTOCOL_DEVICE, PROTOCOL_VERSION, PORT))
        self._write(buf)

        # Send features node
        features = Node("stream:features")
        features.add(Node("readreceipts"))
        features.add(Node("groups_v2"))
        features.add(Node("privacy"))
        features.add(Node("presence"))
        self._write(features)

        # Send auth node
        auth = Node("auth", mechanism="WAUTH-2", user=self.number)

        if self.auth_blob:
            encryption = AuthBlobEncryption(self.secret, self.auth_blob)
            logger.debug("Session Keys (re-using auth challenge): %s",
                         [key.encode("hex") for key in encryption.keys])

            self.reader.decrypt = encryption.decrypt

            # From WhatsAPI. It does not encrypt the data, but generates a MAC
            # based on the keys.
            data = "%s%s%s" % (self.number, self.auth_blob, utils.timestamp())
            auth.data = encryption.encrypt("", False) + data

        self._write(auth)

        def on_success(node):
            self.auth_blob = node.data
            self.account_info = node.attributes

            if node["status"] == "expired":
                self._disconnect()
                raise LoginError("Account marked as expired.")

            self._write(Node("presence", name=self.nickname))

        def on_failure(node):
            self._disconnect()
            raise LoginError("Incorrect number and/or secret.")

        # Wait for either success, or failure
        self.register_callback_and_wait(LoginSuccessCallback(on_success),
                                        LoginFailedCallback(on_failure))
Example #2
0
    def __init__(self, number, secret, nickname=None, keep_alive=True):
        self.number = number
        self.secret = secret
        self.nickname = nickname

        self.addrinfo = None
        self.portindex = 0

        self.debug = False
        self.socket = None
        self.reader = Reader()
        self.writer = Writer()

        self.messages = []
        self.account_info = None

        self.last_ping = time()
        self.keep_alive = keep_alive

        self.callbacks = {}