Apache CMS学习笔记1 - 总体概览

来源:互联网 发布:质量效应2捏脸数据 编辑:程序博客网 时间:2024/05/05 03:17

 

    Apache CMS学习笔记

    by viki 2009/12/08

     

     

     

     

    1.生产者和消费者

    生产者最典型的用法是实现Runnable接口以不断发送消息(实现run方法)。

    void run() = 0;

     

    class HelloWorldProducer : public Runnable

    class AdvisoryProducer : public decaf::lang::Runnable, public cms::MessageListener

     

    生产者需要持有Session指针以创建消息。

    并且需要以Destination指针(Topic派生于Destination)作为参数来createProducer

    virtual MessageProducer* createProducer( const Destination* destination ) throw ( CMSException ) = 0

    生产者如果对消费者发送的消息感兴趣的话,也可以实现MessageListener接口,并且createConsumer对象,即把自己也作为消费者(消息接受者)。

     

    run方法主要是send消息。MessageProducer可以有send方法实现消息发送。

    virtual void send( Message* message ) throw ( CMSException ) = 0;

     

    消费者最基本的要有MessageListener接口(实现onMessage方法)。

    void onMessage( const cms::Message* message ) = 0;

     

    class HelloWorldConsumer : public ExceptionListener,

                               public MessageListener,

                               public Runnable

     

    ExceptionListener可选,用于捕获异常。

     

    class AdvisoryConsumer : public cms::Closeable, public cms::MessageListener

     

    消费者需要持有Session指针。

    需要以Destination指针(Topic派生于Destination)作为参数来createConsumer

    virtual MessageConsumer* createConsumer( const Destination* destination, const std::string& selector, bool noLocal ) throw ( CMSException ) = 0

     

     

    2.接口区分

    Runnable:一个单独的线程进行run的工作

    Closeable:释放资源

    Startable:

    Stoppable:

     

    3.基本对象

    1)Session

    class CMS_API Session : public Closeable

    A Session object is a single-threaded context for producing and consuming messages.

    A session can create and service multiple message producers and consumers.

    单线程,Closeable

    四种确认模式:AUTO_ACKNOWLEDGE,DUPS_OK_ACKNOWLEDGE,CLIENT_ACKNOWLEDGE,SESSION_TRANSACTED,INDIVIDUAL_ACKNOWLEDGE

     

     

     

     

    2)Message

    message->getCMSType()

    message->propertyExists()

    两种投递模式:PERSISTENT,NON_PERSISTENT

     

     

     

     

    3)MessageProducer

     

     

     

    4)MessageConsumer

    virtual void setMessageListener( MessageListener* listener ) throw ( CMSException ) = 0

     

     

    5)Destination

    enum DestinationType {

                TOPIC,//多播

                QUEUE,//点对点

                TEMPORARY_TOPIC,//

                TEMPORARY_QUEUE//

            };

     

    A TemporaryTopic is a special type of Topic Destination that can only be consumed

    from the Connection which created it.  TemporaryTopics are most commonly used as the

    reply to address for Message's that implement the request response pattern.

    A TemporaryTopic is guaranteed to exist at the Provider only for the lifetime of the

    Connection that created it.

    临时主题是特殊的主题destination。它只能被创建它的connection消费。临时主题通常被用来应答地址给实现请求响应模式的Message。临时主题保证存在于provider仅当创建它的connection的生命期内。

     

    A TemporaryQueue is a special type of Queue Destination that can only be consumed

    from the Connection which created it.  TemporaryQueues are most commonly used as the

    reply to address for Message's that implement the request response pattern.

    A TemporaryQueue is guaranteed to exist at the Provider only for the lifetime of the

    Connection that created it.

    临时队列是特殊的队列destination。它只能被创建它的connection消费。临时队列通常被用来应答地址给实现请求响应模式的Message。临时队列保证存在于provider仅当创建它的connection的生命期内。

     

     

    6)Topic

    发布/订阅模式(Publish / Subscribe)的Destination

    All Messages sent to a Topic are broadcast to all Subscribers of that Topic unless the Subscriber defines a Message selector that filters out that Message.

    所有消息都被广播道所有订阅者,除非订阅者定义了消息选择器来过滤消息。

     

    7)Queue

    单订阅者模式(Single Subscribe)的Destination

    This allows for Queues to be used as load balances implementing a SEDA based architecture. The length of time that a Provider will store a Message in a Queue is not defined by the CMS API, consult your Provider documentation for this information.

    允许用队列来做负载均衡,实现以SEDAStaged Event Driven Architecture )为基础的架构。Provider保存一个Messagequeue中的时间不是由CMSAPI定义,查阅您的Provider文档获取相关信息。

     

    8)Thread

    class DECAF_API Thread : public Runnable

    Thread( Runnable* task );

     

     

     

    9)Connection

    class CMS_API Connection : public Startable, public Stoppable, public Closeable

     

     

     

    4.基本流程

    1MQ库初始化

    activemq::library::ActiveMQCPP::initializeLibrary();

     

    2)ConnectionFactory创建Connection

    ip地址和端口创建ConnectionFactory

    string brokerURI = "failover:(tcp://127.0.0.1:61616)";

    auto_ptr<ConnectionFactory> connectionFactory(

                    ConnectionFactory::createCMSConnectionFactory( brokerURI ) );

     

    可以在URI中指定一些参数

    std::string brokerURI =

    "failover:(tcp://127.0.0.1:61616"

    "?wireFormat=openwire"

    //"&connection.alwaysSyncSend=true"//同步发送

    //"&connection.useAsyncSend=true"//异步发送

    //"&transport.commandTracingEnabled=true"

    //"&transport.tcpTracingEnabled=true"

    //"&wireFormat.tightEncodingEnabled=true"

    ")";

     

    创建连接时候的方法

    可以指定用户名,密码,ID

    virtual Connection* createConnection() throw ( CMSException ) = 0;

    virtual cms::Connection* createConnection( const std::string& username, const std::string& password ) throw ( cms::CMSException ) = 0;

    virtual cms::Connection* createConnection( const std::string& username, const std::string& password, const std::string& clientId )

     throw ( cms::CMSException ) = 0;

     

    Connection* connection = connectionFactory->createConnection();

     

    异常

    connection->setExceptionListener(this);

     

    3)Connection创建Destination,Destination创建Session

    可以指定会话模式

    TOPIC, QUEUE, TEMPORARY_TOPIC, TEMPORARY_QUEUE

     

    auto_ptr<cms::Session> session( connection->createSession() );

    OR

    auto_ptr<cms::Session> session( connection->createSession( Session::SESSION_TRANSACTED ) );

     

    4)创建生产者消费者【可选】

    自己根据需要实现生产者和消费者类

    AdvisoryProducer advisoryProducer( session.get() );

    AdvisoryConsumer advisoryConsumer( session.get() );

     

    内部:

    scoped_ptr<cms::MessageProducer> producer;

    shared_ptr<cms::Topic> destination( session->createTopic(

            "HEART-BEAT-CHANNEL" ) );

    producer.reset( session->createProducer( destination.get() ) );

     

    scoped_ptr<cms::MessageConsumer> consumer;

    shared_ptr<cms::Topic> destination( session->createTopic(

            "HEART-BEAT-CHANNEL" ) );

    consumer.reset( session->createConsumer( destination.get() ) );

     

    生产者内部的run利用Session来创建Message等。

    shared_ptr<cms::TextMessage> message( session->createTextMessage( "XXX" ) );

    producer->send( message.get() );

     

    消费者内部的run或者onMessage接受Message。

     

    Message可以指定投递模式:持久和非持久,将影响效率

     

    5)创建Thread使线程run起来(调用run生产者消费者的接口)【可选】

    当需要持续进行生产者和消费者的某些工作的时候,只要实现了Runnable接口,可以委托给Thread进行run

    Thread consumerThread( &advisoryConsumer);

    consumerThread.start();

    Thread producerThread( &advisoryProducer);

    producerThread.start();

    producerThread.join();

    consumerThread.join();

     

     

    6)Connection开始连接

    Connection实现了Startable接口

    connection->start();

     

    7)生产者消费者关闭【可选】

    Thread未提供关闭接口,不用理会

    生产者和消费者关闭时候保证安全退出run循环即可

    advisoryProducer.stop();

     

    8)会话关闭

    session->close();

     

    8)连接关闭

    connection->stop();

     

    9MQ库关闭

    activemq::library::ActiveMQCPP::shutdownLibrary();