Thu Jul 9 13:41:29 2009

Asterisk developer's documentation


res_config_curl.c File Reference

curl plugin for portable configuration engine More...

#include "asterisk.h"
#include <curl/curl.h>
#include "asterisk/file.h"
#include "asterisk/channel.h"
#include "asterisk/pbx.h"
#include "asterisk/config.h"
#include "asterisk/module.h"
#include "asterisk/lock.h"
#include "asterisk/utils.h"

Go to the source code of this file.

Functions

static void __reg_module (void)
static void __unreg_module (void)
static struct ast_configconfig_curl (const char *url, const char *unused, const char *file, struct ast_config *cfg, struct ast_flags flags, const char *sugg_incl, const char *who_asked)
static int destroy_curl (const char *url, const char *unused, const char *keyfield, const char *lookup, va_list ap)
 Execute an DELETE query.
static int load_module (void)
static struct ast_variablerealtime_curl (const char *url, const char *unused, va_list ap)
 Execute a curl query and return ast_variable list.
static struct ast_configrealtime_multi_curl (const char *url, const char *unused, va_list ap)
 Excute an Select query and return ast_config list.
static int store_curl (const char *url, const char *unused, va_list ap)
 Execute an INSERT query.
static int unload_module (void)
static int update_curl (const char *url, const char *unused, const char *keyfield, const char *lookup, va_list ap)
 Execute an UPDATE query.

Variables

static struct ast_module_info __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_DEFAULT , .description = "Realtime Curl configuration" , .key = "This paragraph is copyright (c) 2006 by Digium, Inc. \In order for your module to load, it must return this \key via a function called \"key\". Any code which \includes this paragraph must be licensed under the GNU \General Public License version 2 or later (at your \option). In addition to Digium's general reservations \of rights, Digium expressly reserves the right to \allow other parties to license this paragraph under \different terms. Any use of Digium, Inc. trademarks or \logos (including \"Asterisk\" or \"Digium\") without \express written permission of Digium, Inc. is prohibited.\n" , .buildopt_sum = "068e67f60f50dd9ee86464c05884a49d" , .load = load_module, .unload = unload_module, }
static const struct ast_module_infoast_module_info = &__mod_info
static struct ast_config_engine curl_engine


Detailed Description

curl plugin for portable configuration engine

Author:
Tilghman Lesher <res_config_curl_v1@the-tilghman.com>
ExtRef:
Depends on the CURL library - http://curl.haxx.se/

Definition in file res_config_curl.c.


Function Documentation

static void __reg_module ( void   )  [static]

Definition at line 509 of file res_config_curl.c.

static void __unreg_module ( void   )  [static]

Definition at line 509 of file res_config_curl.c.

static struct ast_config* config_curl ( const char *  url,
const char *  unused,
const char *  file,
struct ast_config cfg,
struct ast_flags  flags,
const char *  sugg_incl,
const char *  who_asked 
) [static]

Definition at line 410 of file res_config_curl.c.

References ast_category_append(), ast_category_new(), ast_config_get_current_category(), ast_config_internal_load(), ast_custom_function_find(), ast_free, ast_log(), ast_malloc, ast_str_create(), ast_str_set(), ast_strlen_zero(), ast_uri_decode(), ast_uri_encode(), ast_variable_append(), ast_variable_new(), LOG_ERROR, pbx_substitute_variables_helper(), S_OR, ast_str::str, and strsep().

