Example #1
0
    def __init__(self, sysname):
        self._sysname = sysname
        self.ready = Event()

        # exchange/queues/bindings
        self._exchanges = {}  # names -> { subscriber, topictrie(queue name) }
        self._queues = {}  # names -> gevent queue
        self._bindings_by_queue = defaultdict(
            list)  # queue name -> [(ex, binding)]
        self._lock_declarables = coros.RLock(
        )  # exchanges, queues, bindings, routing method

        # consumers
        self._consumers = defaultdict(
            list)  # queue name -> [ctag, channel._on_deliver]
        self._consumers_by_ctag = {}  # ctag -> queue_name ??
        self._ctag_pool = IDPool()  # pool of consumer tags
        self._lock_consumers = coros.RLock(
        )  # lock for interacting with any consumer related attrs

        # deliveries
        self._unacked = {}  # dtag -> (ctag, msg)
        self._lock_unacked = coros.RLock(
        )  # lock for interacting with unacked field

        self._gl_msgs = None
        self._gl_pool = Pool()
        self.gl_ioloop = None

        self.errors = []
Example #2
0
 def attach_transport(self, transport):
     """
     Attaches a bound transport and indicates this channel is now open.
     """
     self._transport = transport
     self._lock = coros.RLock()
     self._fsm.process(self.I_ATTACH)
Example #3
0
    def __init__(self):
        self.client = None
        self.running = False
        self.ready = event.Event()
        self._lock = coros.RLock()

        self.interceptors = {}  # endpoint interceptors
Example #4
0
 def __init__(self, sock, address):
     sock.setsockopt(socket.IPPROTO_TCP, socket.TCP_NODELAY, 1)
     self.sock = sock
     self.sockfile = sock.makefile()
     self.writelock = coros.RLock()
     self.address = address
     self.link_state = 'connected'  # or disconnected
Example #5
0
    def __init__(self):
        self.deleted_keys = []
        self.aborted_keys = []
        self.exc = None

        # Protect exc, since some paths test it and then use it, which
        # can run afoul race conditions.
        self._exc_protect = coros.RLock()
Example #6
0
    def __init__(self, sock, address):
        sock.setsockopt(socket.IPPROTO_TCP, socket.TCP_NODELAY, 1)
        sock.read = sock.recv
        sock.write = sock.sendall

        self.sock = sock
        self.unpacker = msgpack.Unpacker(sock, encoding='utf-8')
        self.writelock = coros.RLock()
        self.address = address
        self.link_state = 'connected'  # or disconnected
        self.recv_buf = deque()
Example #7
0
    def __init__(self):
        log.debug("In NodeB.__init__")
        self.ready = event.Event()
        self._lock = coros.RLock()
        self._pool = IDPool()
        self._bidir_pool = {
        }  # maps inactive/active our numbers (from self._pool) to channels
        self._pool_map = {
        }  # maps active pika channel numbers to our numbers (from self._pool)

        amqp.Node.__init__(self)
Example #8
0
    def __init__(self,
                 host='127.0.0.1',
                 port=4212,
                 password='******',
                 connect_timeout=5,
                 result_timeout=5,
                 out_port=8081):
        # Receive buffer
        self._recvbuffer = None
        # Output port
        self._out_port = out_port
        # VLC socket
        self._socket = None
        # Result timeout
        self._resulttimeout = result_timeout
        # Shutting down flag
        self._shuttingDown = gevent.event.Event()
        # Authentication done event
        self._auth = gevent.event.AsyncResult()
        # Request lock
        self._resultlock = coros.RLock()
        # Request result
        self._result = gevent.event.AsyncResult()
        # VLC version string
        self._vlcver = None
        # Saving password
        self._password = password

        # Logger
        logger = logging.getLogger('VlcClient_init')

        # Making connection
        try:
            self._socket = telnetlib.Telnet(host, port, connect_timeout)
            logger.debug("Successfully connected with VLC socket!")
        except Exception as e:
            raise VlcException(
                "Socket creation error! VLC is not running? ERROR: " + repr(e))

        # Spawning recvData greenlet
        gevent.spawn(self._recvData)
        gevent.sleep()

        # Waiting for authentication event
        try:
            if self._auth.get(timeout=self._resulttimeout) == False:
                errmsg = "Authentication error"
                logger.error(errmsg)
                raise VlcException(errmsg)
        except gevent.Timeout:
            errmsg = "Authentication timeout"
            logger.error(errmsg)
            raise VlcException(errmsg)
