class PipeClient(PipeStream): def __init__(self): loop = evergreen.current.loop handle = pyuv.Pipe(loop._loop) super(PipeClient, self).__init__(handle) self._connect_result = None def connect(self, target): if self._connected: raise PipeError('already connected') self._connect_result = Result() try: self._handle.connect(target, self.__connect_cb) except pyuv.error.PipeError as e: raise PipeError(convert_errno(e.args[0]), e.args[1]) try: self._connect_result.wait() except PipeError: self.close() raise else: self._set_connected() finally: self._connect_result = None def __connect_cb(self, handle, error): if error is not None: self._connect_result.set_exception(PipeError(convert_errno(error), pyuv.errno.strerror(error))) else: self._connect_result.set_result(None)
def connect(self, target, source_address=None): if self._connected: raise TCPError('already connected') host, port = target try: r = socket.getaddrinfo(host, port, socket.AF_UNSPEC, socket.SOCK_STREAM) except socket.error as e: raise TCPError(e) if not r: raise TCPError('getaddrinfo returned no result') connect_result = Result() def cb(handle, error): if error is not None: connect_result.set_exception(TCPError(convert_errno(error), pyuv.errno.strerror(error))) else: connect_result.set_result(None) err = None loop = self._handle.loop for item in r: addr = item[-1] if '%' in addr[0]: # Skip addresses such as 'fe80::1%lo0' # TODO: handle this properly continue handle = pyuv.TCP(loop) try: if source_address: handle.bind(source_address) handle.connect(addr, cb) except pyuv.error.TCPError as e: err = TCPError(convert_errno(e.args[0]), e.args[1]) handle.close() continue try: connect_result.wait() except TCPError as e: err = e handle.close() connect_result.clear() continue else: self._handle.close() self._handle = handle break if err is not None: raise err self._set_connected()
def _read(self, n): read_result = Result() def cb(handle, data, error): self._handle.stop_read() if error is not None: if error != pyuv.errno.UV_EOF: read_result.set_exception(PipeError(convert_errno(error), pyuv.errno.strerror(error))) else: read_result.set_result(b'') else: read_result.set_result(data) try: self._handle.start_read(cb) except pyuv.error.PipeError as e: self.close() raise PipeError(convert_errno(e.args[0]), e.args[1]) try: data = read_result.wait() except PipeError as e: self.close() raise else: if not data: self.close() return self._read_buffer.feed(data)
def connect(self, target): if self._connected: raise PipeError('already connected') connect_result = Result() def cb(handle, error): if error is not None: connect_result.set_exception(PipeError(convert_errno(error), pyuv.errno.strerror(error))) else: connect_result.set_result(None) try: self._handle.connect(target, cb) except pyuv.error.PipeError as e: raise PipeError(convert_errno(e.args[0]), e.args[1]) try: connect_result.wait() except PipeError: self.close() raise else: self._set_connected()
class TCPClient(TCPStream): def __init__(self): loop = evergreen.current.loop handle = pyuv.TCP(loop._loop) super(TCPClient, self).__init__(handle) self._connect_result = None def connect(self, target, source_address=None): if self._connected: raise TCPError('already connected') # TODO: getaddrinfo if source_address: try: self._handle.bind(source_address) except pyuv.error.TCPError as e: raise TCPError(e.args[0], e.args[1]) try: self._handle.connect(target, self.__connect_cb) except pyuv.error.TCPError as e: raise TCPError(e.args[0], e.args[1]) self._connect_result = Result() try: self._connect_result.wait() except TCPError: self.close() raise else: self._set_connected() finally: self._connect_result = None def __connect_cb(self, handle, error): if error is not None: self._connect_result.set_exception(TCPError(error, pyuv.errno.strerror(error))) else: self._connect_result.set_result(None)
class TCPClient(TCPStream): def __init__(self): loop = evergreen.current.loop handle = pyuv.TCP(loop._loop) super(TCPClient, self).__init__(handle) self._connect_result = None def connect(self, target, source_address=None): if self._connected: raise TCPError('already connected') # TODO: getaddrinfo if source_address: try: self._handle.bind(source_address) except pyuv.error.TCPError as e: raise TCPError(e.args[0], e.args[1]) try: self._handle.connect(target, self.__connect_cb) except pyuv.error.TCPError as e: raise TCPError(e.args[0], e.args[1]) self._connect_result = Result() try: self._connect_result.wait() except TCPError: self.close() raise else: self._set_connected() finally: self._connect_result = None def __connect_cb(self, handle, error): if error is not None: self._connect_result.set_exception( TCPError(error, pyuv.errno.strerror(error))) else: self._connect_result.set_result(None)
class PipeStream(BaseStream): error_class = PipeError def __init__(self, handle): super(PipeStream, self).__init__() self._handle = handle self._read_result = Result() @property def readable(self): return self._handle.readable @property def writable(self): return self._handle.writable def _read(self, n): try: self._handle.start_read(self.__read_cb) except pyuv.error.PipeError as e: self.close() raise PipeError(convert_errno(e.args[0]), e.args[1]) try: data = self._read_result.wait() except PipeError as e: self.close() raise else: if not data: self.close() return self._read_buffer.feed(data) finally: self._read_result.clear() def _write(self, data): try: self._handle.write(data, self.__write_cb) except pyuv.error.PipeError as e: self.close() raise PipeError(convert_errno(e.args[0]), e.args[1]) def _close(self): self._handle.shutdown(self.__shutdown_cb) def __read_cb(self, handle, data, error): self._handle.stop_read() if error is not None: if error != pyuv.errno.UV_EOF: self._read_result.set_exception(PipeError(convert_errno(error), pyuv.errno.strerror(error))) else: self._read_result.set_result(b'') else: self._read_result.set_result(data) def __write_cb(self, handle, error): if error is not None: # TODO: save error? self.close() def __shutdown_cb(self, handle, error): self._handle.close()
class TTYStream(BaseStream): error_class = TTYError def __init__(self, fd, readable): super(TTYStream, self).__init__() loop = evergreen.current.loop self._handle = pyuv.TTY(loop._loop, fd, readable) self._read_result = Result() self._set_connected() @property def readable(self): return self._handle.readable @property def writable(self): return self._handle.writable @property def winsize(self): return self._handle.get_winsize() def set_mode(self, raw): self._handle.set_mode(raw) def _read(self, n): try: self._handle.start_read(self.__read_cb) except pyuv.error.TTYError as e: self.close() raise TTYError(e.args[0], e.args[1]) try: data = self._read_result.wait() except TTYError as e: self.close() raise else: if not data: self.close() return self._read_buffer.feed(data) finally: self._read_result.clear() def _write(self, data): try: self._handle.write(data, self.__write_cb) except pyuv.error.TTYError as e: self.close() raise TTYError(e.args[0], e.args[1]) def _close(self): self._handle.close() def __read_cb(self, handle, data, error): self._handle.stop_read() if error is not None: if error != pyuv.errno.UV_EOF: self._read_result.set_exception(TTYError(error, pyuv.errno.strerror(error))) else: self._read_result.set_result(b'') else: self._read_result.set_result(data) def __write_cb(self, handle, error): if error is not None: # TODO: store error? self.close()
class TTYStream(BaseStream): error_class = TTYError def __init__(self, fd, readable): super(TTYStream, self).__init__() loop = evergreen.current.loop self._handle = pyuv.TTY(loop._loop, fd, readable) self._read_result = Result() self._set_connected() @property def readable(self): return self._handle.readable @property def writable(self): return self._handle.writable @property def winsize(self): return self._handle.get_winsize() def set_mode(self, raw): self._handle.set_mode(raw) def _read(self, n): try: self._handle.start_read(self.__read_cb) except pyuv.error.TTYError as e: self.close() raise TTYError(e.args[0], e.args[1]) try: data = self._read_result.wait() except TTYError as e: self.close() raise else: if not data: self.close() return self._read_buffer.feed(data) finally: self._read_result.clear() def _write(self, data): try: self._handle.write(data, self.__write_cb) except pyuv.error.TTYError as e: self.close() raise TTYError(e.args[0], e.args[1]) def _close(self): self._handle.close() def __read_cb(self, handle, data, error): self._handle.stop_read() if error is not None: if error != pyuv.errno.UV_EOF: self._read_result.set_exception( TTYError(error, pyuv.errno.strerror(error))) else: self._read_result.set_result(b'') else: self._read_result.set_result(data) def __write_cb(self, handle, error): if error is not None: # TODO: store error? self.close()