00411 {
00412    struct ast_str *query;
00413    char buf1[200];
00414    char *stringp, *line, *pair, *key;
00415    const int EncodeSpecialChars = 1, bufsize = 256000;
00416    int last_cat_metric = -1, cat_metric = -1;
00417    struct ast_category *cat=NULL;
00418    char *buffer, *cur_cat = "";
00419    char *category = "", *var_name = "", *var_val = "";
00420    struct ast_flags loader_flags = { 0 };
00421 
00422    if (!ast_custom_function_find("CURL")) {
00423       ast_log(LOG_ERROR, "func_curl.so must be loaded in order to use res_config_curl.so!!\n");
00424       return NULL;
00425    }
00426 
00427    if (!(query = ast_str_create(1000)))
00428       return NULL;
00429 
00430    if (!(buffer = ast_malloc(bufsize))) {
00431       ast_free(query);
00432       return NULL;
00433    }
00434 
00435    ast_uri_encode(file, buf1, sizeof(buf1), EncodeSpecialChars);
00436    ast_str_set(&query, 0, "${CURL(%s/static?file=%s)}", url, buf1);
00437 
00438    /* Do the CURL query */
00439    pbx_substitute_variables_helper(NULL, query->str, buffer, bufsize);
00440 
00441    /* Line oriented output */
00442    stringp = buffer;
00443    cat = ast_config_get_current_category(cfg);
00444 
00445    while ((line = strsep(&stringp, "\r\n"))) {
00446       if (ast_strlen_zero(line))
00447          continue;
00448 
00449       while ((pair = strsep(&line, "&"))) {
00450          key = strsep(&pair, "=");
00451          ast_uri_decode(key);
00452          if (pair)
00453             ast_uri_decode(pair);
00454 
00455          if (!strcasecmp(key, "category"))
00456             category = S_OR(pair, "");
00457          else if (!strcasecmp(key, "var_name"))
00458             var_name = S_OR(pair, "");
00459          else if (!strcasecmp(key, "var_val"))
00460             var_val = S_OR(pair, "");
00461          else if (!strcasecmp(key, "cat_metric"))
00462             cat_metric = pair ? atoi(pair) : 0;
00463       }
00464 
00465       if (!strcmp(var_name, "#include")) {
00466          if (!ast_config_internal_load(var_val, cfg, loader_flags, "", who_asked))
00467             return NULL;
00468       }
00469 
00470       if (strcmp(category, cur_cat) || last_cat_metric != cat_metric) {
00471          if (!(cat = ast_category_new(category, "", 99999)))
00472             break;
00473          cur_cat = category;
00474          last_cat_metric = cat_metric;
00475          ast_category_append(cfg, cat);
00476       }
00477       ast_variable_append(cat, ast_variable_new(var_name, var_val, ""));
00478    }
00479 
00480    ast_free(buffer);
00481    ast_free(query);
00482    return cfg;
00483 }

static int destroy_curl ( const char *  url,
const char *  unused,
const char *  keyfield,
const char *  lookup,
va_list  ap 
) [static]

Execute an DELETE query.

Parameters:
url 
unused 
keyfield where clause field
lookup value of field for where clause
ap list containing one or more field/value set(s)
Delete a row from a database table, prepare the sql statement using keyfield and lookup control the number of records to change. Additional params to match rows are stored in ap list. Sub-in the values to the prepared statement and execute it.

Return values:
number of rows affected
-1 on failure

Definition at line 356 of file res_config_curl.c.

References ast_custom_function_find(), ast_free, ast_log(), ast_malloc, ast_str_append(), ast_str_create(), ast_str_set(), ast_uri_encode(), LOG_ERROR, pbx_substitute_variables_helper(), and ast_str::str.

