static int cx_handle_parsed_xml(xmlDocPtr doc, /* {{{ */ xmlXPathContextPtr xpath_ctx, cx_t *db) { llentry_t *le; const data_set_t *ds; cx_xpath_t *xpath; int status=-1; le = llist_head (db->list); while (le != NULL) { /* get the ds */ xpath = (cx_xpath_t *) le->value; ds = plugin_get_ds (xpath->type); if ( (cx_check_type(ds, xpath) == 0) && (cx_handle_base_xpath(db->instance, cx_host (db), xpath_ctx, ds, le->key, xpath) == 0) ) status = 0; /* we got atleast one success */ le = le->next; } /* while (le != NULL) */ return status; } /* }}} cx_handle_parsed_xml */
static int cx_read(user_data_t *ud) /* {{{ */ { if ((ud == NULL) || (ud->data == NULL)) { ERROR("curl_xml plugin: cx_read: Invalid user data."); return -1; } long rc; char *url; cx_t *db = (cx_t *)ud->data; db->buffer_fill = 0; curl_easy_setopt(db->curl, CURLOPT_URL, db->url); int status = curl_easy_perform(db->curl); if (status != CURLE_OK) { ERROR("curl_xml plugin: curl_easy_perform failed with status %i: %s (%s)", status, db->curl_errbuf, db->url); return -1; } if (db->stats != NULL) curl_stats_dispatch(db->stats, db->curl, cx_host(db), "curl_xml", db->instance); curl_easy_getinfo(db->curl, CURLINFO_EFFECTIVE_URL, &url); curl_easy_getinfo(db->curl, CURLINFO_RESPONSE_CODE, &rc); /* The response code is zero if a non-HTTP transport was used. */ if ((rc != 0) && (rc != 200)) { ERROR( "curl_xml plugin: curl_easy_perform failed with response code %ld (%s)", rc, url); return -1; } status = cx_parse_xml(db, db->buffer); db->buffer_fill = 0; return status; } /* }}} int cx_read */
static int cx_curl_perform(cx_t *db, CURL *curl) /* {{{ */ { int status; long rc; char *ptr; char *url; db->buffer_fill = 0; curl_easy_setopt(db->curl, CURLOPT_URL, db->url); status = curl_easy_perform(curl); if (status != CURLE_OK) { ERROR("curl_xml plugin: curl_easy_perform failed with status %i: %s (%s)", status, db->curl_errbuf, db->url); return -1; } if (db->stats != NULL) curl_stats_dispatch(db->stats, db->curl, cx_host(db), "curl_xml", db->instance); curl_easy_getinfo(curl, CURLINFO_EFFECTIVE_URL, &url); curl_easy_getinfo(curl, CURLINFO_RESPONSE_CODE, &rc); /* The response code is zero if a non-HTTP transport was used. */ if ((rc != 0) && (rc != 200)) { ERROR( "curl_xml plugin: curl_easy_perform failed with response code %ld (%s)", rc, url); return -1; } ptr = db->buffer; status = cx_parse_stats_xml(BAD_CAST ptr, db); db->buffer_fill = 0; return status; } /* }}} int cx_curl_perform */
static int cx_handle_xpath(const cx_t *db, /* {{{ */ xmlXPathContextPtr xpath_ctx, cx_xpath_t *xpath) { const data_set_t *ds = plugin_get_ds(xpath->type); if (cx_check_type(ds, xpath) != 0) return -1; xmlXPathObjectPtr base_node_obj = cx_evaluate_xpath(xpath_ctx, xpath->path); if (base_node_obj == NULL) return -1; /* error is logged already */ xmlNodeSetPtr base_nodes = base_node_obj->nodesetval; int total_nodes = (base_nodes) ? base_nodes->nodeNr : 0; if (total_nodes == 0) { ERROR("curl_xml plugin: " "xpath expression \"%s\" doesn't match any of the nodes. " "Skipping the xpath block...", xpath->path); xmlXPathFreeObject(base_node_obj); return -1; } /* If base_xpath returned multiple results, then */ /* InstanceFrom or PluginInstanceFrom in the xpath block is required */ if (total_nodes > 1 && xpath->instance == NULL && xpath->plugin_instance_from == NULL) { ERROR("curl_xml plugin: " "InstanceFrom or PluginInstanceFrom is must in xpath block " "since the base xpath expression \"%s\" " "returned multiple results. Skipping the xpath block...", xpath->path); xmlXPathFreeObject(base_node_obj); return -1; } value_list_t vl = VALUE_LIST_INIT; /* set the values for the value_list */ vl.values_len = ds->ds_num; sstrncpy(vl.type, xpath->type, sizeof(vl.type)); sstrncpy(vl.plugin, (db->plugin_name != NULL) ? db->plugin_name : "curl_xml", sizeof(vl.plugin)); sstrncpy(vl.host, cx_host(db), sizeof(vl.host)); for (int i = 0; i < total_nodes; i++) { xpath_ctx->node = base_nodes->nodeTab[i]; if (db->instance != NULL) sstrncpy(vl.plugin_instance, db->instance, sizeof(vl.plugin_instance)); if (cx_handle_instance_xpath(xpath_ctx, xpath, &vl) != 0) continue; /* An error has already been reported. */ if (cx_handle_all_value_xpaths(xpath_ctx, xpath, ds, &vl) != 0) continue; /* An error has been logged. */ } /* for (i = 0; i < total_nodes; i++) */ /* free up the allocated memory */ xmlXPathFreeObject(base_node_obj); return 0; } /* }}} cx_handle_xpath */