Пример #1
0
    def test_eq(self):
        q1 = Queue('xxx', Exchange('xxx', 'direct'), 'xxx')
        q2 = Queue('xxx', Exchange('xxx', 'direct'), 'xxx')
        self.assertEqual(q1, q2)
        self.assertFalse(q1.__eq__(True))

        q3 = Queue('yyy', Exchange('xxx', 'direct'), 'xxx')
        self.assertNotEqual(q1, q3)
Пример #2
0
 def test_declare(self):
     chan = get_conn().channel()
     b = Queue('foo', self.exchange, 'foo', channel=chan)
     self.assertTrue(b.is_bound)
     b.declare()
     self.assertIn('exchange_declare', chan)
     self.assertIn('queue_declare', chan)
     self.assertIn('queue_bind', chan)
Пример #3
0
 def test_declare(self):
     chan = Channel()
     b = Queue("foo", self.exchange, "foo", channel=chan)
     self.assertTrue(b.is_bound)
     b.declare()
     self.assertIn("exchange_declare", chan)
     self.assertIn("queue_declare", chan)
     self.assertIn("queue_bind", chan)
Пример #4
0
    def test_eq(self):
        q1 = Queue("xxx", Exchange("xxx", "direct"), "xxx")
        q2 = Queue("xxx", Exchange("xxx", "direct"), "xxx")
        self.assertEqual(q1, q2)
        self.assertFalse(q1.__eq__(True))

        q3 = Queue("yyy", Exchange("xxx", "direct"), "xxx")
        self.assertNotEqual(q1, q3)
Пример #5
0
class MessConsumer(object):
    def __init__(self, mess, connection, name, exchange_name):
        self._mess = mess
        self._conn = connection
        self._name = name

        self._exchange = Exchange(name=exchange_name, type='topic',
                durable=False, auto_delete=True) #TODO parameterize

        self._channel = None
        self._ops = {}

        self.connect()

    def connect(self):
        self._channel = self._conn.channel()

        self._queue = Queue(channel=self._channel, name=self._name,
                exchange=self._exchange, routing_key=self._name)
        self._queue.declare()

        self._consumer = Consumer(self._channel, [self._queue],
                callbacks=[self._callback])
        self._consumer.consume()

    def consume(self):
        while True:
            self._conn.drain_events()

    def _callback(self, body, message):
        reply_to = message.headers.get('reply-to')

        #TODO error handling for message format
        op = body['op']
        args = body['args']
        kwargs = body['kwargs']

        #TODO error handling for unknown op
        op_fun = self._ops[op]

        ret, err = None, None
        try:
            ret = op_fun(*args, **kwargs)
        except Exception:
            err = sys.exc_info()
        finally:
            if reply_to:
                if err:
                    tb = traceback.format_exception(*err)
                    err = (err[0].__name__, str(err[1]), tb)
                reply = dict(result=ret, error=err)
                self._mess.reply(reply_to, reply)

            message.ack()

    def add_op(self, name, fun):
        self._ops[name] = fun
Пример #6
0
 def test_also_binds_exchange(self):
     chan = Channel()
     b = Queue("foo", self.exchange)
     self.assertFalse(b.is_bound)
     self.assertFalse(b.exchange.is_bound)
     b = b.bind(chan)
     self.assertTrue(b.is_bound)
     self.assertTrue(b.exchange.is_bound)
     self.assertIs(b.channel, b.exchange.channel)
     self.assertIsNot(b.exchange, self.exchange)
Пример #7
0
    def _connect(self, channel):
        self._queue = Queue(channel=channel, **self._queue_kwargs)
        self._queue.declare()

        self._consumer = Consumer(channel, [self._queue],
            callbacks=[self._callback])
        self._consumer.consume()
Пример #8
0
    def connect(self):
        self._channel = self._conn.channel()

        self._queue = Queue(channel=self._channel, name=self._name,
                exchange=self._exchange, routing_key=self._name)
        self._queue.declare()

        self._consumer = Consumer(self._channel, [self._queue],
                callbacks=[self._callback])
        self._consumer.consume()