00357 {
00358    struct ast_str *query;
00359    char buf1[200], buf2[200];
00360    const char *newparam, *newval;
00361    char *stringp;
00362    int i, rowcount = -1;
00363    const int EncodeSpecialChars = 1, bufsize = 100;
00364    char *buffer;
00365 
00366    if (!ast_custom_function_find("CURL")) {
00367       ast_log(LOG_ERROR, "func_curl.so must be loaded in order to use res_config_curl.so!!\n");
00368       return -1;
00369    }
00370 
00371    if (!(query = ast_str_create(1000)))
00372       return -1;
00373 
00374    if (!(buffer = ast_malloc(bufsize))) {
00375       ast_free(query);
00376       return -1;
00377    }
00378 
00379    ast_uri_encode(keyfield, buf1, sizeof(buf1), EncodeSpecialChars);
00380    ast_uri_encode(lookup, buf2, sizeof(buf2), EncodeSpecialChars);
00381    ast_str_set(&query, 0, "${CURL(%s/destroy,%s=%s&", url, buf1, buf2);
00382 
00383    for (i = 0; (newparam = va_arg(ap, const char *)); i++) {
00384       newval = va_arg(ap, const char *);
00385       ast_uri_encode(newparam, buf1, sizeof(buf1), EncodeSpecialChars);
00386       ast_uri_encode(newval, buf2, sizeof(buf2), EncodeSpecialChars);
00387       ast_str_append(&query, 0, "%s%s=%s", i > 0 ? "&" : "", buf1, buf2);
00388    }
00389    va_end(ap);
00390 
00391    ast_str_append(&query, 0, ")}");
00392    pbx_substitute_variables_helper(NULL, query->str, buffer, bufsize);
00393 
00394    /* Line oriented output */
00395    stringp = buffer;
00396    while (*stringp <= ' ')
00397       stringp++;
00398    sscanf(stringp, "%d", &rowcount);
00399 
00400    ast_free(buffer);
00401    ast_free(query);
00402 
00403    if (rowcount >= 0)
00404       return (int)rowcount;
00405 
00406    return -1;
00407 }

static int load_module ( void   )  [static]

Definition at line 502 of file res_config_curl.c.

References ast_config_engine_register(), ast_verb, and curl_engine.

00503 {
00504    ast_config_engine_register(&curl_engine);
00505    ast_verb(1, "res_config_curl loaded.\n");
00506    return 0;
00507 }

static struct ast_variable* realtime_curl ( const char *  url,
const char *  unused,
va_list  ap 
) [static]

Execute a curl query and return ast_variable list.

Parameters:
url The base URL from which to retrieve data
unused Not currently used
ap list containing one or more field/operator/value set.
Return values:
var on success
NULL on failure

Definition at line 56 of file res_config_curl.c.

References ast_custom_function_find(), ast_free, ast_log(), ast_malloc, ast_str_append(), ast_str_create(), ast_str_set(), ast_strlen_zero(), ast_uri_decode(), ast_uri_encode(), ast_variable_new(), LOG_ERROR, pbx_substitute_variables_helper(), S_OR, ast_str::str, strsep(), and var.

00057 {
00058    struct ast_str *query;
00059    char buf1[200], buf2[200];
00060    const char *newparam, *newval;
00061    char *stringp, *pair, *key;
00062    int i;
00063    struct ast_variable *var=NULL, *prev=NULL;
00064    const int EncodeSpecialChars = 1, bufsize = 64000;
00065    char *buffer;
00066 
00067    if (!ast_custom_function_find("CURL")) {
00068       ast_log(LOG_ERROR, "func_curl.so must be loaded in order to use res_config_curl.so!!\n");
00069       return NULL;
00070    }
00071 
00072    if (!(query = ast_str_create(1000)))
00073       return NULL;
00074 
00075    if (!(buffer = ast_malloc(bufsize))) {
00076       ast_free(query);
00077       return NULL;
00078    }
00079 
00080    ast_str_set(&query, 0, "${CURL(%s/single,", url);
00081 
00082    for (i = 0; (newparam = va_arg(ap, const char *)); i++) {
00083       newval = va_arg(ap, const char *);
00084       ast_uri_encode(newparam, buf1, sizeof(buf1), EncodeSpecialChars);
00085       ast_uri_encode(newval, buf2, sizeof(buf2), EncodeSpecialChars);
00086       ast_str_append(&query, 0, "%s%s=%s", i > 0 ? "&" : "", buf1, buf2);
00087    }
00088    va_end(ap);
00089 
00090    ast_str_append(&query, 0, ")}");
00091    pbx_substitute_variables_helper(NULL, query->str, buffer, bufsize);
00092 
00093    /* Remove any trailing newline characters */
00094    if ((stringp = strchr(buffer, '\r')) || (stringp = strchr(buffer, '\n')))
00095       *stringp = '\0';
00096 
00097    stringp = buffer;
00098    while ((pair = strsep(&stringp, "&"))) {
00099       key = strsep(&pair, "=");
00100       ast_uri_decode(key);
00101       if (pair)
00102          ast_uri_decode(pair);
00103 
00104       if (!ast_strlen_zero(key)) {
00105          if (prev) {
00106             prev->next = ast_variable_new(key, S_OR(pair, ""), "");
00107             if (prev->next)
00108                prev = prev->next;
00109          } else 
00110             prev = var = ast_variable_new(key, S_OR(pair, ""), "");
00111       }
00112    }
00113 
00114    ast_free(buffer);
00115    ast_free(query);
00116    return var;
00117 }

