#define STAT_NO_REFRESH 0x00000010 /* do not automatically refresh the stats page */
#define STAT_ADMIN 0x00000020 /* indicate a stats admin level */
#define STAT_CHUNKED 0x00000040 /* use chunked encoding (HTTP/1.1) */
+#define STAT_JSON_SCHM 0x00000080 /* dump the json schema */
#define STAT_BOUND 0x00800000 /* bound statistics to selected proxies/types/services */
#define STAT_STARTED 0x01000000 /* some output has occurred */
+#define STAT_FMT_MASK 0x00000007
+
#define STATS_TYPE_FE 0
#define STATS_TYPE_BE 1
#define STATS_TYPE_SV 2
for (h = lookup; h <= end - 4; h++) {
if (memcmp(h, ";csv", 4) == 0) {
- appctx->ctx.stats.flags &= ~STAT_FMT_HTML;
+ appctx->ctx.stats.flags &= ~(STAT_FMT_MASK|STAT_JSON_SCHM);
break;
}
}
for (h = lookup; h <= end - 6; h++) {
if (memcmp(h, ";typed", 6) == 0) {
- appctx->ctx.stats.flags &= ~STAT_FMT_HTML;
+ appctx->ctx.stats.flags &= ~(STAT_FMT_MASK|STAT_JSON_SCHM);
appctx->ctx.stats.flags |= STAT_FMT_TYPED;
break;
}
}
+ for (h = lookup; h <= end - 5; h++) {
+ if (memcmp(h, ";json", 5) == 0) {
+ appctx->ctx.stats.flags &= ~(STAT_FMT_MASK|STAT_JSON_SCHM);
+ appctx->ctx.stats.flags |= STAT_FMT_JSON;
+ break;
+ }
+ }
+
+ for (h = lookup; h <= end - 12; h++) {
+ if (memcmp(h, ";json-schema", 12) == 0) {
+ appctx->ctx.stats.flags &= ~STAT_FMT_MASK;
+ appctx->ctx.stats.flags |= STAT_JSON_SCHM;
+ break;
+ }
+ }
+
for (h = lookup; h <= end - 8; h++) {
if (memcmp(h, ";st=", 4) == 0) {
int i;
/* one line of stats */
static THREAD_LOCAL struct field stats[ST_F_TOTAL_FIELDS];
+static void stats_dump_json_schema(struct buffer *out);
static int stats_putchk(struct channel *chn, struct htx *htx, struct buffer *chk)
{
(uri->refresh > 0) ? ";norefresh" : "",
scope_txt);
+ chunk_appendf(&trash,
+ "<li><a href=\"%s;json%s%s\">JSON export</a> (<a href=\"%s;json-schema\">schema</a>)<br>\n",
+ uri->uri_prefix,
+ (uri->refresh > 0) ? ";norefresh" : "",
+ scope_txt, uri->uri_prefix);
+
chunk_appendf(&trash,
"</ul></td>"
"<td align=\"left\" valign=\"top\" nowrap width=\"1%%\">"
case STAT_ST_HEAD:
if (appctx->ctx.stats.flags & STAT_FMT_HTML)
stats_dump_html_head(uri);
+ else if (appctx->ctx.stats.flags & STAT_JSON_SCHM)
+ stats_dump_json_schema(&trash);
else if (appctx->ctx.stats.flags & STAT_FMT_JSON)
stats_dump_json_header();
else if (!(appctx->ctx.stats.flags & STAT_FMT_TYPED))
if (!stats_putchk(rep, htx, &trash))
goto full;
+ if (appctx->ctx.stats.flags & STAT_JSON_SCHM) {
+ appctx->st2 = STAT_ST_FIN;
+ return 1;
+ }
appctx->st2 = STAT_ST_INFO;
/* fall through */
if (!htx_add_header(htx, ist("Content-Type"), ist("text/html")))
goto full;
}
+ else if (appctx->ctx.stats.flags & (STAT_FMT_JSON|STAT_JSON_SCHM)) {
+ if (!htx_add_header(htx, ist("Content-Type"), ist("application/json")))
+ goto full;
+ }
else {
if (!htx_add_header(htx, ist("Content-Type"), ist("text/plain")))
goto full;