teamspeak2 plugin by:
Stefan Hacker <stefan.hacker at web.de>
+tcpconns plugin:
+ Michael Stapelberg <michael+git@stapelberg.de> (OpenBSD port)
+
users plugin by:
Sebastian Harl <sh at tokkee.org>
*darwin*)
ac_system="Darwin"
;;
+ *openbsd*)
+ ac_system="OpenBSD"
+ ;;
*)
ac_system="unknown"
esac
AC_SUBST(BUILD_WITH_LIBSTATGRAB_LDFLAGS)
fi
+with_libkvm="no"
AC_CHECK_LIB(kvm, kvm_getprocs, [with_kvm_getprocs="yes"], [with_kvm_getprocs="no"])
if test "x$with_kvm_getprocs" = "xyes"
then
AC_DEFINE(HAVE_LIBKVM_GETPROCS, 1,
[Define to 1 if you have the 'kvm' library with the 'kvm_getprocs' symbol (-lkvm)])
+ with_libkvm="yes"
fi
AM_CONDITIONAL(BUILD_WITH_LIBKVM_GETPROCS, test "x$with_kvm_getprocs" = "xyes")
then
AC_DEFINE(HAVE_LIBKVM_GETSWAPINFO, 1,
[Define to 1 if you have the 'kvm' library with the 'kvm_getswapinfo' symbol (-lkvm)])
+ with_libkvm="yes"
fi
AM_CONDITIONAL(BUILD_WITH_LIBKVM_GETSWAPINFO, test "x$with_kvm_getswapinfo" = "xyes")
+AC_CHECK_LIB(kvm, kvm_nlist, [with_kvm_nlist="yes"], [with_kvm_nlist="no"])
+if test "x$with_kvm_nlist" = "xyes"
+then
+ AC_DEFINE(HAVE_LIBKVM_NLIST, 1,
+ [Define to 1 if you have the 'kvm' library with the 'kvm_nlist' symbol (-lkvm)])
+ with_libkvm="yes"
+fi
+AM_CONDITIONAL(BUILD_WITH_LIBKVM_NLIST, test "x$with_kvm_nlist" = "xyes")
+
with_sensors_cflags=""
with_sensors_ldflags=""
AC_ARG_WITH(lm-sensors, [AS_HELP_STRING([--with-lm-sensors@<:@=PREFIX@:>@], [Path to lm_sensors.])],
fi
fi
+if test "x$ac_system" = "xOpenBSD"
+then
+ plugin_tcpconns="yes"
+fi
+
# Mac OS X devices
if test "x$with_libiokit" = "xyes"
then
plugin_processes="yes"
fi
-if test "x$with_libkvm" = "xyes"
+if test "x$with_kvm_getprocs" = "xyes"
then
plugin_processes="yes"
+fi
+
+if test "x$with_kvm_getswapinfo" = "xyes"
+then
plugin_swap="yes"
fi
+if test "x$with_kvm_nlist" = "xyes"
+then
+ plugin_tcpconns="yes"
+fi
+
if test "x$have_getutent" = "xyes"
then
plugin_users="yes"
'GPRINT:pg_blks_avg:AVERAGE:%4.1lf%s Avg,',
'GPRINT:pg_blks_max:MAX:%4.1lf%s Max,',
'GPRINT:pg_blks_avg:LAST:%4.1lf%s Last'],
+ pg_db_size => ['DEF:pg_db_size_avg={file}:value:AVERAGE',
+ 'DEF:pg_db_size_min={file}:value:MIN',
+ 'DEF:pg_db_size_max={file}:value:MAX',
+ "AREA:pg_db_size_max#$HalfBlue",
+ "AREA:pg_db_size_min#$Canvas",
+ "LINE1:pg_db_size_avg#$FullBlue:Bytes",
+ 'GPRINT:pg_db_size_min:MIN:%4.1lf%s Min,',
+ 'GPRINT:pg_db_size_avg:AVERAGE:%4.1lf%s Avg,',
+ 'GPRINT:pg_db_size_max:MAX:%4.1lf%s Max,',
+ 'GPRINT:pg_db_size_avg:LAST:%4.1lf%s Last'],
pg_n_tup_c => ['DEF:pg_n_tup_avg={file}:value:AVERAGE',
'DEF:pg_n_tup_min={file}:value:MIN',
'DEF:pg_n_tup_max={file}:value:MAX',
pkglib_LTLIBRARIES += tcpconns.la
tcpconns_la_SOURCES = tcpconns.c
tcpconns_la_LDFLAGS = -module -avoid-version
+tcpconns_la_LIBADD =
collectd_LDADD += "-dlopen" tcpconns.la
collectd_DEPENDENCIES += tcpconns.la
+if BUILD_WITH_LIBKVM_NLIST
+tcpconns_la_LIBADD += -lkvm
+endif
endif
if BUILD_PLUGIN_TEAMSPEAK2
postgresql_default.conf
.pod.1:
- pod2man --release=$(VERSION) --center=$(PACKAGE) $< >.pod2man.tmp 2>/dev/null && mv -f .pod2man.tmp $@ || true
+ pod2man --release=$(VERSION) --center=$(PACKAGE) $< \
+ >.pod2man.tmp 2>/dev/null && mv -f .pod2man.tmp $@ || true
+ if grep '\<POD ERRORS\>' $@ >/dev/null 2>&1; \
+ then \
+ echo "$@ has some POD errors!"; false; \
+ fi
.pod.5:
- pod2man --section=5 --release=$(VERSION) --center=$(PACKAGE) $< >.pod2man.tmp 2>/dev/null && mv -f .pod2man.tmp $@ || true
+ pod2man --section=5 --release=$(VERSION) --center=$(PACKAGE) $< \
+ >.pod2man.tmp 2>/dev/null && mv -f .pod2man.tmp $@ || true
+ if grep '\<POD ERRORS\>' $@ >/dev/null 2>&1; \
+ then \
+ echo "$@ has some POD errors!"; false; \
+ fi
install-exec-hook:
$(mkinstalldirs) $(DESTDIR)$(sysconfdir)
=back
+Please note that parameters are only supported by PostgreSQL's protocol
+version 3 and above which was introduced in version 7.4 of PostgreSQL.
+
=item B<Column> I<type> [I<type instance>]
Specify the I<type> and optional I<type instance> used to dispatch the value
=back
-The following predefined queries are available:
+The following predefined queries are available (the definitions can be found
+in the F<postgresql_default.conf> file which, by default, is available at
+C<I<prefix>/share/collectd/>):
=over 4
-=item B<database>
+=item B<backends>
+
+This query collects the number of backends, i.E<nbsp>e. the number of
+connected clients.
+
+=item B<transactions>
+
+This query collects the numbers of committed and rolled-back transactions of
+the user tables.
+
+=item B<queries>
+
+This query collects the numbers of various table modifications (i.E<nbsp>e.
+insertions, updates, deletions) of the user tables.
+
+=item B<query_plans>
+
+This query collects the numbers of various table scans and returned tuples of
+the user tables.
+
+=item B<table_states>
-This query collects general database statistics, i.E<nbsp>e. the number of
-backends and committed and rolled-back transactions.
+This query collects the numbers of live and dead rows in the user tables.
-=item B<user_tables>
+=item B<disk_io>
-This query collects user-table usage statistics, i.E<nbsp>e. the numbers of
-various table scans and the numbers of various table modifications.
+This query collects disk block access counts for user tables.
-=item B<io_user_tables>
+=item B<disk_usage>
-This query collects block access counts for user-tables.
+This query collects the on-disk size of the database in bytes.
=back
Specify a I<query> which should be executed for the database connection. This
may be any of the predefined or user-defined queries. If no such option is
-given, it defaults to "database", "user_tables" and "io_user_tables". Else,
-the specified queries are used only.
+given, it defaults to "backends", "transactions", "queries", "query_plans",
+"table_states", "disk_io" and "disk_usage". Else, the specified queries are
+used only.
=back
PGconn *conn;
c_complain_t conn_complaint;
+ int proto_version;
+
int max_params_num;
/* user configuration */
} c_psql_database_t;
static char *def_queries[] = {
- "database",
- "user_tables",
- "io_user_tables"
+ "backends",
+ "transactions",
+ "queries",
+ "query_plans",
+ "table_states",
+ "disk_io",
+ "disk_usage"
};
static int def_queries_num = STATIC_ARRAY_SIZE (def_queries);
db->conn_complaint.last = 0;
db->conn_complaint.interval = 0;
+ db->proto_version = 0;
+
db->max_params_num = 0;
db->queries = NULL;
db->database, PQerrorMessage (db->conn));
return -1;
}
+
+ db->proto_version = PQprotocolVersion (db->conn);
+ if (3 > db->proto_version)
+ log_warn ("Protocol version %d does not support parameters.",
+ db->proto_version);
}
c_release (LOG_INFO, &db->conn_complaint,
return 0;
} /* c_psql_check_connection */
-static int c_psql_exec_query (c_psql_database_t *db, int idx)
+static PGresult *c_psql_exec_query_params (c_psql_database_t *db,
+ c_psql_query_t *query)
{
- c_psql_query_t *query;
- PGresult *res;
-
char *params[db->max_params_num];
-
- int rows, cols;
- int i;
-
- if (idx >= db->queries_num)
- return -1;
-
- query = db->queries[idx];
+ int i;
assert (db->max_params_num >= query->params_num);
}
}
- res = PQexecParams (db->conn, query->query, query->params_num, NULL,
+ return PQexecParams (db->conn, query->query, query->params_num, NULL,
(const char *const *)((0 == query->params_num) ? NULL : params),
NULL, NULL, /* return text data */ 0);
+} /* c_psql_exec_query_params */
+
+static PGresult *c_psql_exec_query_noparams (c_psql_database_t *db,
+ c_psql_query_t *query)
+{
+ return PQexec (db->conn, query->query);
+} /* c_psql_exec_query_noparams */
+
+static int c_psql_exec_query (c_psql_database_t *db, int idx)
+{
+ c_psql_query_t *query;
+ PGresult *res;
+
+ int rows, cols;
+ int i;
+
+ if (idx >= db->queries_num)
+ return -1;
+
+ query = db->queries[idx];
+
+ if (3 <= db->proto_version)
+ res = c_psql_exec_query_params (db, query);
+ else if (0 == query->params_num)
+ res = c_psql_exec_query_noparams (db, query);
+ else {
+ log_err ("Connection to database \"%s\" does not support parameters "
+ "(protocol version %d) - cannot execute query \"%s\".",
+ db->database, db->proto_version, query->name);
+ return -1;
+ }
if (PGRES_TUPLES_OK != PQresultStatus (res)) {
log_err ("Failed to execute SQL query: %s",
if (0 != c_psql_check_connection (db))
continue;
+ db->proto_version = PQprotocolVersion (db->conn);
+
server_host = PQhost (db->conn);
server_version = PQserverVersion (db->conn);
log_info ("Sucessfully connected to database %s (user %s) "
PQdb (db->conn), PQuser (db->conn),
C_PSQL_SOCKET3 (server_host, PQport (db->conn)),
C_PSQL_SERVER_VERSION3 (server_version),
- PQprotocolVersion (db->conn), PQbackendPID (db->conn));
+ db->proto_version, PQbackendPID (db->conn));
+
+ if (3 > db->proto_version)
+ log_warn ("Protocol version %d does not support parameters.",
+ db->proto_version);
}
plugin_register_read ("postgresql", c_psql_read);
return 0;
} /* config_set_column */
-static int config_set_query (c_psql_database_t *db, const oconfig_item_t *ci)
+static int set_query (c_psql_database_t *db, const char *name)
{
c_psql_query_t *query;
- if ((0 != ci->children_num) || (1 != ci->values_num)
- || (OCONFIG_TYPE_STRING != ci->values[0].type)) {
- log_err ("Query expects a single string argument.");
- return 1;
- }
-
- query = c_psql_query_get (ci->values[0].value.string);
+ query = c_psql_query_get (name);
if (NULL == query) {
log_err ("Query \"%s\" not found - please check your configuration.",
- ci->values[0].value.string);
+ name);
return 1;
}
db->queries[db->queries_num - 1] = query;
return 0;
+} /* set_query */
+
+static int config_set_query (c_psql_database_t *db, const oconfig_item_t *ci)
+{
+ if ((0 != ci->children_num) || (1 != ci->values_num)
+ || (OCONFIG_TYPE_STRING != ci->values[0].type)) {
+ log_err ("Query expects a single string argument.");
+ return 1;
+ }
+ return set_query (db, ci->values[0].value.string);
} /* config_set_query */
static int c_psql_config_query (oconfig_item_t *ci)
}
if (NULL == db->queries) {
- db->queries = (c_psql_query_t **)malloc (def_queries_num
- * sizeof (*db->queries));
-
- for (i = 0; i < def_queries_num; ++i) {
- db->queries[i] = c_psql_query_get (def_queries[i]);
- if (NULL == db->queries[i])
- log_err ("Query \"%s\" not found - "
- "please check your installation.",
- def_queries[i]);
- else
- ++db->queries_num;
- }
+ for (i = 0; i < def_queries_num; ++i)
+ set_query (db, def_queries[i]);
}
return 0;
}
# Pre-defined queries of collectd's postgresql plugin.
-<Query database>
- Query "SELECT numbackends, xact_commit, xact_rollback \
- FROM pg_stat_database \
+<Query backends>
+ Query "SELECT count(*) \
+ FROM pg_stat_activity \
WHERE datname = $1;"
Param database
Column pg_numbackends
+</Query>
+
+<Query transactions>
+ Query "SELECT xact_commit, xact_rollback \
+ FROM pg_stat_database \
+ WHERE datname = $1;"
+
+ Param database
+
Column pg_xact commit
Column pg_xact rollback
</Query>
-<Query user_tables>
- Query "SELECT sum(seq_scan), sum(seq_tup_read), \
- sum(idx_scan), sum(idx_tup_fetch), \
- sum(n_tup_ins), sum(n_tup_upd), sum(n_tup_del), \
- sum(n_tup_hot_upd), sum(n_live_tup), sum(n_dead_tup) \
- FROM pg_stat_user_tables"
-
- Column pg_scan seq
- Column pg_scan seq_tup_read
- Column pg_scan idx
- Column pg_scan idx_tup_fetch
+<Query queries>
+ Query "SELECT sum(n_tup_ins), sum(n_tup_upd), sum(n_tup_del), \
+ sum(n_tup_hot_upd) \
+ FROM pg_stat_user_tables;"
+
Column pg_n_tup_c ins
Column pg_n_tup_c upd
Column pg_n_tup_c del
Column pg_n_tup_c hot_upd
+</Query>
+
+<Query query_plans>
+ Query "SELECT sum(seq_scan), sum(seq_tup_read), \
+ sum(idx_scan), sum(idx_tup_fetch) \
+ FROM pg_stat_user_tables;"
+
+ Column pg_scan seq
+ Column pg_scan seq_tup_read
+ Column pg_scan idx
+ Column pg_scan idx_tup_fetch
+</Query>
+
+<Query table_states>
+ Query "SELECT sum(n_live_tup), sum(n_dead_tup) \
+ FROM pg_stat_user_tables;"
+
Column pg_n_tup_g live
Column pg_n_tup_g dead
</Query>
-<Query io_user_tables>
+<Query disk_io>
Query "SELECT sum(heap_blks_read), sum(heap_blks_hit), \
sum(idx_blks_read), sum(idx_blks_hit), \
sum(toast_blks_read), sum(toast_blks_hit), \
Column pg_blks tidx_hit
</Query>
+<Query disk_usage>
+ Query "SELECT pg_database_size($1);"
+
+ Param database
+
+ Column pg_db_size
+</Query>
+
* Florian octo Forster <octo at verplant.org>
**/
+/**
+ * Code within `HAVE_LIBKVM_NLIST' blocks is provided under the following
+ * license:
+ *
+ * $collectd: parts of tcpconns.c, 2008/08/08 03:48:30 Michael Stapelberg $
+ * $OpenBSD: inet.c,v 1.100 2007/06/19 05:28:30 ray Exp $
+ * $NetBSD: inet.c,v 1.14 1995/10/03 21:42:37 thorpej Exp $
+ *
+ * Copyright (c) 1983, 1988, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the University nor the names of its contributors
+ * may be used to endorse or promote products derived from this software
+ * without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
#include "collectd.h"
#include "common.h"
#include "plugin.h"
-#if !KERNEL_LINUX && !HAVE_SYSCTLBYNAME
+#if !KERNEL_LINUX && !HAVE_SYSCTLBYNAME && !HAVE_LIBKVM_NLIST
# error "No applicable input method."
#endif
# include <netinet/tcpip.h>
# include <netinet/tcp_seq.h>
# include <netinet/tcp_var.h>
-#endif /* HAVE_SYSCTLBYNAME */
+/* #endif HAVE_SYSCTLBYNAME */
+
+/* This is for OpenBSD and possibly NetBSD. */
+#elif HAVE_LIBKVM_NLIST
+# include <sys/queue.h>
+# include <sys/socket.h>
+# include <net/route.h>
+# include <netinet/in.h>
+# include <netinet/in_systm.h>
+# include <netinet/ip.h>
+# include <netinet/in_pcb.h>
+# include <netinet/tcp.h>
+# include <netinet/tcp_timer.h>
+# include <netinet/tcp_var.h>
+# include <netdb.h>
+# include <arpa/inet.h>
+# include <nlist.h>
+# include <kvm.h>
+#endif /* HAVE_LIBKVM_NLIST */
#if KERNEL_LINUX
static const char *tcp_state[] =
# define TCP_STATE_LISTEN 1
# define TCP_STATE_MIN 0
# define TCP_STATE_MAX 10
-#endif /* HAVE_SYSCTLBYNAME */
+/* #endif HAVE_SYSCTLBYNAME */
+
+#elif HAVE_LIBKVM_NLIST
+static const char *tcp_state[] =
+{
+ "CLOSED",
+ "LISTEN",
+ "SYN_SENT",
+ "SYN_RECV",
+ "ESTABLISHED",
+ "CLOSE_WAIT",
+ "FIN_WAIT1",
+ "CLOSING",
+ "LAST_ACK",
+ "FIN_WAIT2",
+ "TIME_WAIT"
+};
+
+static kvm_t *kvmd;
+static u_long inpcbtable_off = 0;
+struct inpcbtable *inpcbtable_ptr = NULL;
+
+# define TCP_STATE_LISTEN 1
+# define TCP_STATE_MIN 1
+# define TCP_STATE_MAX 10
+#endif /* HAVE_LIBKVM_NLIST */
#define PORT_COLLECT_LOCAL 0x01
#define PORT_COLLECT_REMOTE 0x02
/* #endif KERNEL_LINUX */
#elif HAVE_SYSCTLBYNAME
-#endif /* HAVE_SYSCTLBYNAME */
+/* #endif HAVE_SYSCTLBYNAME */
+
+#elif HAVE_LIBKVM_NLIST
+#endif /* HAVE_LIBKVM_NLIST */
static int conn_config (const char *key, const char *value)
{
return (0);
} /* int conn_read */
-#endif /* HAVE_SYSCTLBYNAME */
+/* #endif HAVE_SYSCTLBYNAME */
+
+#elif HAVE_LIBKVM_NLIST
+static int kread (u_long addr, void *buf, int size)
+{
+ int status;
+
+ status = kvm_read (kvmd, addr, buf, size);
+ if (status != size)
+ {
+ ERROR ("tcpconns plugin: kvm_read failed (got %i, expected %i): %s\n",
+ status, size, kvm_geterr (kvmd));
+ return (-1);
+ }
+ return (0);
+} /* int kread */
+
+static int conn_init (void)
+{
+ char buf[_POSIX2_LINE_MAX];
+ struct nlist nl[] =
+ {
+#define N_TCBTABLE 0
+ { "_tcbtable" },
+ { "" }
+ };
+ int status;
+
+ kvmd = kvm_openfiles (NULL, NULL, NULL, O_RDONLY, buf);
+ if (kvmd == NULL)
+ {
+ ERROR ("tcpconns plugin: kvm_openfiles failed: %s", buf);
+ return (-1);
+ }
+
+ status = kvm_nlist (kvmd, nl);
+ if (status < 0)
+ {
+ ERROR ("tcpconns plugin: kvm_nlist failed with status %i.", status);
+ return (-1);
+ }
+
+ if (nl[N_TCBTABLE].n_type == 0)
+ {
+ ERROR ("tcpconns plugin: Error looking up kernel's namelist: "
+ "N_TCBTABLE is invalid.");
+ return (-1);
+ }
+
+ inpcbtable_off = (u_long) nl[N_TCBTABLE].n_value;
+ inpcbtable_ptr = (struct inpcbtable *) nl[N_TCBTABLE].n_value;
+
+ return (0);
+} /* int conn_init */
+
+static int conn_read (void)
+{
+ struct inpcbtable table;
+ struct inpcb *head;
+ struct inpcb *next;
+ struct inpcb inpcb;
+ struct tcpcb tcpcb;
+ int status;
+
+ conn_reset_port_entry ();
+
+ /* Read the pcbtable from the kernel */
+ status = kread (inpcbtable_off, &table, sizeof (table));
+ if (status != 0)
+ return (-1);
+
+ /* Get the `head' pcb */
+ head = (struct inpcb *) &(inpcbtable_ptr->inpt_queue);
+ /* Get the first pcb */
+ next = CIRCLEQ_FIRST (&table.inpt_queue);
+
+ while (next != head)
+ {
+ /* Read the pcb pointed to by `next' into `inpcb' */
+ kread ((u_long) next, &inpcb, sizeof (inpcb));
+
+ /* Advance `next' */
+ next = CIRCLEQ_NEXT (&inpcb, inp_queue);
+
+ /* Ignore sockets, that are not connected. */
+ if (!(inpcb.inp_flags & INP_IPV6)
+ && (inet_lnaof(inpcb.inp_laddr) == INADDR_ANY))
+ continue;
+ if ((inpcb.inp_flags & INP_IPV6)
+ && IN6_IS_ADDR_UNSPECIFIED (&inpcb.inp_laddr6))
+ continue;
+
+ kread ((u_long) inpcb.inp_ppcb, &tcpcb, sizeof (tcpcb));
+ conn_handle_ports (ntohs(inpcb.inp_lport), ntohs(inpcb.inp_fport), tcpcb.t_state);
+ } /* while (next != head) */
+
+ conn_submit_all ();
+
+ return (0);
+}
+#endif /* HAVE_LIBKVM_NLIST */
void module_register (void)
{
config_keys, config_keys_num);
#if KERNEL_LINUX
plugin_register_init ("tcpconns", conn_init);
+#elif HAVE_SYSCTLBYNAME
+ /* no initialization */
+#elif HAVE_LIBKVM_NLIST
+ plugin_register_init ("tcpconns", conn_init);
#endif
plugin_register_read ("tcpconns", conn_read);
} /* void module_register */
/*
- * vim: set shiftwidth=2 softtabstop=2 tabstop=8 :
+ * vim: set shiftwidth=2 softtabstop=2 tabstop=8 fdm=marker :
*/
nginx_requests value:COUNTER:0:134217728
percent percent:GAUGE:0:100.1
pg_blks value:COUNTER:0:U
+pg_db_size value:GAUGE:0:U
pg_n_tup_c value:COUNTER:0:U
pg_n_tup_g value:GAUGE:0:U
pg_numbackends value:GAUGE:0:U