from flow.commands.base import CommandBase
from flow.configuration.inject.broker import BrokerConfiguration
from flow.configuration.settings.injector import setting
from injector import inject
from twisted.internet import defer

import flow.interfaces
import logging
#import time


LOG = logging.getLogger(__name__)


@inject(broker=flow.interfaces.IBroker,
        binding_config=setting('bindings'))
class ConfigureRabbitMQCommand(CommandBase):
    injector_modules = [
        BrokerConfiguration,
    ]


    @staticmethod
    def annotate_parser(parser):
        pass


    @defer.inlineCallbacks
    def _execute(self, parsed_arguments):
        exchanges, queues, bindings = self._parse_config()

        yield self.broker.connect()

        yield self._declare_exchanges(exchanges)
        yield self._declare_queues(queues)
        yield self._declare_bindings(bindings)

        # XXX Dirty workaround.  I can't tell why the bindings aren't declared
        # by the time we get here.
        #time.sleep(2)


    def _parse_config(self):
        exchanges = set()
        queues = set()
        bindings = set()

        for exchange_name, queue_bindings in self.binding_config.iteritems():
            exchanges.add(exchange_name)

            for queue_name, topics in queue_bindings.iteritems():
                queues.add(queue_name)

                for topic in topics:
                    bindings.add( (queue_name, exchange_name, topic) )

        return exchanges, queues, bindings

    def _declare_exchanges(self, exchanges):
        deferreds = []
        deferreds.append(self.broker.declare_exchange('alt'))

        arguments = {'alternate-exchange': 'alt'}
        deferreds.append(self.broker.declare_exchange(
            'dead', arguments=arguments))

        for exchange_name in exchanges:
            deferreds.append(self.broker.declare_exchange(
                exchange_name, arguments=arguments))

        return defer.DeferredList(deferreds)

    def _declare_queues(self, queues):
        deferreds = []
        deferreds.append(self.broker.declare_queue('missing_routing_key'))

        arguments = {'x-dead-letter-exchange': 'dead'}
        for queue in queues:
            deferreds.append(self.broker.declare_queue(
                queue, arguments=arguments))
            deferreds.append(self.broker.declare_queue('dead_' + queue))

        return defer.DeferredList(deferreds)

    def _declare_bindings(self, bindings):
        deferreds = []
        deferreds.append(self.broker.bind_queue(
            'missing_routing_key', 'alt', '#'))

        for queue, exchange, topic in bindings:
            deferreds.append(self.broker.bind_queue(queue, exchange, topic))
            deferreds.append(self.broker.bind_queue(
                'dead_' + queue, 'dead', topic))

        return defer.DeferredList(deferreds)

@@ -701,45 +701,8 @@
 ()%0A%0A
-        yield self.broker.connect()%0A%0A
     
@@ -1556,32 +1556,40 @@
 end(self.broker.
+channel.
 declare_exchange
@@ -1677,32 +1677,40 @@
 end(self.broker.
+channel.
 declare_exchange
@@ -1827,32 +1827,40 @@
 end(self.broker.
+channel.
 declare_exchange
@@ -2052,32 +2052,40 @@
 end(self.broker.
+channel.
 declare_queue('m
@@ -2224,32 +2224,40 @@
 end(self.broker.
+channel.
 declare_queue(%0A 
@@ -2341,16 +2341,24 @@
 .broker.
+channel.
 declare_
@@ -2523,32 +2523,40 @@
 end(self.broker.
+channel.
 bind_queue(%0A    
@@ -2681,32 +2681,40 @@
 end(self.broker.
+channel.
 bind_queue(queue
@@ -2774,16 +2774,24 @@
 .broker.
+channel.
 bind_que

Update configurerabbitmq to new amqp_broker interface