diff --git a/weboob/bcall.py b/weboob/bcall.py index 476cc39b..727c9ef7 100644 --- a/weboob/bcall.py +++ b/weboob/bcall.py @@ -31,6 +31,9 @@ class CallErrors(Exception): Exception.__init__(self, "Several errors have been raised:\n%s" % ('\n'.join(['%s: %s' % (b, e) for b, e in errors]))) self.errors = copy(errors) + def __iter__(self): + return self.errors.__iter__() + class Result(object): def __init__(self, backend, result): self.backend = backend @@ -48,6 +51,11 @@ class Result(object): class BackendsCall(object): def __init__(self, backends, function, *args, **kwargs): + """ + @param backends list of backends to call + @param function backends' method name, or callable object + @param args, kwargs arguments given to called functions + """ # Store if a backend is finished self.backends = {} for backend in backends: @@ -69,9 +77,9 @@ class BackendsCall(object): with self.mutex: for b in backends: debug('New timer for %s' % b) - self.threads.append(Timer(0, self.caller, (b, function, args, kwargs)).start()) + self.threads.append(Timer(0, self._caller, (b, function, args, kwargs)).start()) - def caller(self, b, function, args, kwargs): + def _caller(self, b, function, args, kwargs): debug('Hello from timer %s' % b) with b: try: diff --git a/weboob/ouiboube.py b/weboob/ouiboube.py index e6530915..49bfaffd 100644 --- a/weboob/ouiboube.py +++ b/weboob/ouiboube.py @@ -93,16 +93,48 @@ class Weboob(object): return self.backends def iter_backends(self, caps=None): + """ + Iter on each backends. + + Note: each backend is locked when it is returned. + + @param caps Optional list of capabilities to select backends + @return iterator on selected backends. + """ for name, backend in self.backends.iteritems(): if caps is None or backend.has_caps(caps): with backend: yield backend def do(self, function, *args, **kwargs): + """ + Do calls on loaded backends with specified arguments, in separated + threads. + + This function has two modes: + - If 'function' is a string, it calls the method with this name on + each backends with the specified arguments; + - If 'function' is a callable, it calls it in a separated thread with + the locked backend instance at first arguments, and *args and + **kwargs. + + @param function backend's method name, or callable object + @return an iterator of results + """ backends = [b for b in self.iter_backends()] return BackendsCall(backends, function, *args, **kwargs) def do_caps(self, caps, function, *args, **kwargs): + """ + Do calls on loaded modules with the specified capabilities, in + separated threads. + + See also documentation of the 'do' method. + + @param caps list of caps or cap to select backends + @param function backend's method name, or callable object + @return an iterator of results + """ backends = [b for b in self.iter_backends(caps)] return BackendsCall(backends, function, *args, **kwargs)