static struct ast_config* realtime_multi_curl ( const char *  url,
const char *  unused,
va_list  ap 
) [static]

Excute an Select query and return ast_config list.

Parameters:
url 
unused 
ap list containing one or more field/operator/value set.
Return values:
struct ast_config pointer on success
NULL on failure

Definition at line 128 of file res_config_curl.c.

References ast_category_append(), ast_category_new(), ast_category_rename(), ast_config_new(), ast_custom_function_find(), ast_free, ast_log(), ast_malloc, ast_str_append(), ast_str_create(), ast_str_set(), ast_strdupa, ast_strlen_zero(), ast_uri_decode(), ast_uri_encode(), ast_variable_append(), ast_variable_new(), LOG_ERROR, pbx_substitute_variables_helper(), S_OR, ast_str::str, strsep(), and var.

00129 {
00130    struct ast_str *query;
00131    char buf1[200], buf2[200];
00132    const char *newparam, *newval;
00133    char *stringp, *line, *pair, *key, *initfield = NULL;
00134    int i;
00135    const int EncodeSpecialChars = 1, bufsize = 256000;
00136    struct ast_variable *var=NULL;
00137    struct ast_config *cfg=NULL;
00138    struct ast_category *cat=NULL;
00139    char *buffer;
00140 
00141    if (!ast_custom_function_find("CURL")) {
00142       ast_log(LOG_ERROR, "func_curl.so must be loaded in order to use res_config_curl.so!!\n");
00143       return NULL;
00144    }
00145 
00146    if (!(query = ast_str_create(1000)))
00147       return NULL;
00148 
00149    if (!(buffer = ast_malloc(bufsize))) {
00150       ast_free(query);
00151       return NULL;
00152    }
00153 
00154    ast_str_set(&query, 0, "${CURL(%s/multi,", url);
00155 
00156    for (i = 0; (newparam = va_arg(ap, const char *)); i++) {
00157       newval = va_arg(ap, const char *);
00158       if (i == 0) {
00159          char *op;
00160          initfield = ast_strdupa(newparam);
00161          if ((op = strchr(initfield, ' ')))
00162             *op = '\0';
00163       }
00164       ast_uri_encode(newparam, buf1, sizeof(buf1), EncodeSpecialChars);
00165       ast_uri_encode(newval, buf2, sizeof(buf2), EncodeSpecialChars);
00166       ast_str_append(&query, 0, "%s%s=%s", i > 0 ? "&" : "", buf1, buf2);
00167    }
00168    va_end(ap);
00169 
00170    ast_str_append(&query, 0, ")}");
00171 
00172    /* Do the CURL query */
00173    pbx_substitute_variables_helper(NULL, query->str, buffer, bufsize);
00174 
00175    if (!(cfg = ast_config_new()))
00176       goto exit_multi;
00177 
00178    /* Line oriented output */
00179    stringp = buffer;
00180    while ((line = strsep(&stringp, "\r\n"))) {
00181       if (ast_strlen_zero(line))
00182          continue;
00183 
00184       if (!(cat = ast_category_new("", "", 99999)))
00185          continue;
00186 
00187       while ((pair = strsep(&line, "&"))) {
00188          key = strsep(&pair, "=");
00189          ast_uri_decode(key);
00190          if (pair)
00191             ast_uri_decode(pair);
00192 
00193          if (!strcasecmp(key, initfield) && pair)
00194             ast_category_rename(cat, pair);
00195 
00196          if (!ast_strlen_zero(key)) {
00197             var = ast_variable_new(key, S_OR(pair, ""), "");
00198             ast_variable_append(cat, var);
00199          }
00200       }
00201       ast_category_append(cfg, cat);
00202    }
00203 
00204 exit_multi:
00205    ast_free(buffer);
00206    ast_free(query);
00207    return cfg;
00208 }

