int jx_error_valid(struct jx *j) { if (!jx_istype(j, JX_OBJECT)) return 0; if (!jx_istype(jx_lookup(j, "source"), JX_STRING)) return 0; if (!jx_istype(jx_lookup(j, "name"), JX_STRING)) return 0; if (!jx_istype(jx_lookup(j, "message"), JX_STRING)) return 0; return 1; }
static void log_updates( struct jx_database *db, const char *key, struct jx *a, struct jx *b ) { // For each item in the old object: // If the new one is different, log an update event. // If the new one is missing, log a remove event. struct jx_pair *p; for(p=a->u.pairs;p;p=p->next) { const char *name = p->key->u.string_value; struct jx *avalue = p->value; // Do not log these special cases, because they do not carry new information: if(!strcmp(name,"lastheardfrom")) continue; if(!strcmp(name,"uptime")) continue; struct jx *bvalue = jx_lookup(b,name); if(bvalue) { if(jx_equals(avalue,bvalue)) { // items match, do nothing. } else { // item changed, print it. char *str = jx_print_string(bvalue); log_message(db,"U %s %s %s\n",key,name,str); free(str); } } else { // item was removed. log_message(db,"R %s %s\n",key,name); } } // For each item in the new object: // If it doesn't exist in the old one, log an update event. for(p=b->u.pairs;p;p=p->next) { const char *name = p->key->u.string_value; struct jx *bvalue = p->value; struct jx *avalue = jx_lookup(a,name); if(!avalue) { // item changed, print it. char *str = jx_print_string(bvalue); log_message(db,"U %s %s %s\n",key,name,str); free(str); } } }
void initialize_watch_events(struct rmonitor_file_watch_info *f, struct jx *watch_spec) { struct jx *events_array = jx_lookup(watch_spec, "events"); if(!events_array) { fatal("File watch for '%s' did not define any events", f->filename); } if(!jx_istype(events_array, JX_ARRAY)) { fatal("Value for key 'events' in file watch for '%s' is not an array.", f->filename); } f->events = list_create(0); struct jx *event_spec; int error = 0; for (void *i = NULL; (event_spec = jx_iterate_array(events_array, &i));) { struct rmonitor_file_watch_event *e = parse_event(f->filename, event_spec); if(e) { if(e->on_pattern) { // at least one event defines a pattern, thus we need line by // line processing. f->event_with_pattern = 1; } list_push_tail(f->events, e); debug(D_RMON, "Added event for file '%s', label '%s', max_count %" PRId64, f->filename, e->label, e->max_count); } else { error = 1; } } if(error) { fatal("Error parsing file watch for '%s'.", f->filename); } }
struct jx * jx_eval( struct jx *j, struct jx *context ) { if(!j) return 0; switch(j->type) { case JX_SYMBOL: if(context) { struct jx *result = jx_lookup(context,j->u.symbol_name); if(result) return jx_copy(result); } return jx_null(); case JX_DOUBLE: case JX_BOOLEAN: case JX_INTEGER: case JX_STRING: case JX_NULL: return jx_copy(j); case JX_ARRAY: return jx_array(jx_eval_item(j->u.items,context)); case JX_OBJECT: return jx_object(jx_eval_pair(j->u.pairs,context)); case JX_OPERATOR: return jx_eval_operator(&j->u.oper,context); } /* not reachable, but some compilers complain. */ return 0; }
static struct jx * jx_eval_lookup( struct jx *left, struct jx *right ) { if(left->type==JX_OBJECT && right->type==JX_STRING) { struct jx *r = jx_lookup(left,right->u.string_value); if(r) { return jx_copy(r); } else { return jx_null(); } } else if(left->type==JX_ARRAY && right->type==JX_INTEGER) { struct jx_item *item = left->u.items; int count = right->u.integer_value; if(count<0) return jx_null(); while(count>0) { if(!item) return jx_null(); item = item->next; count--; } if(item) { return jx_copy(item->value); } else { return jx_null(); } } else { return jx_null(); } }
double jx_lookup_double( struct jx *object, const char *key ) { struct jx *j = jx_lookup(object,key); if(j && jx_istype(j,JX_DOUBLE)) { return j->u.double_value; } else { return 0; } }
int jx_lookup_boolean( struct jx *object, const char *key ) { struct jx *j = jx_lookup(object,key); if(j && jx_istype(j,JX_BOOLEAN)) { return !!j->u.boolean_value; } else { return 0; } }
jx_int_t jx_lookup_integer( struct jx *object, const char *key ) { struct jx *j = jx_lookup(object,key); if(j && jx_istype(j,JX_INTEGER)) { return j->u.integer_value; } else { return 0; } }
const char * jx_lookup_string( struct jx *object, const char *key ) { struct jx *j = jx_lookup(object,key); if(j && jx_istype(j,JX_STRING)) { return j->u.string_value; } else { return 0; } }
static char* aws_job_def(char* aws_jobid){ char* cmd = string_format("aws batch describe-jobs --jobs %s",aws_jobid); struct jx* jx = run_command(cmd); free(cmd); struct jx* jobs_array = jx_lookup(jx,"jobs"); if(!jobs_array){ debug(D_BATCH,"Problem with given aws_jobid: %s",aws_jobid); return NULL; } struct jx* first_item = jx_array_index(jobs_array,0); if(!first_item){ debug(D_BATCH,"Problem with given aws_jobid: %s",aws_jobid); return NULL; } char* ret = string_format("%s",(char*)jx_lookup_string(first_item,"jobDefinition")); jx_delete(jx); return ret; }
static int finished_aws_job_exit_code(char* aws_jobid, char* env_var){ char* cmd = string_format("aws batch describe-jobs --jobs %s",aws_jobid); struct jx* jx = run_command(cmd); free(cmd); struct jx* jobs_array = jx_lookup(jx,"jobs"); if(!jobs_array){ debug(D_BATCH,"Problem with given aws_jobid: %s",aws_jobid); return DESCRIBE_AWS_JOB_NON_EXIST; } struct jx* first_item = jx_array_index(jobs_array,0); if(!first_item){ debug(D_BATCH,"Problem with given aws_jobid: %s",aws_jobid); return DESCRIBE_AWS_JOB_NON_EXIST; } int ret = (int)jx_lookup_integer(first_item,"exitCode"); jx_delete(jx); return ret; }
static void update_blacklisted_workers( struct batch_queue *queue, struct list *masters_list ) { if(!masters_list || list_size(masters_list) < 1) return; buffer_t b; struct jx *j; buffer_init(&b); const char *sep = ""; list_first_item(masters_list); while((j=list_next_item(masters_list))) { struct jx *blacklisted = jx_lookup(j,"workers_blacklisted"); if(!blacklisted) { continue; } if(jx_istype(blacklisted, JX_STRING)) { buffer_printf(&b, "%s%s", sep, blacklisted->u.string_value); sep = " "; } if(jx_istype(blacklisted, JX_ARRAY)) { struct jx *item; for (void *i = NULL; (item = jx_iterate_array(blacklisted, &i));) { if(jx_istype(item, JX_STRING)) { buffer_printf(&b, "%s%s", sep, item->u.string_value); sep = " "; } } } } if(buffer_pos(&b) > 0) { batch_queue_set_option(queue, "workers-blacklisted", buffer_tostring(&b)); } else { batch_queue_set_option(queue, "workers-blacklisted", NULL); } buffer_free(&b); }
static int describe_aws_job(char* aws_jobid, char* env_var){ char* cmd = string_format("aws batch describe-jobs --jobs %s",aws_jobid); struct jx* jx = run_command(cmd); free(cmd); int succeed = DESCRIBE_AWS_JOB_NON_FINAL; //default status struct jx* jobs_array = jx_lookup(jx,"jobs"); if(!jobs_array){ debug(D_BATCH,"Problem with given aws_jobid: %s",aws_jobid); return DESCRIBE_AWS_JOB_NON_EXIST; } struct jx* first_item = jx_array_index(jobs_array,0); if(!first_item){ debug(D_BATCH,"Problem with given aws_jobid: %s",aws_jobid); return DESCRIBE_AWS_JOB_NON_EXIST; } if(strstr((char*)jx_lookup_string(first_item,"status"),"SUCCEEDED")){ succeed = DESCRIBE_AWS_JOB_SUCCESS; } if(strstr((char*)jx_lookup_string(first_item,"status"),"FAILED")){ succeed = DESCRIBE_AWS_JOB_FAILED; } //start and stop if(succeed == DESCRIBE_AWS_JOB_SUCCESS || succeed == DESCRIBE_AWS_JOB_FAILED){ int64_t created_string = (int64_t) jx_lookup_integer(first_item,"createdAt"); int64_t start_string = (int64_t)jx_lookup_integer(first_item,"startedAt"); int64_t end_string = (int64_t)jx_lookup_integer(first_item,"stoppedAt"); if(created_string != 0 ){ debug(D_BATCH,"Job %s was created at: %"PRIi64"",aws_jobid,created_string); } if(start_string != 0 ){ debug(D_BATCH,"Job %s started at: %"PRIi64"",aws_jobid,start_string); } if(end_string != 0 ){ debug(D_BATCH,"Job %s ended at: %"PRIi64"",aws_jobid,end_string); } } jx_delete(jx); return succeed; }