Пример #9
0
    def call(self, name, op, *args, **kwargs):
        # create a direct exchange and queue for the reply
        # TODO probably better to pool these or something?
        msg_id = uuid.uuid4().hex
        exchange = Exchange(name=msg_id, type='direct',
                durable=False, auto_delete=True) #TODO parameterize

        # check out a connection from the pool
        with connections[self._conn].acquire(block=True) as conn:
            channel = conn.channel()
            queue = Queue(channel=channel, name=msg_id, exchange=exchange,
                    routing_key=msg_id, exclusive=True, durable=False,
                    auto_delete=True)
            queue.declare()

            # I think this can be done without gevent directly, but need to
            # learn more about kombu first

            messages = []

            def _callback(body, message):
                messages.append(body)
                message.ack()

            consumer = Consumer(channel=channel, queues=[queue],
                callbacks=[_callback])

            d = dict(op=op, args=args, kwargs=kwargs)
            headers = {'reply-to' : msg_id}

            with producers[self._conn].acquire(block=True) as producer:
                producer.publish(d, routing_key=name, headers=headers)

            with consumer:
                # only expecting one event
                conn.drain_events()

            msg_body = messages[0]
            if msg_body.get('error'):
                raise Exception(*msg_body['error'])
            else:
                return msg_body.get('result')
Пример #10
0
 def test___enter____exit__(self):
     channel = self.connection.channel()
     queue = Queue("qname", self.exchange, "rkey")
     consumer = Consumer(channel, queue, auto_declare=True)
     context = consumer.__enter__()
     self.assertIs(context, consumer)
     self.assertTrue(consumer._active_tags)
     res = consumer.__exit__(None, None, None)
     self.assertFalse(res)
     self.assertIn("basic_cancel", channel)
     self.assertFalse(consumer._active_tags)
Пример #11
0
    def test_basic_reject__requeue(self):
        channel = self.connection.channel()
        b1 = Queue('qname1', self.exchange, 'rkey')
        consumer = Consumer(channel, [b1])

        def callback(message_data, message):
            message.requeue()

        consumer.register_callback(callback)
        consumer._receive_callback({'foo': 'bar'})
        self.assertIn('basic_reject:requeue', channel)
Пример #12
0
    def test_basic_reject__requeue(self):
        channel = self.connection.channel()
        b1 = Queue("qname1", self.exchange, "rkey")
        consumer = Consumer(channel, [b1])

        def callback(message_data, message):
            message.requeue()

        consumer.register_callback(callback)
        consumer._receive_callback({"foo": "bar"})
        self.assertIn("basic_reject:requeue", channel)
Пример #13
0
    def connect(self):
        self._channel = self._conn.channel()

        self._queue = Queue(channel=self._channel, name=self._name,
                exchange=self._exchange, routing_key=self._name,
                durable=self._dashi.durable,
                auto_delete=self._dashi.auto_delete)
        self._queue.declare()

        self._consumer = Consumer(self._channel, [self._queue],
                callbacks=[self._callback])
        self._consumer.consume()
Пример #14
0
    def test_basic_ack_twice(self):
        channel = self.connection.channel()
        b1 = Queue("qname1", self.exchange, "rkey")
        consumer = Consumer(channel, [b1])

        def callback(message_data, message):
            message.ack()
            message.ack()

        consumer.register_callback(callback)
        with self.assertRaises(MessageStateError):
            consumer._receive_callback({"foo": "bar"})
Пример #15
0
 def __init__(self, connection, handlers=None, routing_key="#",
         node_id=None, app=None):
     self.app = app_or_default(app)
     self.connection = connection
     if handlers is not None:
         self.handlers = handlers
     self.routing_key = routing_key
     self.node_id = node_id or gen_unique_id()
     self.queue = Queue("%s.%s" % ("celeryev", self.node_id),
                        exchange=event_exchange,
                        routing_key=self.routing_key,
                        auto_delete=True,
                        durable=False)
Пример #16
0
    def test_basic_reject_twice(self):
        channel = self.connection.channel()
        b1 = Queue('qname1', self.exchange, 'rkey')
        consumer = Consumer(channel, [b1])

        def callback(message_data, message):
            message.reject()
            message.reject()

        consumer.register_callback(callback)
        with self.assertRaises(MessageStateError):
            consumer._receive_callback({'foo': 'bar'})
        self.assertIn('basic_reject', channel)
Пример #17
0
def worker_direct(hostname):
    """Returns :class:`kombu.Queue` that is a direct route to
    a worker by hostname.

    :param hostname: The fully qualified node name of a worker
                     (e.g. ``[email protected]``).  If passed a
                     :class:`kombu.Queue` instance it will simply return
                     that instead.
    """
    if isinstance(hostname, Queue):
        return hostname
    return Queue(WORKER_DIRECT_QUEUE_FORMAT.format(hostname=hostname),
                 WORKER_DIRECT_EXCHANGE,
                 hostname, auto_delete=True)