Example #9
0
class RPCRequestEndpointUnit(RequestEndpointUnit):
    def _send(self, msg, headers=None, **kwargs):
        log.info("MESSAGE SEND [S->D] RPC: %s" % str(msg))

        try:
            res, res_headers = RequestEndpointUnit._send(self,
                                                         msg,
                                                         headers=headers,
                                                         **kwargs)
        except exception.Timeout:
            self._sample_request(-1, 'Timeout', msg, headers, '', {})
            raise

        # possibly sample before we do any raising
        self._sample_request(res_headers['status_code'],
                             res_headers['error_message'], msg, headers, res,
                             res_headers)

        # Check response header
        if res_headers["status_code"] != 200:
            log.debug("RPCRequestEndpointUnit received an error (%d): %s",
                      res_headers['status_code'], res_headers['error_message'])
            self._raise_exception(res_headers["status_code"],
                                  res_headers["error_message"])

        return res, res_headers

    def _sample_request(self, status, status_descr, msg, headers, response,
                        response_headers):
        """
        Performs sFlow sampling of a completed/errored RPC request (if configured to).

        Makes two calls:
        1) get_sflow_manager (overridden at process level)
        2) make sample dict (the kwargs to sflow_manager.transaction, may be overridden where appropriate)

        Then performs the transact call if the manager says to do so.
        """
        if CFG.container.get('sflow', {}).get('enabled', False):
            sm = self._get_sflow_manager()
            if sm and sm.should_sample:
                app_name = self._get_sample_name()
                try:
                    trans_kwargs = self._build_sample(app_name, status,
                                                      status_descr, msg,
                                                      headers, response,
                                                      response_headers)
                    sm.transaction(**trans_kwargs)
                except Exception:
                    log.exception("Could not sample, ignoring")

            else:
                log.debug(
                    "No SFlowManager or it told us not to sample this transaction"
                )

    def _get_sample_name(self):
        """
        Gets the app_name that should be used for the sample.

        Typically this would be a process id.
        """
        # at the rpc level we really don't know, we're not a process.
        return "unknown-rpc-client"

    def _get_sflow_manager(self):
        """
        Finds the sFlow manager that should be used.
        """
        # at this level, we don't have any ref back to the container other than the singleton
        from pyon.container.cc import Container
        if Container.instance:
            return Container.instance.sflow_manager

        return None

    def _build_sample(self, name, status, status_descr, msg, headers, response,
                      response_headers):
        """
        Builds a transaction sample.

        Should return a dict in the form of kwargs to be passed to SFlowManager.transaction.
        """
        # build args to pass to transaction
        extra_attrs = {
            'conv-id': headers.get('conv-id', ''),
            'service': response_headers.get('sender-service', '')
        }

        cur_time_ms = int(time.time() * 1000)
        time_taken = (cur_time_ms - int(headers.get(
            'ts', cur_time_ms))) * 1000  # sflow wants microseconds!

        # build op name: typically sender-service.op, or falling back to sender.op
        op_first = response_headers.get(
            'sender-service',
            response_headers.get('sender', headers.get('receiver', '')))
        if "," in op_first:
            op_first = op_first.rsplit(',', 1)[-1]

        op = ".".join((op_first, headers.get('op', 'unknown')))

        # status code map => ours to sFlow (defaults to 3 aka INTERNAL_ERROR)
        status = SFlowManager.status_map.get(status, 3)

        sample = {
            'app_name': name,
            'op': op,
            'attrs': extra_attrs,
            'status_descr': status_descr,
            'status': str(status),
            'req_bytes': len(str(msg)),
            'resp_bytes': len(str(response)),
            'uS': time_taken,
            'initiator': headers.get('sender', ''),
            'target': headers.get('receiver', '')
        }

        return sample

    conv_id_counter = 0
    _lock = coros.RLock()  # @TODO: is this safe?
    _conv_id_root = None

    def _build_conv_id(self):
        """
        Builds a unique conversation id based on the container name.
        """
        with RPCRequestEndpointUnit._lock:
            RPCRequestEndpointUnit.conv_id_counter += 1

            if not RPCRequestEndpointUnit._conv_id_root:
                # set default to use uuid-4, similar to what we'd get out of the container id anyway
                RPCRequestEndpointUnit._conv_id_root = str(uuid.uuid4())[0:6]

                # try to get the real one from the container, but do it safely
                try:
                    from pyon.container.cc import Container
                    if Container.instance and Container.instance.id:
                        RPCRequestEndpointUnit._conv_id_root = Container.instance.id
                except:
                    pass

        return "%s-%d" % (RPCRequestEndpointUnit._conv_id_root,
                          RPCRequestEndpointUnit.conv_id_counter)

    def _build_header(self, raw_msg):
        """
        Build header override.

        This should set header values that are invariant or have nothing to do with the specific
        call being made (such as op).
        """
        headers = RequestEndpointUnit._build_header(self, raw_msg)
        headers['protocol'] = 'rpc'
        headers[
            'conv-seq'] = 1  # @TODO will not work well with agree/status etc
        headers['conv-id'] = self._build_conv_id()
        headers['language'] = 'ion-r2'
        headers['encoding'] = 'msgpack'
        headers['format'] = raw_msg.__class__.__name__  # hmm
        headers['reply-by'] = 'todo'  # clock sync is a problem

        return headers

    def _raise_exception(self, code, message):
        if str(code) in exception_map:
            raise exception_map[str(code)](message)
        else:
            log.debug("Raising ServerError")
            raise ServerError(message)