int redisc_exec_pipelined_cmd(str *srv) { redisc_server_t *rsrv=NULL; if (srv == NULL) { LM_ERR("invalid parameters"); return -1; } if (srv->len == 0) { LM_ERR("invalid parameters"); return -1; } rsrv = redisc_get_server(srv); if (rsrv == NULL) { LM_ERR("no redis server found: %.*s\n", srv->len, srv->s); return -1; } if (rsrv->ctxRedis == NULL) { LM_ERR("no redis context for server: %.*s\n", srv->len, srv->s); return -1; } return redisc_exec_pipelined(rsrv); }
int check_cluster_reply(redisReply *reply, redisc_server_t **rsrv) { redisc_server_t *rsrv_new; char buffername[100]; unsigned int port; str addr = {0, 0}, tmpstr = {0, 0}, name = {0, 0}; if (redis_cluster_param) { LM_DBG("Redis replied: \"%.*s\"\n", reply->len, reply->str); if ((reply->len > 7) && (strncmp(reply->str, "MOVED", 5) == 0)) { port = 6379; if (strchr(reply->str, ':') > 0) { tmpstr.s = strchr(reply->str, ':') + 1; tmpstr.len = reply->len - (tmpstr.s - reply->str); if(str2int(&tmpstr, &port) < 0) port = 6379; LM_DBG("Port \"%.*s\" [%i] => %i\n", tmpstr.len, tmpstr.s, tmpstr.len, port); } else { LM_ERR("No Port in REDIS MOVED Reply (%.*s)\n", reply->len, reply->str); return 0; } if (strchr(reply->str+6, ' ') > 0) { addr.len = tmpstr.s - strchr(reply->str+6, ' ') - 2; addr.s = strchr(reply->str+6, ' ') + 1; LM_DBG("Host \"%.*s\" [%i]\n", addr.len, addr.s, addr.len); } else { LM_ERR("No Host in REDIS MOVED Reply (%.*s)\n", reply->len, reply->str); return 0; } memset(buffername, 0, sizeof(buffername)); name.len = snprintf(buffername, sizeof(buffername), "%.*s:%i", addr.len, addr.s, port); name.s = buffername; LM_DBG("Name of new connection: %.*s\n", name.len, name.s); rsrv_new = redisc_get_server(&name); if (rsrv_new) { LM_DBG("Reusing Connection\n"); *rsrv = rsrv_new; return 1; } else { LM_ERR("No Connection with name (%.*s)\n", name.len, name.s); } } } return 0; }
int redisc_exec(str *srv, str *res, str *cmd, ...) { redisc_server_t *rsrv=NULL; redisc_reply_t *rpl; char c; va_list ap; va_start(ap, cmd); rsrv = redisc_get_server(srv); if(srv==NULL || cmd==NULL || res==NULL) { LM_ERR("invalid parameters"); goto error_exec; } if(srv->len==0 || res->len==0 || cmd->len==0) { LM_ERR("invalid parameters"); goto error_exec; } if(rsrv==NULL) { LM_ERR("no redis server found: %.*s\n", srv->len, srv->s); goto error_exec; } if(rsrv->ctxRedis==NULL) { LM_ERR("no redis context for server: %.*s\n", srv->len, srv->s); goto error_exec; } rpl = redisc_get_reply(res); if(rpl==NULL) { LM_ERR("no redis reply id found: %.*s\n", res->len, res->s); goto error_exec; } if(rpl->rplRedis!=NULL) { /* clean up previous redis reply */ freeReplyObject(rpl->rplRedis); rpl->rplRedis = NULL; } c = cmd->s[cmd->len]; cmd->s[cmd->len] = '\0'; rpl->rplRedis = redisvCommand(rsrv->ctxRedis, cmd->s, ap ); if(rpl->rplRedis == NULL) { /* null reply, reconnect and try again */ if(rsrv->ctxRedis->err) { LM_ERR("Redis error: %s\n", rsrv->ctxRedis->errstr); } if(redisc_reconnect_server(rsrv)==0) { rpl->rplRedis = redisvCommand(rsrv->ctxRedis, cmd->s, ap); } else { LM_ERR("unable to reconnect to redis server: %.*s\n", srv->len, srv->s); cmd->s[cmd->len] = c; goto error_exec; } } cmd->s[cmd->len] = c; va_end(ap); return 0; error_exec: va_end(ap); return -1; }
int redisc_exec(str *srv, str *res, str *cmd, ...) { redisc_server_t *rsrv=NULL; redisc_reply_t *rpl; char c; va_list ap, ap2, ap3, ap4; va_start(ap, cmd); va_copy(ap2, ap); va_copy(ap3, ap); va_copy(ap4, ap); if(srv==NULL || cmd==NULL || res==NULL) { LM_ERR("invalid parameters"); goto error_exec; } if(srv->len==0 || res->len==0 || cmd->len==0) { LM_ERR("invalid parameters"); goto error_exec; } rsrv = redisc_get_server(srv); if(rsrv==NULL) { LM_ERR("no redis server found: %.*s\n", srv->len, srv->s); goto error_exec; } LM_DBG("rsrv->ctxRedis = %p\n", rsrv->ctxRedis); if(rsrv->ctxRedis==NULL) { LM_ERR("no redis context for server: %.*s\n", srv->len, srv->s); goto error_exec; } LM_DBG("rsrv->ctxRedis = %p\n", rsrv->ctxRedis); if (rsrv->piped.pending_commands != 0) { LM_NOTICE("Calling redis_cmd with pipelined commands in the buffer. Automatically call redis_execute"); redisc_exec_pipelined(rsrv); } /* if server is disabled do nothing unless the disable time has passed */ if (redis_check_server(rsrv)) { goto srv_disabled; } rpl = redisc_get_reply(res); if(rpl==NULL) { LM_ERR("no redis reply id found: %.*s\n", res->len, res->s); goto error_exec; } c = cmd->s[cmd->len]; cmd->s[cmd->len] = '\0'; if(rpl->rplRedis!=NULL) { /* clean up previous redis reply */ freeReplyObject(rpl->rplRedis); rpl->rplRedis = NULL; } rpl->rplRedis = redisvCommand(rsrv->ctxRedis, cmd->s, ap ); if(rpl->rplRedis == NULL) { /* null reply, reconnect and try again */ if(rsrv->ctxRedis->err) { LM_ERR("Redis error: %s\n", rsrv->ctxRedis->errstr); } if(redisc_reconnect_server(rsrv)==0) { rpl->rplRedis = redisvCommand(rsrv->ctxRedis, cmd->s, ap2); if (rpl->rplRedis ==NULL) { redis_count_err_and_disable(rsrv); goto error_exec; } } else { redis_count_err_and_disable(rsrv); LM_ERR("unable to reconnect to redis server: %.*s\n", srv->len, srv->s); cmd->s[cmd->len] = c; goto error_exec; } } if (check_cluster_reply(rpl->rplRedis, &rsrv)) { LM_DBG("rsrv->ctxRedis = %p\n", rsrv->ctxRedis); if(rsrv->ctxRedis==NULL) { LM_ERR("no redis context for server: %.*s\n", srv->len, srv->s); goto error_exec; } LM_DBG("rsrv->ctxRedis = %p\n", rsrv->ctxRedis); if(rpl->rplRedis!=NULL) { /* clean up previous redis reply */ freeReplyObject(rpl->rplRedis); rpl->rplRedis = NULL; } rpl->rplRedis = redisvCommand(rsrv->ctxRedis, cmd->s, ap3 ); if(rpl->rplRedis == NULL) { /* null reply, reconnect and try again */ if(rsrv->ctxRedis->err) { LM_ERR("Redis error: %s\n", rsrv->ctxRedis->errstr); } if(redisc_reconnect_server(rsrv)==0) { rpl->rplRedis = redisvCommand(rsrv->ctxRedis, cmd->s, ap4); } else { LM_ERR("unable to reconnect to redis server: %.*s\n", srv->len, srv->s); cmd->s[cmd->len] = c; goto error_exec; } } } cmd->s[cmd->len] = c; rsrv->disable.consecutive_errors = 0; va_end(ap); va_end(ap2); va_end(ap3); va_end(ap4); LM_DBG("rsrv->ctxRedis = %p\n", rsrv->ctxRedis); return 0; error_exec: va_end(ap); va_end(ap2); va_end(ap3); va_end(ap4); return -1; srv_disabled: va_end(ap); va_end(ap2); va_end(ap3); va_end(ap4); return -2; }
int redisc_append_cmd(str *srv, str *res, str *cmd, ...) { redisc_server_t *rsrv=NULL; redisc_reply_t *rpl; char c; va_list ap; va_start(ap, cmd); if(srv==NULL || cmd==NULL || res==NULL) { LM_ERR("invalid parameters"); goto error_cmd; } if(srv->len==0 || res->len==0 || cmd->len==0) { LM_ERR("invalid parameters"); goto error_cmd; } rsrv = redisc_get_server(srv); if(rsrv==NULL) { LM_ERR("no redis server found: %.*s\n", srv->len, srv->s); goto error_cmd; } if(rsrv->ctxRedis==NULL) { LM_ERR("no redis context for server: %.*s\n", srv->len, srv->s); goto error_cmd; } if (rsrv->piped.pending_commands >= MAXIMUM_PIPELINED_COMMANDS) { LM_ERR("Too many pipelined commands, maximum is %d\n",MAXIMUM_PIPELINED_COMMANDS); goto error_cmd; } rpl = redisc_get_reply(res); if(rpl==NULL) { LM_ERR("no redis reply id found: %.*s\n", res->len, res->s); goto error_cmd; } c = cmd->s[cmd->len]; cmd->s[cmd->len] = '\0'; rsrv->piped.commands[rsrv->piped.pending_commands].len = redisvFormatCommand( &rsrv->piped.commands[rsrv->piped.pending_commands].s, cmd->s, ap); if (rsrv->piped.commands[rsrv->piped.pending_commands].len < 0) { LM_ERR("Invalid redis command : %s\n",cmd->s); goto error_cmd; } rsrv->piped.replies[rsrv->piped.pending_commands]=rpl; rsrv->piped.pending_commands++; cmd->s[cmd->len] = c; va_end(ap); return 0; error_cmd: va_end(ap); return -1; }