static int store_curl ( const char *  url,
const char *  unused,
va_list  ap 
) [static]

Execute an INSERT query.

Parameters:
url 
unused 
ap list containing one or more field/value set(s)
Insert a new record into database table, prepare the sql statement. All values to be changed are stored in ap list. Sub-in the values to the prepared statement and execute it.

Return values:
number of rows affected
-1 on failure

Definition at line 291 of file res_config_curl.c.

References ast_custom_function_find(), ast_free, ast_log(), ast_malloc, ast_str_append(), ast_str_create(), ast_str_set(), ast_uri_encode(), LOG_ERROR, pbx_substitute_variables_helper(), and ast_str::str.

00292 {
00293    struct ast_str *query;
00294    char buf1[200], buf2[200];
00295    const char *newparam, *newval;
00296    char *stringp;
00297    int i, rowcount = -1;
00298    const int EncodeSpecialChars = 1, bufsize = 100;
00299    char *buffer;
00300 
00301    if (!ast_custom_function_find("CURL")) {
00302       ast_log(LOG_ERROR, "func_curl.so must be loaded in order to use res_config_curl.so!!\n");
00303       return -1;
00304    }
00305 
00306    if (!(query = ast_str_create(1000)))
00307       return -1;
00308 
00309    if (!(buffer = ast_malloc(bufsize))) {
00310       ast_free(query);
00311       return -1;
00312    }
00313 
00314    ast_str_set(&query, 0, "${CURL(%s/store,", url);
00315 
00316    for (i = 0; (newparam = va_arg(ap, const char *)); i++) {
00317       newval = va_arg(ap, const char *);
00318       ast_uri_encode(newparam, buf1, sizeof(buf1), EncodeSpecialChars);
00319       ast_uri_encode(newval, buf2, sizeof(buf2), EncodeSpecialChars);
00320       ast_str_append(&query, 0, "%s%s=%s", i > 0 ? "&" : "", buf1, buf2);
00321    }
00322    va_end(ap);
00323 
00324    ast_str_append(&query, 0, ")}");
00325    pbx_substitute_variables_helper(NULL, query->str, buffer, bufsize);
00326 
00327    stringp = buffer;
00328    while (*stringp <= ' ')
00329       stringp++;
00330    sscanf(stringp, "%d", &rowcount);
00331 
00332    ast_free(buffer);
00333    ast_free(query);
00334 
00335    if (rowcount >= 0)
00336       return (int)rowcount;
00337 
00338    return -1;
00339 }

static int unload_module ( void   )  [static]

Definition at line 495 of file res_config_curl.c.

References ast_config_engine_deregister(), ast_verb, and curl_engine.

00496 {
00497    ast_config_engine_deregister(&curl_engine);
00498    ast_verb(1, "res_config_curl unloaded.\n");
00499    return 0;
00500 }

static int update_curl ( const char *  url,
const char *  unused,
const char *  keyfield,
const char *  lookup,
va_list  ap 
) [static]

Execute an UPDATE query.

