You've already forked wp-prometheus
289 lines
7.6 KiB
PHP
289 lines
7.6 KiB
PHP
|
|
<?php
|
||
|
|
/**
|
||
|
|
* Metrics collector class.
|
||
|
|
*
|
||
|
|
* @package WP_Prometheus
|
||
|
|
*/
|
||
|
|
|
||
|
|
namespace Magdev\WpPrometheus\Metrics;
|
||
|
|
|
||
|
|
use Prometheus\CollectorRegistry;
|
||
|
|
use Prometheus\Storage\InMemory;
|
||
|
|
use Prometheus\RenderTextFormat;
|
||
|
|
|
||
|
|
// Prevent direct file access.
|
||
|
|
if ( ! defined( 'ABSPATH' ) ) {
|
||
|
|
exit;
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Collector class.
|
||
|
|
*
|
||
|
|
* Collects and manages Prometheus metrics.
|
||
|
|
*/
|
||
|
|
class Collector {
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Prometheus collector registry.
|
||
|
|
*
|
||
|
|
* @var CollectorRegistry
|
||
|
|
*/
|
||
|
|
private CollectorRegistry $registry;
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Metric namespace.
|
||
|
|
*
|
||
|
|
* @var string
|
||
|
|
*/
|
||
|
|
private string $namespace = 'wordpress';
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Constructor.
|
||
|
|
*/
|
||
|
|
public function __construct() {
|
||
|
|
$this->registry = new CollectorRegistry( new InMemory() );
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Get the collector registry.
|
||
|
|
*
|
||
|
|
* @return CollectorRegistry
|
||
|
|
*/
|
||
|
|
public function get_registry(): CollectorRegistry {
|
||
|
|
return $this->registry;
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Get the metric namespace.
|
||
|
|
*
|
||
|
|
* @return string
|
||
|
|
*/
|
||
|
|
public function get_namespace(): string {
|
||
|
|
return $this->namespace;
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Collect all enabled metrics.
|
||
|
|
*
|
||
|
|
* @return void
|
||
|
|
*/
|
||
|
|
public function collect(): void {
|
||
|
|
$enabled_metrics = get_option( 'wp_prometheus_enabled_metrics', array() );
|
||
|
|
|
||
|
|
// Always collect WordPress info.
|
||
|
|
if ( in_array( 'wordpress_info', $enabled_metrics, true ) ) {
|
||
|
|
$this->collect_wordpress_info();
|
||
|
|
}
|
||
|
|
|
||
|
|
// Collect user metrics.
|
||
|
|
if ( in_array( 'wordpress_users_total', $enabled_metrics, true ) ) {
|
||
|
|
$this->collect_users_total();
|
||
|
|
}
|
||
|
|
|
||
|
|
// Collect posts metrics.
|
||
|
|
if ( in_array( 'wordpress_posts_total', $enabled_metrics, true ) ) {
|
||
|
|
$this->collect_posts_total();
|
||
|
|
}
|
||
|
|
|
||
|
|
// Collect comments metrics.
|
||
|
|
if ( in_array( 'wordpress_comments_total', $enabled_metrics, true ) ) {
|
||
|
|
$this->collect_comments_total();
|
||
|
|
}
|
||
|
|
|
||
|
|
// Collect plugins metrics.
|
||
|
|
if ( in_array( 'wordpress_plugins_total', $enabled_metrics, true ) ) {
|
||
|
|
$this->collect_plugins_total();
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Fires after default metrics are collected.
|
||
|
|
*
|
||
|
|
* @param Collector $collector The metrics collector instance.
|
||
|
|
*/
|
||
|
|
do_action( 'wp_prometheus_collect_metrics', $this );
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Render metrics in Prometheus text format.
|
||
|
|
*
|
||
|
|
* @return string
|
||
|
|
*/
|
||
|
|
public function render(): string {
|
||
|
|
$this->collect();
|
||
|
|
|
||
|
|
$renderer = new RenderTextFormat();
|
||
|
|
return $renderer->render( $this->registry->getMetricFamilySamples() );
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Collect WordPress info metric.
|
||
|
|
*
|
||
|
|
* @return void
|
||
|
|
*/
|
||
|
|
private function collect_wordpress_info(): void {
|
||
|
|
$gauge = $this->registry->getOrRegisterGauge(
|
||
|
|
$this->namespace,
|
||
|
|
'info',
|
||
|
|
'WordPress installation information',
|
||
|
|
array( 'version', 'php_version', 'multisite' )
|
||
|
|
);
|
||
|
|
|
||
|
|
$gauge->set(
|
||
|
|
1,
|
||
|
|
array(
|
||
|
|
get_bloginfo( 'version' ),
|
||
|
|
PHP_VERSION,
|
||
|
|
is_multisite() ? 'yes' : 'no',
|
||
|
|
)
|
||
|
|
);
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Collect total users metric.
|
||
|
|
*
|
||
|
|
* @return void
|
||
|
|
*/
|
||
|
|
private function collect_users_total(): void {
|
||
|
|
$gauge = $this->registry->getOrRegisterGauge(
|
||
|
|
$this->namespace,
|
||
|
|
'users_total',
|
||
|
|
'Total number of WordPress users',
|
||
|
|
array( 'role' )
|
||
|
|
);
|
||
|
|
|
||
|
|
$user_count = count_users();
|
||
|
|
foreach ( $user_count['avail_roles'] as $role => $count ) {
|
||
|
|
$gauge->set( $count, array( $role ) );
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Collect total posts metric.
|
||
|
|
*
|
||
|
|
* @return void
|
||
|
|
*/
|
||
|
|
private function collect_posts_total(): void {
|
||
|
|
$gauge = $this->registry->getOrRegisterGauge(
|
||
|
|
$this->namespace,
|
||
|
|
'posts_total',
|
||
|
|
'Total number of posts by type and status',
|
||
|
|
array( 'post_type', 'status' )
|
||
|
|
);
|
||
|
|
|
||
|
|
$post_types = get_post_types( array( 'public' => true ) );
|
||
|
|
foreach ( $post_types as $post_type ) {
|
||
|
|
$counts = wp_count_posts( $post_type );
|
||
|
|
foreach ( get_object_vars( $counts ) as $status => $count ) {
|
||
|
|
if ( $count > 0 ) {
|
||
|
|
$gauge->set( (int) $count, array( $post_type, $status ) );
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Collect total comments metric.
|
||
|
|
*
|
||
|
|
* @return void
|
||
|
|
*/
|
||
|
|
private function collect_comments_total(): void {
|
||
|
|
$gauge = $this->registry->getOrRegisterGauge(
|
||
|
|
$this->namespace,
|
||
|
|
'comments_total',
|
||
|
|
'Total number of comments by status',
|
||
|
|
array( 'status' )
|
||
|
|
);
|
||
|
|
|
||
|
|
$comments = wp_count_comments();
|
||
|
|
$statuses = array(
|
||
|
|
'approved' => $comments->approved,
|
||
|
|
'moderated' => $comments->moderated,
|
||
|
|
'spam' => $comments->spam,
|
||
|
|
'trash' => $comments->trash,
|
||
|
|
'total_comments' => $comments->total_comments,
|
||
|
|
);
|
||
|
|
|
||
|
|
foreach ( $statuses as $status => $count ) {
|
||
|
|
$gauge->set( (int) $count, array( $status ) );
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Collect total plugins metric.
|
||
|
|
*
|
||
|
|
* @return void
|
||
|
|
*/
|
||
|
|
private function collect_plugins_total(): void {
|
||
|
|
if ( ! function_exists( 'get_plugins' ) ) {
|
||
|
|
require_once ABSPATH . 'wp-admin/includes/plugin.php';
|
||
|
|
}
|
||
|
|
|
||
|
|
$gauge = $this->registry->getOrRegisterGauge(
|
||
|
|
$this->namespace,
|
||
|
|
'plugins_total',
|
||
|
|
'Total number of plugins by status',
|
||
|
|
array( 'status' )
|
||
|
|
);
|
||
|
|
|
||
|
|
$all_plugins = get_plugins();
|
||
|
|
$active_plugins = get_option( 'active_plugins', array() );
|
||
|
|
|
||
|
|
$gauge->set( count( $all_plugins ), array( 'installed' ) );
|
||
|
|
$gauge->set( count( $active_plugins ), array( 'active' ) );
|
||
|
|
$gauge->set( count( $all_plugins ) - count( $active_plugins ), array( 'inactive' ) );
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Register a custom gauge metric.
|
||
|
|
*
|
||
|
|
* @param string $name Metric name.
|
||
|
|
* @param string $help Metric description.
|
||
|
|
* @param array $labels Label names.
|
||
|
|
* @return \Prometheus\Gauge
|
||
|
|
*/
|
||
|
|
public function register_gauge( string $name, string $help, array $labels = array() ): \Prometheus\Gauge {
|
||
|
|
return $this->registry->getOrRegisterGauge(
|
||
|
|
$this->namespace,
|
||
|
|
$name,
|
||
|
|
$help,
|
||
|
|
$labels
|
||
|
|
);
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Register a custom counter metric.
|
||
|
|
*
|
||
|
|
* @param string $name Metric name.
|
||
|
|
* @param string $help Metric description.
|
||
|
|
* @param array $labels Label names.
|
||
|
|
* @return \Prometheus\Counter
|
||
|
|
*/
|
||
|
|
public function register_counter( string $name, string $help, array $labels = array() ): \Prometheus\Counter {
|
||
|
|
return $this->registry->getOrRegisterCounter(
|
||
|
|
$this->namespace,
|
||
|
|
$name,
|
||
|
|
$help,
|
||
|
|
$labels
|
||
|
|
);
|
||
|
|
}
|
||
|
|
|
||
|
|
/**
|
||
|
|
* Register a custom histogram metric.
|
||
|
|
*
|
||
|
|
* @param string $name Metric name.
|
||
|
|
* @param string $help Metric description.
|
||
|
|
* @param array $labels Label names.
|
||
|
|
* @param array|null $buckets Histogram buckets.
|
||
|
|
* @return \Prometheus\Histogram
|
||
|
|
*/
|
||
|
|
public function register_histogram( string $name, string $help, array $labels = array(), ?array $buckets = null ): \Prometheus\Histogram {
|
||
|
|
return $this->registry->getOrRegisterHistogram(
|
||
|
|
$this->namespace,
|
||
|
|
$name,
|
||
|
|
$help,
|
||
|
|
$labels,
|
||
|
|
$buckets
|
||
|
|
);
|
||
|
|
}
|
||
|
|
}
|