Пример #18
0
    def getCabbage(self):
        connectUri = CabbageHolder._getConnectUri()
        work = CacheHolder.getCache().get(HOST_NAME, WORKS)
        if work.queues and len(work.queues) > 0:
            queues = []
            for queueName in work.queues:
                brokerQueue = StoreHolder.getStore().getQueue(queueName)
                queues.append(
                    Queue(name=brokerQueue.queueName,
                          exchange=Exchange(brokerQueue.exchangeName),
                          routing_key=brokerQueue.routingKey))
            celeryconfig.CELERY_QUEUES = tuple(queues)

        return Cabbage(broker=str(connectUri))
Пример #19
0
 def setUp(self):
     try:
         data_folder_in = tempfile.mkdtemp()
         data_folder_out = tempfile.mkdtemp()
     except Exception:
         raise SkipTest('filesystem transport: cannot create tempfiles')
     self.c = Connection(transport='filesystem',
                         transport_options={
                             'data_folder_in': data_folder_in,
                             'data_folder_out': data_folder_out,
                         })
     self.p = Connection(transport='filesystem',
                         transport_options={
                             'data_folder_in': data_folder_out,
                             'data_folder_out': data_folder_in,
                         })
     self.e = Exchange('test_transport_filesystem')
     self.q = Queue('test_transport_filesystem',
                    exchange=self.e,
                    routing_key='test_transport_filesystem')
     self.q2 = Queue('test_transport_filesystem2',
                     exchange=self.e,
                     routing_key='test_transport_filesystem2')
Пример #20
0
 def __init__(self, connection, handlers=None, routing_key="#",
         node_id=None, app=None, queue_prefix="celeryev"):
     self.app = app_or_default(app)
     self.connection = connection
     if handlers is not None:
         self.handlers = handlers
     self.routing_key = routing_key
     self.node_id = node_id or uuid()
     self.queue_prefix = queue_prefix
     self.queue = Queue('.'.join([self.queue_prefix, self.node_id]),
                        exchange=event_exchange,
                        routing_key=self.routing_key,
                        auto_delete=True,
                        durable=False)
Пример #21
0
    def test_declare_but_no_exchange(self):
        q = Queue('a')
        q.queue_declare = Mock()
        q.queue_bind = Mock()
        q.exchange = None

        q.declare()
        q.queue_declare.assert_called_with(False, passive=False)
        q.queue_bind.assert_called_with(False)
Пример #22
0
def worker_direct(hostname):
    """Return the :class:`kombu.Queue` being a direct route to a worker.

    Arguments:
        hostname (str, ~kombu.Queue): The fully qualified node name of
            a worker (e.g., ``[email protected]``).  If passed a
            :class:`kombu.Queue` instance it will simply return
            that instead.
    """
    if isinstance(hostname, Queue):
        return hostname
    return Queue(
        WORKER_DIRECT_QUEUE_FORMAT.format(hostname=hostname),
        WORKER_DIRECT_EXCHANGE,
        hostname,
    )
Пример #23
0
    def test_on_decode_error_callback(self):
        channel = self.connection.channel()
        b1 = Queue("qname1", self.exchange, "rkey")
        thrown = []

        def on_decode_error(msg, exc):
            thrown.append((msg.body, exc))

        consumer = Consumer(channel, [b1], on_decode_error=on_decode_error)
        consumer.channel.throw_decode_error = True
        consumer._receive_callback({"foo": "bar"})

        self.assertTrue(thrown)
        m, exc = thrown[0]
        self.assertEqual(anyjson.loads(m), {"foo": "bar"})
        self.assertIsInstance(exc, ValueError)
Пример #24
0
class Worker(ConsumerMixin):
    task_queue = Queue('xadmin-notify', Exchange(name='xnotify', type='fanout'), routing_key='xnotify')

    def __init__(self, app):
        self._app = app
        self.logger = app.logger
        self.connection = celery_app.connection_for_read()

    def get_consumers(self, Consumer, channel):
        return [Consumer(queues=[self.task_queue],
                         callbacks=[self.on_event])]

    def on_event(self, body, message):
        # print('Got task: {0!r}'.format(body))
        # type_, data = json.loads(body)
        type_, data = body
        if type_.startswith('job-'):
            self._on_job(type_, data)
        message.ack()

    def _on_job(self, type_, data):
        self.logger.info('Received: %s - %s', type_, data)
        obj = Job.objects.filter(alias=data['job']).first()
        # print('Job =>', obj)
        if obj.last_batch_id != data['batch_id']:
            # print('!!last_batch_id==', obj.last_batch_id)
            if obj.type == 0:
                return
            elif obj.type == 1:
                obj.last_batch_id = data['batch_id']

        job = JobAction(obj.project.alias, obj.alias, obj.last_batch_id)
        if type_ == 'job-finished':  # job-finished
            r = job.stop()
            obj.status = obj.status & 0xf0 | STATUS_STOP
        elif type_ == 'job-pause':
            r = job.pause()
            obj.status = obj.status & 0xf0 | STATUS_PAUSE
        elif type_ == 'job-started':
            if obj.type == 0:
                return
            elif obj.type == 1:
                obj.status = obj.status & 0xf0 | STATUS_START
        obj.save()

    def stop(self):
        self.should_stop = True
