PluginProbe
Code Profiler – WordPress Performance Profiling and Debugging Made Easy / 1.5
Code Profiler – WordPress Performance Profiling and Debugging Made Easy v1.5
1.9.5 1.9.4 1.9.3 trunk 1.4 1.4.1 1.4.2 1.4.3 1.4.4 1.5 1.5.1 1.5.2 1.5.3 1.5.4 1.5.5 1.6 1.6.1 1.6.10 1.6.2 1.6.3 1.6.4 1.6.5 1.6.6 1.6.7 1.6.8 All 40 releases
code-profiler / lib / class-profiler.php

class-profiler.php in Code Profiler – WordPress Performance Profiling and Debugging Made Easy 1.5, at lib/class-profiler.php

163 lines 4.7 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /*
3 +=====================================================================+
4 | ____ _ ____ __ _ _ |
5 | / ___|___ __| | ___ | _ \ _ __ ___ / _(_) | ___ _ __ |
6 | | | / _ \ / _` |/ _ \ | |_) | '__/ _ \| |_| | |/ _ \ '__| |
7 | | |__| (_) | (_| | __/ | __/| | | (_) | _| | | __/ | |
8 | \____\___/ \__,_|\___| |_| |_| \___/|_| |_|_|\___|_| |
9 | |
10 | (c) Jerome Bruandet ~ https://code-profiler.com/ |
11 +=====================================================================+
12 */
13
14 if (! defined( 'ABSPATH' ) ) { die( 'Forbidden' ); }
15
16 // =====================================================================
17
18 class CodeProfiler_Profiler {
19
20 static $tick_list;
21 static $buffer = 10000000;
22 static $metrics;
23
24 private $tmp_iostats;
25 private $tmp_summary;
26 private $tmp_diskio;
27 private $tmp_ticks;
28
29 /*
30 * Initialize
31 */
32 public function __construct() {
33
34 $microtime = sanitize_file_name( $_REQUEST['CODE_PROFILER_ON'] );
35
36 $this->tmp_summary = CODE_PROFILER_UPLOAD_DIR ."/$microtime." .
37 CODE_PROFILER_TMP_SUMMARY_LOG;
38 $this->tmp_iostats = CODE_PROFILER_UPLOAD_DIR ."/$microtime." .
39 CODE_PROFILER_TMP_IOSTATS_LOG;
40 $this->tmp_ticks = CODE_PROFILER_UPLOAD_DIR ."/$microtime." .
41 CODE_PROFILER_TMP_TICKS_LOG;
42 $this->tmp_diskio = CODE_PROFILER_UPLOAD_DIR ."/$microtime." .
43 CODE_PROFILER_TMP_DISKIO_LOG;
44
45 // Clear the temporary log because the buffer will be written
46 // with the FILE_APPEND flag
47 if ( file_exists( $this->tmp_ticks ) ) {
48 unlink( $this->tmp_ticks );
49 }
50
51 if ( version_compare( PHP_VERSION, '7.3', '<' ) ) {
52 self::$metrics = 'microtime';
53 } else {
54 self::$metrics = 'hrtime';
55 }
56
57 $cp_options = get_option('code-profiler');
58 if ( empty( $cp_options['accuracy'] ) ) {
59 define('CODE_PROFILER_TICKS', 1 );
60 } else {
61 define('CODE_PROFILER_TICKS', (int) $cp_options['accuracy'] );
62 }
63 define('CODE_PROFILER_LENGTH', 17 + strlen( (string) CODE_PROFILER_TICKS ) );
64
65 register_shutdown_function( array( $this, 'code_profiler_shutdown' ) );
66
67 require 'class-stream.php';
68 CodeProfiler_Stream::start();
69 register_tick_function( array( $this, 'code_profiler_tick_handler' ) );
70 }
71
72 /*
73 * Save data and check for potential PHP errors.
74 */
75 public function code_profiler_shutdown() {
76
77 CodeProfiler_Stream::stop();
78
79 $summary['memory'] = memory_get_peak_usage();
80 $summary['queries'] = get_num_queries() - 2;
81 file_put_contents( $this->tmp_summary, json_encode( $summary ) );
82
83 // Catch potential error
84 $e = error_get_last();
85 if ( isset( $e['type'] ) && $e['type'] === E_ERROR ) {
86 $err = str_replace( "\n", ' - ', $e['message'] );
87 code_profiler_log_error( sprintf(
88 /* Translators: Error message, line number and script */
89 esc_html__('Error: E_ERROR (%s - line %s in %s)', 'code-profiler'),
90 esc_html( $err ),
91 (int) $e['line'],
92 esc_html( $e['file'] )
93 ));
94 }
95
96 $err_msg = esc_html__('Cannot open file for writting: %s', 'code-profiler');
97 $res = file_put_contents( $this->tmp_iostats, json_encode( CodeProfiler_Stream::$io_stats ) );
98 if ( $res === false ) {
99 $msg = sprintf( $err_msg, $this->tmp_iostats );
100 code_profiler_log_error( $msg );
101 }
102 $res = file_put_contents( $this->tmp_ticks, self::$tick_list, FILE_APPEND );
103 if ( $res === false ) {
104 $msg = sprintf( $err_msg, $this->tmp_ticks );
105 code_profiler_log_error( $msg );
106 }
107 $res = file_put_contents(
108 $this->tmp_diskio, "read\t". CodeProfiler_Stream::$io_read ."\nwrite\t".
109 CodeProfiler_Stream::$io_write
110 );
111
112 }
113
114 /*
115 * Our tick handler.
116 */
117 public function code_profiler_tick_handler() {
118
119 if ( self::$metrics == 'hrtime' ) {
120 $start = hrtime( true );
121 } else {
122 $start = microtime( true );
123 }
124
125 $backtrace = debug_backtrace( DEBUG_BACKTRACE_IGNORE_ARGS, 2 );
126 if ( isset( $backtrace[1] ) ) {
127 $el = $backtrace[1];
128 } else {
129 $el = $backtrace[0];
130 }
131
132 if ( empty( $el['file'] ) ) {
133 return;
134 }
135
136 self::$tick_list .= "{$el['file']}\t";
137 if ( isset( $backtrace[0]['file'][0] ) ) {
138 self::$tick_list .= $backtrace[0]['file'];
139 } else {
140 self::$tick_list .= '-';
141 }
142
143 if ( self::$metrics == 'hrtime' ) {
144 self::$tick_list .="\t{$start}\t". hrtime(true) ."\n";
145 } else {
146 self::$tick_list .="\t{$start}\t". microtime(true) ."\n";
147 }
148
149 // Buffer can grow *very* big hence we flush it every 10MB by default
150 if ( strlen( self::$tick_list ) > self::$buffer ) {
151 CodeProfiler_Stream::stop();
152 file_put_contents( $this->tmp_ticks, self::$tick_list, FILE_APPEND );
153 CodeProfiler_Stream::start();
154 self::$tick_list = '';
155 }
156 }
157 }
158
159 new CodeProfiler_Profiler();
160
161 // =====================================================================
162 // EOF
163