/************************************************************************** * * STATUSJSON.C - Nagios CGI for returning JSON-formatted status data * * Copyright (c) 2013 Nagios Enterprises, LLC * Last Modified: 04-13-2013 * * License: * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 as * published by the Free Software Foundation. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. *************************************************************************/ /* TODO: Return an error when the authenticated user is not authorized for the requested host or service Consolidate criteria functions for *count and *list queries Move static programstatus information to objectjson.c? */ #include "../include/config.h" #include "../include/common.h" #include "../include/objects.h" #include "../include/statusdata.h" #include "../include/comments.h" #include "../include/downtime.h" #include "../include/cgiutils.h" #include "../include/getcgi.h" #include "../include/cgiauth.h" #include "../include/jsonutils.h" #include "../include/objectjson.h" #include "../include/statusjson.h" #define THISCGI "statusjson.cgi" #ifdef JSON_NAGIOS_4X #define HOST_STATUS_ALL (SD_HOST_UP | SD_HOST_DOWN | SD_HOST_UNREACHABLE | HOST_PENDING) #define SERVICE_STATUS_ALL (SERVICE_OK | SERVICE_WARNING | SERVICE_CRITICAL | SERVICE_UNKNOWN | SERVICE_PENDING) #else #define HOST_STATUS_ALL (HOST_UP | HOST_DOWN | HOST_UNREACHABLE | HOST_PENDING) #define SERVICE_STATUS_ALL (SERVICE_OK | SERVICE_WARNING | SERVICE_CRITICAL | SERVICE_UNKNOWN | SERVICE_PENDING) #endif extern char main_config_file[MAX_FILENAME_LENGTH]; extern char *status_file; extern host *host_list; extern hoststatus *hoststatus_list; extern service *service_list; #if 0 extern contact *contact_list; #endif extern servicestatus *servicestatus_list; extern nagios_comment *comment_list; extern scheduled_downtime *scheduled_downtime_list; /* Program status variables */ extern unsigned long modified_host_process_attributes; extern unsigned long modified_service_process_attributes; extern int nagios_pid; extern int daemon_mode; extern time_t program_start; #ifndef JSON_NAGIOS_4X extern time_t last_command_check; #endif extern time_t last_log_rotation; extern int enable_notifications; extern int execute_service_checks; extern int accept_passive_service_checks; extern int execute_host_checks; extern int accept_passive_host_checks; extern int enable_event_handlers; extern int obsess_over_services; extern int obsess_over_hosts; extern int check_service_freshness; extern int check_host_freshness; extern int enable_flap_detection; #ifndef JSON_NAGIOS_4X extern int enable_failure_prediction; #endif extern int process_performance_data; #if 0 extern char *global_host_event_handler; extern char *global_service_event_handler; extern unsigned long next_comment_id; extern unsigned long next_downtime_id; extern unsigned long next_event_id; extern unsigned long next_problem_id; extern unsigned long next_notification_id; extern int external_command_buffer_slots; extern check_stats check_statistics[MAX_CHECK_STATS_TYPES]; #endif /* Performance data variables */ extern int program_stats[MAX_CHECK_STATS_TYPES][3]; extern int buffer_stats[1][3]; void document_header(int); void document_footer(void); void init_cgi_data(status_json_cgi_data *); int process_cgivars(json_object *, status_json_cgi_data *, time_t); void free_cgi_data(status_json_cgi_data *); int validate_arguments(json_object *, status_json_cgi_data *, time_t); authdata current_authdata; const string_value_mapping valid_queries[] = { { "hostcount", STATUS_QUERY_HOSTCOUNT, "Return the number of hosts in each state" }, { "hostlist", STATUS_QUERY_HOSTLIST, "Return a list of hosts and their current status" }, { "host", STATUS_QUERY_HOST, "Return the status of a single host." }, { "servicecount", STATUS_QUERY_SERVICECOUNT, "Return the number of services in each state" }, { "servicelist", STATUS_QUERY_SERVICELIST, "Return a list of services and their current status" }, { "service", STATUS_QUERY_SERVICE, "Return the status of a single service" }, #if 0 { "contactcount", STATUS_QUERY_CONTACTCOUNT, "Return the number of contacts" }, { "contactlist", STATUS_QUERY_CONTACTLIST, "Return a list of of contacts and their current status" }, { "contact", STATUS_QUERY_CONTACT, "Return a single contact" }, #endif { "commentcount", STATUS_QUERY_COMMENTCOUNT, "Return the number of comments" }, { "commentlist", STATUS_QUERY_COMMENTLIST, "Return a list of comments" }, { "comment", STATUS_QUERY_COMMENT, "Return a single comment" }, { "downtimecount", STATUS_QUERY_DOWNTIMECOUNT, "Return the number of downtimes" }, { "downtimelist", STATUS_QUERY_DOWNTIMELIST, "Return a list of downtimes" }, { "downtime", STATUS_QUERY_DOWNTIME, "Return a single downtime" }, { "programstatus", STATUS_QUERY_PROGRAMSTATUS, "Return the Nagios Core program status" }, { "performancedata", STATUS_QUERY_PERFORMANCEDATA, "Return the Nagios Core performance data" }, { "help", STATUS_QUERY_HELP, "Display help for this CGI" }, { NULL, -1, NULL}, }; static const int query_status[][2] = { { STATUS_QUERY_HOSTCOUNT, QUERY_STATUS_RELEASED }, { STATUS_QUERY_HOSTLIST, QUERY_STATUS_RELEASED }, { STATUS_QUERY_HOST, QUERY_STATUS_RELEASED }, { STATUS_QUERY_SERVICECOUNT, QUERY_STATUS_RELEASED }, { STATUS_QUERY_SERVICELIST, QUERY_STATUS_RELEASED }, { STATUS_QUERY_SERVICE, QUERY_STATUS_RELEASED }, #if 0 { STATUS_QUERY_CONTACTCOUNT, QUERY_STATUS_BETA }, { STATUS_QUERY_CONTACTLIST, QUERY_STATUS_BETA }, { STATUS_QUERY_CONTACT, QUERY_STATUS_BETA }, #endif { STATUS_QUERY_COMMENTCOUNT, QUERY_STATUS_RELEASED }, { STATUS_QUERY_COMMENTLIST, QUERY_STATUS_RELEASED }, { STATUS_QUERY_COMMENT, QUERY_STATUS_RELEASED }, { STATUS_QUERY_DOWNTIMECOUNT, QUERY_STATUS_RELEASED }, { STATUS_QUERY_DOWNTIMELIST, QUERY_STATUS_RELEASED }, { STATUS_QUERY_DOWNTIME, QUERY_STATUS_RELEASED }, { STATUS_QUERY_PROGRAMSTATUS, QUERY_STATUS_RELEASED }, { STATUS_QUERY_PERFORMANCEDATA, QUERY_STATUS_RELEASED }, { STATUS_QUERY_HELP, QUERY_STATUS_RELEASED }, { -1, -1}, }; const string_value_mapping svm_host_time_fields[] = { { "lastupdate", STATUS_TIME_LAST_UPDATE, "Last Update" }, { "lastcheck", STATUS_TIME_LAST_CHECK, "Last Check" }, { "nextcheck", STATUS_TIME_NEXT_CHECK, "Next Check" }, { "laststatechange", STATUS_TIME_LAST_STATE_CHANGE, "Last State Change" }, { "lasthardstatechange", STATUS_TIME_LAST_HARD_STATE_CHANGE, "Last Hard State Change" }, { "lasttimeup", STATUS_TIME_LAST_TIME_UP, "Last Time Up" }, { "lasttimedown", STATUS_TIME_LAST_TIME_DOWN, "Last Time Down" }, { "lasttimeunreachable", STATUS_TIME_LAST_TIME_UNREACHABLE, "Last Time Unreachable" }, { "lastnotification", STATUS_TIME_LAST_NOTIFICATION, "Last Notification" }, { "nextnotification", STATUS_TIME_NEXT_NOTIFICATION, "Next Notification" }, { NULL, -1, NULL }, }; const string_value_mapping svm_service_time_fields[] = { { "lastupdate", STATUS_TIME_LAST_UPDATE, "Last Update" }, { "lastcheck", STATUS_TIME_LAST_CHECK, "Last Check" }, { "nextcheck", STATUS_TIME_NEXT_CHECK, "Next Check" }, { "laststatechange", STATUS_TIME_LAST_STATE_CHANGE, "Last State Change" }, { "lasthardstatechange", STATUS_TIME_LAST_HARD_STATE_CHANGE, "Last Hard State Change" }, { "lasttimeok", STATUS_TIME_LAST_TIME_OK, "Last Time OK" }, { "lasttimewarning", STATUS_TIME_LAST_TIME_WARNING, "Last Time Warning" }, { "lasttimecritical", STATUS_TIME_LAST_TIME_CRITICAL, "Last Time Critical" }, { "lasttimeunknown", STATUS_TIME_LAST_TIME_UNKNOWN, "Last Time Unknown" }, { "lastnotification", STATUS_TIME_LAST_NOTIFICATION, "Last Notification" }, { "nextnotification", STATUS_TIME_NEXT_NOTIFICATION, "Next Notification" }, { NULL, -1, NULL }, }; const string_value_mapping svm_valid_comment_types[] = { { "host", COMMENT_TYPE_HOST, "Host Comment" }, { "service", COMMENT_TYPE_SERVICE, "Service Comment" }, { NULL, -1, NULL }, }; const string_value_mapping svm_valid_comment_entry_types[] = { { "user", COMMENT_ENTRY_USER, "User Comment" }, { "downtime", COMMENT_ENTRY_DOWNTIME, "Downtime Comment" }, { "flapping", COMMENT_ENTRY_FLAPPING, "Flapping Comment" }, { "acknowledgement", COMMENT_ENTRY_ACKNOWLEDGEMENT, "Acknowledgement Comment" }, { NULL, -1, NULL }, }; const string_value_mapping svm_valid_persistence[] = { { "yes", BOOLEAN_TRUE, "Persistent Comment" }, { "no", BOOLEAN_FALSE, "Non-Persistent Comment" }, { NULL, -1, NULL }, }; const string_value_mapping svm_valid_expiration[] = { { "yes", BOOLEAN_TRUE, "Comment Expires" }, { "no", BOOLEAN_FALSE, "Comment Does Not Expire" }, { NULL, -1, NULL }, }; const string_value_mapping svm_comment_time_fields[] = { { "entrytime", STATUS_TIME_ENTRY_TIME, "Entry Time" }, { "expiretime", STATUS_TIME_EXPIRE_TIME, "Expiration Time" }, { NULL, -1, NULL }, }; const string_value_mapping svm_downtime_time_fields[] = { { "entrytime", STATUS_TIME_ENTRY_TIME, "Entry Time" }, { "starttime", STATUS_TIME_START_TIME, "Start Time" }, { "flexdowntimestart", STATUS_TIME_FLEX_DOWNTIME_START, "Flex Downtime Start" }, { "endtime", STATUS_TIME_END_TIME, "End Time" }, { NULL, -1, NULL }, }; const string_value_mapping svm_valid_downtime_object_types[] = { { "host", DOWNTIME_OBJECT_TYPE_HOST, "Host Downtime" }, { "service", DOWNTIME_OBJECT_TYPE_SERVICE, "Service Downtime" }, { NULL, -1, NULL }, }; const string_value_mapping svm_valid_downtime_types[] = { { "fixed", DOWNTIME_TYPE_FIXED, "Fixed Downtime" }, { "flexible", DOWNTIME_TYPE_FLEXIBLE, "Flexible Downtime" }, { NULL, -1, NULL }, }; const string_value_mapping svm_valid_triggered_status[] = { { "yes", BOOLEAN_TRUE, "Downtime Triggered" }, { "no", BOOLEAN_FALSE, "Downtime Not Triggered" }, { NULL, -1, NULL }, }; const string_value_mapping svm_valid_in_effect_status[] = { { "yes", BOOLEAN_TRUE, "Downtime In Effect" }, { "no", BOOLEAN_FALSE, "Downtime Not In Effect" }, { NULL, -1, NULL }, }; option_help status_json_help[] = { { "query", "Query", "enumeration", { "all", NULL }, { NULL }, NULL, "Specifies the type of query to be executed.", valid_queries }, { "formatoptions", "Format Options", "list", { NULL }, { "all", NULL }, NULL, "Specifies the formatting options to be used when displaying the results. Multiple options are allowed and are separated by a plus (+) sign..", svm_format_options }, { "start", "Start", "integer", { NULL }, { "hostlist", "servicelist", NULL }, NULL, "Specifies the index (zero-based) of the first object in the list to be returned.", NULL }, { "count", "Count", "integer", { NULL }, { "hostlist", "servicelist", NULL }, NULL, "Specifies the number of objects in the list to be returned.", NULL }, { "parenthost", "Parent Host", "nagios:objectjson/hostlist", { NULL }, { "hostcount", "hostlist", "servicecount", "servicelist", NULL }, NULL, "Limits the hosts or services returned to those whose host parent is specified. A value of 'none' returns all hosts or services reachable directly by the Nagios core host.", parent_host_extras }, { "childhost", "Child Host", "nagios:objectjson/hostlist", { NULL }, { "hostcount", "hostlist", "servicecount", "servicelist", NULL }, NULL, "Limits the hosts or services returned to those whose having the host specified as a child host. A value of 'none' returns all hosts or services with no child hosts.", child_host_extras }, { "details", "Show Details", "boolean", { NULL }, { "hostlist", "servicelist", "commentlist", "downtimelist", NULL }, NULL, "Returns the details for all entities in the list.", NULL }, { "dateformat", "Date Format", "string", { NULL }, { "all", NULL }, NULL, "strftime format string for values of type time_t. In the absence of a format, the Javascript default format of the number of milliseconds since the beginning of the Unix epoch is used. Because of URL encoding, percent signs must be encoded as %25 and a space must be encoded as a plus (+) sign.", NULL }, { "hostname", "Host Name", "nagios:objectjson/hostlist", { "host", "service", NULL }, { "servicecount", "servicelist", "commentcount", "commentlist", "downtimecount", "downtimelist", NULL }, NULL, "Name for the host requested.", NULL }, { "hostgroup", "Host Group", "nagios:objectjson/hostgrouplist", { "hostgroup", NULL }, { "hostcount", "hostlist", "servicecount", "servicelist", NULL }, NULL, "Returns information applicable to the hostgroup or the hosts in the hostgroup depending on the query.", NULL }, { "hoststatus", "Host Status", "list", { NULL }, { "hostcount", "hostlist", "servicecount", "servicelist", NULL }, NULL, "Limits returned information to those hosts whose status matches this list. Host statuses are space separated.", svm_host_statuses }, { "servicegroup", "Service Group", "nagios:objectjson/servicegrouplist", { "servicegroup", NULL }, { "servicecount", "servicelist", NULL }, NULL, "Returns information applicable to the servicegroup or the services in the servicegroup depending on the query.", NULL }, { "servicestatus", "Service Status", "list", { NULL }, { "servicecount", "servicelist" }, NULL, "Limits returned information to those services whose status matches this list. Service statuses are space separated.", svm_service_statuses }, { "parentservice", "Parent Service", "nagios:objectjson/servicelist", { NULL }, { "servicecount", "servicelist", NULL }, NULL, "Limits the services returned to those whose service parent has the name specified. A value of 'none' returns all services with no service parent.", parent_service_extras }, { "childservice", "Child Service", "nagios:objectjson/servicelist", { NULL }, { "servicecount", "servicelist", NULL }, NULL, "Limits the services returned to those whose having the named service as a child service. A value of 'none' returns all services with no child services.", child_service_extras }, { "contactgroup", "Contact Group", "nagios:objectjson/contactgrouplist", { "contactgroup", NULL }, { "hostcount", "hostlist", "servicecount", "servicelist", NULL }, NULL, "Returns information applicable to the contactgroup or the contacts in the contactgroup depending on the query.", NULL }, { "servicedescription", "Service Description", "nagios:objectjson/servicelist", /* "for query: 'service'",*/ { "service", NULL }, { "servicecount", "servicelist", "commentcount", "commentlist", "downtimecount", "downtimelist", NULL }, "hostname", "Description for the service requested.", NULL }, { "checktimeperiod", "Check Timeperiod Name", "nagios:objectjson/timeperiodlist", { NULL }, { "hostcount","hostlist", "servicecount", "servicelist", NULL }, NULL, "Name of a check timeperiod to be used as selection criteria.", NULL }, { "hostnotificationtimeperiod", "Host Notification Timeperiod Name", "nagios:objectjson/timeperiodlist", { NULL }, { "hostcount","hostlist", NULL }, NULL, "Name of a host notification timeperiod to be used as selection criteria.", NULL }, { "servicenotificationtimeperiod", "Service Notification Timeperiod Name", "nagios:objectjson/timeperiodlist", { NULL }, { "servicecount", "servicelist", NULL }, NULL, "Name of a service notification timeperiod to be used as selection criteria.", NULL }, { "checkcommand", "Check Command Name", "nagios:objectjson/commandlist", { NULL }, { "hostcount", "hostlist", "servicecount", "servicelist", NULL }, NULL, "Name of a check command to be be used as a selector.", NULL }, { "eventhandler", "Event Handler Name", "nagios:objectjson/commandlist", { NULL }, { "hostcount", "hostlist", "servicecount", "servicelist", NULL }, NULL, "Name of an event handler to be be used as a selector.", NULL }, { "commenttypes", "Comment Type", "list", { NULL }, { "commentcount", "commentlist", NULL }, NULL, "Comment type for the comment requested.", svm_valid_comment_types }, { "entrytypes", "Entry Type", "list", { NULL }, { "commentcount", "commentlist", NULL }, NULL, "Entry type for the comment requested.", svm_valid_comment_entry_types }, { "persistence", "Comment Persistence", "list", { NULL }, { "commentcount", "commentlist", NULL }, NULL, "Persistence for the comment requested.", svm_valid_persistence }, { "expiring", "Comment Expiration", "list", { NULL }, { "commentcount", "commentlist", NULL }, NULL, "Whether or not the comment expires.", svm_valid_expiration }, { "downtimeobjecttypes", "Downtime Object Type", "list", { NULL }, { "downtimecount", "downtimelist", NULL }, NULL, "The type of object to which the downtime applies.", svm_valid_downtime_object_types }, { "downtimetypes", "Downtime Type", "list", { NULL }, { "downtimecount", "downtimelist", NULL }, NULL, "The type of the downtime.", svm_valid_downtime_types }, { "triggered", "Downtime Triggered", "list", { NULL }, { "downtimecount", "downtimelist", NULL }, NULL, "Whether or not the downtime is triggered.", svm_valid_triggered_status }, { "triggeredby", "Triggered By", "nagios:statusjson/downtimelist", { NULL }, { "downtimecount", "downtimelist", NULL }, NULL, "ID of the downtime which triggers other downtimes.", NULL }, { "ineffect", "Downtime In Effect", "list", { NULL }, { "downtimecount", "downtimelist", NULL }, NULL, "Whether or not the downtime is in effect.", svm_valid_in_effect_status }, { "commentid", "Comment ID", "nagios:statusjson/commentlist", { "comment", NULL }, { NULL }, NULL, "Comment ID for the comment requested.", NULL }, { "downtimeid", "Downtime ID", "nagios:statusjson/downtimelist", { "downtime", NULL }, { NULL }, NULL, "Downtime ID for the downtime requested.", NULL }, { "contactname", "Contact Name", "nagios:objectjson/contactlist", { NULL }, { "hostcount", "hostlist", "servicecount", "servicelist", NULL }, NULL, "Name for the contact requested.", NULL }, { "hosttimefield", "Host Time Field", "enumeration", { NULL }, { "hostcount", "hostlist", NULL }, NULL, "Field to use when comparing times on a hostlist query.", svm_host_time_fields }, { "servicetimefield", "Service Time Field", "enumeration", { NULL }, { "servicecount", "servicelist", NULL }, NULL, "Field to use when comparing times on a servicelist query.", svm_service_time_fields }, { "commenttimefield", "Comment Time Field", "enumeration", { NULL }, { "commentcount", "commentlist", NULL }, NULL, "Field to use when comparing times on a commentlist query.", svm_comment_time_fields }, { "downtimetimefield", "Downtime Time Field", "enumeration", { NULL }, { "downtimecount", "downtimelist", NULL }, NULL, "Field to use when comparing times on a downtimelist query.", svm_downtime_time_fields }, { "starttime", "Start Time", "integer", { NULL }, { "hostcount", "hostlist", "servicecount", "servicelist", "commentcount", "commentlist", "downtimecount", "downtimelist", NULL }, NULL, "Starting time to use when querying based on a time range. Not specifying a start time implies all entries since the beginning of time. Supplying a plus or minus sign means times relative to the query time.", NULL, }, { "endtime", "End Time", "integer", { NULL }, { "hostcount", "hostlist", "servicecount", "servicelist", "commentcount", "commentlist", "downtimecount", "downtimelist", NULL }, NULL, "Ending time to use when querying based on a time range. Not specifying an end time implies all entries until the time of the query. Specifying plus or minus sign means times relative to the query time.", NULL, }, { /* The last entry must contain all NULL entries */ NULL, NULL, NULL, { NULL }, { NULL }, NULL, NULL, NULL }, }; extern const json_escape percent_escapes; int json_status_host_passes_selection(host *, int, host *, int, host *, hostgroup *, contact *, hoststatus *, int, time_t, time_t, contactgroup *, timeperiod *, timeperiod *, command *, command *); json_object *json_status_host_display_selectors(unsigned, int, int, int, host *, int, host *, hostgroup *, int, contact *, int, time_t, time_t, contactgroup *, timeperiod *, timeperiod *, command *, command *); int json_status_service_passes_host_selection(host *, int, host *, int, host *, hostgroup *, host *, int); int json_status_service_passes_service_selection(service *, servicegroup *, contact *, servicestatus *, int, time_t, time_t, char *, char *, char *, contactgroup *, timeperiod *, timeperiod *, command *, command *); json_object *json_status_service_selectors(unsigned, int, int, int, host *, int, host *, hostgroup *, host *, servicegroup *, int, int, contact *, int, time_t, time_t, char *, char *, char *, contactgroup *, timeperiod *, timeperiod *, command *, command *); int json_status_comment_passes_selection(nagios_comment *, int, time_t, time_t, unsigned, unsigned, unsigned, unsigned, char *, char *); json_object *json_status_comment_selectors(unsigned, int, int, int, time_t, time_t, unsigned, unsigned, unsigned, unsigned, char *, char *); int json_status_downtime_passes_selection(scheduled_downtime *, int, time_t, time_t, unsigned, unsigned, unsigned, int, unsigned, char *, char *); json_object *json_status_downtime_selectors(unsigned, int, int, int, time_t, time_t, unsigned, unsigned, unsigned, int, unsigned, char *, char *); int main(void) { int result = OK; time_t query_time; status_json_cgi_data cgi_data; json_object *json_root; struct stat sdstat; time_t last_status_data_update = (time_t)0; hoststatus *temp_hoststatus = NULL; servicestatus *temp_servicestatus = NULL; /* The official time of the query */ time(&query_time); json_root = json_new_object(); if(NULL == json_root) { printf( "Failed to create new json object\n"); exit( 1); } json_object_append_integer(json_root, "format_version", OUTPUT_FORMAT_VERSION); /* Initialize shared configuration variables */ init_shared_cfg_vars(1); init_cgi_data(&cgi_data); document_header(cgi_data.format_options & JSON_FORMAT_WHITESPACE); /* get the arguments passed in the URL */ result = process_cgivars(json_root, &cgi_data, query_time); if(result != RESULT_SUCCESS) { json_object_append_object(json_root, "data", json_help(status_json_help)); json_object_print(json_root, 0, 1, cgi_data.strftime_format, cgi_data.format_options); document_footer(); return ERROR; } /* reset internal variables */ reset_cgi_vars(); /* read the CGI configuration file */ result = read_cgi_config_file(get_cgi_config_location(), NULL); if(result == ERROR) { json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), (time_t)-1, NULL, RESULT_FILE_OPEN_READ_ERROR, "Error: Could not open CGI configuration file '%s' for reading!", get_cgi_config_location())); json_object_append_object(json_root, "data", json_help(status_json_help)); json_object_print(json_root, 0, 1, cgi_data.strftime_format, cgi_data.format_options); document_footer(); return ERROR; } /* read the main configuration file */ result = read_main_config_file(main_config_file); if(result == ERROR) { json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), (time_t)-1, NULL, RESULT_FILE_OPEN_READ_ERROR, "Error: Could not open main configuration file '%s' for reading!", main_config_file)); json_object_append_object(json_root, "data", json_help(status_json_help)); json_object_print(json_root, 0, 1, cgi_data.strftime_format, cgi_data.format_options); document_footer(); return ERROR; } /* read all object configuration data */ result = read_all_object_configuration_data(main_config_file, READ_ALL_OBJECT_DATA); if(result == ERROR) { json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), (time_t)-1, NULL, RESULT_FILE_OPEN_READ_ERROR, "Error: Could not read some or all object configuration data!")); json_object_append_object(json_root, "data", json_help(status_json_help)); json_object_print(json_root, 0, 1, cgi_data.strftime_format, cgi_data.format_options); document_footer(); return ERROR; } /* Get the update time on the status data file. This needs to occur before the status data is read because the read_all_status_data() function clears the name of the status file */ if(stat(status_file, &sdstat) < 0) { json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), (time_t)-1, NULL, RESULT_FILE_OPEN_READ_ERROR, "Error: Could not obtain status data file status: %s!", strerror(errno))); json_object_append_object(json_root, "data", json_help(status_json_help)); document_footer(); return ERROR; } last_status_data_update = sdstat.st_mtime; /* read all status data */ result = read_all_status_data(status_file, READ_ALL_STATUS_DATA); if(result == ERROR) { json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), (time_t)-1, NULL, RESULT_FILE_OPEN_READ_ERROR, "Error: Could not read host and service status information!")); json_object_append_object(json_root, "data", json_help(status_json_help)); json_object_print(json_root, 0, 1, cgi_data.strftime_format, cgi_data.format_options); document_footer(); return ERROR; } /* validate arguments in URL */ result = validate_arguments(json_root, &cgi_data, query_time); if(result != RESULT_SUCCESS) { json_object_append_object(json_root, "data", json_help(status_json_help)); json_object_print(json_root, 0, 1, cgi_data.strftime_format, cgi_data.format_options); document_footer(); return ERROR; } /* get authentication information */ get_authentication_information(¤t_authdata); /* For most locales, floats get output with a comma instead of a * decimal point, which messes up the JSON data structure. */ setlocale(LC_NUMERIC, "C"); /* Return something to the user */ switch( cgi_data.query) { case STATUS_QUERY_HOSTCOUNT: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_object_append_object(json_root, "data", json_status_hostcount(cgi_data.format_options, cgi_data.use_parent_host, cgi_data.parent_host, cgi_data.use_child_host, cgi_data.child_host, cgi_data.hostgroup, cgi_data.host_statuses, cgi_data.contact, cgi_data.host_time_field, cgi_data.start_time, cgi_data.end_time, cgi_data.contactgroup, cgi_data.check_timeperiod, cgi_data.host_notification_timeperiod, cgi_data.check_command, cgi_data.event_handler)); break; case STATUS_QUERY_HOSTLIST: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_object_append_object(json_root, "data", json_status_hostlist(cgi_data.format_options, cgi_data.start, cgi_data.count, cgi_data.details, cgi_data.use_parent_host, cgi_data.parent_host, cgi_data.use_child_host, cgi_data.child_host, cgi_data.hostgroup, cgi_data.host_statuses, cgi_data.contact, cgi_data.host_time_field, cgi_data.start_time, cgi_data.end_time, cgi_data.contactgroup, cgi_data.check_timeperiod, cgi_data.host_notification_timeperiod, cgi_data.check_command, cgi_data.event_handler)); break; case STATUS_QUERY_HOST: temp_hoststatus = find_hoststatus(cgi_data.host_name); if( NULL == temp_hoststatus) { json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), (time_t)-1, ¤t_authdata, RESULT_OPTION_VALUE_INVALID, "The status for host '%s' could not be found.", cgi_data.host_name)); result = ERROR; } else { json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_object_append_object(json_root, "data", json_status_host(cgi_data.format_options, cgi_data.host, temp_hoststatus)); } break; case STATUS_QUERY_SERVICECOUNT: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_object_append_object(json_root, "data", json_status_servicecount(cgi_data.format_options, cgi_data.host, cgi_data.use_parent_host, cgi_data.parent_host, cgi_data.use_child_host, cgi_data.child_host, cgi_data.hostgroup, cgi_data.servicegroup, cgi_data.host_statuses, cgi_data.service_statuses, cgi_data.contact, cgi_data.service_time_field, cgi_data.start_time, cgi_data.end_time, cgi_data.service_description, cgi_data.parent_service_name, cgi_data.child_service_name, cgi_data.contactgroup, cgi_data.check_timeperiod, cgi_data.service_notification_timeperiod, cgi_data.check_command, cgi_data.event_handler)); break; case STATUS_QUERY_SERVICELIST: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_object_append_object(json_root, "data", json_status_servicelist(cgi_data.format_options, cgi_data.start, cgi_data.count, cgi_data.details, cgi_data.host, cgi_data.use_parent_host, cgi_data.parent_host, cgi_data.use_child_host, cgi_data.child_host, cgi_data.hostgroup, cgi_data.servicegroup, cgi_data.host_statuses, cgi_data.service_statuses, cgi_data.contact, cgi_data.service_time_field, cgi_data.start_time, cgi_data.end_time, cgi_data.service_description, cgi_data.parent_service_name, cgi_data.child_service_name, cgi_data.contactgroup, cgi_data.check_timeperiod, cgi_data.service_notification_timeperiod, cgi_data.check_command, cgi_data.event_handler)); break; case STATUS_QUERY_SERVICE: temp_servicestatus = find_servicestatus(cgi_data.host_name, cgi_data.service_description); if( NULL == temp_servicestatus) { json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), (time_t)-1, ¤t_authdata, RESULT_OPTION_VALUE_INVALID, "The status for service '%s' on host '%s' could not be found.", cgi_data.service_description, cgi_data.host_name)); result = ERROR; } else { json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_object_append_object(json_root, "data", json_status_service(cgi_data.format_options, cgi_data.service, temp_servicestatus)); } break; #if 0 case STATUS_QUERY_CONTACTCOUNT: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_status_contactcount(1, cgi_data.format_options, cgi_data.start, cgi_data.count, cgi_data.details, cgi_data.contactgroup); break; case STATUS_QUERY_CONTACTLIST: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_status_contactlist(1, cgi_data.format_options, cgi_data.start, cgi_data.count, cgi_data.details, cgi_data.contactgroup); break; case STATUS_QUERY_CONTACT: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_status_contact(1, cgi_data.format_options, cgi_data.contact); break; #endif case STATUS_QUERY_COMMENTCOUNT: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_object_append_object(json_root, "data", json_status_commentcount(cgi_data.format_options, cgi_data.comment_time_field, cgi_data.start_time, cgi_data.end_time, cgi_data.comment_types, cgi_data.entry_types, cgi_data.persistence, cgi_data.expiring, cgi_data.host_name, cgi_data.service_description)); break; case STATUS_QUERY_COMMENTLIST: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_object_append_object(json_root, "data", json_status_commentlist(cgi_data.format_options, cgi_data.start, cgi_data.count, cgi_data.details, cgi_data.comment_time_field, cgi_data.start_time, cgi_data.end_time, cgi_data.comment_types, cgi_data.entry_types, cgi_data.persistence, cgi_data.expiring, cgi_data.host_name, cgi_data.service_description)); break; case STATUS_QUERY_COMMENT: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_object_append_object(json_root, "data", json_status_comment(cgi_data.format_options, cgi_data.comment)); break; case STATUS_QUERY_DOWNTIMECOUNT: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_object_append_object(json_root, "data", json_status_downtimecount(cgi_data.format_options, cgi_data.downtime_time_field, cgi_data.start_time, cgi_data.end_time, cgi_data.downtime_object_types, cgi_data.downtime_types, cgi_data.triggered, cgi_data.triggered_by, cgi_data.in_effect, cgi_data.host_name, cgi_data.service_description)); break; case STATUS_QUERY_DOWNTIMELIST: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_object_append_object(json_root, "data", json_status_downtimelist(cgi_data.format_options, cgi_data.start, cgi_data.count, cgi_data.details, cgi_data.downtime_time_field, cgi_data.start_time, cgi_data.end_time, cgi_data.downtime_object_types, cgi_data.downtime_types, cgi_data.triggered, cgi_data.triggered_by, cgi_data.in_effect, cgi_data.host_name, cgi_data.service_description)); break; case STATUS_QUERY_DOWNTIME: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_object_append_object(json_root, "data", json_status_downtime(cgi_data.format_options, cgi_data.downtime)); break; case STATUS_QUERY_PROGRAMSTATUS: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_object_append_object(json_root, "data", json_status_program(cgi_data.format_options)); break; case STATUS_QUERY_PERFORMANCEDATA: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), last_status_data_update, ¤t_authdata, RESULT_SUCCESS, "")); json_object_append_object(json_root, "data", json_status_performance()); break; case STATUS_QUERY_HELP: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), compile_time(__DATE__, __TIME__), ¤t_authdata, RESULT_SUCCESS, "")); json_object_append_object(json_root, "data", json_help(status_json_help)); break; default: json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data.query, valid_queries), get_query_status(query_status, cgi_data.query), (time_t)-1, ¤t_authdata, RESULT_OPTION_MISSING, "Error: Object Type not specified. See data for help.")); json_object_append_object(json_root, "data", json_help(status_json_help)); break; } json_object_print(json_root, 0, 1, cgi_data.strftime_format, cgi_data.format_options); document_footer(); /* free all allocated memory */ free_cgi_data( &cgi_data); json_free_object(json_root, 1); free_memory(); return OK; } void document_header(int whitespace) { char date_time[MAX_DATETIME_LENGTH]; time_t expire_time; time_t current_time; time(¤t_time); printf("Cache-Control: no-store\r\n"); printf("Pragma: no-cache\r\n"); get_time_string(¤t_time, date_time, (int)sizeof(date_time), HTTP_DATE_TIME); printf("Last-Modified: %s\r\n", date_time); expire_time = (time_t)0L; get_time_string(&expire_time, date_time, (int)sizeof(date_time), HTTP_DATE_TIME); printf("Expires: %s\r\n", date_time); printf("Content-type: application/json; charset=utf-8\r\n\r\n"); return; } void document_footer(void) { printf( "\n"); return; } void init_cgi_data(status_json_cgi_data *cgi_data) { cgi_data->format_options = 0; cgi_data->query = STATUS_QUERY_INVALID; cgi_data->start = 0; cgi_data->count = 0; cgi_data->details = 0; cgi_data->strftime_format = NULL; cgi_data->parent_host_name = NULL; cgi_data->use_parent_host = 0; cgi_data->parent_host = NULL; cgi_data->child_host_name = NULL; cgi_data->use_child_host = 0; cgi_data->child_host = NULL; cgi_data->host_name = NULL; cgi_data->host = NULL; cgi_data->host_statuses = HOST_STATUS_ALL; cgi_data->hostgroup_name = NULL; cgi_data->hostgroup = NULL; cgi_data->servicegroup_name = NULL; cgi_data->servicegroup = NULL; cgi_data->service_description = NULL; cgi_data->service = NULL; cgi_data->service_statuses = SERVICE_STATUS_ALL; cgi_data->parent_service_name = NULL; cgi_data->child_service_name = NULL; cgi_data->contactgroup_name = NULL; cgi_data->contactgroup = NULL; cgi_data->contact_name = NULL; cgi_data->contact = NULL; cgi_data->check_timeperiod_name = NULL; cgi_data->check_timeperiod = NULL; cgi_data->host_notification_timeperiod_name = NULL; cgi_data->host_notification_timeperiod = NULL; cgi_data->service_notification_timeperiod_name = NULL; cgi_data->service_notification_timeperiod = NULL; cgi_data->check_command_name = NULL; cgi_data->check_command = NULL; cgi_data->event_handler_name = NULL; cgi_data->event_handler = NULL; cgi_data->comment_types = COMMENT_TYPE_ALL; cgi_data->entry_types = COMMENT_ENTRY_ALL; cgi_data->persistence = BOOLEAN_EITHER; cgi_data->expiring = BOOLEAN_EITHER; cgi_data->comment_id = -1; cgi_data->comment = NULL; cgi_data->downtime_id = -1; cgi_data->downtime = NULL; cgi_data->start_time = (time_t)0; cgi_data->end_time = (time_t)0; cgi_data->host_time_field = STATUS_TIME_INVALID; cgi_data->service_time_field = STATUS_TIME_INVALID; cgi_data->comment_time_field = STATUS_TIME_INVALID; cgi_data->downtime_time_field = STATUS_TIME_INVALID; cgi_data->downtime_object_types = DOWNTIME_OBJECT_TYPE_ALL; cgi_data->downtime_types = DOWNTIME_TYPE_ALL; cgi_data->triggered = BOOLEAN_EITHER; cgi_data->triggered_by = -1; cgi_data->in_effect = BOOLEAN_EITHER; } void free_cgi_data( status_json_cgi_data *cgi_data) { if( NULL != cgi_data->parent_host_name) free( cgi_data->parent_host_name); if( NULL != cgi_data->child_host_name) free( cgi_data->child_host_name); if( NULL != cgi_data->host_name) free( cgi_data->host_name); if( NULL != cgi_data->hostgroup_name) free( cgi_data->hostgroup_name); if( NULL != cgi_data->servicegroup_name) free(cgi_data->servicegroup_name); if( NULL != cgi_data->service_description) free(cgi_data->service_description); if( NULL != cgi_data->parent_service_name) free(cgi_data->parent_service_name); if( NULL != cgi_data->child_service_name) free(cgi_data->child_service_name); if( NULL != cgi_data->contactgroup_name) free(cgi_data->contactgroup_name); if( NULL != cgi_data->contact_name) free(cgi_data->contact_name); if( NULL != cgi_data->check_timeperiod_name) free(cgi_data->check_timeperiod_name); if( NULL != cgi_data->host_notification_timeperiod_name) free(cgi_data->host_notification_timeperiod_name); if( NULL != cgi_data->service_notification_timeperiod_name) free(cgi_data->service_notification_timeperiod_name); if( NULL != cgi_data->check_command_name) free(cgi_data->check_command_name); if( NULL != cgi_data->event_handler_name) free(cgi_data->event_handler_name); } int process_cgivars(json_object *json_root, status_json_cgi_data *cgi_data, time_t query_time) { char **variables; int result = RESULT_SUCCESS; int x; authdata *authinfo = NULL; /* Currently always NULL because get_authentication_information() hasn't been called yet, but in case we want to use it in the future... */ variables = getcgivars(); for(x = 0; variables[x]; x++) { /* We set these each iteration because they could change with each iteration */ /* we found the query argument */ if(!strcmp(variables[x], "query")) { if((result = parse_enumeration_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], valid_queries, &(cgi_data->query))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "formatoptions")) { cgi_data->format_options = 0; if((result = parse_bitmask_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], svm_format_options, &(cgi_data->format_options))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "start")) { if((result = parse_int_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->start))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "count")) { if((result = parse_int_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->count))) != RESULT_SUCCESS) { break; } if(cgi_data->count == 0) { json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, RESULT_OPTION_VALUE_INVALID, "The count option value is invalid. " "It must be an integer greater than zero")); result = RESULT_OPTION_VALUE_INVALID; break; } x++; } else if(!strcmp(variables[x], "parenthost")) { if((result = parse_string_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->parent_host_name))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "childhost")) { if((result = parse_string_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->child_host_name))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "hostname")) { if((result = parse_string_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->host_name))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "hostgroup")) { if((result = parse_string_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->hostgroup_name))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "hoststatus")) { cgi_data->host_statuses = 0; if((result = parse_bitmask_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], svm_host_statuses, &(cgi_data->host_statuses))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "servicegroup")) { if((result = parse_string_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->servicegroup_name))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "servicestatus")) { cgi_data->service_statuses = 0; if((result = parse_bitmask_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], svm_service_statuses, &(cgi_data->service_statuses))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "parentservice")) { if((result = parse_string_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->parent_service_name))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "childservice")) { if((result = parse_string_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->child_service_name))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "checktimeperiod")) { if((result = parse_string_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->check_timeperiod_name))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "hostnotificationtimeperiod")) { if((result = parse_string_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->host_notification_timeperiod_name))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "servicenotificationtimeperiod")) { if((result = parse_string_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->service_notification_timeperiod_name))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "checkcommand")) { if((result = parse_string_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->check_command_name))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "eventhandler")) { if((result = parse_string_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->event_handler_name))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "commenttypes")) { cgi_data->comment_types = 0; if((result = parse_bitmask_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], svm_valid_comment_types, &(cgi_data->comment_types))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "entrytypes")) { cgi_data->entry_types = 0; if((result = parse_bitmask_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], svm_valid_comment_entry_types, &(cgi_data->entry_types))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "persistence")) { cgi_data->persistence = 0; if((result = parse_bitmask_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], svm_valid_persistence, &(cgi_data->persistence))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "expiring")) { cgi_data->expiring = 0; if((result = parse_bitmask_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], svm_valid_expiration, &(cgi_data->expiring))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "commentid")) { if((result = parse_int_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->comment_id))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "downtimeid")) { if((result = parse_int_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->downtime_id))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "downtimeobjecttypes")) { cgi_data->downtime_object_types = 0; if((result = parse_bitmask_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], svm_valid_downtime_object_types, &(cgi_data->downtime_object_types))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "downtimetypes")) { cgi_data->downtime_types = 0; if((result = parse_bitmask_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], svm_valid_downtime_types, &(cgi_data->downtime_types))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "triggered")) { cgi_data->triggered = 0; if((result = parse_bitmask_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], svm_valid_triggered_status, &(cgi_data->triggered))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "triggeredby")) { if((result = parse_int_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->triggered_by))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "ineffect")) { cgi_data->in_effect = 0; if((result = parse_bitmask_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], svm_valid_in_effect_status, &(cgi_data->in_effect))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "contactgroup")) { if((result = parse_string_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->contactgroup_name))) != RESULT_SUCCESS) { result = ERROR; break; } x++; } else if(!strcmp(variables[x], "servicedescription")) { if((result = parse_string_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->service_description))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "contactname")) { if((result = parse_string_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->contact_name))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "details")) { if((result = parse_boolean_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->details))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "dateformat")) { if((result = parse_string_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->strftime_format))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "hosttimefield")) { if((result = parse_enumeration_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], svm_host_time_fields, &(cgi_data->host_time_field))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "servicetimefield")) { if((result = parse_enumeration_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], svm_service_time_fields, &(cgi_data->service_time_field))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "commenttimefield")) { if((result = parse_enumeration_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], svm_comment_time_fields, &(cgi_data->comment_time_field))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "downtimetimefield")) { if((result = parse_enumeration_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], svm_downtime_time_fields, &(cgi_data->downtime_time_field))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "starttime")) { if((result = parse_time_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->start_time))) != RESULT_SUCCESS) { break; } x++; } else if(!strcmp(variables[x], "endtime")) { if((result = parse_time_cgivar(THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), json_root, query_time, authinfo, variables[x], variables[x+1], &(cgi_data->end_time))) != RESULT_SUCCESS) { result = ERROR; break; } x++; } else if(!strcmp(variables[x], "NagFormId")) ++x; else if(!strcmp(variables[x], "")); else { json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, RESULT_OPTION_INVALID, "Invalid option: '%s'.", variables[x])); result = RESULT_OPTION_INVALID; break; } } /* free memory allocated to the CGI variables */ free_cgivars(variables); return result; } int validate_arguments(json_object *json_root, status_json_cgi_data *cgi_data, time_t query_time) { int result = RESULT_SUCCESS; host *temp_host = NULL; hostgroup *temp_hostgroup = NULL; servicegroup *temp_servicegroup = NULL; service *temp_service = NULL; contactgroup *temp_contactgroup = NULL; timeperiod *temp_timeperiod = NULL; command *temp_command = NULL; contact *temp_contact = NULL; nagios_comment *temp_comment = NULL; scheduled_downtime *temp_downtime = NULL; authdata *authinfo = NULL; /* Currently always NULL because get_authentication_information() hasn't been called yet, but in case we want to use it in the future... */ /* Validate that required parameters were supplied */ switch(cgi_data->query) { case STATUS_QUERY_HOSTCOUNT: break; case STATUS_QUERY_HOSTLIST: if(((cgi_data->start_time > 0) || (cgi_data->end_time > 0)) && (STATUS_TIME_INVALID == cgi_data->host_time_field)) { result = RESULT_OPTION_MISSING; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "Start and/or end time supplied, but time field specified.")); } break; case STATUS_QUERY_HOST: if( NULL == cgi_data->host_name) { result = RESULT_OPTION_MISSING; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "Host information requested, but no host name specified.")); } break; case STATUS_QUERY_SERVICECOUNT: break; case STATUS_QUERY_SERVICELIST: if(((cgi_data->start_time > 0) || (cgi_data->end_time > 0)) && (STATUS_TIME_INVALID == cgi_data->service_time_field)) { result = RESULT_OPTION_MISSING; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "Start and/or end time supplied, but time field specified.")); } break; case STATUS_QUERY_SERVICE: if( NULL == cgi_data->host_name) { result = RESULT_OPTION_MISSING; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "Service information requested, but no host name specified.")); } if( NULL == cgi_data->service_description) { result = RESULT_OPTION_MISSING; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "Service information requested, but no service description specified.")); } break; case STATUS_QUERY_COMMENTCOUNT: break; case STATUS_QUERY_COMMENTLIST: if(((cgi_data->start_time > 0) || (cgi_data->end_time > 0)) && (STATUS_TIME_INVALID == cgi_data->comment_time_field)) { result = RESULT_OPTION_MISSING; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "Start and/or end time supplied, but time field specified.")); } break; case STATUS_QUERY_COMMENT: if( -1 == cgi_data->comment_id) { result = RESULT_OPTION_MISSING; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "Comment information requested, but no id specified.")); } break; case STATUS_QUERY_DOWNTIMECOUNT: break; case STATUS_QUERY_DOWNTIMELIST: if(((cgi_data->start_time > 0) || (cgi_data->end_time > 0)) && (STATUS_TIME_INVALID == cgi_data->downtime_time_field)) { result = RESULT_OPTION_MISSING; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "Start and/or end time supplied, but time field specified.")); } break; case STATUS_QUERY_DOWNTIME: if( -1 == cgi_data->downtime_id) { result = RESULT_OPTION_MISSING; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "Downtime information requested, but no id specified.")); } break; case STATUS_QUERY_PROGRAMSTATUS: break; case STATUS_QUERY_PERFORMANCEDATA: break; #if 0 case STATUS_QUERY_CONTACTCOUNT: break; case STATUS_QUERY_CONTACTLIST: break; case STATUS_QUERY_CONTACT: if( NULL == cgi_data->contact_name) { result = RESULT_OPTION_MISSING; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "Contact information requested, but no contact name specified.")); } break; #endif case STATUS_QUERY_HELP: break; default: result = RESULT_OPTION_MISSING; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "Missing validation for object type %u.", cgi_data->query)); break; } /* Validate the requested parent host */ if( NULL != cgi_data->parent_host_name) { cgi_data->use_parent_host = 1; cgi_data->parent_host = NULL; if(strcmp(cgi_data->parent_host_name, "none")) { temp_host = find_host(cgi_data->parent_host_name); if( NULL == temp_host) { cgi_data->use_parent_host = 0; result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The parenthost '%s' could not be found.", cgi_data->parent_host_name)); } else { cgi_data->parent_host = temp_host; } } } /* Validate the requested child host */ if( NULL != cgi_data->child_host_name) { cgi_data->use_child_host = 1; cgi_data->child_host = NULL; if(strcmp(cgi_data->child_host_name, "none")) { temp_host = find_host(cgi_data->child_host_name); if( NULL == temp_host) { cgi_data->use_child_host = 0; result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The childhost '%s' could not be found.", cgi_data->child_host_name)); } else { cgi_data->child_host = temp_host; } } } /* Validate the requested host */ if( NULL != cgi_data->host_name) { temp_host = find_host(cgi_data->host_name); if( NULL == temp_host) { result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The host '%s' could not be found.", cgi_data->host_name)); } else { cgi_data->host = temp_host; } } /* Validate the requested hostgroup */ if( NULL != cgi_data->hostgroup_name) { temp_hostgroup = find_hostgroup(cgi_data->hostgroup_name); if( NULL == temp_hostgroup) { result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The hostgroup '%s' could not be found.", cgi_data->hostgroup_name)); } else { cgi_data->hostgroup = temp_hostgroup; } } /* Validate the requested servicegroup */ if( NULL != cgi_data->servicegroup_name) { temp_servicegroup = find_servicegroup(cgi_data->servicegroup_name); if( NULL == temp_servicegroup) { result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The servicegroup '%s' could not be found.", cgi_data->servicegroup_name)); } else { cgi_data->servicegroup = temp_servicegroup; } } /* Validate the requested contactgroup */ if( NULL != cgi_data->contactgroup_name) { temp_contactgroup = find_contactgroup(cgi_data->contactgroup_name); if( NULL == temp_contactgroup) { result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The contactgroup '%s' could not be found.", cgi_data->contactgroup_name)); } else { cgi_data->contactgroup = temp_contactgroup; } } /* Validate the requested service. Because a service description may be requested without specifying a host name, it may not make sense to look for a specific service object */ if((NULL != cgi_data->service_description) && (NULL != cgi_data->host_name)) { temp_service = find_service(cgi_data->host_name, cgi_data->service_description); if( NULL == temp_service) { result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The service '%s' on host '%s' could not be found.", cgi_data->service_description, cgi_data->host_name)); } else { cgi_data->service = temp_service; } } /* Validate the requested check timeperiod */ if( NULL != cgi_data->check_timeperiod_name) { temp_timeperiod = find_timeperiod(cgi_data->check_timeperiod_name); if( NULL == temp_timeperiod) { result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The check timeperiod '%s' could not be found.", cgi_data->check_timeperiod_name)); } else { cgi_data->check_timeperiod = temp_timeperiod; } } /* Validate the requested host notification timeperiod */ if( NULL != cgi_data->host_notification_timeperiod_name) { temp_timeperiod = find_timeperiod(cgi_data->host_notification_timeperiod_name); if( NULL == temp_timeperiod) { result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The host notification timeperiod '%s' could not be found.", cgi_data->host_notification_timeperiod_name)); } else { cgi_data->host_notification_timeperiod = temp_timeperiod; } } /* Validate the requested service notification timeperiod */ if( NULL != cgi_data->service_notification_timeperiod_name) { temp_timeperiod = find_timeperiod(cgi_data->service_notification_timeperiod_name); if( NULL == temp_timeperiod) { result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The service notification timeperiod '%s' could not be found.", cgi_data->service_notification_timeperiod_name)); } else { cgi_data->service_notification_timeperiod = temp_timeperiod; } } /* Validate the requested check command */ if( NULL != cgi_data->check_command_name) { temp_command = find_command(cgi_data->check_command_name); if( NULL == temp_command) { result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The check command '%s' could not be found.", cgi_data->check_command_name)); } else { cgi_data->check_command = temp_command; } } /* Validate the requested event_handler */ if( NULL != cgi_data->event_handler_name) { temp_command = find_command(cgi_data->event_handler_name); if( NULL == temp_command) { result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The event_handler '%s' could not be found.", cgi_data->event_handler_name)); } else { cgi_data->event_handler = temp_command; } } /* Validate the requested comment */ if(-1 != cgi_data->comment_id) { temp_comment = find_host_comment(cgi_data->comment_id); if(NULL == temp_comment) { temp_comment = find_service_comment(cgi_data->comment_id); } if(NULL == temp_comment) { result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The comment with ID '%d' could not be found.", cgi_data->comment_id)); } else { cgi_data->comment = temp_comment; } } /* Validate the requested downtime */ if(-1 != cgi_data->downtime_id) { temp_downtime = find_downtime(ANY_DOWNTIME, cgi_data->downtime_id); if(NULL == temp_downtime) { result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The downtime with ID '%d' could not be found.", cgi_data->downtime_id)); } else { cgi_data->downtime = temp_downtime; } } /* Validate the requested triggered-by downtime */ if(-1 != cgi_data->triggered_by) { temp_downtime = find_downtime(ANY_DOWNTIME, cgi_data->triggered_by); if(NULL == temp_downtime) { result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The triggering downtime with ID '%d' could not be found.", cgi_data->triggered_by)); } } /* Validate the requested contact */ if( NULL != cgi_data->contact_name) { temp_contact = find_contact(cgi_data->contact_name); if( NULL == temp_contact) { result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The contact '%s' could not be found.", cgi_data->contact_name)); } else { cgi_data->contact = temp_contact; } } /* Validate the requested start time is before the requested end time */ if((cgi_data->start_time > 0) && (cgi_data->end_time > 0) && ( cgi_data->start_time >= cgi_data->end_time)) { result = RESULT_OPTION_VALUE_INVALID; json_object_append_object(json_root, "result", json_result(query_time, THISCGI, svm_get_string_from_value(cgi_data->query, valid_queries), get_query_status(query_status, cgi_data->query), (time_t)-1, authinfo, result, "The requested start time must be before the end time.")); } return result; } int json_status_host_passes_selection(host *temp_host, int use_parent_host, host *parent_host, int use_child_host, host *child_host, hostgroup *temp_hostgroup, contact *temp_contact, hoststatus *temp_hoststatus, int time_field, time_t start_time, time_t end_time, contactgroup *temp_contactgroup, timeperiod *check_timeperiod, timeperiod *notification_timeperiod, command *check_command, command *event_handler) { host *temp_host2; /* Skip if user is not authorized for this host */ if(FALSE == is_authorized_for_host(temp_host, ¤t_authdata)) { return 0; } /* If the host parent was specified, skip the hosts whose parent is not the parent host specified */ if( 1 == use_parent_host && FALSE == is_host_immediate_child_of_host(parent_host, temp_host)) { return 0; } /* If the hostgroup was specified, skip the hosts that are not members of the hostgroup specified */ if( NULL != temp_hostgroup && ( FALSE == is_host_member_of_hostgroup(temp_hostgroup, temp_host))) { return 0; } /* If the contact was specified, skip the hosts that do not have the contact specified */ if( NULL != temp_contact && ( FALSE == is_contact_for_host(temp_host, temp_contact))) { return 0; } /* If a contactgroup was specified, skip the hosts that do not have the contactgroup specified */ if(NULL != temp_contactgroup && (FALSE == is_contactgroup_for_host(temp_host, temp_contactgroup))) { return 0; } switch(time_field) { case STATUS_TIME_INVALID: break; case STATUS_TIME_LAST_UPDATE: if((start_time > 0) && (temp_hoststatus->last_update < start_time)) { return 0; } if((end_time > 0) && (temp_hoststatus->last_update > end_time)) { return 0; } break; case STATUS_TIME_LAST_CHECK: if((start_time > 0) && (temp_hoststatus->last_check < start_time)) { return 0; } if((end_time > 0) && (temp_hoststatus->last_check > end_time)) { return 0; } break; case STATUS_TIME_NEXT_CHECK: if((start_time > 0) && (temp_hoststatus->next_check < start_time)) { return 0; } if((end_time > 0) && (temp_hoststatus->next_check > end_time)) { return 0; } break; case STATUS_TIME_LAST_STATE_CHANGE: if((start_time > 0) && (temp_hoststatus->last_state_change < start_time)) { return 0; } if((end_time > 0) && (temp_hoststatus->last_state_change > end_time)) { return 0; } break; case STATUS_TIME_LAST_HARD_STATE_CHANGE: if((start_time > 0) && (temp_hoststatus->last_hard_state_change < start_time)) { return 0; } if((end_time > 0) && (temp_hoststatus->last_hard_state_change > end_time)) { return 0; } break; case STATUS_TIME_LAST_TIME_UP: if((start_time > 0) && (temp_hoststatus->last_time_up < start_time)) { return 0; } if((end_time > 0) && (temp_hoststatus->last_time_up > end_time)) { return 0; } break; case STATUS_TIME_LAST_TIME_DOWN: if((start_time > 0) && (temp_hoststatus->last_time_down < start_time)) { return 0; } if((end_time > 0) && (temp_hoststatus->last_time_down > end_time)) { return 0; } break; case STATUS_TIME_LAST_TIME_UNREACHABLE: if((start_time > 0) && (temp_hoststatus->last_time_unreachable < start_time)) { return 0; } if((end_time > 0) && (temp_hoststatus->last_time_unreachable > end_time)) { return 0; } break; case STATUS_TIME_LAST_NOTIFICATION: if((start_time > 0) && (temp_hoststatus->last_notification < start_time)) { return 0; } if((end_time > 0) && (temp_hoststatus->last_notification > end_time)) { return 0; } break; case STATUS_TIME_NEXT_NOTIFICATION: if((start_time > 0) && (temp_hoststatus->next_notification < start_time)) { return 0; } if((end_time > 0) && (temp_hoststatus->next_notification > end_time)) { return 0; } break; default: return 0; } /* If a check timeperiod was specified, skip this host if it does not have the check timeperiod specified */ if(NULL != check_timeperiod && (check_timeperiod != temp_host->check_period_ptr)) { return 0; } /* If a notification timeperiod was specified, skip this host if it does not have the notification timeperiod specified */ if(NULL != notification_timeperiod && (notification_timeperiod != temp_host->notification_period_ptr)) { return 0; } /* If a check command was specified, skip this host if it does not have the check command specified */ if(NULL != check_command && (check_command != temp_host->check_command_ptr)) { return 0; } /* If an event handler was specified, skip this host if it does not have the event handler specified */ if(NULL != event_handler && (event_handler != temp_host->event_handler_ptr)) { return 0; } /* If a child host was specified... (leave this for last since it is the most expensive check) */ if(1 == use_child_host) { /* If the child host is "none", skip this host if it has children */ if(NULL == child_host) { for(temp_host2 = host_list; temp_host2 != NULL; temp_host2 = temp_host2->next) { if(TRUE == is_host_immediate_child_of_host(temp_host, temp_host2)) { return 0; } } } /* Otherwise, skip this host if it does not have the specified host as a child */ else if(FALSE == is_host_immediate_child_of_host(temp_host, child_host)) { return 0; } } return 1; } json_object *json_status_host_selectors(unsigned format_options, int start, int count, int use_parent_host, host *parent_host, int use_child_host, host *child_host, hostgroup *temp_hostgroup, int host_statuses, contact *temp_contact, int time_field, time_t start_time, time_t end_time, contactgroup *temp_contactgroup, timeperiod *check_timeperiod, timeperiod *notification_timeperiod, command *check_command, command *event_handler) { json_object *json_selectors; json_selectors = json_new_object(); if(start > 0) { json_object_append_integer(json_selectors, "start", start); } if(count > 0) { json_object_append_integer(json_selectors, "count", count); } if(1 == use_parent_host) { json_object_append_string(json_selectors, "parenthost", &percent_escapes, ( NULL == parent_host ? "none" : parent_host->name)); } if(1 == use_child_host) { json_object_append_string(json_selectors, "childhost", &percent_escapes, ( NULL == child_host ? "none" : child_host->name)); } if(NULL != temp_hostgroup) { json_object_append_string(json_selectors, "hostgroup", &percent_escapes, temp_hostgroup->group_name); } if(HOST_STATUS_ALL != host_statuses) { json_bitmask(json_selectors, format_options, "hoststatus", host_statuses, svm_host_statuses); } if(NULL != temp_contact) { json_object_append_string(json_selectors, "contact",&percent_escapes, temp_contact->name); } if(NULL != temp_contactgroup) { json_object_append_string(json_selectors, "contactgroup", &percent_escapes, temp_contactgroup->group_name); } if(time_field > 0) { json_enumeration(json_selectors, format_options, "hosttimefield", time_field, svm_host_time_fields); } if(start_time > 0) { json_object_append_time_t(json_selectors, "starttime", start_time); } if(end_time > 0) { json_object_append_time_t(json_selectors, "endtime", end_time); } if( NULL != check_timeperiod) { json_object_append_string(json_selectors, "checktimeperiod", &percent_escapes, check_timeperiod->name); } if( NULL != notification_timeperiod) { json_object_append_string(json_selectors, "hostnotificationtimeperiod", &percent_escapes, notification_timeperiod->name); } if( NULL != check_command) { json_object_append_string(json_selectors, "checkcommand", &percent_escapes, check_command->name); } if( NULL != event_handler) { json_object_append_string(json_selectors, "eventhandler", &percent_escapes, event_handler->name); } return json_selectors; } json_object *json_status_hostcount(unsigned format_options, int use_parent_host, host *parent_host, int use_child_host, host *child_host, hostgroup *temp_hostgroup, int host_statuses, contact *temp_contact, int time_field, time_t start_time, time_t end_time, contactgroup *temp_contactgroup, timeperiod *check_timeperiod, timeperiod *notification_timeperiod, command *check_command, command *event_handler) { json_object *json_data; json_object *json_count; host *temp_host; hoststatus *temp_hoststatus; int up = 0; int down = 0; int unreachable = 0; int pending = 0; json_data = json_new_object(); json_object_append_object(json_data, "selectors", json_status_host_selectors(format_options, 0, 0, use_parent_host, parent_host, use_child_host, child_host, temp_hostgroup, host_statuses, temp_contact, time_field, start_time, end_time, temp_contactgroup, check_timeperiod, notification_timeperiod, check_command, event_handler)); json_count = json_new_object(); for(temp_host = host_list; temp_host != NULL; temp_host = temp_host->next) { /* If we cannot get the status of the host, skip it. This should probably return an error and doing so is in the todo list. */ temp_hoststatus = find_hoststatus(temp_host->name); if( NULL == temp_hoststatus) { continue; } if(json_status_host_passes_selection(temp_host, use_parent_host, parent_host, use_child_host, child_host, temp_hostgroup, temp_contact, temp_hoststatus, time_field, start_time, end_time, temp_contactgroup, check_timeperiod, notification_timeperiod, check_command, event_handler) == 0) { continue; } /* Count the hosts in each state */ switch(temp_hoststatus->status) { case HOST_PENDING: pending++; break; #ifdef JSON_NAGIOS_4X case SD_HOST_UP: #else case HOST_UP: #endif up++; break; #ifdef JSON_NAGIOS_4X case SD_HOST_UNREACHABLE: #else case HOST_UNREACHABLE: #endif unreachable++; break; #ifdef JSON_NAGIOS_4X case SD_HOST_DOWN: #else case HOST_DOWN: #endif down++; break; } } #ifdef JSON_NAGIOS_4X if( host_statuses & SD_HOST_UP) #else if( host_statuses & HOST_UP) #endif json_object_append_integer(json_count, "up", up); #ifdef JSON_NAGIOS_4X if( host_statuses & SD_HOST_DOWN) #else if( host_statuses & HOST_DOWN) #endif json_object_append_integer(json_count, "down", down); #ifdef JSON_NAGIOS_4X if( host_statuses & SD_HOST_UNREACHABLE) #else if( host_statuses & HOST_UNREACHABLE) #endif json_object_append_integer(json_count, "unreachable", unreachable); if( host_statuses & HOST_PENDING) json_object_append_integer(json_count, "pending", pending); json_object_append_object(json_data, "count", json_count); return json_data; } json_object *json_status_hostlist(unsigned format_options, int start, int count, int details, int use_parent_host, host *parent_host, int use_child_host, host *child_host, hostgroup *temp_hostgroup, int host_statuses, contact *temp_contact, int time_field, time_t start_time, time_t end_time, contactgroup *temp_contactgroup, timeperiod *check_timeperiod, timeperiod *notification_timeperiod, command *check_command, command *event_handler) { json_object *json_data; json_object *json_hostlist; json_object *json_host_details; host *temp_host; hoststatus *temp_hoststatus; int current = 0; int counted = 0; json_data = json_new_object(); json_object_append_object(json_data, "selectors", json_status_host_selectors(format_options, start, count, use_parent_host, parent_host, use_child_host, child_host, temp_hostgroup, host_statuses, temp_contact, time_field, start_time, end_time, temp_contactgroup, check_timeperiod, notification_timeperiod, check_command, event_handler)); json_hostlist = json_new_object(); for(temp_host = host_list; temp_host != NULL; temp_host = temp_host->next) { /* If we cannot get the status of the host, skip it. This should probably return an error and doing so is in the todo list. */ temp_hoststatus = find_hoststatus(temp_host->name); if( NULL == temp_hoststatus) { continue; } if(json_status_host_passes_selection(temp_host, use_parent_host, parent_host, use_child_host, child_host, temp_hostgroup, temp_contact, temp_hoststatus, time_field, start_time, end_time, temp_contactgroup, check_timeperiod, notification_timeperiod, check_command, event_handler) == 0) { continue; } /* If the status of the host does not match one of the status the user requested, skip the host */ if(!(temp_hoststatus->status & host_statuses)) { continue; } /* If the current item passes the start and limit tests, display it */ if( passes_start_and_count_limits(start, count, current, counted)) { if( details > 0) { json_host_details = json_new_object(); json_status_host_details(json_host_details, format_options, temp_host, temp_hoststatus); json_object_append_object(json_hostlist, temp_host->name, json_host_details); } else { json_enumeration(json_hostlist, format_options, temp_host->name, temp_hoststatus->status, svm_host_statuses); } counted++; } current++; } json_object_append_object(json_data, "hostlist", json_hostlist); return json_data; } json_object *json_status_host(unsigned format_options, host *temp_host, hoststatus *temp_hoststatus) { json_object *json_host = json_new_object(); json_object *json_details = json_new_object(); json_object_append_string(json_details, "name", &percent_escapes, temp_host->name); json_status_host_details(json_details, format_options, temp_host, temp_hoststatus); json_object_append_object(json_host, "host", json_details); return json_host; } void json_status_host_details(json_object *json_details, unsigned format_options, host *temp_host, hoststatus *temp_hoststatus) { json_object_append_string(json_details, "name", &percent_escapes, temp_host->name); json_object_append_string(json_details, "plugin_output", &percent_escapes, temp_hoststatus->plugin_output); json_object_append_string(json_details, "long_plugin_output", &percent_escapes, temp_hoststatus->long_plugin_output); json_object_append_string(json_details, "perf_data", &percent_escapes, temp_hoststatus->perf_data); json_enumeration(json_details, format_options, "status", temp_hoststatus->status, svm_host_statuses); json_object_append_time_t(json_details, "last_update", temp_hoststatus->last_update); json_object_append_boolean(json_details, "has_been_checked", temp_hoststatus->has_been_checked); json_object_append_boolean(json_details, "should_be_scheduled", temp_hoststatus->should_be_scheduled); json_object_append_integer(json_details, "current_attempt", temp_hoststatus->current_attempt); json_object_append_integer(json_details, "max_attempts", temp_hoststatus->max_attempts); json_object_append_time_t(json_details, "last_check", temp_hoststatus->last_check); json_object_append_time_t(json_details, "next_check", temp_hoststatus->next_check); json_bitmask(json_details, format_options, "check_options", temp_hoststatus->check_options, svm_check_options); json_enumeration(json_details, format_options, "check_type", temp_hoststatus->check_type, svm_host_check_types); json_object_append_time_t(json_details, "last_state_change", temp_hoststatus->last_state_change); json_object_append_time_t(json_details, "last_hard_state_change", temp_hoststatus->last_hard_state_change); json_enumeration(json_details, format_options, "last_hard_state", temp_hoststatus->last_hard_state, svm_host_states); json_object_append_time_t(json_details, "last_time_up", temp_hoststatus->last_time_up); json_object_append_time_t(json_details, "last_time_down", temp_hoststatus->last_time_down); json_object_append_time_t(json_details, "last_time_unreachable", temp_hoststatus->last_time_unreachable); json_enumeration(json_details, format_options, "state_type", temp_hoststatus->state_type, svm_state_types); json_object_append_time_t(json_details, "last_notification", temp_hoststatus->last_notification); json_object_append_time_t(json_details, "next_notification", temp_hoststatus->next_notification); json_object_append_boolean(json_details, "no_more_notifications", temp_hoststatus->no_more_notifications); json_object_append_boolean(json_details, "notifications_enabled", temp_hoststatus->notifications_enabled); json_object_append_boolean(json_details, "problem_has_been_acknowledged", temp_hoststatus->problem_has_been_acknowledged); json_enumeration(json_details, format_options, "acknowledgement_type", temp_hoststatus->acknowledgement_type, svm_acknowledgement_types); json_object_append_integer(json_details, "current_notification_number", temp_hoststatus->current_notification_number); #ifdef JSON_NAGIOS_4X json_object_append_boolean(json_details, "accept_passive_checks", temp_hoststatus->accept_passive_checks); #else json_object_append_boolean(json_details, "accept_passive_host_checks", temp_hoststatus->accept_passive_host_checks); #endif json_object_append_boolean(json_details, "event_handler_enabled", temp_hoststatus->event_handler_enabled); json_object_append_boolean(json_details, "checks_enabled", temp_hoststatus->checks_enabled); json_object_append_boolean(json_details, "flap_detection_enabled", temp_hoststatus->flap_detection_enabled); json_object_append_boolean(json_details, "is_flapping", temp_hoststatus->is_flapping); json_object_append_real(json_details, "percent_state_change", temp_hoststatus->percent_state_change); json_object_append_real(json_details, "latency", temp_hoststatus->latency); json_object_append_real(json_details, "execution_time", temp_hoststatus->execution_time); json_object_append_integer(json_details, "scheduled_downtime_depth", temp_hoststatus->scheduled_downtime_depth); #ifndef JSON_NAGIOS_4X json_object_append_boolean(json_details, "failure_prediction_enabled", temp_hoststatus->failure_prediction_enabled); #endif json_object_append_boolean(json_details, "process_performance_data", temp_hoststatus->process_performance_data); #ifdef JSON_NAGIOS_4X json_object_append_boolean(json_details, "obsess", temp_hoststatus->obsess); #else json_object_append_boolean(json_details, "obsess_over_host", temp_hoststatus->obsess_over_host); #endif } int json_status_service_passes_host_selection(host *temp_host, int use_parent_host, host *parent_host, int use_child_host, host *child_host, hostgroup *temp_hostgroup, host *match_host, int host_statuses) { hoststatus *temp_hoststatus; host *temp_host2; /* Skip if user is not authorized for this service */ if(FALSE == is_authorized_for_host(temp_host, ¤t_authdata)) { return 0; } /* If the host parent was specified, skip the services whose host is not a child of the parent host specified */ if( 1 == use_parent_host && NULL != temp_host && FALSE == is_host_immediate_child_of_host(parent_host, temp_host)) { return 0; } /* If the hostgroup was specified, skip the services on hosts that are not members of the hostgroup specified */ if( NULL != temp_hostgroup && NULL != temp_host && ( FALSE == is_host_member_of_hostgroup(temp_hostgroup, temp_host))) { return 0; } /* If the host was specified, skip the services not on the host specified */ if( NULL != match_host && NULL != temp_host && temp_host != match_host) { return 0; } /* If we cannot get the status of the host, skip it. This should probably return an error and doing so is in the todo list. */ temp_hoststatus = find_hoststatus(temp_host->name); if( NULL == temp_hoststatus) { return 0; } /* If a child host was specified... */ if(1 == use_child_host) { /* If the child host is "none", skip this host if it has children */ if(NULL == child_host) { for(temp_host2 = host_list; temp_host2 != NULL; temp_host2 = temp_host2->next) { if(TRUE == is_host_immediate_child_of_host(temp_host, temp_host2)) { return 0; } } } /* Otherwise, skip this host if it does not have the specified host as a child */ else if(FALSE == is_host_immediate_child_of_host(temp_host, child_host)) { return 0; } } return 1; } int json_status_service_passes_service_selection(service *temp_service, servicegroup *temp_servicegroup, contact *temp_contact, servicestatus *temp_servicestatus, int time_field, time_t start_time, time_t end_time, char *service_description, char *parent_service_name, char *child_service_name, contactgroup *temp_contactgroup, timeperiod *check_timeperiod, timeperiod *notification_timeperiod, command *check_command, command *event_handler) { servicesmember *temp_servicesmember; /* Skip if user is not authorized for this service */ if(FALSE == is_authorized_for_service(temp_service, ¤t_authdata)) { return 0; } /* If the servicegroup was specified, skip the services that are not members of the servicegroup specified */ if( NULL != temp_servicegroup && ( FALSE == is_service_member_of_servicegroup(temp_servicegroup, temp_service))) { return 0; } /* If the contact was specified, skip the services that do not have the contact specified */ if( NULL != temp_contact && ( FALSE == is_contact_for_service(temp_service, temp_contact))) { return 0; } /* If a contactgroup was specified, skip the services that do not have the contactgroup specified */ if(NULL != temp_contactgroup && (FALSE == is_contactgroup_for_service(temp_service, temp_contactgroup))) { return 0; } switch(time_field) { case STATUS_TIME_INVALID: break; case STATUS_TIME_LAST_UPDATE: if((start_time > 0) && (temp_servicestatus->last_update < start_time)) { return 0; } if((end_time > 0) && (temp_servicestatus->last_update > end_time)) { return 0; } break; case STATUS_TIME_LAST_CHECK: if((start_time > 0) && (temp_servicestatus->last_check < start_time)) { return 0; } if((end_time > 0) && (temp_servicestatus->last_check > end_time)) { return 0; } break; case STATUS_TIME_NEXT_CHECK: if((start_time > 0) && (temp_servicestatus->next_check < start_time)) { return 0; } if((end_time > 0) && (temp_servicestatus->next_check > end_time)) { return 0; } break; case STATUS_TIME_LAST_STATE_CHANGE: if((start_time > 0) && (temp_servicestatus->last_state_change < start_time)) { return 0; } if((end_time > 0) && (temp_servicestatus->last_state_change > end_time)) { return 0; } break; case STATUS_TIME_LAST_HARD_STATE_CHANGE: if((start_time > 0) && (temp_servicestatus->last_hard_state_change < start_time)) { return 0; } if((end_time > 0) && (temp_servicestatus->last_hard_state_change > end_time)) { return 0; } break; case STATUS_TIME_LAST_TIME_OK: if((start_time > 0) && (temp_servicestatus->last_time_ok < start_time)) { return 0; } if((end_time > 0) && (temp_servicestatus->last_time_ok > end_time)) { return 0; } break; case STATUS_TIME_LAST_TIME_WARNING: if((start_time > 0) && (temp_servicestatus->last_time_warning < start_time)) { return 0; } if((end_time > 0) && (temp_servicestatus->last_time_warning > end_time)) { return 0; } break; case STATUS_TIME_LAST_TIME_CRITICAL: if((start_time > 0) && (temp_servicestatus->last_time_critical < start_time)) { return 0; } if((end_time > 0) && (temp_servicestatus->last_time_critical > end_time)) { return 0; } break; case STATUS_TIME_LAST_TIME_UNKNOWN: if((start_time > 0) && (temp_servicestatus->last_time_unknown < start_time)) { return 0; } if((end_time > 0) && (temp_servicestatus->last_time_unknown > end_time)) { return 0; } break; case STATUS_TIME_LAST_NOTIFICATION: if((start_time > 0) && (temp_servicestatus->last_notification < start_time)) { return 0; } if((end_time > 0) && (temp_servicestatus->last_notification > end_time)) { return 0; } break; case STATUS_TIME_NEXT_NOTIFICATION: if((start_time > 0) && (temp_servicestatus->next_notification < start_time)) { return 0; } if((end_time > 0) && (temp_servicestatus->next_notification > end_time)) { return 0; } break; default: return 0; } /* If a service description was specified, skip the services that do not have the service description specified */ if(NULL != service_description && strcmp(temp_service->description, service_description)) { return 0; } /* If a check timeperiod was specified, skip this service if it does not have the check timeperiod specified */ if(NULL != check_timeperiod && (check_timeperiod != temp_service->check_period_ptr)) { return 0; } /* If a notification timeperiod was specified, skip this service if it does not have the notification timeperiod specified */ if(NULL != notification_timeperiod && (notification_timeperiod != temp_service->notification_period_ptr)) { return 0; } /* If a check command was specified, skip this service if it does not have the check command specified */ if(NULL != check_command && (check_command != temp_service->check_command_ptr)) { return 0; } /* If a event handler was specified, skip this service if it does not have the event handler specified */ if(NULL != event_handler && (event_handler != temp_service->event_handler_ptr)) { return 0; } /* If a parent service was specified... */ if(NULL != parent_service_name) { /* If the parent service is "none", skip this service if it has parentren */ if(!strcmp(parent_service_name,"none")) { if(NULL != temp_service->parents) { return 0; } } /* Otherwise, skip this service if it does not have the specified service as a parent */ else { int found = 0; for(temp_servicesmember = temp_service->parents; temp_servicesmember != NULL; temp_servicesmember = temp_servicesmember->next) { if(!strcmp(temp_servicesmember->service_description, parent_service_name)) { found = 1; } } if(0 == found) { return 0; } } } /* If a child service was specified... */ if(NULL != child_service_name) { /* If the child service is "none", skip this service if it has children */ if(!strcmp(child_service_name,"none")) { if(NULL != temp_service->children) { return 0; } } /* Otherwise, skip this service if it does not have the specified service as a child */ else { int found = 0; for(temp_servicesmember = temp_service->children; temp_servicesmember != NULL; temp_servicesmember = temp_servicesmember->next) { if(!strcmp(temp_servicesmember->service_description, child_service_name)) { found = 1; } } if(0 == found) { return 0; } } } return 1; } json_object *json_status_service_selectors(unsigned format_options, int start, int count, int use_parent_host, host *parent_host, int use_child_host, host *child_host, hostgroup *temp_hostgroup, host *match_host, servicegroup *temp_servicegroup, int host_statuses, int service_statuses, contact *temp_contact, int time_field, time_t start_time, time_t end_time, char *service_description, char *parent_service_name, char *child_service_name, contactgroup *temp_contactgroup, timeperiod *check_timeperiod, timeperiod *notification_timeperiod, command *check_command, command *event_handler) { json_object *json_selectors; json_selectors = json_new_object(); if( start > 0) { json_object_append_integer(json_selectors, "start", start); } if( count > 0) { json_object_append_integer(json_selectors, "count", count); } if( 1 == use_parent_host) { json_object_append_string(json_selectors, "parenthost", &percent_escapes, ( NULL == parent_host ? "none" : parent_host->name)); } if( 1 == use_child_host) { json_object_append_string(json_selectors, "childhost", &percent_escapes, ( NULL == child_host ? "none" : child_host->name)); } if( NULL != temp_hostgroup) { json_object_append_string(json_selectors, "hostgroup", &percent_escapes, temp_hostgroup->group_name); } if( NULL != temp_servicegroup) { json_object_append_string(json_selectors, "servicegroup", &percent_escapes, temp_servicegroup->group_name); } if(HOST_STATUS_ALL != host_statuses) { json_bitmask(json_selectors, format_options, "host_status", host_statuses, svm_host_statuses); } if(SERVICE_STATUS_ALL != service_statuses) { json_bitmask(json_selectors, format_options, "service_status", service_statuses, svm_service_statuses); } if(NULL != temp_contact) { json_object_append_string(json_selectors, "contact",&percent_escapes, temp_contact->name); } if(NULL != temp_contactgroup) { json_object_append_string(json_selectors, "contactgroup", &percent_escapes, temp_contactgroup->group_name); } if(time_field > 0) { json_enumeration(json_selectors, format_options, "servicetimefield", time_field, svm_service_time_fields); } if(start_time > 0) { json_object_append_time_t(json_selectors, "starttime", start_time); } if(end_time > 0) { json_object_append_time_t(json_selectors, "endtime", end_time); } if(NULL != service_description) { json_object_append_string(json_selectors, "servicedescription", &percent_escapes, service_description); } if( NULL != parent_service_name) { json_object_append_string(json_selectors, "parentservice", &percent_escapes, parent_service_name); } if( NULL != child_service_name) { json_object_append_string(json_selectors, "childservice", &percent_escapes, child_service_name); } if( NULL != check_timeperiod) { json_object_append_string(json_selectors, "checktimeperiod", &percent_escapes, check_timeperiod->name); } if( NULL != notification_timeperiod) { json_object_append_string(json_selectors, "servicenotificationtimeperiod", &percent_escapes, notification_timeperiod->name); } if( NULL != check_command) { json_object_append_string(json_selectors, "checkcommand", &percent_escapes, check_command->name); } if( NULL != event_handler) { json_object_append_string(json_selectors, "eventhandler", &percent_escapes, event_handler->name); } return json_selectors; } json_object *json_status_servicecount(unsigned format_options, host *match_host, int use_parent_host, host *parent_host, int use_child_host, host *child_host, hostgroup *temp_hostgroup, servicegroup *temp_servicegroup, int host_statuses, int service_statuses, contact *temp_contact, int time_field, time_t start_time, time_t end_time, char *service_description, char *parent_service_name, char *child_service_name, contactgroup *temp_contactgroup, timeperiod *check_timeperiod, timeperiod *notification_timeperiod, command *check_command, command *event_handler) { json_object *json_data; json_object *json_count; host *temp_host; service *temp_service; servicestatus *temp_servicestatus; int ok = 0; int warning = 0; int critical = 0; int unknown = 0; int pending = 0; json_data = json_new_object(); json_object_append_object(json_data, "selectors", json_status_service_selectors(format_options, 0, 0, use_parent_host, parent_host, use_child_host, child_host, temp_hostgroup, match_host, temp_servicegroup, host_statuses, service_statuses, temp_contact, time_field, start_time, end_time, service_description, parent_service_name, child_service_name, temp_contactgroup, check_timeperiod, notification_timeperiod, check_command, event_handler)); json_count = json_new_object(); for(temp_service = service_list; temp_service != NULL; temp_service = temp_service->next) { temp_host = find_host(temp_service->host_name); if(NULL == temp_host) { continue; } if(!json_status_service_passes_host_selection(temp_host, use_parent_host, parent_host, use_child_host, child_host, temp_hostgroup, match_host, host_statuses)) { continue; } /* Get the service status. If we cannot get the status of the service, skip it. This should probably return an error and doing so is in the todo list. */ temp_servicestatus = find_servicestatus(temp_service->host_name, temp_service->description); if( NULL == temp_servicestatus) { continue; } if(!json_status_service_passes_service_selection(temp_service, temp_servicegroup, temp_contact, temp_servicestatus, time_field, start_time, end_time, service_description, parent_service_name, child_service_name, temp_contactgroup, check_timeperiod, notification_timeperiod, check_command, event_handler)) { continue; } /* Count the services in each state */ switch(temp_servicestatus->status) { case SERVICE_PENDING: pending++; break; case SERVICE_OK: ok++; break; case SERVICE_WARNING: warning++; break; case SERVICE_CRITICAL: critical++; break; case SERVICE_UNKNOWN: unknown++; break; } } if( service_statuses & SERVICE_OK) json_object_append_integer(json_count, "ok", ok); if( service_statuses & SERVICE_WARNING) json_object_append_integer(json_count, "warning", warning); if( service_statuses & SERVICE_CRITICAL) json_object_append_integer(json_count, "critical", critical); if( service_statuses & SERVICE_UNKNOWN) json_object_append_integer(json_count, "unknown", unknown); if( service_statuses & SERVICE_PENDING) json_object_append_integer(json_count, "pending", pending); json_object_append_object(json_data, "count", json_count); return json_data; } json_object *json_status_servicelist(unsigned format_options, int start, int count, int details, host *match_host, int use_parent_host, host *parent_host, int use_child_host, host *child_host, hostgroup *temp_hostgroup, servicegroup *temp_servicegroup, int host_statuses, int service_statuses, contact *temp_contact, int time_field, time_t start_time, time_t end_time, char *service_description, char *parent_service_name, char *child_service_name, contactgroup *temp_contactgroup, timeperiod *check_timeperiod, timeperiod *notification_timeperiod, command *check_command, command *event_handler) { json_object *json_data; json_object *json_hostlist; json_object *json_servicelist; json_object *json_service_details; host *temp_host; service *temp_service; servicestatus *temp_servicestatus; int current = 0; int counted = 0; int service_count; /* number of services on a host */ json_data = json_new_object(); json_object_append_object(json_data, "selectors", json_status_service_selectors(format_options, start, count, use_parent_host, parent_host, use_child_host, child_host, temp_hostgroup, match_host, temp_servicegroup, host_statuses, service_statuses, temp_contact, time_field, start_time, end_time, service_description, parent_service_name, child_service_name, temp_contactgroup, check_timeperiod, notification_timeperiod, check_command, event_handler)); json_hostlist = json_new_object(); for(temp_host = host_list; temp_host != NULL; temp_host = temp_host->next) { if(json_status_service_passes_host_selection(temp_host, use_parent_host, parent_host, use_child_host, child_host, temp_hostgroup, match_host, host_statuses) == 0) { continue; } json_servicelist = json_new_object(); service_count = 0; for(temp_service = service_list; temp_service != NULL; temp_service = temp_service->next) { /* If this service isn't on the host we're currently working with, skip it */ if( strcmp( temp_host->name, temp_service->host_name)) continue; /* Get the service status. If we cannot get the status of the service, skip it. This should probably return an error and doing so is in the todo list. */ temp_servicestatus = find_servicestatus(temp_service->host_name, temp_service->description); if( NULL == temp_servicestatus) { continue; } if(json_status_service_passes_service_selection(temp_service, temp_servicegroup, temp_contact, temp_servicestatus, time_field, start_time, end_time, service_description, parent_service_name, child_service_name, temp_contactgroup, check_timeperiod, notification_timeperiod, check_command, event_handler) == 0) { continue; } /* If the status of the service does not match one of the status the user requested, skip the service */ if(!(temp_servicestatus->status & service_statuses)) { continue; } service_count++; /* If the current item passes the start and limit tests, display it */ if( passes_start_and_count_limits(start, count, current, counted)) { if( details > 0) { json_service_details = json_new_object(); json_status_service_details(json_service_details, format_options, temp_service, temp_servicestatus); json_object_append_object(json_servicelist, temp_service->description, json_service_details); } else { json_enumeration(json_servicelist, format_options, temp_service->description, temp_servicestatus->status, svm_service_statuses); } counted++; } current++; } if( service_count > 0) { json_object_append_object(json_hostlist, temp_host->name, json_servicelist); } } json_object_append_object(json_data, "servicelist", json_hostlist); return json_data; } json_object *json_status_service(unsigned format_options, service *temp_service, servicestatus *temp_servicestatus) { json_object *json_service = json_new_object(); json_object *json_details = json_new_object(); json_object_append_string(json_details, "host_name", &percent_escapes, temp_service->host_name); json_object_append_string(json_details, "description", &percent_escapes, temp_service->description); json_status_service_details(json_details, format_options, temp_service, temp_servicestatus); json_object_append_object(json_service, "service", json_details); return json_service; } void json_status_service_details(json_object *json_details, unsigned format_options, service *temp_service, servicestatus *temp_servicestatus) { json_object_append_string(json_details, "host_name", &percent_escapes, temp_service->host_name); json_object_append_string(json_details, "description", &percent_escapes, temp_service->description); json_object_append_string(json_details, "plugin_output", &percent_escapes, temp_servicestatus->plugin_output); json_object_append_string(json_details, "long_plugin_output", &percent_escapes, temp_servicestatus->long_plugin_output); json_object_append_string(json_details, "perf_data", &percent_escapes, temp_servicestatus->perf_data); json_object_append_integer(json_details, "max_attempts", temp_servicestatus->max_attempts); json_object_append_integer(json_details, "current_attempt", temp_servicestatus->current_attempt); json_enumeration(json_details, format_options, "status", temp_servicestatus->status, svm_service_statuses); json_object_append_time_t(json_details, "last_update", temp_servicestatus->last_update); json_object_append_boolean(json_details, "has_been_checked", temp_servicestatus->has_been_checked); json_object_append_boolean(json_details, "should_be_scheduled", temp_servicestatus->should_be_scheduled); json_object_append_time_t(json_details, "last_check", temp_servicestatus->last_check); json_bitmask(json_details, format_options, "check_options", temp_servicestatus->check_options, svm_check_options); json_enumeration(json_details, format_options, "check_type", temp_servicestatus->check_type, svm_service_check_types); json_object_append_boolean(json_details, "checks_enabled", temp_servicestatus->checks_enabled); json_object_append_time_t(json_details, "last_state_change", temp_servicestatus->last_state_change); json_object_append_time_t(json_details, "last_hard_state_change", temp_servicestatus->last_hard_state_change); json_enumeration(json_details, format_options, "last_hard_state", temp_servicestatus->last_hard_state, svm_service_states); json_object_append_time_t(json_details, "last_time_ok", temp_servicestatus->last_time_ok); json_object_append_time_t(json_details, "last_time_warning", temp_servicestatus->last_time_warning); json_object_append_time_t(json_details, "last_time_unknown", temp_servicestatus->last_time_unknown); json_object_append_time_t(json_details, "last_time_critical", temp_servicestatus->last_time_critical); json_enumeration(json_details, format_options, "state_type", temp_servicestatus->state_type, svm_state_types); json_object_append_time_t(json_details, "last_notification", temp_servicestatus->last_notification); json_object_append_time_t(json_details, "next_notification", temp_servicestatus->next_notification); json_object_append_time_t(json_details, "next_check", temp_servicestatus->next_check); json_object_append_boolean(json_details, "no_more_notifications", temp_servicestatus->no_more_notifications); json_object_append_boolean(json_details, "notifications_enabled", temp_servicestatus->notifications_enabled); json_object_append_boolean(json_details, "problem_has_been_acknowledged", temp_servicestatus->problem_has_been_acknowledged); json_enumeration(json_details, format_options, "acknowledgement_type", temp_servicestatus->acknowledgement_type, svm_acknowledgement_types); json_object_append_integer(json_details, "current_notification_number", temp_servicestatus->current_notification_number); #ifdef JSON_NAGIOS_4X json_object_append_boolean(json_details, "accept_passive_checks", temp_servicestatus->accept_passive_checks); #else json_object_append_boolean(json_details, "accept_passive_service_checks", temp_servicestatus->accept_passive_service_checks); #endif json_object_append_boolean(json_details, "event_handler_enabled", temp_servicestatus->event_handler_enabled); json_object_append_boolean(json_details, "flap_detection_enabled", temp_servicestatus->flap_detection_enabled); json_object_append_boolean(json_details, "is_flapping", temp_servicestatus->is_flapping); json_object_append_real(json_details, "percent_state_change", temp_servicestatus->percent_state_change); json_object_append_real(json_details, "latency", temp_servicestatus->latency); json_object_append_real(json_details, "execution_time", temp_servicestatus->execution_time); json_object_append_integer(json_details, "scheduled_downtime_depth", temp_servicestatus->scheduled_downtime_depth); #ifndef JSON_NAGIOS_4X json_object_append_boolean(json_details, "failure_prediction_enabled", temp_servicestatus->failure_prediction_enabled); #endif json_object_append_boolean(json_details, "process_performance_data", temp_servicestatus->process_performance_data); #ifdef JSON_NAGIOS_4X json_object_append_boolean(json_details, "obsess", temp_servicestatus->obsess); #else json_object_append_boolean(json_details, "obsess_over_service", temp_servicestatus->obsess_over_service); #endif } int json_status_comment_passes_selection(nagios_comment *temp_comment, int time_field, time_t start_time, time_t end_time, unsigned comment_types, unsigned entry_types, unsigned persistence, unsigned expiring, char *host_name, char *service_description) { switch(time_field) { case STATUS_TIME_INVALID: break; case STATUS_TIME_ENTRY_TIME: if((start_time > 0) && (temp_comment->entry_time < start_time)) { return 0; } if((end_time > 0) && (temp_comment->entry_time > end_time)) { return 0; } break; case STATUS_TIME_EXPIRE_TIME: if((start_time > 0) && (temp_comment->expire_time < start_time)) { return 0; } if((end_time > 0) && (temp_comment->expire_time > end_time)) { return 0; } break; default: return 0; } if(comment_types != COMMENT_TYPE_ALL) { switch(temp_comment->comment_type) { case HOST_COMMENT: if(!(comment_types & COMMENT_TYPE_HOST)) { return 0; } break; case SERVICE_COMMENT: if(!(comment_types & COMMENT_TYPE_SERVICE)) { return 0; } break; } } if(entry_types != COMMENT_ENTRY_ALL) { switch(temp_comment->entry_type) { case USER_COMMENT: if(!(entry_types & COMMENT_ENTRY_USER)) { return 0; } break; case DOWNTIME_COMMENT: if(!(entry_types & COMMENT_ENTRY_DOWNTIME)) { return 0; } break; case FLAPPING_COMMENT: if(!(entry_types & COMMENT_ENTRY_FLAPPING)) { return 0; } break; case ACKNOWLEDGEMENT_COMMENT: if(!(entry_types & COMMENT_ENTRY_ACKNOWLEDGEMENT)) { return 0; } break; } } if(persistence != BOOLEAN_EITHER) { switch(temp_comment->persistent) { case 0: /* false */ if(!(persistence & BOOLEAN_FALSE)) { return 0; } break; case 1: /* true */ if(!(persistence & BOOLEAN_TRUE)) { return 0; } break; } } if(expiring != BOOLEAN_EITHER) { switch(temp_comment->expires) { case 0: /* false */ if(!(expiring & BOOLEAN_FALSE)) { return 0; } break; case 1: /* true */ if(!(expiring & BOOLEAN_TRUE)) { return 0; } break; } } if(NULL != host_name) { if((NULL == temp_comment->host_name) || strcmp(temp_comment->host_name, host_name)) { return 0; } } if(NULL != service_description) { if((NULL == temp_comment->service_description) || strcmp(temp_comment->service_description, service_description)) { return 0; } } return 1; } json_object *json_status_comment_selectors(unsigned format_options, int start, int count, int time_field, time_t start_time, time_t end_time, unsigned comment_types, unsigned entry_types, unsigned persistence, unsigned expiring, char *host_name, char *service_description) { json_object *json_selectors; json_selectors = json_new_object(); if( start > 0) { json_object_append_integer(json_selectors, "start", start); } if( count > 0) { json_object_append_integer(json_selectors, "count", count); } if(time_field > 0) { json_enumeration(json_selectors, format_options, "commenttimefield", time_field, svm_comment_time_fields); } if(start_time > 0) { json_object_append_time_t(json_selectors, "starttime", start_time); } if(end_time > 0) { json_object_append_time_t(json_selectors, "endtime", end_time); } if(comment_types != COMMENT_TYPE_ALL) { json_bitmask(json_selectors, format_options, "commenttypes", comment_types, svm_valid_comment_types); } if(entry_types != COMMENT_ENTRY_ALL) { json_bitmask(json_selectors, format_options, "entrytypes", entry_types, svm_valid_comment_entry_types); } if(persistence != BOOLEAN_EITHER) { json_bitmask(json_selectors, format_options, "persistence", persistence, svm_valid_persistence); } if(expiring != BOOLEAN_EITHER) { json_bitmask(json_selectors, format_options, "expiring", expiring, svm_valid_expiration); } if(NULL != host_name) { json_object_append_string(json_selectors, "hostname", &percent_escapes, host_name); } if(NULL != service_description) { json_object_append_string(json_selectors, "servicedescription", &percent_escapes, service_description); } return json_selectors; } json_object *json_status_commentcount(unsigned format_options, int time_field, time_t start_time, time_t end_time, unsigned comment_types, unsigned entry_types, unsigned persistence, unsigned expiring, char *host_name, char *service_description) { json_object *json_data; nagios_comment *temp_comment; int count = 0; json_data = json_new_object(); json_object_append_object(json_data, "selectors", json_status_comment_selectors(format_options, 0, 0, time_field, start_time, end_time, comment_types, entry_types, persistence, expiring, host_name, service_description)); for(temp_comment = comment_list; temp_comment != NULL; temp_comment = temp_comment->next) { if(json_status_comment_passes_selection(temp_comment, time_field, start_time, end_time, comment_types, entry_types, persistence, expiring, host_name, service_description) == 0) { continue; } count++; } json_object_append_integer(json_data, "count", count); return json_data; } json_object *json_status_commentlist(unsigned format_options, int start, int count, int details, int time_field, time_t start_time, time_t end_time, unsigned comment_types, unsigned entry_types, unsigned persistence, unsigned expiring, char *host_name, char *service_description) { json_object *json_data; json_object *json_commentlist_object = NULL; json_object *json_commentlist_array = NULL; json_object *json_comment_details; nagios_comment *temp_comment; int current = 0; int counted = 0; char *buf; json_data = json_new_object(); json_object_append_object(json_data, "selectors", json_status_comment_selectors(format_options, start, count, time_field, start_time, end_time, comment_types, entry_types, persistence, expiring, host_name, service_description)); if(details > 0) { json_commentlist_object = json_new_object(); } else { json_commentlist_array = json_new_array(); } for(temp_comment = comment_list; temp_comment != NULL; temp_comment = temp_comment->next) { if(json_status_comment_passes_selection(temp_comment, time_field, start_time, end_time, comment_types, entry_types, persistence, expiring, host_name, service_description) == 0) { continue; } /* If the current item passes the start and limit tests, display it */ if( passes_start_and_count_limits(start, count, current, counted)) { if( details > 0) { asprintf(&buf, "%lu", temp_comment->comment_id); json_comment_details = json_new_object(); json_status_comment_details(json_comment_details, format_options, temp_comment); json_object_append_object(json_commentlist_object, buf, json_comment_details); } else { json_array_append_integer(json_commentlist_array, temp_comment->comment_id); } counted++; } current++; } if(details > 0) { json_object_append_object(json_data, "commentlist", json_commentlist_object); } else { json_object_append_array(json_data, "commentlist", json_commentlist_array); } return json_data; } json_object *json_status_comment(unsigned format_options, nagios_comment *temp_comment) { json_object *json_comment = json_new_object(); json_object *json_details = json_new_object(); json_object_append_integer(json_details, "comment_id", temp_comment->comment_id); json_status_comment_details(json_details, format_options, temp_comment); json_object_append_object(json_comment, "comment", json_details); return json_comment; } void json_status_comment_details(json_object *json_details, unsigned format_options, nagios_comment *temp_comment) { json_object_append_integer(json_details, "comment_id", temp_comment->comment_id); json_enumeration(json_details, format_options, "comment_type", temp_comment->comment_type, svm_comment_types); json_enumeration(json_details, format_options, "entry_type", temp_comment->entry_type, svm_comment_entry_types); json_object_append_integer(json_details, "source", temp_comment->source); json_object_append_boolean(json_details, "persistent", temp_comment->persistent); json_object_append_time_t(json_details, "entry_time", temp_comment->entry_time); json_object_append_boolean(json_details, "expires", temp_comment->expires); json_object_append_time_t(json_details, "expire_time", temp_comment->expire_time); json_object_append_string(json_details, "host_name", &percent_escapes, temp_comment->host_name); if(SERVICE_COMMENT == temp_comment->comment_type) { json_object_append_string(json_details, "service_description", &percent_escapes, temp_comment->service_description); } json_object_append_string(json_details, "author", &percent_escapes, temp_comment->author); json_object_append_string(json_details, "comment_data", &percent_escapes, temp_comment->comment_data); } int json_status_downtime_passes_selection(scheduled_downtime *temp_downtime, int time_field, time_t start_time, time_t end_time, unsigned object_types, unsigned downtime_types, unsigned triggered, int triggered_by, unsigned in_effect, char *host_name, char *service_description) { switch(time_field) { case STATUS_TIME_INVALID: break; case STATUS_TIME_ENTRY_TIME: if((start_time > 0) && (temp_downtime->entry_time < start_time)) { return 0; } if((end_time > 0) && (temp_downtime->entry_time > end_time)) { return 0; } break; case STATUS_TIME_START_TIME: if((start_time > 0) && (temp_downtime->start_time < start_time)) { return 0; } if((end_time > 0) && (temp_downtime->start_time > end_time)) { return 0; } break; case STATUS_TIME_FLEX_DOWNTIME_START: if((start_time > 0) && (temp_downtime->flex_downtime_start < start_time)) { return 0; } if((end_time > 0) && (temp_downtime->flex_downtime_start > end_time)) { return 0; } break; case STATUS_TIME_END_TIME: if((start_time > 0) && (temp_downtime->end_time < start_time)) { return 0; } if((end_time > 0) && (temp_downtime->end_time > end_time)) { return 0; } break; default: return 0; } if(object_types != DOWNTIME_OBJECT_TYPE_ALL) { switch(temp_downtime->type) { case HOST_DOWNTIME: if(!(object_types & DOWNTIME_OBJECT_TYPE_HOST)) { return 0; } break; case SERVICE_DOWNTIME: if(!(object_types & DOWNTIME_OBJECT_TYPE_SERVICE)) { return 0; } break; } } if(downtime_types != DOWNTIME_TYPE_ALL) { if(temp_downtime->fixed) { if(!(downtime_types & DOWNTIME_TYPE_FIXED)) { return 0; } } else { if(!(downtime_types & DOWNTIME_TYPE_FLEXIBLE)) { return 0; } } } if(triggered != BOOLEAN_EITHER) { if(0 == temp_downtime->triggered_by) { if(!(triggered & BOOLEAN_FALSE)) { return 0; } } else { if(!(triggered & BOOLEAN_TRUE)) { return 0; } } } if(triggered_by != -1) { if(temp_downtime->triggered_by != (unsigned long)triggered_by) { return 0; } } if(in_effect != BOOLEAN_EITHER) { if(0 == temp_downtime->is_in_effect) { if(!(in_effect & BOOLEAN_FALSE)) { return 0; } } else { if(!(in_effect & BOOLEAN_TRUE)) { return 0; } } } if(NULL != host_name) { if((NULL == temp_downtime->host_name) || strcmp(temp_downtime->host_name, host_name)) { return 0; } } if(NULL != service_description) { if((NULL == temp_downtime->service_description) || strcmp(temp_downtime->service_description, service_description)) { return 0; } } return 1; } json_object *json_status_downtime_selectors(unsigned format_options, int start, int count, int time_field, time_t start_time, time_t end_time, unsigned object_types, unsigned downtime_types, unsigned triggered, int triggered_by, unsigned in_effect, char *host_name, char *service_description) { json_object *json_selectors; json_selectors = json_new_object(); if( start > 0) { json_object_append_integer(json_selectors, "start", start); } if( count > 0) { json_object_append_integer(json_selectors, "count", count); } if(time_field > 0) { json_enumeration(json_selectors, format_options, "downtimetimefield", time_field, svm_downtime_time_fields); } if(start_time > 0) { json_object_append_time_t(json_selectors, "starttime", start_time); } if(end_time > 0) { json_object_append_time_t(json_selectors, "endtime", end_time); } if(object_types != DOWNTIME_OBJECT_TYPE_ALL) { json_bitmask(json_selectors, format_options, "downtimeobjecttypes", object_types, svm_valid_downtime_object_types); } if(downtime_types != DOWNTIME_TYPE_ALL) { json_bitmask(json_selectors, format_options, "downtimetypes", downtime_types, svm_valid_downtime_types); } if(triggered != BOOLEAN_EITHER) { json_bitmask(json_selectors, format_options, "triggered", triggered, svm_valid_triggered_status); } if(triggered_by != -1) { json_object_append_integer(json_selectors, "triggeredby", triggered_by); } if(in_effect != BOOLEAN_EITHER) { json_bitmask(json_selectors, format_options, "ineffect", in_effect, svm_valid_in_effect_status); } if(NULL != host_name) { json_object_append_string(json_selectors, "hostname", &percent_escapes, host_name); } if(NULL != service_description) { json_object_append_string(json_selectors, "servicedescription", &percent_escapes, service_description); } return json_selectors; } json_object *json_status_downtimecount(unsigned format_options, int time_field, time_t start_time, time_t end_time, unsigned object_types, unsigned downtime_types, unsigned triggered, int triggered_by, unsigned in_effect, char *host_name, char *service_description) { json_object *json_data; scheduled_downtime *temp_downtime; int count = 0; json_data = json_new_object(); json_object_append_object(json_data, "selectors", json_status_downtime_selectors(format_options, 0, 0, time_field, start_time, end_time, object_types, downtime_types, triggered, triggered_by, in_effect, host_name, service_description)); for(temp_downtime = scheduled_downtime_list; temp_downtime != NULL; temp_downtime = temp_downtime->next) { if(!json_status_downtime_passes_selection(temp_downtime, time_field, start_time, end_time, object_types, downtime_types, triggered, triggered_by, in_effect, host_name, service_description)) { continue; } count++; } json_object_append_integer(json_data, "count", count); return json_data; } json_object *json_status_downtimelist(unsigned format_options, int start, int count, int details, int time_field, time_t start_time, time_t end_time, unsigned object_types, unsigned downtime_types, unsigned triggered, int triggered_by, unsigned in_effect, char *host_name, char *service_description) { json_object *json_data; json_object *json_downtimelist_object = NULL; json_object *json_downtimelist_array = NULL; json_object *json_downtime_details; scheduled_downtime *temp_downtime; int current = 0; int counted = 0; char *buf; json_data = json_new_object(); json_object_append_object(json_data, "selectors", json_status_downtime_selectors(format_options, start, count, time_field, start_time, end_time, object_types, downtime_types, triggered, triggered_by, in_effect, host_name, service_description)); if(details > 0) { json_downtimelist_object = json_new_object(); } else { json_downtimelist_array = json_new_array(); } for(temp_downtime = scheduled_downtime_list; temp_downtime != NULL; temp_downtime = temp_downtime->next) { if(!json_status_downtime_passes_selection(temp_downtime, time_field, start_time, end_time, object_types, downtime_types, triggered, triggered_by, in_effect, host_name, service_description)) { continue; } /* If the current item passes the start and limit tests, display it */ if( passes_start_and_count_limits(start, count, current, counted)) { if( details > 0) { asprintf(&buf, "%lu", temp_downtime->downtime_id); json_downtime_details = json_new_object(); json_status_downtime_details(json_downtime_details, format_options, temp_downtime); json_object_append_object(json_downtimelist_object, buf, json_downtime_details); } else { json_array_append_integer(json_downtimelist_array, temp_downtime->downtime_id); } counted++; } current++; } if(details > 0) { json_object_append_object(json_data, "downtimelist", json_downtimelist_object); } else { json_object_append_array(json_data, "downtimelist", json_downtimelist_array); } return json_data; } json_object *json_status_downtime(unsigned format_options, scheduled_downtime *temp_downtime) { json_object *json_downtime = json_new_object(); json_object *json_details = json_new_object(); json_object_append_integer(json_details, "downtime_id", temp_downtime->downtime_id); json_status_downtime_details(json_details, format_options, temp_downtime); json_object_append_object(json_downtime, "downtime", json_details); return json_downtime; } void json_status_downtime_details(json_object *json_details, unsigned format_options, scheduled_downtime *temp_downtime) { json_object_append_integer(json_details, "downtime_id", temp_downtime->downtime_id); json_enumeration(json_details, format_options, "type", temp_downtime->type, svm_downtime_types); json_object_append_string(json_details, "host_name", &percent_escapes, temp_downtime->host_name); if(SERVICE_DOWNTIME == temp_downtime->type) { json_object_append_string(json_details, "service_description", &percent_escapes, temp_downtime->service_description); } json_object_append_time_t(json_details, "entry_time", temp_downtime->entry_time); json_object_append_time_t(json_details, "start_time", temp_downtime->start_time); json_object_append_time_t(json_details, "flex_downtime_start", temp_downtime->flex_downtime_start); json_object_append_time_t(json_details, "end_time", temp_downtime->end_time); json_object_append_boolean(json_details, "fixed", temp_downtime->fixed); json_object_append_integer(json_details, "triggered_by", (int)temp_downtime->triggered_by); json_object_append_integer(json_details, "duration", (int)temp_downtime->duration); json_object_append_boolean(json_details, "is_in_effect", temp_downtime->is_in_effect); json_object_append_boolean(json_details, "start_notification_sent", temp_downtime->start_notification_sent); json_object_append_string(json_details, "author", &percent_escapes, temp_downtime->author); json_object_append_string(json_details, "comment", &percent_escapes, temp_downtime->comment); } json_object *json_status_program(unsigned format_options) { json_object *json_data; json_object *json_status; json_data = json_new_object(); json_status = json_new_object(); #if 0 json_object_append_unsigned(json_status, "modified_host_attributes", (unsigned long long)modified_host_process_attributes); json_object_append_unsigned(json_status, "modified_service_process_attributes", (unsigned long long)modified_service_process_attributes); #endif json_object_append_string(json_status, "version", NULL, PROGRAM_VERSION); json_object_append_integer(json_status, "nagios_pid", nagios_pid); json_object_append_boolean(json_status, "daemon_mode", daemon_mode); json_object_append_time_t(json_status, "program_start", program_start); #ifndef JSON_NAGIOS_4X json_object_append_time_t(json_status, "last_command_check", last_command_check); #endif json_object_append_time_t(json_status, "last_log_rotation", last_log_rotation); json_object_append_boolean(json_status, "enable_notifications", enable_notifications); json_object_append_boolean(json_status, "execute_service_checks", execute_service_checks); json_object_append_boolean(json_status, "accept_passive_service_checks", accept_passive_service_checks); json_object_append_boolean(json_status, "execute_host_checks", execute_host_checks); json_object_append_boolean(json_status, "accept_passive_host_checks", accept_passive_host_checks); json_object_append_boolean(json_status, "enable_event_handlers", enable_event_handlers); json_object_append_boolean(json_status, "obsess_over_services", obsess_over_services); json_object_append_boolean(json_status, "obsess_over_hosts", obsess_over_hosts); json_object_append_boolean(json_status, "check_service_freshness", check_service_freshness); json_object_append_boolean(json_status, "check_host_freshness", check_host_freshness); json_object_append_boolean(json_status, "enable_flap_detection", enable_flap_detection); #ifndef JSON_NAGIOS_4X json_object_append_boolean(json_status, "enable_failure_prediction", enable_failure_prediction); #endif json_object_append_boolean(json_status, "process_performance_data", process_performance_data); #if 0 json_object_append_string(json_status, "global_host_event_handler", &percent_escapes, global_host_event_handler); json_object_append_string(json_status, "global_service_event_handler", &percent_escapes, global_service_event_handler); json_object_append_unsigned(json_status, "next_comment_id", (unsigned long long)next_comment_id); json_object_append_unsigned(json_status, "next_downtime_id", (unsigned long long)next_downtime_id); json_object_append_unsigned(json_status, "next_event_id", (unsigned long long)next_event_id); json_object_append_unsigned(json_status, "next_problem_id", (unsigned long long)next_problem_id); json_object_append_unsigned(json_status, "next_notification_id", (unsigned long long)next_notification_id); json_object_append_unsigned(json_status, "total_external_command_buffer_slots", (unsigned long long)external_command_buffer_slots); json_object_append_unsigned(json_status, "used_external_command_buffer_slots", (unsigned long long)used_external_command_buffer_slots); json_object_append_unsigned(json_status, "high_external_command_buffer_slots", (unsigned long long)high_external_command_buffer_slots); json_object_append_string(json_status, "active_scheduled_host_check_stats", NULL, "%d,%d,%d", check_statistics[ACTIVE_SCHEDULED_HOST_CHECK_STATS].minute_stats[0], check_statistics[ACTIVE_SCHEDULED_HOST_CHECK_STATS].minute_stats[1], check_statistics[ACTIVE_SCHEDULED_HOST_CHECK_STATS].minute_stats[2]); json_object_append_string(json_status, "active_ondemand_host_check_stats", NULL, "%d,%d,%d", check_statistics[ACTIVE_ONDEMAND_HOST_CHECK_STATS].minute_stats[0], check_statistics[ACTIVE_ONDEMAND_HOST_CHECK_STATS].minute_stats[1], check_statistics[ACTIVE_ONDEMAND_HOST_CHECK_STATS].minute_stats[2]); json_object_append_string(json_status, "passive_host_check_stats", NULL, "%d,%d,%d", check_statistics[PASSIVE_HOST_CHECK_STATS].minute_stats[0], check_statistics[PASSIVE_HOST_CHECK_STATS].minute_stats[1], check_statistics[PASSIVE_HOST_CHECK_STATS].minute_stats[2]); json_object_append_string(json_status, "active_scheduled_service_check_stats", NULL, "%d,%d,%d", check_statistics[ACTIVE_SCHEDULED_SERVICE_CHECK_STATS].minute_stats[0], check_statistics[ACTIVE_SCHEDULED_SERVICE_CHECK_STATS].minute_stats[1], check_statistics[ACTIVE_SCHEDULED_SERVICE_CHECK_STATS].minute_stats[2]); json_object_append_string(json_status, "active_ondemand_service_check_stats", NULL, "%d,%d,%d", check_statistics[ACTIVE_ONDEMAND_SERVICE_CHECK_STATS].minute_stats[0], check_statistics[ACTIVE_ONDEMAND_SERVICE_CHECK_STATS].minute_stats[1], check_statistics[ACTIVE_ONDEMAND_SERVICE_CHECK_STATS].minute_stats[2]); json_object_append_string(json_status, "passive_service_check_stats", NULL, "%d,%d,%d", check_statistics[PASSIVE_SERVICE_CHECK_STATS].minute_stats[0], check_statistics[PASSIVE_SERVICE_CHECK_STATS].minute_stats[1], check_statistics[PASSIVE_SERVICE_CHECK_STATS].minute_stats[2]); json_object_append_string(json_status, "cached_host_check_stats", NULL, "%d,%d,%d", check_statistics[ACTIVE_CACHED_HOST_CHECK_STATS].minute_stats[0], check_statistics[ACTIVE_CACHED_HOST_CHECK_STATS].minute_stats[1], check_statistics[ACTIVE_CACHED_HOST_CHECK_STATS].minute_stats[2]); json_object_append_string(json_status, "cached_service_check_stats", NULL, "%d,%d,%d", check_statistics[ACTIVE_CACHED_SERVICE_CHECK_STATS].minute_stats[0], check_statistics[ACTIVE_CACHED_SERVICE_CHECK_STATS].minute_stats[1], check_statistics[ACTIVE_CACHED_SERVICE_CHECK_STATS].minute_stats[2]); json_object_append_string(json_status, "external_command_stats", NULL, "%d,%d,%d", check_statistics[EXTERNAL_COMMAND_STATS].minute_stats[0], check_statistics[EXTERNAL_COMMAND_STATS].minute_stats[1], check_statistics[EXTERNAL_COMMAND_STATS].minute_stats[2]); json_object_append_string(json_status, "parallel_host_check_stats", NULL, "%d,%d,%d", check_statistics[PARALLEL_HOST_CHECK_STATS].minute_stats[0], check_statistics[PARALLEL_HOST_CHECK_STATS].minute_stats[1], check_statistics[PARALLEL_HOST_CHECK_STATS].minute_stats[2]); json_object_append_string(json_status, "serial_host_check_stats", NULL, "%d,%d,%d", check_statistics[SERIAL_HOST_CHECK_STATS].minute_stats[0], check_statistics[SERIAL_HOST_CHECK_STATS].minute_stats[1], check_statistics[SERIAL_HOST_CHECK_STATS].minute_stats[2]); #endif json_object_append_object(json_data, "programstatus", json_status); return json_data; } json_object *json_status_performance(void) { service *temp_service = NULL; servicestatus *temp_servicestatus = NULL; host *temp_host = NULL; hoststatus *temp_hoststatus = NULL; int total_active_service_checks = 0; int total_passive_service_checks = 0; double min_service_execution_time = 0.0; double max_service_execution_time = 0.0; double total_service_execution_time = 0.0; int have_min_service_execution_time = FALSE; int have_max_service_execution_time = FALSE; double min_service_latency = 0.0; double max_service_latency = 0.0; double long total_service_latency = 0.0; int have_min_service_latency = FALSE; int have_max_service_latency = FALSE; double min_host_latency = 0.0; double max_host_latency = 0.0; double total_host_latency = 0.0; int have_min_host_latency = FALSE; int have_max_host_latency = FALSE; double min_service_percent_change_a = 0.0; double max_service_percent_change_a = 0.0; double total_service_percent_change_a = 0.0; int have_min_service_percent_change_a = FALSE; int have_max_service_percent_change_a = FALSE; double min_service_percent_change_b = 0.0; double max_service_percent_change_b = 0.0; double total_service_percent_change_b = 0.0; int have_min_service_percent_change_b = FALSE; int have_max_service_percent_change_b = FALSE; int active_service_checks_1min = 0; int active_service_checks_5min = 0; int active_service_checks_15min = 0; int active_service_checks_1hour = 0; int active_service_checks_start = 0; int active_service_checks_ever = 0; int passive_service_checks_1min = 0; int passive_service_checks_5min = 0; int passive_service_checks_15min = 0; int passive_service_checks_1hour = 0; int passive_service_checks_start = 0; int passive_service_checks_ever = 0; int total_active_host_checks = 0; int total_passive_host_checks = 0; double min_host_execution_time = 0.0; double max_host_execution_time = 0.0; double total_host_execution_time = 0.0; int have_min_host_execution_time = FALSE; int have_max_host_execution_time = FALSE; double min_host_percent_change_a = 0.0; double max_host_percent_change_a = 0.0; double total_host_percent_change_a = 0.0; int have_min_host_percent_change_a = FALSE; int have_max_host_percent_change_a = FALSE; double min_host_percent_change_b = 0.0; double max_host_percent_change_b = 0.0; double total_host_percent_change_b = 0.0; int have_min_host_percent_change_b = FALSE; int have_max_host_percent_change_b = FALSE; int active_host_checks_1min = 0; int active_host_checks_5min = 0; int active_host_checks_15min = 0; int active_host_checks_1hour = 0; int active_host_checks_start = 0; int active_host_checks_ever = 0; int passive_host_checks_1min = 0; int passive_host_checks_5min = 0; int passive_host_checks_15min = 0; int passive_host_checks_1hour = 0; int passive_host_checks_start = 0; int passive_host_checks_ever = 0; time_t current_time; json_object *json_data; json_object *json_programstatus; json_object *json_service_checks; json_object *json_host_checks; json_object *json_check_statistics; json_object *json_buffer_usage; json_object *json_active; json_object *json_passive; json_object *json_checks; json_object *json_metrics; json_object *json_temp; time(¤t_time); /* check all services */ for(temp_servicestatus = servicestatus_list; temp_servicestatus != NULL; temp_servicestatus = temp_servicestatus->next) { /* find the service */ temp_service = find_service(temp_servicestatus->host_name, temp_servicestatus->description); if(NULL == temp_service) { continue; } /* make sure the user has rights to view service information */ if(FALSE == is_authorized_for_service(temp_service, ¤t_authdata)) { continue; } /* is this an active or passive check? */ if(SERVICE_CHECK_ACTIVE == temp_servicestatus->check_type) { total_active_service_checks++; total_service_execution_time += temp_servicestatus->execution_time; if(have_min_service_execution_time == FALSE || temp_servicestatus->execution_time < min_service_execution_time) { have_min_service_execution_time = TRUE; min_service_execution_time = temp_servicestatus->execution_time; } if(have_max_service_execution_time == FALSE || temp_servicestatus->execution_time > max_service_execution_time) { have_max_service_execution_time = TRUE; max_service_execution_time = temp_servicestatus->execution_time; } total_service_percent_change_a += temp_servicestatus->percent_state_change; if(have_min_service_percent_change_a == FALSE || temp_servicestatus->percent_state_change < min_service_percent_change_a) { have_min_service_percent_change_a = TRUE; min_service_percent_change_a = temp_servicestatus->percent_state_change; } if(have_max_service_percent_change_a == FALSE || temp_servicestatus->percent_state_change > max_service_percent_change_a) { have_max_service_percent_change_a = TRUE; max_service_percent_change_a = temp_servicestatus->percent_state_change; } total_service_latency += temp_servicestatus->latency; if(have_min_service_latency == FALSE || temp_servicestatus->latency < min_service_latency) { have_min_service_latency = TRUE; min_service_latency = temp_servicestatus->latency; } if(have_max_service_latency == FALSE || temp_servicestatus->latency > max_service_latency) { have_max_service_latency = TRUE; max_service_latency = temp_servicestatus->latency; } if(temp_servicestatus->last_check >= (current_time - 60)) active_service_checks_1min++; if(temp_servicestatus->last_check >= (current_time - 300)) active_service_checks_5min++; if(temp_servicestatus->last_check >= (current_time - 900)) active_service_checks_15min++; if(temp_servicestatus->last_check >= (current_time - 3600)) active_service_checks_1hour++; if(temp_servicestatus->last_check >= program_start) active_service_checks_start++; if(temp_servicestatus->last_check != (time_t)0) active_service_checks_ever++; } else { total_passive_service_checks++; total_service_percent_change_b += temp_servicestatus->percent_state_change; if(have_min_service_percent_change_b == FALSE || temp_servicestatus->percent_state_change < min_service_percent_change_b) { have_min_service_percent_change_b = TRUE; min_service_percent_change_b = temp_servicestatus->percent_state_change; } if(have_max_service_percent_change_b == FALSE || temp_servicestatus->percent_state_change > max_service_percent_change_b) { have_max_service_percent_change_b = TRUE; max_service_percent_change_b = temp_servicestatus->percent_state_change; } if(temp_servicestatus->last_check >= (current_time - 60)) passive_service_checks_1min++; if(temp_servicestatus->last_check >= (current_time - 300)) passive_service_checks_5min++; if(temp_servicestatus->last_check >= (current_time - 900)) passive_service_checks_15min++; if(temp_servicestatus->last_check >= (current_time - 3600)) passive_service_checks_1hour++; if(temp_servicestatus->last_check >= program_start) passive_service_checks_start++; if(temp_servicestatus->last_check != (time_t)0) passive_service_checks_ever++; } } /* check all hosts */ for(temp_hoststatus = hoststatus_list; temp_hoststatus != NULL; temp_hoststatus = temp_hoststatus->next) { /* find the host */ temp_host = find_host(temp_hoststatus->host_name); if(NULL == temp_host) { continue; } /* make sure the user has rights to view host information */ if(FALSE == is_authorized_for_host(temp_host, ¤t_authdata)) { continue; } /* is this an active or passive check? */ if(temp_hoststatus->check_type == HOST_CHECK_ACTIVE) { total_active_host_checks++; total_host_execution_time += temp_hoststatus->execution_time; if(have_min_host_execution_time == FALSE || temp_hoststatus->execution_time < min_host_execution_time) { have_min_host_execution_time = TRUE; min_host_execution_time = temp_hoststatus->execution_time; } if(have_max_host_execution_time == FALSE || temp_hoststatus->execution_time > max_host_execution_time) { have_max_host_execution_time = TRUE; max_host_execution_time = temp_hoststatus->execution_time; } total_host_percent_change_a += temp_hoststatus->percent_state_change; if(have_min_host_percent_change_a == FALSE || temp_hoststatus->percent_state_change < min_host_percent_change_a) { have_min_host_percent_change_a = TRUE; min_host_percent_change_a = temp_hoststatus->percent_state_change; } if(have_max_host_percent_change_a == FALSE || temp_hoststatus->percent_state_change > max_host_percent_change_a) { have_max_host_percent_change_a = TRUE; max_host_percent_change_a = temp_hoststatus->percent_state_change; } total_host_latency += temp_hoststatus->latency; if(have_min_host_latency == FALSE || temp_hoststatus->latency < min_host_latency) { have_min_host_latency = TRUE; min_host_latency = temp_hoststatus->latency; } if(have_max_host_latency == FALSE || temp_hoststatus->latency > max_host_latency) { have_max_host_latency = TRUE; max_host_latency = temp_hoststatus->latency; } if(temp_hoststatus->last_check >= (current_time - 60)) active_host_checks_1min++; if(temp_hoststatus->last_check >= (current_time - 300)) active_host_checks_5min++; if(temp_hoststatus->last_check >= (current_time - 900)) active_host_checks_15min++; if(temp_hoststatus->last_check >= (current_time - 3600)) active_host_checks_1hour++; if(temp_hoststatus->last_check >= program_start) active_host_checks_start++; if(temp_hoststatus->last_check != (time_t)0) active_host_checks_ever++; } else { total_passive_host_checks++; total_host_percent_change_b += temp_hoststatus->percent_state_change; if(have_min_host_percent_change_b == FALSE || temp_hoststatus->percent_state_change < min_host_percent_change_b) { have_min_host_percent_change_b = TRUE; min_host_percent_change_b = temp_hoststatus->percent_state_change; } if(have_max_host_percent_change_b == FALSE || temp_hoststatus->percent_state_change > max_host_percent_change_b) { have_max_host_percent_change_b = TRUE; max_host_percent_change_b = temp_hoststatus->percent_state_change; } if(temp_hoststatus->last_check >= (current_time - 60)) passive_host_checks_1min++; if(temp_hoststatus->last_check >= (current_time - 300)) passive_host_checks_5min++; if(temp_hoststatus->last_check >= (current_time - 900)) passive_host_checks_15min++; if(temp_hoststatus->last_check >= (current_time - 3600)) passive_host_checks_1hour++; if(temp_hoststatus->last_check >= program_start) passive_host_checks_start++; if(temp_hoststatus->last_check != (time_t)0) passive_host_checks_ever++; } } /* Avoid divide by zero errors */ if(0 == total_active_service_checks) { total_active_service_checks = 1; } if(0 == total_passive_service_checks) { total_passive_service_checks = 1; } if(0 == total_active_host_checks) { total_active_host_checks = 1; } if(0 == total_passive_host_checks) { total_passive_host_checks = 1; } json_data = json_new_object(); json_programstatus = json_new_object(); json_service_checks = json_new_object(); /* Active Service Checks */ json_active = json_new_object(); json_checks = json_new_object(); json_object_append_integer(json_checks, "1min", active_service_checks_1min); json_object_append_integer(json_checks, "5min", active_service_checks_5min); json_object_append_integer(json_checks, "15min", active_service_checks_15min); json_object_append_integer(json_checks, "1hour", active_service_checks_1hour); json_object_append_integer(json_checks, "start", active_service_checks_start); json_object_append_object(json_active, "checks", json_checks); json_metrics = json_new_object(); json_temp = json_new_object(); json_object_append_real(json_temp, "min", min_service_execution_time); json_object_append_real(json_temp, "max", max_service_execution_time); json_object_append_real(json_temp, "average", (double)((double)total_service_execution_time / (double)total_active_service_checks)); json_object_append_object(json_metrics, "check_execution_time", json_temp); json_temp = json_new_object(); json_object_append_real(json_temp, "min", min_service_latency); json_object_append_real(json_temp, "max", max_service_latency); json_object_append_real(json_temp, "average", (double)((double)total_service_latency / (double)total_active_service_checks)); json_object_append_object(json_metrics, "check_latency", json_temp); json_temp = json_new_object(); json_object_append_real(json_temp, "min", min_service_percent_change_a); json_object_append_real(json_temp, "max", max_service_percent_change_a); json_object_append_real(json_temp, "average", (double)((double)total_service_percent_change_a / (double)total_active_service_checks)); json_object_append_object(json_metrics, "percent_state_change", json_temp); json_object_append_object(json_active, "metrics", json_metrics); json_object_append_object(json_service_checks, "active", json_active); /* Passive Service Checks */ json_passive = json_new_object(); json_checks = json_new_object(); json_object_append_integer(json_checks, "1min", passive_service_checks_1min); json_object_append_integer(json_checks, "5min", passive_service_checks_5min); json_object_append_integer(json_checks, "15min", passive_service_checks_15min); json_object_append_integer(json_checks, "1hour", passive_service_checks_1hour); json_object_append_integer(json_checks, "start", passive_service_checks_start); json_object_append_object(json_passive, "checks", json_checks); json_metrics = json_new_object(); json_temp = json_new_object(); json_object_append_real(json_temp, "min", min_service_percent_change_b); json_object_append_real(json_temp, "max", max_service_percent_change_b); json_object_append_real(json_temp, "average", (double)((double)total_service_percent_change_b / (double)total_active_service_checks)); json_object_append_object(json_metrics, "percent_state_change", json_temp); json_object_append_object(json_passive, "metrics", json_metrics); json_object_append_object(json_service_checks, "passive", json_passive); json_object_append_object(json_programstatus, "service_checks", json_service_checks); json_host_checks = json_new_object(); /* Active Host Checks */ json_active = json_new_object(); json_checks = json_new_object(); json_object_append_integer(json_checks, "1min", active_host_checks_1min); json_object_append_integer(json_checks, "5min", active_host_checks_5min); json_object_append_integer(json_checks, "15min", active_host_checks_15min); json_object_append_integer(json_checks, "1hour", active_host_checks_1hour); json_object_append_integer(json_checks, "start", active_host_checks_start); json_object_append_object(json_active, "checks", json_checks); json_metrics = json_new_object(); json_temp = json_new_object(); json_object_append_real(json_temp, "min", min_host_execution_time); json_object_append_real(json_temp, "max", max_host_execution_time); json_object_append_real(json_temp, "average", (double)((double)total_host_execution_time / (double)total_active_host_checks)); json_object_append_object(json_metrics, "check_execution_time", json_temp); json_temp = json_new_object(); json_object_append_real(json_temp, "min", min_host_latency); json_object_append_real(json_temp, "max", max_host_latency); json_object_append_real(json_temp, "average", (double)((double)total_host_latency / (double)total_active_host_checks)); json_object_append_object(json_metrics, "check_latency", json_temp); json_temp = json_new_object(); json_object_append_real(json_temp, "min", min_host_percent_change_a); json_object_append_real(json_temp, "max", max_host_percent_change_a); json_object_append_real(json_temp, "average", (double)((double)total_host_percent_change_a / (double)total_active_host_checks)); json_object_append_object(json_metrics, "percent_state_change", json_temp); json_object_append_object(json_active, "metrics", json_metrics); json_object_append_object(json_host_checks, "active", json_active); /* Passive Host Checks */ json_passive = json_new_object(); json_checks = json_new_object(); json_object_append_integer(json_checks, "1min", passive_host_checks_1min); json_object_append_integer(json_checks, "5min", passive_host_checks_5min); json_object_append_integer(json_checks, "15min", passive_host_checks_15min); json_object_append_integer(json_checks, "1hour", passive_host_checks_1hour); json_object_append_integer(json_checks, "start", passive_host_checks_start); json_object_append_object(json_passive, "checks", json_checks); json_metrics = json_new_object(); json_temp = json_new_object(); json_object_append_real(json_temp, "min", min_host_percent_change_b); json_object_append_real(json_temp, "max", max_host_percent_change_b); json_object_append_real(json_temp, "average", (double)((double)total_host_percent_change_b / (double)total_active_host_checks)); json_object_append_object(json_metrics, "percent_state_change", json_temp); json_object_append_object(json_passive, "metrics", json_metrics); json_object_append_object(json_host_checks, "passive", json_passive); json_object_append_object(json_programstatus, "host_checks", json_host_checks); /* Check Stats */ json_check_statistics = json_new_object(); json_temp = json_new_object(); json_object_append_integer(json_temp, "1min", program_stats[ACTIVE_SCHEDULED_HOST_CHECK_STATS][0]); json_object_append_integer(json_temp, "5min", program_stats[ACTIVE_SCHEDULED_HOST_CHECK_STATS][1]); json_object_append_integer(json_temp, "15min", program_stats[ACTIVE_SCHEDULED_HOST_CHECK_STATS][2]); json_object_append_object(json_check_statistics, "active_scheduled_host_checks", json_temp); json_temp = json_new_object(); json_object_append_integer(json_temp, "1min", program_stats[ACTIVE_ONDEMAND_HOST_CHECK_STATS][0]); json_object_append_integer(json_temp, "5min", program_stats[ACTIVE_ONDEMAND_HOST_CHECK_STATS][1]); json_object_append_integer(json_temp, "15min", program_stats[ACTIVE_ONDEMAND_HOST_CHECK_STATS][2]); json_object_append_object(json_check_statistics, "active_ondemand_host_checks", json_temp); json_temp = json_new_object(); json_object_append_integer(json_temp, "1min", program_stats[PARALLEL_HOST_CHECK_STATS][0]); json_object_append_integer(json_temp, "5min", program_stats[PARALLEL_HOST_CHECK_STATS][1]); json_object_append_integer(json_temp, "15min", program_stats[PARALLEL_HOST_CHECK_STATS][2]); json_object_append_object(json_check_statistics, "parallel_host_checks", json_temp); json_temp = json_new_object(); json_object_append_integer(json_temp, "1min", program_stats[SERIAL_HOST_CHECK_STATS][0]); json_object_append_integer(json_temp, "5min", program_stats[SERIAL_HOST_CHECK_STATS][1]); json_object_append_integer(json_temp, "15min", program_stats[SERIAL_HOST_CHECK_STATS][2]); json_object_append_object(json_check_statistics, "serial_host_checks", json_temp); json_temp = json_new_object(); json_object_append_integer(json_temp, "1min", program_stats[ACTIVE_CACHED_HOST_CHECK_STATS][0]); json_object_append_integer(json_temp, "5min", program_stats[ACTIVE_CACHED_HOST_CHECK_STATS][1]); json_object_append_integer(json_temp, "15min", program_stats[ACTIVE_CACHED_HOST_CHECK_STATS][2]); json_object_append_object(json_check_statistics, "cached_host_checks", json_temp); json_temp = json_new_object(); json_object_append_integer(json_temp, "1min", program_stats[PASSIVE_HOST_CHECK_STATS][0]); json_object_append_integer(json_temp, "5min", program_stats[PASSIVE_HOST_CHECK_STATS][1]); json_object_append_integer(json_temp, "15min", program_stats[PASSIVE_HOST_CHECK_STATS][2]); json_object_append_object(json_check_statistics, "passive_host_checks", json_temp); json_temp = json_new_object(); json_object_append_integer(json_temp, "1min", program_stats[ACTIVE_SCHEDULED_SERVICE_CHECK_STATS][0]); json_object_append_integer(json_temp, "5min", program_stats[ACTIVE_SCHEDULED_SERVICE_CHECK_STATS][1]); json_object_append_integer(json_temp, "15min", program_stats[ACTIVE_SCHEDULED_SERVICE_CHECK_STATS][2]); json_object_append_object(json_check_statistics, "active_scheduled_service_checks", json_temp); json_temp = json_new_object(); json_object_append_integer(json_temp, "1min", program_stats[ACTIVE_ONDEMAND_SERVICE_CHECK_STATS][0]); json_object_append_integer(json_temp, "5min", program_stats[ACTIVE_ONDEMAND_SERVICE_CHECK_STATS][1]); json_object_append_integer(json_temp, "15min", program_stats[ACTIVE_ONDEMAND_SERVICE_CHECK_STATS][2]); json_object_append_object(json_check_statistics, "active_ondemand_service_checks", json_temp); json_temp = json_new_object(); json_object_append_integer(json_temp, "1min", program_stats[ACTIVE_CACHED_SERVICE_CHECK_STATS][0]); json_object_append_integer(json_temp, "5min", program_stats[ACTIVE_CACHED_SERVICE_CHECK_STATS][1]); json_object_append_integer(json_temp, "15min", program_stats[ACTIVE_CACHED_SERVICE_CHECK_STATS][2]); json_object_append_object(json_check_statistics, "cached_service_checks", json_temp); json_temp = json_new_object(); json_object_append_integer(json_temp, "1min", program_stats[PASSIVE_SERVICE_CHECK_STATS][0]); json_object_append_integer(json_temp, "5min", program_stats[PASSIVE_SERVICE_CHECK_STATS][1]); json_object_append_integer(json_temp, "15min", program_stats[PASSIVE_SERVICE_CHECK_STATS][2]); json_object_append_object(json_check_statistics, "passive_service_checks", json_temp); json_temp = json_new_object(); json_object_append_integer(json_temp, "1min", program_stats[EXTERNAL_COMMAND_STATS][0]); json_object_append_integer(json_temp, "5min", program_stats[EXTERNAL_COMMAND_STATS][1]); json_object_append_integer(json_temp, "15min", program_stats[EXTERNAL_COMMAND_STATS][2]); json_object_append_object(json_check_statistics, "external_commands", json_temp); json_object_append_object(json_programstatus, "check_statistics", json_check_statistics); /* Buffer Stats */ json_buffer_usage = json_new_object(); json_temp = json_new_object(); json_object_append_integer(json_temp, "in_use", buffer_stats[0][1]); json_object_append_integer(json_temp, "max_used", buffer_stats[0][2]); json_object_append_integer(json_temp, "total_available", buffer_stats[0][0]); json_object_append_object(json_buffer_usage, "external_commands", json_temp); json_object_append_object(json_programstatus, "buffer_usage", json_buffer_usage); json_object_append_object(json_data, "programstatus", json_programstatus); return json_data; }