Пример #25
0
    def connect(self):

        self._channel = self._conn.channel()

        if self._sysname is not None:
            name = "%s.%s" % (self._sysname, self._name)
        else:
            name = self._name
        self._queue = Queue(channel=self._channel, name=name,
                exchange=self._exchange, routing_key=name,
                durable=self._dashi.durable,
                auto_delete=self._dashi.auto_delete)
        self._queue.declare()

        self._consumer = Consumer(self._channel, [self._queue],
                callbacks=[self._callback])
        self._consumer.consume()
Пример #26
0
    def test_receive_callback(self):
        channel = self.connection.channel()
        b1 = Queue('qname1', self.exchange, 'rkey')
        consumer = Consumer(channel, [b1])
        received = []

        def callback(message_data, message):
            received.append(message_data)
            message.ack()
            message.payload     # trigger cache

        consumer.register_callback(callback)
        consumer._receive_callback({u'foo': u'bar'})

        self.assertIn('basic_ack', channel)
        self.assertIn('message_to_python', channel)
        self.assertEqual(received[0], {u'foo': u'bar'})
Пример #27
0
 def testUrl(self):
     client = KombuClient(
         url=
         "amqp://*****:*****@172.16.4.134:5672/cabbage_vhost"
     )
     conn = client.conn
     conn.connect()
     video_queue = Queue('hdfs',
                         exchange=Exchange("hdfs"),
                         routing_key='hdfs')
     with conn.Consumer(video_queue,
                        callbacks=[process_media],
                        accept=['json', 'pickle', 'msgpack',
                                'yaml']) as consumer:
         # Process messages and handle events on all channels
         while True:
             conn.drain_events()
Пример #28
0
    def test_receive_callback(self):
        channel = self.connection.channel()
        b1 = Queue("qname1", self.exchange, "rkey")
        consumer = Consumer(channel, [b1])
        received = []

        def callback(message_data, message):
            received.append(message_data)
            message.ack()
            message.payload  # trigger cache

        consumer.register_callback(callback)
        consumer._receive_callback({u"foo": u"bar"})

        self.assertIn("basic_ack", channel)
        self.assertIn("message_to_python", channel)
        self.assertEqual(received[0], {u"foo": u"bar"})
Пример #29
0
    def test_manual_declare(self):
        channel = self.connection.channel()
        queue = Queue("qname", self.exchange, "rkey")
        consumer = Consumer(channel, queue, auto_declare=False)
        self.assertIsNot(consumer.queues[0], queue)
        self.assertTrue(consumer.queues[0].is_bound)
        self.assertTrue(consumer.queues[0].exchange.is_bound)
        self.assertIsNot(consumer.queues[0].exchange, self.exchange)

        for meth in ("exchange_declare", "queue_declare", "basic_consume"):
            self.assertNotIn(meth, channel)

        consumer.declare()
        for meth in ("exchange_declare", "queue_declare", "queue_bind"):
            self.assertIn(meth, channel)
        self.assertNotIn("basic_consume", channel)

        consumer.consume()
        self.assertIn("basic_consume", channel)
