Publish/subscribe__c++ in the C + + test Redis

Source: Internet
Author: User
Tags assert redis semaphore redis server
Using the Redis_publisher.h redis_publisher.cpp in http://blog.csdn.net/xumaojun/article/details/51558237 redis_ Subscriber.h redis_subscriber.cpp four files, do an action class to test. Header file Policy.h
#pragma once
#include "redis_publisher.h"
#include "redis_subscriber.h"
#include <iostream>

using namespace std;

Class Policy
{public
:
    Policy ();
    ~policy ();
    void publish ();
    static void Recieve_message (const char *channel_name,const char *message, int len);

    Credispublisher publisher;
    Credissubscriber subscriber;
};
code file Policy.cpp
#include "Policy.h" Policy::P olicy () {BOOL ret = Publisher.init ();

    if (!ret) {printf ("Init failed.\n");
    ret = Publisher.connect ();

    if (!ret) {printf ("Connect failed."); //*********************************** CREDISSUBSCRIBER::NOTIFYMESSAGEFN fn = bind (recieve_message, std:

    : TR1::p laceholders::_1, std::tr1::p laceholders::_2, std::tr1::p laceholders::_3);
    BOOL Ret1 = Subscriber.init (FN);
    if (!ret1) {printf ("Init failed.\n");
    } Ret1 = Subscriber.connect ();
    if (!ret1) {printf ("Connect failed.\n");
} subscriber.subscribe ("Test-channel");
    } policy::~policy () {publisher.disconnect ();

    Publisher.uninit ();
    Subscriber.disconnect ();
Subscriber.uninit ();
    } void Policy::p ublish () {cout<< "Policy::p ublish () ... \ n" <<endl;
Publisher.publish ("Test-channel", "test Message"); } void Policy::recieve_message (const char *channel_name, const char *message, int len) {printf ("Recieve Message:channel Name:%s Message:%s\n", channel_name, mess
Age);
 }

Test file TestPolicy.cpp
#include "Policy.h"
int main (int argc, char *argv[])
{
    Policy m_policy;
    int i=0;
    while (i<8) {
        m_policy.publish ();
        Sleep (2);
        cout<< "Main sleep...\n";
        i++;
    }
    return 0;
}

Makefile
Exe=server_main client_main  
cc=g++  
flag=-lhiredis-levent-pthread  
obj=redis_publisher.o redis_ SUBSCRIBER.O policy.o testpolicy.o  


all:$ (EXE)

$ (EXE): $ (OBJ)
	$ (CC)-O testpolicy  redis_ PUBLISHER.O redis_subscriber.o policy.o testpolicy.o  $ (FLAG)
  
redis_publisher.o:redis_publisher.h
Redis_subscriber.o:redis_subscriber.h

Policy.o:policy.h

After compiling this, you can spontaneously collect. The purpose of this example is to simply implement heterogeneous data delivery in the project.
Attach Original code: REDIS_PUBLISHER.H
/************************************************************************* > File name:redis_publisher.h ;  Author:chenzengba > Mail:chenzengba@gmail.com > Created time:sat Apr 2016 10:15:09 PM CST > Description: Encapsulating Hiredis, implementing message Publishing to Redis function ************************************************************************/# ifndef redis_publisher_h #define Redis_publisher_h #include <stdlib.h> #include  

Redis_publisher.cpp
/************************************************************************* > File Name:redis_publisher.cpp & Gt  Author:chenzengba > Mail:chenzengba@gmail.com > Created time:sat Apr 2016 10:15:09 PM CST >   
Description: ************************************************************************/#include <stddef.h> #include <assert.h> #include <string.h> #include "redis_publisher.h" Credispublisher::credispublis  
  
