From 0b4e2f13d43b7accdb37c40e82f62c8504975e28 Mon Sep 17 00:00:00 2001 From: moyamo Date: Sat, 2 Jan 2016 16:00:47 +0200 Subject: [PATCH] Add call function to use for deferreds --- deferred.py | 38 +++++++++++++++++++++++++++++++++++++- session.py | 18 +++++++----------- 2 files changed, 44 insertions(+), 12 deletions(-) diff --git a/deferred.py b/deferred.py index 0bbc4e2..3e86dcf 100644 --- a/deferred.py +++ b/deferred.py @@ -1,3 +1,5 @@ +from functools import partial + class Deferred(object): """ Represents a delayed computation. This is a more elegant way to deal with @@ -8,7 +10,8 @@ class Deferred(object): value by using the then method. Computations dependent on the Deferred will only proceed when the run method is called. - Attributes of a Deferred can be accessed directly as methods. + Attributes of a Deferred can be accessed directly as methods. The result of + calling these functions will be Deferred. Example: image = Deferred() @@ -92,6 +95,39 @@ class Then(object): return self.deferred.then(func) return helper +def call(func, *args, **kwargs): + """ + Call a function with deferred arguments + + Example: + colors = Deferred() + colors.append('blue') + colors.run(['red', 'green']) +call(print, colors) #=> ['red', 'green', 'blue'] + call(print, 'hi', colors) #=> hi ['red', 'green', 'blue'] + """ + for i, c in enumerate(args): + if isinstance(c, Deferred): + # Function without deferred arguments + normalfunc = partial(func, *args[:i]) + # Function with deferred and possibly deferred arguments + def restfunc(*arg2, **kwarg2): + apply_deferred = partial(normalfunc, *arg2, **kwarg2) + return call(apply_deferred, *args[i + 1:], **kwargs) + return c.then(restfunc) + items = kwargs.items() + for i, (k, v) in enumerate(items): + if isinstance(v, Deferred): + # Function without deferred arguments + normalfunc = partial(func, *args, **dict(items[:i])) + # Function with deferred and possibly deferred arguments + def restfunc2(*arg2, **kwarg2): + apply_deferred = partial(normalfunc, *arg2, **kwarg2) + return call(apply_deferred, **dict(items[i + 1:])) + return c.then(restfunc2) + # No items deferred + return func(*args, **kwargs) + class DeferredHasValue(Exception): def __init__(self, string): super(DeferredHasValue, self).__init__(string) diff --git a/session.py b/session.py index b21af20..6b97580 100644 --- a/session.py +++ b/session.py @@ -40,8 +40,8 @@ from threading import Timer from group import Group from bot import Bot import deferred +from deferred import call from yowsupwrapper import YowsupApp -from functools import partial class MsgIDs: @@ -736,22 +736,18 @@ class Session(YowsupApp): # Send VCard if ID != None: - response.pictureId().then(partial( - self.logger.debug, 'Sending VCard (%s) with image id %s', ID - )) + call(self.logger.debug, 'Sending VCard (%s) with image id %s', + ID, response.pictureId()) pictureData = response.pictureData() - response.pictureData().then(partial( - self.backend.handleVCard, self.user, ID, buddy, "", "" - )) + call(self.backend.handleVCard, self.user, ID, buddy, "", "", + response.pictureData()) # Send image hash if not buddy == self.legacyName: obuddy = self.buddies[buddy] image_hash = pictureData.then(utils.sha1hash) - image_hash.then(partial(self.logger.debug, 'Image hash is %s')) - image_hash.then(partial( - self.updateBuddy, buddy, obuddy.nick, obuddy.groups - )) + call(self.logger.debug, 'Image hash is %s', image_hash) + call(self.updateBuddy, buddy, obuddy.nick, obuddy.groups, image_hash) def onDlsuccess(self, path):