Пример #30
0
    def test_auto_declare(self):
        channel = self.connection.channel()
        queue = Queue("qname", self.exchange, "rkey")
        consumer = Consumer(channel, queue, auto_declare=True)
        consumer.consume()
        consumer.consume()  # twice is a noop
        self.assertIsNot(consumer.queues[0], queue)
        self.assertTrue(consumer.queues[0].is_bound)
        self.assertTrue(consumer.queues[0].exchange.is_bound)
        self.assertIsNot(consumer.queues[0].exchange, self.exchange)

        for meth in ("exchange_declare", "queue_declare", "queue_bind",
                     "basic_consume"):
            self.assertIn(meth, channel)
        self.assertEqual(channel.called.count("basic_consume"), 1)
        self.assertTrue(consumer._active_tags)

        consumer.cancel_by_queue(queue.name)
        consumer.cancel_by_queue(queue.name)
        self.assertFalse(consumer._active_tags)
    def _initJobs(self, cabbage):
        store = StoreHolder.getRetryStore()
        jobs = store.getJobs()
        work = store.getWork(HOST_NAME)
        queues = work.queues
        routes = {}
        queues_celery = []
        for que in queues:
            que = store.getQueue(que)
            queues_celery.append(
                Queue(que.queueName,
                      Exchange(que.queueName),
                      routing_key=que.queueName,
                      queue_arguments={'x-max-priority': int(que.priority)}))

        for job in jobs:
            if job.status != JOB_DELETE and job.brokerQueue in queues:

                #fixbug 动态扩容时,缓存JOB
                if not CacheHolder.getCache().hasKey(job.jobId, JOBS):
                    CacheHolder.getCache().put(job.jobId, job, JOBS)

                clientDir = ConfigHolder.getConfig().getProperty(
                    BASE, CLIENT_FILE_DIRECTORY)
                path = clientDir + "/" + job.jobId
                if not os.path.isdir(path):
                    # @FIX BUG  文件不同步
                    syncJob(job.jobId, store)

                self.addScriptJobId(job.jobId, cabbage)

                for taskName in job.tasks:
                    que = store.getQueue(job.brokerQueue)
                    routes[taskName] = {
                        'queue': que.queueName,
                        'routing_key': que.routingKey
                    }

        log.info(routes)
        celeryconfig.CELERY_QUEUES = tuple(queues_celery)
        celeryconfig.CELERY_ROUTES = routes
Пример #32
0
    def test_manual_declare(self):
        channel = self.connection.channel()
        queue = Queue('qname', self.exchange, 'rkey')
        consumer = Consumer(channel, queue, auto_declare=False)
        self.assertIsNot(consumer.queues[0], queue)
        self.assertTrue(consumer.queues[0].is_bound)
        self.assertTrue(consumer.queues[0].exchange.is_bound)
        self.assertIsNot(consumer.queues[0].exchange, self.exchange)

        for meth in ('exchange_declare',
                     'queue_declare',
                     'basic_consume'):
            self.assertNotIn(meth, channel)

        consumer.declare()
        for meth in ('exchange_declare',
                     'queue_declare',
                     'queue_bind'):
            self.assertIn(meth, channel)
        self.assertNotIn('basic_consume', channel)

        consumer.consume()
        self.assertIn('basic_consume', channel)
Пример #33
0
 def test_as_dict(self):
     q = Queue("foo", self.exchange, "rk")
     d = q.as_dict(recurse=True)
     self.assertEqual(d["exchange"]["name"], self.exchange.name)
Пример #34
0
 def test_unbind(self):
     b = Queue("foo", self.exchange, "foo", channel=get_conn().channel())
     b.unbind()
     self.assertIn("queue_unbind", b.channel)
Пример #35
0
 def test_delete(self):
     b = Queue("foo", self.exchange, "foo", channel=get_conn().channel())
     b.delete()
     self.assertIn("queue_delete", b.channel)
Пример #36
0
 def test_cancel(self):
     b = Queue("foo", self.exchange, "foo", channel=get_conn().channel())
     b.cancel("fifafo")
     self.assertIn("basic_cancel", b.channel)