Parameters:
url 
unused 
keyfield where clause field
lookup value of field for where clause
ap list containing one or more field/value set(s).
Update a database table, prepare the sql statement using keyfield and lookup control the number of records to change. All values to be changed are stored in ap list. Sub-in the values to the prepared statement and execute it.

Return values:
number of rows affected
-1 on failure

Definition at line 225 of file res_config_curl.c.

References ast_custom_function_find(), ast_free, ast_log(), ast_malloc, ast_str_append(), ast_str_create(), ast_str_set(), ast_uri_encode(), LOG_ERROR, pbx_substitute_variables_helper(), and ast_str::str.

00226 {
00227    struct ast_str *query;
00228    char buf1[200], buf2[200];
00229    const char *newparam, *newval;
00230    char *stringp;
00231    int i, rowcount = -1;
00232    const int EncodeSpecialChars = 1, bufsize = 100;
00233    char *buffer;
00234 
00235    if (!ast_custom_function_find("CURL")) {
00236       ast_log(LOG_ERROR, "func_curl.so must be loaded in order to use res_config_curl.so!!\n");
00237       return -1;
00238    }
00239 
00240    if (!(query = ast_str_create(1000)))
00241       return -1;
00242 
00243    if (!(buffer = ast_malloc(bufsize))) {
00244       ast_free(query);
00245       return -1;
00246    }
00247 
00248    ast_uri_encode(keyfield, buf1, sizeof(buf1), EncodeSpecialChars);
00249    ast_uri_encode(lookup, buf2, sizeof(buf2), EncodeSpecialChars);
00250    ast_str_set(&query, 0, "${CURL(%s/update?%s=%s,", url, buf1, buf2);
00251 
00252    for (i = 0; (newparam = va_arg(ap, const char *)); i++) {
00253       newval = va_arg(ap, const char *);
00254       ast_uri_encode(newparam, buf1, sizeof(buf1), EncodeSpecialChars);
00255       ast_uri_encode(newval, buf2, sizeof(buf2), EncodeSpecialChars);
00256       ast_str_append(&query, 0, "%s%s=%s", i > 0 ? "&" : "", buf1, buf2);
00257    }
00258    va_end(ap);
00259 
00260    ast_str_append(&query, 0, ")}");
00261    pbx_substitute_variables_helper(NULL, query->str, buffer, bufsize);
00262 
00263    /* Line oriented output */
00264    stringp = buffer;
00265    while (*stringp <= ' ')
00266       stringp++;
00267    sscanf(stringp, "%d", &rowcount);
00268 
00269    ast_free(buffer);
00270    ast_free(query);
00271 
00272    if (rowcount >= 0)
00273       return (int)rowcount;
00274 
00275    return -1;
00276 }


Variable Documentation

struct ast_module_info __mod_info = { .name = AST_MODULE, .flags = AST_MODFLAG_DEFAULT , .description = "Realtime Curl configuration" , .key = "This paragraph is copyright (c) 2006 by Digium, Inc. \In order for your module to load, it must return this \key via a function called \"key\". Any code which \includes this paragraph must be licensed under the GNU \General Public License version 2 or later (at your \option). In addition to Digium's general reservations \of rights, Digium expressly reserves the right to \allow other parties to license this paragraph under \different terms. Any use of Digium, Inc. trademarks or \logos (including \"Asterisk\" or \"Digium\") without \express written permission of Digium, Inc. is prohibited.\n" , .buildopt_sum = "068e67f60f50dd9ee86464c05884a49d" , .load = load_module, .unload = unload_module, } [static]

Definition at line 509 of file res_config_curl.c.

const struct ast_module_info* ast_module_info = &__mod_info [static]

Definition at line 509 of file res_config_curl.c.

struct ast_config_engine curl_engine [static]

Definition at line 485 of file res_config_curl.c.

Referenced by load_module(), and unload_module().


Generated on Thu Jul 9 13:41:29 2009 for Asterisk - the Open Source PBX by  doxygen 1.4.7