Her (): _event_base (0), _event_thread (0), _redis_context (0) {} credispublisher::~credispublisher () {}    BOOL Credispublisher::init () {//Initialize the event _event_base = Event_base_new ();  
        Create Libevent Object if (NULL = = _event_base) {printf (": Create Redis event failed.\n");  
    return false;  
    } memset (&_event_sem, 0, sizeof (_EVENT_SEM));  
    int ret = sem_init (&_event_sem, 0, 0);  
       if (ret!= 0) { printf (": Init sem failed.\n");  
    return false;  
return true;  
      
    BOOL Credispublisher::uninit () {_event_base = NULL;     
    Sem_destroy (&_event_sem);  
return true; BOOL Credispublisher::connect () {//connect Redis _redis_context = Redisasyncconnect ("127.0.0.1", 63    79);  
        Connect asynchronously to the Redis server using the default port if (NULL = _redis_context) {printf (": Connect Redis failed.\n");  
    return false; } if (_redis_context->err) {printf (": Connect Redis Error:%d,%s\n", _redis_c    Ontext->err, _REDIS_CONTEXT-&GT;ERRSTR);  
    Output error message return false;    }//Attach the event Redislibeventattach (_redis_context, _event_base); Bind the event to the Redis context so that the callback set to Redis is associated with the event//create an event-handling thread int ret = pthread_create (&_event_thread, 0, & Amp  
    Credispublisher::event_thread, this); if (ret!= 0) {printf (": Create Event Thread failed.\n");  
        Disconnect ();  
    return false; //Sets the connection callback, which is invoked after the server processes the connection request after the connection is invoked asynchronously, notifying the caller of the status of the connection Redisasyncsetconnectcallback (_redis_context, ;  
  
    Credispublisher::connect_callback); Sets the disconnect callback and notifies the caller that the connection is disconnected after the server disconnects, and the caller can use this function to implement the reconnection Redisasyncsetdisconnectcallback (_redis_context, &credi  
  
    Spublisher::d isconnect_callback);  
    Start Event thread Sem_post (&AMP;_EVENT_SEM);  
return true; BOOL Credispublisher::d isconnect () {if (_redis_context) {Redisasyncdisconnect (_redis_cont  
        EXT);  
        Redisasyncfree (_redis_context);  
    _redis_context = NULL;  
return true;  
    BOOL Credispublisher::p ublish (const std::string &channel_name, const std::string &message) {   
        int ret = Redisasynccommand (_redis_context, &credispublisher::command_callback, this, "PUBLISH%s%s", Channel_name.c_str (), Message.c_str ());  
        if (Redis_err = ret) {printf ("Publish command failed:%d\n", ret);  
    return false;  
return true; } void Credispublisher::connect_callback (const redisasynccontext *redis_context, int status) {if (stat  
    US!= redis_ok) {printf (": Error:%s\n", REDIS_CONTEXT-&GT;ERRSTR);  
    else {printf (": Redis connected!\n");  
    } void Credispublisher::d isconnect_callback (const redisasynccontext *redis_context, int status) {  
    if (status!= redis_ok) {//Here exits abnormally, you can try to connect printf (": Error:%s\n", REDIS_CONTEXT-&GT;ERRSTR); }//message receive callback function void Credispublisher::command_callback (Redisasynccontext *redis_context, void *reply,  
    void *privdata) {printf ("command callback.\n"); No action is performed here} void *credispublisher::event_thread (void *data) {if (NULL = = data) {printf (": error!\n ");  
        ASSERT (FALSE);  
    return NULL;  
    } credispublisher *self_this = Reinterpret_cast<credispublisher *> (data);  
return Self_this->event_proc ();  
      
    } void *credispublisher::event_proc () {sem_wait (&_event_sem);  
  
    Open Event distribution, Event_base_dispatch will block Event_base_dispatch (_event_base);  
return NULL; }

Redis_subscriber.h
/************************************************************************* > File name:redis_subscriber.h &G T  Author:chenzengba > Mail:chenzengba@gmail.com > Created time:sat Apr 2016 10:15:09 PM CST > Description: Encapsulating Hiredis, realizing message subscription Redis function ************************************************************************/#i  
Fndef redis_subscriber_h #define Redis_subscriber_h #include <stdlib.h> #include  

Redis_subscriber.cpp
/************************************************************************* > File Name:redis_subscriber.cpp 
    > Author:chenzengba > Mail:chenzengba@gmail.com > Created time:sat Apr 2016 10:15:09 PM CST > Description: ************************************************************************/#include <stddef. h> #include <assert.h> #include <string.h> #include "redis_subscriber.h" Credissubscriber::credi   
Ssubscriber (): _event_base (0), _event_thread (0), _redis_context (0) {} credissubscriber::~credissubscriber () { BOOL Credissubscriber::init (const NOTIFYMESSAGEFN &AMP;FN) {//Initialize the event _notify_messa  
    GE_FN = fn;    _event_base = Event_base_new ();  
        Create Libevent Object if (NULL = = _event_base) {printf (": Create Redis event failed.\n");  
    return false;  
    } memset (&_event_sem, 0, sizeof (_EVENT_SEM)); int ret = SEM_init (&_event_sem, 0, 0);  
        if (ret!= 0) {printf (": Init sem failed.\n");  
    return false;  
return true;  
      
    BOOL Credissubscriber::uninit () {_event_base = NULL;     
    Sem_destroy (&_event_sem);  
return true; BOOL Credissubscriber::connect () {//connect Redis _redis_context = Redisasyncconnect ("127.0.0.1", 6    379);  
        Connect asynchronously to the Redis server using the default port if (NULL = _redis_context) {printf (": Connect Redis failed.\n");  
    return false; } if (_redis_context->err) {printf (": Connect Redis Error:%d,%s\n", _redis_c    Ontext->err, _REDIS_CONTEXT-&GT;ERRSTR);  
    Output error message return false;    }//Attach the event Redislibeventattach (_redis_context, _event_base); Bind the event to the Redis context so that the callback set to Redis is associated with the event//create an event-handling thread int ret = pthread_create (&_event_thread, 0, & Amp CredissuBscriber::event_thread, this);  
        if (ret!= 0) {printf (": Create Event Thread failed.\n");  
        Disconnect ();  
    return false; //Sets the connection callback, which is invoked after the server processes the connection request after the connection is invoked asynchronously, notifying the caller of the status of the connection Redisasyncsetconnectcallback (_redis_context, ;  
  
    Credissubscriber::connect_callback); Sets the disconnect callback and notifies the caller that the connection is disconnected after the server disconnects, and the caller can use this function to implement the reconnection Redisasyncsetdisconnectcallback (_redis_context, &credi  
  
    Ssubscriber::d isconnect_callback);  
    Start Event thread Sem_post (&AMP;_EVENT_SEM);  
return true; BOOL Credissubscriber::d isconnect () {if (_redis_context) {Redisasyncdisconnect (_redis_con  
        Text);  
        Redisasyncfree (_redis_context);  
    _redis_context = NULL;  
return true; BOOL Credissubscriber::subscribe (const std::string &channel_name) {int ret = Redisasynccommand (_redis_ Context, &credissubscriber::command_callback, this, "SUBSCRIBE %s ", Channel_name.c_str ());  
        if (Redis_err = ret) {printf ("Subscribe command failed:%d\n", ret);  
    return false;  
    printf (": Subscribe success:%s\n", Channel_name.c_str ());  
return true; } void Credissubscriber::connect_callback (const redisasynccontext *redis_context, int status) {if STA  
    Tus!= redis_ok) {printf (": Error:%s\n", REDIS_CONTEXT-&GT;ERRSTR);  
    else {printf (": Redis connected!");  
    } void Credissubscriber::d isconnect_callback (const redisasynccontext *redis_context, int status) {  
    if (status!= redis_ok) {//Here exits abnormally, you can try to connect printf (": Error:%s\n", REDIS_CONTEXT-&GT;ERRSTR);  }//message receive callback function void Credissubscriber::command_callback (Redisasynccontext *redis_context, void *reply, void *privdata) {if (NULL = = Reply | |  
    NULL = = Privdata) {return; } 
  
    In a static function, to use the member variable of the class, pass the current this pointer in and use this pointer to access Credissubscriber *self_this = REINTERPRET_CAST&LT;CREDISSUBSCR  
    Iber *> (Privdata);  
      
    Redisreply *redis_reply = reinterpret_cast<redisreply *> (reply);  
    The message received by the subscription is an array with a ternary element if (Redis_reply->type = = Redis_reply_array && redis_reply->elements = 3) {printf (": Recieve message:%s:%d:%s:%d:%s:%d\n", Redis_reply->element[0]->str, Redis_repl Y->element[0]->len, Redis_reply->element[1]->str, Redis_reply->element[1]->len, Redi  
          
        S_reply->element[2]->str, Redis_reply->element[2]->len); Call the Function object to notify the outer self_this->_notify_message_fn of the message (REDIS_REPLY-&GT;ELEMENT[1]-&GT;STR, redis_reply  
    ->element[2]->str, Redis_reply->element[2]->len); } void *credissubscriber::event_thread (void *data) {if (NULL = = data) {printf (": ErroR!\n ");  
        ASSERT (FALSE);  
    return NULL;  
    } credissubscriber *self_this = Reinterpret_cast<credissubscriber *> (data);  
return Self_this->event_proc ();  
      
    } void *credissubscriber::event_proc () {sem_wait (&_event_sem);  
  
    Open Event distribution, Event_base_dispatch will block Event_base_dispatch (_event_base);  
return NULL; }





Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.