Пример #37
0
class DashiConsumer(object):
    def __init__(self, dashi, connection, name, exchange, sysname=None):
        self._dashi = dashi
        self._conn = connection
        self._name = name
        self._exchange = exchange
        self._sysname = sysname

        self._channel = None
        self._ops = {}
        self._cancelled = False
        self._consumer_lock = threading.Lock()
        self._last_heartbeat_check = datetime.min

        self.connect()

    def connect(self):

        self._channel = self._conn.channel()

        if self._sysname is not None:
            name = "%s.%s" % (self._sysname, self._name)
        else:
            name = self._name
        self._queue = Queue(channel=self._channel, name=name,
                exchange=self._exchange, routing_key=name,
                durable=self._dashi.durable,
                auto_delete=self._dashi.auto_delete)
        self._queue.declare()

        self._consumer = Consumer(self._channel, [self._queue],
                callbacks=[self._callback])
        self._consumer.consume()

    def disconnect(self):
        self._consumer.cancel()
        self._channel.close()
        self._conn.release()

    def consume(self, count=None, timeout=None):

        # hold a lock for the duration of the consuming. this prevents
        # multiple consumers and allows cancel to detect when consuming
        # has ended.
        if not self._consumer_lock.acquire(False):
            raise Exception("only one consumer thread may run concurrently")

        try:
            if count:
                i = 0
                while i < count and not self._cancelled:
                    self._consume_one(timeout)
                    i += 1
            else:
                while not self._cancelled:
                    self._consume_one(timeout)
        finally:
            self._consumer_lock.release()
            self._cancelled = False

    def _consume_one(self, timeout=None):

        # do consuming in a busy-ish loop, checking for cancel. There doesn't
        # seem to be an easy way to interrupt drain_events other than the
        # timeout. This could probably be added to kombu if needed. In
        # practice cancellation is likely infrequent (except in tests) so this
        # should hold for now. Can use a long timeout for production and a
        # short one for tests.

        inner_timeout = self._dashi.consumer_timeout
        elapsed = 0

        # keep trying until a single event is drained or timeout hit
        while not self._cancelled:

            self.heartbeat()

            try:
                self._conn.drain_events(timeout=inner_timeout)
                break

            except socket.timeout:
                if timeout:
                    elapsed += inner_timeout
                    if elapsed >= timeout:
                        raise

                    if elapsed + inner_timeout > timeout:
                        inner_timeout = timeout - elapsed

    def heartbeat(self):
        if self._dashi._heartbeat_interval is None:
            return

        time_between_tics = timedelta(seconds=self._dashi._heartbeat_interval / 2)

        if self._dashi.consumer_timeout > time_between_tics.seconds:
            msg = "dashi consumer timeout (%s) must be half or smaller than the heartbeat interval %s" % (
                    self._dashi.consumer_timeout, self._dashi._heartbeat_interval)

            raise DashiError(msg)

        if datetime.now() - self._last_heartbeat_check > time_between_tics:
            self._last_heartbeat_check = datetime.now()
            self._conn.heartbeat_check()


    def cancel(self, block=True):
        self._cancelled = True
        if block:
            # acquire the lock and release it immediately
            with self._consumer_lock:
                pass

    def _callback(self, body, message):
        reply_to = None
        ret = None
        err = None
        try:
            reply_to = message.headers.get('reply-to')

            try:
                op = str(body['op'])
                args = body.get('args')
            except Exception, e:
                log.warn("Failed to interpret message body: %s", body,
                         exc_info=True)
                raise BadRequestError("Invalid request: %s" % str(e))

            op_spec = self._ops.get(op)
            if not op_spec:
                raise UnknownOperationError("Unknown operation: " + op)
            op_fun = op_spec.function

            # stick the sender into kwargs if handler requested it
            if op_spec.sender_kwarg:
                sender = message.headers.get('sender')
                args[op_spec.sender_kwarg] = sender

            try:
                ret = op_fun(**args)
            except TypeError, e:
                log.exception("Type error with handler for %s:%s", self._name, op)
                raise BadRequestError("Type error: %s" % str(e))
            except Exception:
                log.exception("Error in handler for %s:%s", self._name, op)
                raise
Пример #38
0
 def test_cancel(self):
     b = Queue("foo", self.exchange, "foo", channel=Channel())
     b.cancel("fifafo")
     self.assertIn("basic_cancel", b.channel)
Пример #39
0
 def test_purge(self):
     b = Queue("foo", self.exchange, "foo", channel=Channel())
     b.purge()
     self.assertIn("queue_purge", b.channel)
Пример #40
0
 def test_consume(self):
     b = Queue('foo', self.exchange, 'foo', channel=get_conn().channel())
     b.consume('fifafo', None)
     self.assertIn('basic_consume', b.channel)
Пример #41
0
 def get_queue(self, hostname):
     return Queue("%s.%s.pidbox" % (hostname, self.namespace),
                  exchange=self.exchange,
                  durable=False,
                  auto_delete=True)
Пример #42
0
 def test__repr__(self):
     b = Queue("foo", self.exchange, "foo")
     self.assertIn("foo", repr(b))
     self.assertIn("Queue", repr(b))
Пример #43
0
 def test_as_dict(self):
     q = Queue('foo', self.exchange, 'rk')
     d = q.as_dict(recurse=True)
     self.assertEqual(d['exchange']['name'], self.exchange.name)
Пример #44
0
 def test_get(self):
     b = Queue('foo', self.exchange, 'foo', channel=get_conn().channel())
     b.get()
     self.assertIn('basic_get', b.channel)
Пример #45
0
 def test_when_bound_but_no_exchange(self):
     q = Queue('a')
     q.exchange = None
     self.assertIsNone(q.when_bound())
