Aleksander Machniak
2015-11-22 9f1f754daf4b57a0d0d3aea95d2321716d218cf5
commit | author | age
48e9c1 1 <?php
T 2
3 /**
0389fa 4  * runlog
AM 5  *
6  * @author Ziba Scott <ziba@umich.edu>
48e9c1 7  */
T 8 class runlog {
9
0389fa 10     private $start_time   = FALSE;
48e9c1 11     private $parent_stack = array();
0389fa 12     private $file_handles = array();
AM 13     private $indent       = 0;
14     private $run_log      = array();
48e9c1 15
T 16     public $print_to_console = FALSE;
0389fa 17     public $threshold        = 0;
AM 18     public $tag_count        = array();
19     public $timestamp        = "d-M-Y H:i:s O";
20     public $max_line_size    = 150;
48e9c1 21
T 22     function runlog()
23     {
0389fa 24         $this->start_time = microtime(true);
48e9c1 25     }
T 26
0389fa 27     public function start($name, $tag = false)
48e9c1 28     {
0389fa 29         $this->run_log[] = array(
AM 30                 'type'    => 'start',
31                 'tag'     => $tag,
32                 'index'   => count($this->run_log),
33                 'value'   => $name,
34                 'time'    => microtime(true),
35                 'parents' => $this->parent_stack,
36                 'ended'   => false,
37         );
38
48e9c1 39         $this->parent_stack[] = $name;
T 40
41         $this->print_to_console("start: ".$name, $tag, 'start');
42         $this->print_to_file("start: ".$name, $tag, 'start');
43         $this->indent++;
44     }
45
46     public function end()
47     {
0389fa 48         $name = array_pop($this->parent_stack);
AM 49         foreach ($this->run_log as $k => $entry) {
50             if ($entry['value'] == $name && $entry['type'] == 'start' && !$entry['ended']) {
48e9c1 51                 $lastk = $k;
T 52             }
53         }
54
0389fa 55         $start = $this->run_log[$lastk]['time'];
AM 56         $this->run_log[$lastk]['duration'] = microtime(true) - $start;
57         $this->run_log[$lastk]['ended'] = true;
58         $this->run_log[] = array(
59                 'type'     => 'end',
60                 'tag'      =>  $this->run_log[$lastk]['tag'],
61                 'index'    => $lastk,
62                 'value'    => $name,
63                 'time'     => microtime(true),
64                 'duration' => microtime(true) - $start,
65                 'parents'  => $this->parent_stack,
66         );
67
48e9c1 68         $this->indent--;
0389fa 69         if ($this->run_log[$lastk]['duration'] >= $this->threshold) {
48e9c1 70             $tag_report = "";
0389fa 71             foreach($this->tag_count as $tag => $count){
48e9c1 72                 $tag_report .= "$tag: $count, ";
T 73             }
0389fa 74             if (!empty($tag_report)) {
48e9c1 75 //                $tag_report = "\n$tag_report\n";
T 76             }
0389fa 77             $end_txt = sprintf("end: $name - %0.4f seconds $tag_report", $this->run_log[$lastk]['duration']);
AM 78             $this->print_to_console($end_txt, $this->run_log[$lastk]['tag'], 'end');
48e9c1 79             $this->print_to_file($end_txt,  $this->run_log[$lastk]['tag'], 'end');
T 80         }
81     }
82
0389fa 83     public function increase_tag_count($tag)
AM 84     {
85         if (!isset($this->tag_count[$tag])) {
86             $this->tag_count[$tag] = 0;
87         }
88
89         $this->tag_count[$tag]++;
48e9c1 90     }
T 91
0389fa 92     public function get_text()
AM 93     {
48e9c1 94         $text = "";
0389fa 95         foreach ($this->run_log as $entry){
AM 96             $text .= str_repeat("   ",count($entry['parents']));
97             if ($entry['tag'] != 'text'){
98                 $text .= $entry['tag'].': ';
99             }
100             $text .= $entry['value'];
48e9c1 101
0389fa 102             if ($entry['tag'] == 'end') {
AM 103                 $text .= sprintf(" - %0.4f seconds", $entry['duration']);
104             }
48e9c1 105
0389fa 106             $text .= "\n";
48e9c1 107         }
0389fa 108
48e9c1 109         return $text;
T 110     }
111
0389fa 112     public function set_file($filename, $tag = 'master')
AM 113     {
114         if (!isset($this->file_handle[$tag])) {
48e9c1 115             $this->file_handles[$tag] = fopen($filename, 'a');
0389fa 116             if (!$this->file_handles[$tag]) {
48e9c1 117                 trigger_error('Could not open file for writing: '.$filename);
T 118             }
119         }
120     }
121
0389fa 122     public function note($msg, $tag = false)
48e9c1 123     {
0389fa 124         if ($tag) {
48e9c1 125             $this->increase_tag_count($tag);
T 126         }
0389fa 127         if (is_array($msg)) {
AM 128             $msg = '<pre>' . print_r($msg, true) . '</pre>';
48e9c1 129         }
T 130         $this->debug_messages[] = $msg;
0389fa 131         $this->run_log[] = array(
AM 132                 'type'    => 'note',
9f1f75 133                 'tag'     => $tag ?: 'text',
0389fa 134                 'value'   => htmlentities($msg),
AM 135                 'time'    => microtime(true),
136                 'parents' => $this->parent_stack,
137         );
48e9c1 138
0389fa 139         $this->print_to_file($msg, $tag);
AM 140         $this->print_to_console($msg, $tag);
48e9c1 141     }
T 142
0389fa 143     public function print_to_file($msg, $tag = false, $type = false)
AM 144     {
145         if (!$tag) {
146             $file_handle_tag = 'master';
48e9c1 147         }
0389fa 148         else{
AM 149             $file_handle_tag = $tag;
150         }
151
152         if ($file_handle_tag != 'master' && isset($this->file_handles[$file_handle_tag])) {
153             $buffer = $this->get_indent();
154             $buffer .= "$msg\n";
155             if (!empty($this->timestamp)) {
156                 $buffer = sprintf("[%s] %s",date($this->timestamp, time()), $buffer);
157             }
158             fwrite($this->file_handles[$file_handle_tag], wordwrap($buffer, $this->max_line_size, "\n     "));
159         }
160
161         if (isset($this->file_handles['master']) && $this->file_handles['master']) {
162             $buffer = $this->get_indent();
163             if ($tag) {
164                 $buffer .= "$tag: ";
165             }
166             $msg = str_replace("\n","",$msg);
167             $buffer .= "$msg";
168             if (!empty($this->timestamp)) {
169                 $buffer = sprintf("[%s] %s",date($this->timestamp, time()), $buffer);
170             }
171             if(strlen($buffer) > $this->max_line_size){
172                 $buffer = substr($buffer,0,$this->max_line_size - 3) . "...";
173             }
174             fwrite($this->file_handles['master'], $buffer."\n");
175         }
48e9c1 176     }
T 177
0389fa 178     public function print_to_console($msg, $tag = false)
AM 179     {
180         if ($this->print_to_console) {
181             if (is_array($this->print_to_console)) {
182                 if (in_array($tag, $this->print_to_console)) {
48e9c1 183                     echo $this->get_indent();
0389fa 184                     if ($tag) {
48e9c1 185                         echo "$tag: ";
T 186                     }
187                     echo "$msg\n";
188                 }
189             }
0389fa 190             else {
48e9c1 191                 echo $this->get_indent();
0389fa 192                 if ($tag) {
48e9c1 193                     echo "$tag: ";
T 194                 }
195                 echo "$msg\n";
196             }
197         }
198     }
199
0389fa 200     public function print_totals()
AM 201     {
48e9c1 202         $totals = array();
2193f6 203         foreach ($this->run_log as $entry) {
0389fa 204             if ($entry['type'] == 'start' && $entry['ended']) {
48e9c1 205                 $totals[$entry['value']]['duration'] += $entry['duration'];
T 206                 $totals[$entry['value']]['count'] += 1;
207             }
208         }
0389fa 209
AM 210         if ($this->file_handle) {
211             foreach ($totals as $name => $details) {
212                 fwrite($this->file_handle,$name.": ".number_format($details['duration'],4)."sec,  ".$details['count']." calls \n");
213             }
48e9c1 214         }
T 215     }
216
0389fa 217     private function get_indent()
AM 218     {
219         $buf = "";
220         for ($i = 0; $i < $this->indent; $i++) {
221             $buf .= "  ";
222         }
223         return $buf;
48e9c1 224     }
T 225
226
0389fa 227     function  __destruct()
AM 228     {
229         foreach ($this->file_handles as $handle) {
48e9c1 230             fclose($handle);
T 231         }
232     }
233 }