PluginProbe
Black Bar / trunk
Black Bar vtrunk
trunk 1.0.0 1.1.0 1.2.0 2.0.0 2.1.0 2.1.1 2.1.2 2.1.3 2.1.4 2.2.0 2.2.1 3.0.0 3.1.0 4.0.0 4.0.1 4.0.2 4.0.3 4.1.0 4.1.1 4.1.2 4.1.3 4.1.4 4.2.0
blackbar / plugin / Modules / Queries.php

Queries.php in Black Bar trunk, at plugin/Modules/Queries.php

105 lines 3.4 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 namespace GeminiLabs\BlackBar\Modules;
4
5 class Queries extends Module
6 {
7 public function classes(): string
8 {
9 $entries = $this->entries();
10 $isError = array_filter(wp_list_pluck($entries, 'is_error'));
11 if (!empty($isError)) {
12 return sprintf('%s glbb-error', $this->id());
13 }
14 $isWarning = array_filter(wp_list_pluck($entries, 'is_warning'));
15 if (!empty($isWarning)) {
16 return sprintf('%s glbb-warning', $this->id());
17 }
18 return $this->id();
19 }
20
21 public function entries(): array
22 {
23 if (!empty($this->entries)) {
24 return $this->entries;
25 }
26 global $wpdb;
27 $entries = [];
28 $index = 0;
29 $search = [
30 'FROM', 'GROUP BY', 'INNER JOIN', 'LEFT JOIN', 'LIMIT',
31 'ON DUPLICATE KEY UPDATE', 'ORDER BY', 'OFFSET', ' SET', 'WHERE',
32 ];
33 $replace = array_map(function ($value) {
34 return PHP_EOL.$value;
35 }, $search);
36 $errorThreshold = (int) apply_filters('blackbar/queries/ms_error', 1000); // 1s
37 $warningThreshold = (int) apply_filters('blackbar/queries/ms_warning', 50); // 50ms
38 foreach ($wpdb->queries as $query) {
39 $sql = preg_replace('/\s\s+/', ' ', trim($query[0]));
40 $sql = str_replace(PHP_EOL, ' ', $sql);
41 $sql = str_replace(['( ', ' )', ' ,'], ['(', ')', ','], $sql);
42 $sql = str_replace($search, $replace, $sql);
43 $parts = explode(PHP_EOL, $sql);
44 $sql = array_reduce($parts, function ($carry, $part) {
45 if (str_starts_with($part, 'SELECT') && strlen($part) > 100) {
46 $part = preg_replace('/\s*(,)\s*/', ','.PHP_EOL.' ', $part);
47 }
48 if (str_starts_with($part, 'WHERE')) {
49 $part = str_replace('AND', PHP_EOL.' AND', $part);
50 }
51 return $carry.$part.PHP_EOL;
52 });
53 $trace = explode(', ', $query[2]);
54 $nanoseconds = (int) round($query[1] * 1e9);
55 $entries[] = [
56 'index' => $index++,
57 'is_error' => round($nanoseconds / 1e6, 2) > $errorThreshold,
58 'is_warning' => round($nanoseconds / 1e6, 2) > $warningThreshold,
59 'sql' => $sql,
60 'time' => $nanoseconds,
61 'time_formatted' => $this->formatTime($nanoseconds),
62 'trace' => array_reverse($trace, true),
63 ];
64 }
65 uasort($entries, [$this, 'sortByTime']);
66 $this->entries = $entries;
67 return $entries;
68 }
69
70 public function hasEntries(): bool
71 {
72 global $wpdb;
73 return !empty($wpdb->queries);
74 }
75
76 public function icon(): string
77 {
78 return 'dashicons-database';
79 }
80
81 public function info(): string
82 {
83 if (!defined('SAVEQUERIES') || !SAVEQUERIES) {
84 return '';
85 }
86 global $wpdb;
87 $seconds = (float) array_sum(wp_list_pluck($wpdb->queries, 1));
88 $nanoseconds = (int) round($seconds * 1e9);
89 return $this->formatTime($nanoseconds);
90 }
91
92 public function label(): string
93 {
94 return __('SQL', 'blackbar');
95 }
96
97 protected function sortByTime(array $a, array $b): int
98 {
99 if ($a['time'] !== $b['time']) {
100 return ($a['time'] > $b['time']) ? -1 : 1;
101 }
102 return 0;
103 }
104 }
105