Пример #46
0
 def get_reply_queue(self, ticket):
     return Queue("%s.%s" % (ticket, self.reply_exchange.name),
                  exchange=self.reply_exchange,
                  routing_key=ticket,
                  durable=False,
                  auto_delete=True)
Пример #47
0
class DashiConsumer(object):
    def __init__(self, dashi, connection, name, exchange, sysname=None):
        self._dashi = dashi
        self._conn = connection
        self._name = name
        self._exchange = exchange
        self._sysname = sysname

        self._ops = {}
        self._cancelled = threading.Event()
        self._consumer_lock = threading.Lock()

        if self._sysname is not None:
            self._queue_name = "%s.%s" % (self._sysname, self._name)
        else:
            self._queue_name = self._name

        self._queue_kwargs = dict(
            name=self._queue_name,
            exchange=self._exchange,
            routing_key=self._queue_name,
            durable=self._dashi.durable,
            auto_delete=self._dashi.auto_delete,
            queue_arguments={'x-expires': int(DEFAULT_QUEUE_EXPIRATION * 1000)})

        self.connect()

    def connect(self):
        self._dashi.ensure(self._conn, self._connect)

    def _connect(self, channel):
        self._queue = Queue(channel=channel, **self._queue_kwargs)
        self._queue.declare()

        self._consumer = Consumer(channel, [self._queue],
            callbacks=[self._callback])
        self._consumer.consume()

    def disconnect(self):
        self._consumer.cancel()
        self._conn.release()

    def consume(self, count=None, timeout=None):

        # hold a lock for the duration of the consuming. this prevents
        # multiple consumers and allows cancel to detect when consuming
        # has ended.
        if not self._consumer_lock.acquire(False):
            raise Exception("only one consumer thread may run concurrently")

        try:
            self._dashi._consume(self._conn, self._consumer, count=count,
                                timeout=timeout, until_event=self._cancelled)
        finally:
            self._consumer_lock.release()
            self._cancelled.clear()

    def cancel(self, block=True):
        self._cancelled.set()
        if block:
            # acquire the lock and release it immediately
            with self._consumer_lock:
                pass

    def _callback(self, body, message):
        reply_to = None
        ret = None
        err = None
        err_dict = None
        try:
            reply_to = message.headers.get('reply-to')

            try:
                op = str(body['op'])
                args = body.get('args')
            except Exception, e:
                log.warn("Failed to interpret message body: %s", body,
                         exc_info=True)
                raise BadRequestError("Invalid request: %s" % str(e))

            op_spec = self._ops.get(op)
            if not op_spec:
                raise UnknownOperationError("Unknown operation: " + op)
            op_fun = op_spec.function

            # stick the sender into kwargs if handler requested it
            if op_spec.sender_kwarg:
                sender = message.headers.get('sender')
                args[op_spec.sender_kwarg] = sender

            try:
                ret = op_fun(**args)
            except TypeError, e:
                log.exception("Type error with handler for %s:%s", self._name, op)
                raise BadRequestError("Type error: %s" % str(e))
            except Exception:
                raise
Пример #48
0
    def call(self, name, operation, timeout=10, args=None, **kwargs):
        """Send a message and wait for reply

        @param name: name of destination service queue
        @param operation: name of service operation to invoke
        @param timeout: RPC timeout to await a reply
        @param args: dictionary of keyword args to pass to operation.
                     Use this OR kwargs.
        @param kwargs: additional args to pass to operation
        """

        if args:
            if kwargs:
                raise TypeError("specify args dict or keyword arguments, not both")
        else:
            args = kwargs

        # create a direct queue for the reply. This may end up being a
        # bottleneck for performance: each rpc call gets a brand new
        # exclusive queue. However this approach is used nova.rpc and
        # seems to have carried them pretty far. If/when this
        # becomes a bottleneck we can set up a long-lived backend queue and
        # use correlation_id to deal with concurrent RPC calls. See:
        #   http://www.rabbitmq.com/tutorials/tutorial-six-python.html
        msg_id = uuid.uuid4().hex

        # expire the reply queue shortly after the timeout. it will be
        # (lazily) deleted by the broker if we don't clean it up first
        queue_arguments = {'x-expires': int((timeout + 1) * 1000)}
        queue = Queue(name=msg_id, exchange=self._exchange, routing_key=msg_id,
                      durable=False, queue_arguments=queue_arguments)

        messages = []
        event = threading.Event()

        def _callback(body, message):
            messages.append(body)
            message.ack()
            event.set()

        d = dict(op=operation, args=args)
        headers = {'reply-to': msg_id, 'sender': self.add_sysname(self.name)}
        dest = self.add_sysname(name)

        def _declare_and_send(channel):
            consumer = Consumer(channel, (queue,), callbacks=(_callback,))
            with Producer(channel) as producer:
                producer.publish(d, routing_key=dest, headers=headers,
                    exchange=self._exchange, serializer=self._serializer)
            return consumer

        log.debug("sending call to %s:%s", dest, operation)
        with connections[self._pool_conn].acquire(block=True) as conn:
            consumer, channel = self.ensure(conn, _declare_and_send)
            try:
                self._consume(conn, consumer, timeout=timeout, until_event=event)

                # try to delete queue, but don't worry if it fails (will expire)
                try:
                    queue = queue.bind(channel)
                    queue.delete(nowait=True)
                except Exception:
                    log.exception("error deleting queue")

            finally:
                conn.maybe_close_channel(channel)

        msg_body = messages[0]
        if msg_body.get('error'):
            raise_error(msg_body['error'])
        else:
            return msg_body.get('result')
