From 2b0a95c431c37d546416216f0bd928b2ecf8092e Mon Sep 17 00:00:00 2001 From: Jean-Francois Smigielski Date: Mon, 15 Oct 2018 11:11:15 +0200 Subject: [PATCH 1/5] cmake: Fix the version --- CMakeLists.txt | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index faaed13..ad05c31 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -5,14 +5,11 @@ include(CheckIncludeFile) include(CheckLibraryExists) include(CheckTypeSize) -set(GridInit_VERSION_MAJOR 1) -set(GridInit_VERSION_MINOR 1) -set(GridInit_RELEASE 5) +set(GridInit_VERSION_MAJOR 2) +set(GridInit_VERSION_MINOR 0) +set(GridInit_RELEASE 1) set(API_VERSION "${GridInit_VERSION_MAJOR}.${GridInit_VERSION_MINOR}.${GridInit_RELEASE}") set(SHORT_API_VERSION "${GridInit_VERSION_MAJOR}.${GridInit_VERSION_MINOR}") -if (NOT ABI_VERSION) - set(ABI_VERSION 0) -endif() add_definitions(-DAPI_VERSION="${API_VERSION}") add_definitions(-DSHORT_API_VERSION="${SHORT_API_VERSION}") From 5599cfb71ee924bbb1ae97e9f6f45ebdc14bc9ed Mon Sep 17 00:00:00 2001 From: Jean-Francois Smigielski Date: Mon, 15 Oct 2018 11:11:41 +0200 Subject: [PATCH 2/5] cmake: Fix the requirement on cmake(s version 2.6 -> 3.0 --- CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index ad05c31..f1f1edd 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,4 +1,4 @@ -cmake_minimum_required(VERSION 2.6) +cmake_minimum_required(VERSION 3.0) project (GridInit C) include(CheckIncludeFile) From cf4df65192e144b773b2d1f012d2d26e9ddba91b Mon Sep 17 00:00:00 2001 From: Jean-Francois Smigielski Date: Mon, 15 Oct 2018 11:15:33 +0200 Subject: [PATCH 3/5] gridinit_cmd: Fix output oddities --- CMakeLists.txt | 1 - main/format_output.c | 157 ------------------------------- main/format_output.h | 36 -------- main/gridinit_cmd.c | 215 +++++++++++++++++++++++++------------------ 4 files changed, 123 insertions(+), 286 deletions(-) delete mode 100644 main/format_output.c delete mode 100644 main/format_output.h diff --git a/CMakeLists.txt b/CMakeLists.txt index f1f1edd..c5ac640 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -126,7 +126,6 @@ add_dependencies(gridinit add_executable(gridinit_cmd main/gridinit_cmd.c - main/format_output.c main/utils.c) target_link_libraries(gridinit_cmd ${GLIB2_LIBRARIES}) diff --git a/main/format_output.c b/main/format_output.c deleted file mode 100644 index 9c23559..0000000 --- a/main/format_output.c +++ /dev/null @@ -1,157 +0,0 @@ -/* -Copyright (C) 2015 OpenIO SAS, as part of OpenIO SDS - -This program is free software: you can redistribute it and/or modify -it under the terms of the GNU Affero General Public License as -published by the Free Software Foundation, either version 3 of the -License, or (at your option) any later version. -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 Affero General Public License for more details. -You should have received a copy of the GNU Affero General Public License -along with this program. If not, see . -*/ - -#include -#include -#include "./format_output.h" - -FORMAT -parse_format(gchar *format) -{ - if (g_strcmp0(format, "json") == 0) - return JSON; - if (g_strcmp0(format, "csv") == 0) - return CSV; - else - return DEFAULT; -} - -void -print_as_json(gchar *status, gchar *start, gchar *error, gboolean first) -{ - gchar header[] = " {\n"; - gchar footer[] = " }"; - gchar tab[] = " "; - - if(!first) - fprintf(stdout, ",\n"); - - fprintf(stdout, "%s", header); - fprintf(stdout, "%s\"status\": \"%s\",\n", tab, status); - fprintf(stdout, "%s\"start\": \"%s\",\n", tab, start); - fprintf(stdout, "%s\"error\": \"%s\"\n", tab, error); - fprintf(stdout, "%s", footer); -} - -void -print_as_csv(gchar *status, gchar *start, gchar *error) -{ - fprintf(stdout, "%s,%s,%s\n", status, start, error); -} - - -void -print_header(FORMAT format) -{ - switch (format) { - case JSON: - fprintf(stdout, "[\n"); - break; - case CSV: - fprintf(stdout, "status,start,error\n"); - break; - default: - break; - } -} - -void -print_footer(FORMAT format) -{ - switch (format) { - case JSON: - fprintf(stdout, "\n]\n"); - break; - default: - break; - } - return; -} - -void -print_body(FORMAT format, gchar *status, gchar *start, gchar *error, gboolean first) -{ - switch (format) { - case JSON: - print_as_json(status, start, error, first); - break; - case CSV: - print_as_csv(status, start, error); - break; - default: - fprintf(stdout, "%s\t%s\t%s\n", status, start, error); - } -} - -void -print_status_header(FORMAT format) -{ - switch (format) { - case JSON: - case CSV: - fprintf(stdout, - "key,status,pid,#start,#died,csz,ssz,mfd,since,group,cmd\n"); - break; - default: - break; - } -} - -void -status_body_json(gchar *fmt_line, int size) -{ - g_snprintf(fmt_line, size, - " {\n \"key\":\"%%s\",\n \"status\":\"%%s\"," - "\n \"pid\":\"%%d\",\n \"#start\":\"%%d\"," - "\n \"#died\":\"%%d\",\n \"csz\":\"%%ld\"," - "\n \"ssz\":\"%%ld\",\n \"mfd\":\"%%ld\"," - "\n \"since\":\"%%s\",\n \"group\":\"%%s\"," - "\n \"cmd\":\"%%s\"\n }"); -} - - -void -status_body_csv(gchar *fmt_line, int size) -{ - g_snprintf(fmt_line, size, - "%%s,%%s,%%d,%%d,%%d,%%ld,%%ld,%%ld,%%s,%%s,%%s\n"); -} - -void -print_status_sep(FORMAT format, int count) -{ - switch (format) { - case JSON: - if(count) - fprintf(stdout, ",\n"); - default: - break; - } -} - -void -get_line_format(FORMAT format, gchar *fmt_line, int size) -{ - switch (format) { - case JSON: - status_body_json(fmt_line, size); - break; - case CSV: - status_body_csv(fmt_line, size); - break; - default: - break; - } -} diff --git a/main/format_output.h b/main/format_output.h deleted file mode 100644 index cbc393a..0000000 --- a/main/format_output.h +++ /dev/null @@ -1,36 +0,0 @@ -/* -Copyright (C) 2015 OpenIO SAS, as part of OpenIO SDS - -This program is free software: you can redistribute it and/or modify -it under the terms of the GNU Affero General Public License as -published by the Free Software Foundation, either version 3 of the -License, or (at your option) any later version. -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 Affero General Public License for more details. -You should have received a copy of the GNU Affero General Public License -along with this program. If not, see . -*/ - -#ifndef __FORMAT_OUTPUT__ -#define __FORMAT_OUTPUT__ - -# include - -typedef enum FORMAT FORMAT; -enum FORMAT {DEFAULT = 0, CSV = 1, JSON = 2}; - -FORMAT parse_format(gchar *format); -void print_as_json(gchar *status, gchar *start, char *error, gboolean first); -void print_as_csv(gchar *status, gchar *start, char *error); -void print_header(FORMAT format); -void print_footer(FORMAT format); -void print_body(FORMAT format, gchar *status, gchar *start, gchar *error, gboolean first); -void print_status_header(FORMAT format); -void status_body_json(gchar *fmt_line, int size); -void status_body_csv(gchar *fmt_line, int size); -void print_status_sep(FORMAT format, int count); -void get_line_format(FORMAT format, gchar *fmt_line, int size); - -#endif diff --git a/main/gridinit_cmd.c b/main/gridinit_cmd.c index 72f4db7..1bfcb9b 100644 --- a/main/gridinit_cmd.c +++ b/main/gridinit_cmd.c @@ -29,7 +29,6 @@ along with this program. If not, see . #include -#include "./format_output.h" #include "./gridinit_internals.h" #define MINI 0 @@ -148,6 +147,21 @@ static const gchar description[] = "with ID the key of a process, or '@GROUP', with GROUP the name of a process\n" "group\n"; +typedef enum FORMAT FORMAT; + +enum FORMAT {DEFAULT = 0, CSV = 1, JSON = 2}; + +static FORMAT +parse_format(const gchar *cfg_format) +{ + if (g_strcmp0(cfg_format, "json") == 0) + return JSON; + if (g_strcmp0(cfg_format, "csv") == 0) + return CSV; + else + return DEFAULT; +} + static int __open_unix_client(const char *path) @@ -292,8 +306,19 @@ dump_as_is(FILE *in_stream, void *udata) else kw = &KEYWORDS_NORMAL; - print_header(format_t); + /* Prin tthe title */ + switch (format_t) { + case JSON: + fputs("[", stdout); + break; + case CSV: + fputs("status,start,error\n", stdout); + /* FALLTHROUGH */ + default: + break; + } + /* Print the lines */ while (!feof(in_stream) && !ferror(in_stream)) { bzero(line, sizeof(line)); if (NULL != fgets(line, sizeof(line), in_stream)) { @@ -308,13 +333,27 @@ dump_as_is(FILE *in_stream, void *udata) dump_args->count_errors ++; } gchar *status = (gchar *) (code==0 ? kw->done : - (code==EALREADY?kw->already:kw->failed)); - gchar *error = strerror(code); - print_body(format_t, status, start, error,first); + (code==EALREADY?kw->already:kw->failed)); + const char *error = strerror(code); + + switch (format_t) { + case JSON: + if(!first) + fprintf(stdout, ",\n"); + fprintf(stdout, "{\"status\": \"%s\",\"start\": \"%s\",\"error\": \"%s\"}\n", status, start, error); + break; + case CSV: + fprintf(stdout, "%s,%s,%s\n", status, start, error); + break; + default: + fprintf(stdout, "%s\t%s\t%s\n", status, start, error); + } first = FALSE; } } - print_footer(format_t); + + if (format_t == JSON) + fputs("]", stdout); fflush(stdout); } @@ -410,7 +449,7 @@ _filter_services(GList *original, char **filters, int *counters) static int command_status(int lvl, int argc, char **args) { - char fmt_title[256], fmt_line[256]; + char fmt_line[256]; int *counters = alloca(sizeof(int) * (argc+1)); memset(counters, 0, sizeof(int) * (argc+1)); @@ -418,53 +457,59 @@ command_status(int lvl, int argc, char **args) GList *all_jobs = _fetch_services(); GList *jobs = _filter_services(all_jobs, args, counters); FORMAT format_t = parse_format(format); - /* compute the max length of several variable field, for well aligned - * columns on the output. */ - const size_t maxkey = get_longest_key(jobs); - const size_t maxgroup = get_longest_group(jobs); - - if (format_t != DEFAULT) { - print_status_header(format_t); - get_line_format(format_t, fmt_line, sizeof(fmt_line)); - goto print_lines; - } - /* write the title */ - switch (lvl) { - case 0: - g_snprintf(fmt_title, sizeof(fmt_title), - "%%-%us %%-8s %%6s %%s\n", - (guint)maxkey); - g_snprintf(fmt_line, sizeof(fmt_line), - "%%-%us %%s %%6d %%s\n", - (guint)maxkey); - fprintf(stdout, fmt_title, "KEY", "STATUS", "PID", "GROUP"); - break; - case 1: - g_snprintf(fmt_title, sizeof(fmt_title), - "%%-%us %%-8s %%5s %%6s %%5s %%19s %%%us %%s\n", - (guint)maxkey, (guint)maxgroup); + /* Print the header and compute the format for each line */ + if (format_t == DEFAULT) { + const size_t maxkey = get_longest_key(jobs); + const size_t maxgroup = get_longest_group(jobs); + char fmt_title[256]; + switch (lvl) { + case 0: + g_snprintf(fmt_title, sizeof(fmt_title), + "%%-%us %%-8s %%6s %%s\n", + (guint)maxkey); + g_snprintf(fmt_line, sizeof(fmt_line), + "%%-%us %%s %%6d %%s\n", + (guint)maxkey); + fprintf(stdout, fmt_title, "KEY", "STATUS", "PID", "GROUP"); + break; + case 1: + g_snprintf(fmt_title, sizeof(fmt_title), + "%%-%us %%-8s %%5s %%6s %%5s %%19s %%%us %%s\n", + (guint)maxkey, (guint)maxgroup); + g_snprintf(fmt_line, sizeof(fmt_line), + "%%-%us %%s %%5d %%6d %%5d %%19s %%%us %%s\n", + (guint)maxkey, (guint)maxgroup); + fprintf(stdout, fmt_title, "KEY", "STATUS", "PID", "#START", + "#DIED", "SINCE", "GROUP", "CMD"); + break; + default: + g_snprintf(fmt_title, sizeof(fmt_title), + "%%-%us %%-8s %%5s %%6s %%5s %%8s %%8s %%8s %%19s %%%us %%s\n", + (guint)maxkey, (guint)maxgroup); + g_snprintf(fmt_line, sizeof(fmt_line), + "%%-%us %%s %%5d %%6d %%5d %%8ld %%8ld %%8ld %%19s %%%us %%s\n", + (guint)maxkey, (guint)maxgroup); + + fprintf(stdout, fmt_title, "KEY", "STATUS", "PID", "#START", + "#DIED", "CSZ", "SSZ", "MFD", "SINCE", "GROUP", "CMD"); + break; + } + } else if (format_t == CSV) { g_snprintf(fmt_line, sizeof(fmt_line), - "%%-%us %%s %%5d %%6d %%5d %%19s %%%us %%s\n", - (guint)maxkey, (guint)maxgroup); - fprintf(stdout, fmt_title, "KEY", "STATUS", "PID", "#START", - "#DIED", "SINCE", "GROUP", "CMD"); - break; - default: - g_snprintf(fmt_title, sizeof(fmt_title), - "%%-%us %%-8s %%5s %%6s %%5s %%8s %%8s %%8s %%19s %%%us %%s\n", - (guint)maxkey, (guint)maxgroup); + "%%s,%%s,%%d,%%d,%%d,%%ld,%%ld,%%ld,%%s,%%s,%%s\n"); + /* Print the title */ + fputs("key,status,pid,#start,#died,csz,ssz,mfd,since,group,cmd\n", stdout); + } else if (format_t == JSON) { g_snprintf(fmt_line, sizeof(fmt_line), - "%%-%us %%s %%5d %%6d %%5d %%8ld %%8ld %%8ld %%19s %%%us %%s\n", - (guint)maxkey, (guint)maxgroup); - - fprintf(stdout, fmt_title, "KEY", "STATUS", "PID", "#START", - "#DIED", "CSZ", "SSZ", "MFD", "SINCE", "GROUP", "CMD"); - break; + "{\"key\":\"%%s\",\"status\":\"%%s\",\"pid\":%%d," + "\"#start\":%%d,\"#died\":%%d,\"csz\":%%ld,\"ssz\":%%ld,\"mfd\":%%ld," + "\"since\":\"%%s\",\"group\":\"%%s\"," + "\"cmd\":\"%%s\"}\n"); + /* Print the opening of the object */ + fputs("[", stdout); } - print_lines:; - int count_misses = 0, count_broken = 0, count_down = 0, count_all = 0; struct keyword_set_s *kw; @@ -479,56 +524,55 @@ command_status(int lvl, int argc, char **args) for (GList *l=jobs; l ;l=l->next) { char str_time[20] = "---------- --------"; const char * str_status = "-"; - struct child_info_s *ci = NULL; - - ci = l->data; + struct child_info_s *ci = ci = l->data; /* Prepare some fields */ - if (ci->pid > 0) - strftime(str_time, sizeof(str_time), "%Y-%m-%d %H:%M:%S", + strftime(str_time, sizeof(str_time), "%Y-%m-%d %H:%M:%S", gmtime(&(ci->last_start_attempt))); str_status = get_child_status(ci, kw); /* Manage counters */ - if (str_status == kw->down) count_down ++; if (str_status == kw->broken) count_broken ++; count_all ++; + /* Print now! */ if (format_t != DEFAULT) { - print_status_sep(format_t, count_all-1); + if (format_t == JSON && count_all > 1) + fputs(",", stdout); fprintf(stdout, fmt_line, ci->key, str_status, ci->pid, ci->counter_started, ci->counter_died, ci->rlimits.core_size, ci->rlimits.stack_size, ci->rlimits.nb_files, str_time, ci->group, ci->cmd); - goto end; - } - switch (lvl) { - case 0: - fprintf(stdout, fmt_line, ci->key, str_status, ci->pid, ci->group); - break; - case 1: - fprintf(stdout, fmt_line, - ci->key, str_status, ci->pid, - ci->counter_started, ci->counter_died, - str_time, ci->group, ci->cmd); - break; - default: - fprintf(stdout, fmt_line, - ci->key, str_status, ci->pid, - ci->counter_started, ci->counter_died, - ci->rlimits.core_size, ci->rlimits.stack_size, ci->rlimits.nb_files, - str_time, ci->group, ci->cmd); - break; + } else { + switch (lvl) { + case 0: + fprintf(stdout, fmt_line, ci->key, str_status, ci->pid, ci->group); + break; + case 1: + fprintf(stdout, fmt_line, + ci->key, str_status, ci->pid, + ci->counter_started, ci->counter_died, + str_time, ci->group, ci->cmd); + break; + default: + fprintf(stdout, fmt_line, + ci->key, str_status, ci->pid, + ci->counter_started, ci->counter_died, + ci->rlimits.core_size, ci->rlimits.stack_size, ci->rlimits.nb_files, + str_time, ci->group, ci->cmd); + break; + } } - end:; } + g_list_free_full(all_jobs, (GDestroyNotify)child_info_free); + g_list_free(jobs); - if (format_t != DEFAULT) - print_footer(format_t); + if (format_t == JSON) + fputs("]", stdout); fflush(stdout); /* If patterns have been specified, we must find items (the user @@ -537,20 +581,7 @@ command_status(int lvl, int argc, char **args) if (!counters[i]) count_misses ++; } - - g_list_free_full(all_jobs, (GDestroyNotify)child_info_free); - g_list_free(jobs); - - int rc = 0; - - if (count_down) - rc |= 1; - if (count_misses) - rc |= 2; - if (count_broken) - rc |= 4; - - return rc; + return (count_down ? 1 : 0) | (count_misses ? 2 : 0) | (count_broken ? 4 : 0); } From f51802756a210e738e9b14199b94a2320bd9b644 Mon Sep 17 00:00:00 2001 From: Jean-Francois Smigielski Date: Mon, 15 Oct 2018 11:16:27 +0200 Subject: [PATCH 4/5] ci: Remove useless Travis-CI dependencies --- .travis.yml | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/.travis.yml b/.travis.yml index 121b3ac..fded9ac 100644 --- a/.travis.yml +++ b/.travis.yml @@ -2,9 +2,8 @@ sudo: required dist: trusty language: c install: - - sudo apt-add-repository "deb http://archive.ubuntu.com/ubuntu trusty-backports main restricted universe multiverse" - - sudo apt-get update -qq - - sudo apt-get install -y --force-yes autoconf automake libtool xutils-dev gcc make cmake libglib2.0-dev + - sudo apt-get install -y --force-yes gcc make cmake libglib2.0-dev + - sudo apt-get install -y --force-yes autoconf automake libtool xutils-dev env: matrix: - BUILD_TYPE=Debug From 732258ad62c6e17e219857970b27da7c2780ab5b Mon Sep 17 00:00:00 2001 From: Jean-Francois Smigielski Date: Mon, 15 Oct 2018 11:26:43 +0200 Subject: [PATCH 5/5] ci: Test the JSON output --- .travis.yml | 12 ++++++++++-- tools/cycle.sh | 17 +++++++++++++++++ tools/gridinit-genconf.sh | 32 ++++++++++++++++++++++---------- 3 files changed, 49 insertions(+), 12 deletions(-) create mode 100755 tools/cycle.sh diff --git a/.travis.yml b/.travis.yml index fded9ac..64b0ee6 100644 --- a/.travis.yml +++ b/.travis.yml @@ -4,14 +4,22 @@ language: c install: - sudo apt-get install -y --force-yes gcc make cmake libglib2.0-dev - sudo apt-get install -y --force-yes autoconf automake libtool xutils-dev + - sudo apt-get install -y --force-yes jq env: matrix: - BUILD_TYPE=Debug - BUILD_TYPE=Release -script: +before_script: - set -e - mkdir /tmp/oio - - export CMAKE_OPTS='-DCMAKE_INSTALL_PREFIX=/tmp/oio -DLD_LIBDIR=lib' + - export CMAKE_OPTS='-DCMAKE_INSTALL_PREFIX=/tmp/ROOT' - cmake ${CMAKE_OPTS} -DCMAKE_BUILD_TYPE=$BUILD_TYPE . - make all - make install +script: + - set -e + - export PATH="$PATH:/tmp/ROOT/bin" TMPDIR=/tmp + - ./tools/gridinit-genconf.sh 15 + - gridinit -d -s gridinit /tmp/gridinit/gridinit.conf + - ./tools/cycle.sh + - pkill gridinit diff --git a/tools/cycle.sh b/tools/cycle.sh new file mode 100755 index 0000000..44b2181 --- /dev/null +++ b/tools/cycle.sh @@ -0,0 +1,17 @@ +#!/usr/bin/env bash +set -e +set -x + +CMD="gridinit_cmd -S /tmp/gridinit/gridinit.sock" + +$CMD -f json status | jq + +for G in @test-0 @test-1 '' '@test-0 @test-1' ; do + $CMD status $G + $CMD stop $G + $CMD start $G + $CMD status $G +done + +$CMD -f json status | jq + diff --git a/tools/gridinit-genconf.sh b/tools/gridinit-genconf.sh index f81a5f1..65fe75d 100755 --- a/tools/gridinit-genconf.sh +++ b/tools/gridinit-genconf.sh @@ -1,30 +1,42 @@ #!/usr/bin/env bash set -e -MAX=$1 -shift +set -x +MAX=$1 ; shift [[ -n "$MAX" ]] -cat > /tmp/gridinit.conf < "$BASEDIR/gridinit.conf" <> /tmp/gridinit.conf <> $BASEDIR/$sub/service-${i}.conf <