예제 #1
0
def _GetPromiseAndFunctions():
  functions = {}
  def GeneratorFunction(resolve, reject):
    functions['resolve'] = resolve
    functions['reject'] = reject
  p = promise.Promise(GeneratorFunction)
  return (p, functions['resolve'], functions['reject'])
예제 #2
0
 def testGeneratorFunctionResolveToPromise(self):
   (p1, resolve, _) = _GetPromiseAndFunctions()
   p2 = promise.Promise(lambda x, y: x(p1))
   self.assertEquals(p2.state, promise.Promise.STATE_PENDING)
   p2.Then(self._AddToAccumulated)
   resolve(promise.Promise.Resolve(0))
   self.assertEquals(self.accumulated, [0])
예제 #3
0
def CopyFromDataPipe(data_pipe, deadline):
    """
  Returns a Promise that operates as follows:
  - If |data_pipe| is successfully read from, the promise resolves with the
    bytes that were read.
  - Otherwise, the promise rejects with an exception whose message contains the
    status from the attempted read.
  """
    class DataPipeCopyHelper():
        def __init__(self, data_pipe, deadline, resolve, reject):
            self.data_pipe = data_pipe
            self.original_deadline = deadline
            self.start_time = mojo_system.GetTimeTicksNow()
            self.resolve = resolve
            self.reject = reject
            self.buffer_size = 1024
            self.data = bytearray(self.buffer_size)
            self.index = 0

        def _ComputeCurrentDeadline(self):
            if self.original_deadline == mojo_system.DEADLINE_INDEFINITE:
                return self.original_deadline
            elapsed_time = mojo_system.GetTimeTicksNow() - self.start_time
            return max(0, self.original_deadline - elapsed_time)

        def CopyFromDataPipeAsync(self, result):
            while result == mojo_system.RESULT_OK:
                assert self.index <= len(self.data)
                if self.index == len(self.data):
                    self.buffer_size *= 2
                    self.data.extend(itertools.repeat(0, self.buffer_size))

                # Careful! Have to construct a memoryview object here as otherwise the
                # slice operation will create a copy of |data| and hence not write into
                # |data| as desired.
                result, read_bytes = self.data_pipe.ReadData(
                    memoryview(self.data)[self.index:])
                if read_bytes:
                    self.index += len(read_bytes)
                del read_bytes

            if result == mojo_system.RESULT_SHOULD_WAIT:
                data_pipe.AsyncWait(mojo_system.HANDLE_SIGNAL_READABLE,
                                    self._ComputeCurrentDeadline(),
                                    self.CopyFromDataPipeAsync)
                return

            # Treat a failed precondition as EOF.
            if result == mojo_system.RESULT_FAILED_PRECONDITION:
                self.resolve(self.data[:self.index])
                return

            self.reject(DataPipeCopyException("Result: %d" % result))

    def GenerationMethod(resolve, reject):
        helper = DataPipeCopyHelper(data_pipe, deadline, resolve, reject)
        helper.CopyFromDataPipeAsync(mojo_system.RESULT_OK)

    return promise.Promise(GenerationMethod)
예제 #4
0
    def _Call(self, *args, **kwargs):
        def GenerationMethod(resolve, reject):
            message = _GetMessage(method, flags, None, *args, **kwargs)
            if method.response_struct:

                def Accept(message):
                    try:
                        assert message.header.message_type == method.ordinal
                        payload = message.payload
                        response = method.response_struct.Deserialize(
                            serialization.RootDeserializationContext(
                                payload.data, payload.handles))
                        as_dict = response.AsDict()
                        if len(as_dict) == 1:
                            value = as_dict.values()[0]
                            if not isinstance(value, dict):
                                response = value
                        resolve(response)
                        return True
                    except Exception as e:
                        # Adding traceback similarly to python 3.0 (pep-3134)
                        e.__traceback__ = sys.exc_info()[2]
                        reject(e)
                        return False
                    finally:
                        self._error_handler.RemoveCallback(reject)

                self._error_handler.AddCallback(reject)
                if not self._router.AcceptWithResponder(
                        message, messaging.ForwardingMessageReceiver(Accept)):
                    self._error_handler.RemoveCallback(reject)
                    reject(
                        messaging.MessagingException(
                            "Unable to send message."))
            else:
                if (self._router.Accept(message)):
                    resolve(None)
                else:
                    reject(
                        messaging.MessagingException(
                            "Unable to send message."))

        return promise.Promise(GenerationMethod)