Пример #49
0
 def test_unbind(self):
     b = Queue("foo", self.exchange, "foo", channel=Channel())
     b.unbind()
     self.assertIn("queue_unbind", b.channel)
Пример #50
0
 def test_get(self):
     b = Queue("foo", self.exchange, "foo", channel=Channel())
     b.get()
     self.assertIn("basic_get", b.channel)
Пример #51
0
 def test_unbind(self):
     b = Queue('foo', self.exchange, 'foo', channel=get_conn().channel())
     b.unbind()
     self.assertIn('queue_unbind', b.channel)
Пример #52
0
 def test_consume(self):
     b = Queue("foo", self.exchange, "foo", channel=Channel())
     b.consume("fifafo", None)
     self.assertIn("basic_consume", b.channel)
Пример #53
0
 def test_consume(self):
     b = Queue("foo", self.exchange, "foo", channel=get_conn().channel())
     b.consume("fifafo", None)
     self.assertIn("basic_consume", b.channel)
Пример #54
0
 def test_delete(self):
     b = Queue("foo", self.exchange, "foo", channel=Channel())
     b.delete()
     self.assertIn("queue_delete", b.channel)
Пример #55
0
 def test_cancel(self):
     b = Queue('foo', self.exchange, 'foo', channel=get_conn().channel())
     b.cancel('fifafo')
     self.assertIn('basic_cancel', b.channel)
Пример #56
0
 def test_get(self):
     b = Queue("foo", self.exchange, "foo", channel=get_conn().channel())
     b.get()
     self.assertIn("basic_get", b.channel)
Пример #57
0
 def test_delete(self):
     b = Queue('foo', self.exchange, 'foo', channel=get_conn().channel())
     b.delete()
     self.assertIn('queue_delete', b.channel)
Пример #58
0
CELERY_SEND_TASK_SENT_EVENT = True

CELERY_SEND_EVENTS = True

#CELERY_RESULT_BACKEND = 'amqp'
#CELERY_RESULT_EXCHANGE = 'celereyResults'

# CELERY_ACCEPT_CONTENT = ['json']
# CELERY_TASK_SERIALIZER = 'json'
# CELERY_RESULT_SERIALIZER = 'json'
# from kombu import serialization
# serialization.registry._decoders.pop("application/x-python-serialize")
#CELERY_IGNORE_RESULT = False # this is less important

BROKER_HEARTBEAT = 0

#CELERY_QUEUES = ( Queue('celery', Exchange('celery'), routing_key='celery'),)

CELERYD_MAX_TASKS_PER_CHILD = 40

CELERY_ROUTES = {}

CELERYD_LOG_FORMAT = "[%(asctime)s: %(levelname)s/" + HOST_NAME + ":" + LOCAL_IP + "/%(processName)s] %(message)s"
#print "[%(asctime)s: %(levelname)s/"+getHostName()+"/%(processName)s][%(task_name)s(%(task_id)s)] %(message)s"
CELERYD_TASK_LOG_FORMAT = "[%(asctime)s: %(levelname)s/" + HOST_NAME + ":" + LOCAL_IP + "/%(processName)s][%(task_name)s(%(task_id)s)] %(message)s"
#
CELERY_QUEUES = (Queue('celery', Exchange('celery'), routing_key='celery'), )

#CELERY_IMPORTS = ('cabbage.test.task.test_mac_task.TestMacTask',)
Пример #59
0
 def test_as_dict(self):
     q = Queue("foo", self.exchange, "rk")
     d = q.as_dict(recurse=True)
     self.assertEqual(d["exchange"]["name"], self.exchange.name)