下面是 hiredis 異步調(diào)用使用的一個例子(算是對于官方簡單例子的一個補充葬凳,可能長得更像實際業(yè)務(wù)中使用的樣子)膨疏,一般使用場景是我們監(jiān)聽一個端口讼油,當(dāng)有請求來的時候厅翔,就執(zhí)行回調(diào)又活,而回調(diào)里面可能需要讀寫 Redis。(涉及 IO 的操作都需要異步處理C痰俊)
#include <hiredis/hiredis.h>
#include <hiredis/adapters/libevent.h>
#include <sys/socket.h>
void do_accept(evutil_socket_t listener, short event, void *arg) {
redisAsyncContext *ac = (redisAsyncContext *)arg;
evutil_socket_t fd;
struct sockaddr_in sin;
socklen_t slen = sizeof(sin);
fd = accept(listener, (struct sockaddr *)&sin, &slen);
if (fd < 0) {
perror("[ERROR] accept error");
return;
}
redisAsyncCommand(ac, NULL, NULL, "SET key test");
}
int main() {
signal(SIGPIPE, SIG_IGN);
struct event_base *base = event_base_new();
/* 創(chuàng)建套接字 */
int listenfd;
struct sockaddr_in servaddr;
if ((listenfd = socket(AF_INET, SOCK_STREAM, 0)) < 0) {
printf("[ERROR] socket error");
exit(-1);
}
bzero(&servaddr, sizeof(servaddr));
servaddr.sin_family = AF_INET;
servaddr.sin_addr.s_addr = htonl(INADDR_ANY);
servaddr.sin_port = htons(17777);
bind(listenfd, (const struct sockaddr*) &servaddr, sizeof(servaddr));
if (listen(listenfd, 1024) < 0) {
printf("[ERROR] listen error");
exit(-1);
}
redisAsyncContext *c = redisAsyncConnect("127.0.0.1", 6379);
if (c->err) {
/* Let *c leak for now... */
printf("Error: %s\n", c->errstr);
return 1;
}
redisLibeventAttach(c,base);
c->data = (void *)base;
struct event *listen_event;
listen_event = event_new(base, listenfd, EV_READ|EV_PERSIST, do_accept, (void *)c);
event_add(listen_event, NULL);
event_base_dispatch(base);
return 0;
}