source: trunk/web/addons/toga/toga-functions.php @ 107

Last change on this file since 107 was 107, checked in by bastiaans, 18 years ago

toga/toga-functions.php:

  • First working clusterimage
File size: 9.6 KB
Line 
1<?php
2$GANGLIA_PATH = "/var/www/ganglia";
3
4include_once "$GANGLIA_PATH/conf.php";
5include_once "$GANGLIA_PATH/functions.php";
6
7if ( !empty( $_GET ) ) {
8        extract( $_GET );
9}
10
11class HTTPVariables {
12
13        var $clustername, $metricname;
14
15        function HTTPVariables() {
16
17                global $HTTP_GET_VARS;
18
19                $this->clustername = $HTTP_GET_VARS["c"] ? $HTTP_GET_VARS["c"] : null;
20                $this->metricname = $HTTP_GET_VARS["m"] ? $HTTP_GET_VARS["m"] : null;
21        }
22
23        function getClusterName() {
24                return $this->clustername;
25        }
26
27        function getMetricName() {
28                return $this->metricname;
29        }
30}
31
32class DataSource {
33
34        var $data, $ip, $port;
35
36        function DataSource( $ip = '127.0.0.1', $port = 8649 ) {
37                $this->ip = $ip;
38                $this->port = $port;
39        }
40
41        function getData() {
42
43                $errstr;
44                $errno = 0;
45                $timeout = 3;
46
47                $fp = fsockopen( $this->ip, $this->port, &$errno, &$errstr, $timeout );
48
49                if( !$fp ) {
50                        echo 'Unable to connect to '.$this->ip.':'.$this->port; // printf( 'Unable to connect to [%s:%.0f]', $this->ip, $this->port );
51                        return;
52                }
53
54                while ( !feof( $fp ) ) {
55                       
56                        $data .= fread( $fp, 16384 );
57                }
58
59                fclose( $fp );
60
61                return $data;
62        }
63}
64
65class DataGatherer {
66
67        var $xmlhandler, $data, $httpvars;
68
69        function DataGatherer() {
70
71                $this->parser = xml_parser_create();
72                $this->source = new DataSource();
73                $this->httpvars = new HTTPVariables();
74                $this->xmlhandler = new TorqueXMLHandler();
75                xml_set_element_handler( $this->parser, array( &$this->xmlhandler, 'startElement' ), array( &$this->xmlhandler, 'stopElement' ) );
76        }
77
78        function parseXML() {
79
80                $src = &$this->source;
81                $this->data = $src->getData();
82
83                if ( !xml_parse( &$this->parser, $this->data ) ) {
84                        $error = sprintf( 'XML error: %s at %d', xml_error_string( xml_get_error_code( &$this->parser ) ), xml_get_current_line_number( &$this->parser ) );
85                        // die( $error );
86                }
87        }
88
89        function printInfo() {
90                $handler = $this->xmlhandler;
91                $handler->printInfo();
92        }
93
94        function getNodes() {
95                $handler = $this->xmlhandler;
96                return $handler->getNodes();
97        }
98
99        function getJobs() {
100                $handler = $this->xmlhandler;
101                return $handler->getJobs();
102        }
103
104}
105
106class TorqueXMLHandler {
107
108        var $clusters, $heartbeat, $nodes, $jobs;
109
110        function TorqueXMLHandler() {
111                $jobs = array();
112                $clusters = array();
113                $nodes = array();
114                $heartbeat = array();
115        }
116
117        function gotNode( $hostname, $location = 'unspecified', $jobid = null ) {
118
119                $nodes = &$this->nodes;
120
121                if( !isset( $nodes[$hostname] ) ) {
122
123                        $nodes[$hostname] = new Node( $hostname );
124                }
125
126                if( $location ) {
127
128                        $nodes[$hostname]->setLocation( $location );
129                }
130
131                if( $jobid ) {
132                        $nodes[$hostname]->addJob( $jobid );
133                }
134        }
135
136        function startElement( $parser, $name, $attrs ) {
137
138                $jobs = &$this->jobs;
139
140                if ( $attrs[TN] ) {
141
142                        // Ignore dead metrics. Detect and mask failures.
143                        if ( $attrs[TN] > $attrs[TMAX] * 4 )
144                                return;
145                }
146
147                $jobid = null;
148
149                // printf( '%s=%s', $attrs[NAME], $attrs[VAL] );
150
151                if( $name == 'CLUSTER' ) {
152
153                        $clustername = $attrs[VAL];
154
155                        if( !isset( $clusters[$clustername] ) )
156                                $clusters[$clustername] = array();
157
158                } else if( $name == 'HOST' ) {
159
160                        $hostname = $attrs[NAME];
161                        $location = $attrs[LOCATION];
162
163                        $this->gotNode( $hostname, $location, null );
164
165                } else if( $name == 'METRIC' and strstr( $attrs[NAME], 'TOGA' ) ) {
166
167                        if( strstr( $attrs[NAME], 'TOGA-HEARTBEAT' ) ) {
168
169                                $heartbeat['time'] = $attrs[VAL];
170                                //printf( "heartbeat %s\n", $heartbeat['time'] );
171
172                        } else if( strstr( $attrs[NAME], 'TOGA-JOB' ) ) {
173
174                                sscanf( $attrs[NAME], 'TOGA-JOB-%d', $jobid );
175
176                                //printf( "jobid %s\n", $jobid );
177
178                                if( !isset( $jobs[$jobid] ) )
179                                        $jobs[$jobid] = array();
180
181                                $fields = explode( ' ', $attrs[VAL] );
182
183                                foreach( $fields as $f ) {
184                                        $togavalues = explode( '=', $f );
185
186                                        $toganame = $togavalues[0];
187                                        $togavalue = $togavalues[1];
188
189                                        //printf( "\t%s\t= %s\n", $toganame, $togavalue );
190
191                                        if( $toganame == 'nodes' ) {
192
193                                                if( !isset( $jobs[$jobid][$toganame] ) )
194                                                        $jobs[$jobid][$toganame] = array();
195
196                                                $nodes = explode( ';', $togavalue );
197
198                                                foreach( $nodes as $node ) {
199
200                                                        $hostname = $node.'.'.$jobs[$jobid][domain];
201                                                        $jobs[$jobid][$toganame][] = $hostname;
202                                                        $this->gotNode( $hostname, null, $jobid );
203                                                }
204
205                                        } else {
206
207                                                $jobs[$jobid][$toganame] = $togavalue;
208                                        }
209                                }
210                        }
211                }
212        }
213
214        function stopElement( $parser, $name ) {
215        }
216
217        function printInfo() {
218
219                $jobs = &$this->jobs;
220
221                printf( "---jobs---\n" );
222
223                foreach( $jobs as $jobid => $job ) {
224
225                        printf( "job %s\n", $jobid );
226
227                        if( isset( $job[nodes] ) ) {
228
229                                foreach( $job[nodes] as $node ) {
230
231                                        $mynode = $this->nodes[$node];
232                                        $hostname = $mynode->getHostname();
233                                        $location = $mynode->getLocation();
234
235                                        printf( "\t- node %s\tlocation %s\n", $hostname, $location );
236                                        //$this->nodes[$hostname]->setLocation( "hier draait job ".$jobid );
237                                }
238                        }
239                }
240
241                printf( "---nodes---\n" );
242
243                $nodes = &$this->nodes;
244
245                foreach( $nodes as $node ) {
246
247                        $hostname = $node->getHostname();
248                        $location = $node->getLocation();
249                        $jobs = implode( ' ', $node->getJobs() );
250                        printf( "* node %s\tlocation %s\tjobs %s\n", $hostname, $location, $jobs );
251                }
252        }
253
254        function getNodes() {
255                return $this->nodes;
256        }
257
258        function getJobs() {
259                return $this->jobs;
260        }
261}
262
263class Node {
264
265        var $img, $hostname, $location, $jobs;
266        var $x, $y;
267
268        function Node( $hostname ) {
269
270                $this->hostname = $hostname;
271                //$this->img = new NodeImg();
272                $this->jobs = array();
273        }
274
275        function addJob( $jobid ) {
276                $jobs = &$this->jobs;
277
278                $jobs[] = $jobid;
279        }
280
281        function setLocation( $location ) {
282                $this->location = $location;
283        }
284
285        function setHostname( $hostname ) {
286                $this->hostname = $hostname;
287        }
288
289        function setCpus( $cpus ) {
290                $this->cpus = $cpus;
291        }
292
293        function getHostname() {
294                return $this->hostname;
295        }
296
297        function getLocation() {
298                return $this->location;
299        }
300
301        function getCpus() {
302                return $this->cpus;
303        }
304
305        function getJobs() {
306                return $this->jobs;
307        }
308
309        function setCoords( $x, $y ) {
310                $myimg = $this->img;
311                $myimg->setCoords( $x, $y );
312        }
313
314        function setImage( $image ) {
315                $myimg = $this->img;
316                $myimg->setImage( &$image );
317        }
318
319        function draw() {
320                $myimg = $this->img;
321
322                $cpus = $metrics[$this->hostname]["cpu_num"][VAL];
323                if (!$cpus) $cpus=1;
324                $load_one = $metrics[$this->hostname]["load_one"][VAL];
325                $load = ((float) $load_one)/$cpus;
326
327                $myimg->setLoad( $load );
328                $myimg->draw();
329        }
330}
331
332class NodeImage {
333
334        var $image, $x, $y;
335
336        function NodeImage( $image, $x, $y ) {
337
338                $this->image = $image;
339                $this->x = $x;
340                $this->y = $y;
341        }
342
343        function setCoords( $x, $y ) {
344
345                $this->x = $x;
346                $this->y = $y;
347        }
348
349        function colorHex( $color ) {
350       
351                $my_color = imageColorAllocate( $this->image, hexdec( substr( $color, 0, 2 )), hexdec( substr( $color, 2, 4 )), hexdec( substr( $color, 4, 6 )) );
352
353                return $my_color;
354        }
355
356        function setImage( $image ) {
357                $this->image = $image;
358        }
359
360        function setLoad( $load ) {
361                $this->load = $load;
362        }
363
364        function drawNode( $load ) {
365
366                if( !isset( $this->x ) or !isset( $this->y ) or !isset( $load ) ) {
367                        printf( "aborting\n" );
368                        printf( "x %d y %d load %f\n", $this->x, $this->y, $load );
369                        return;
370                }
371
372                $queue_color = imageColorAllocate( &$this->image, 0, 102, 304 );
373                $job_color = imageColorAllocate( &$this->image, 204, 204, 0 );
374
375                // Convert Ganglias Hexadecimal load color to a Decimal one
376                $my_loadcolor = $this->colorHex( load_color($load) );
377
378                imageFilledRectangle( $this->image, $this->x, $this->y, $this->x+12, $this->y+12, $queuecolor );
379                imageFilledRectangle( $this->image, $this->x+2, $this->y+2, $this->x+10, $this->y+10, $my_loadcolor );
380
381                // Een job markering?
382                //imageFilledEllipse( $this->image, ($this->x+9)/2, ($this->y+9)/2, 6, 6, $jobcolor );
383        }
384
385        function draw() {
386
387                $cpus = $metrics[$this->hostname]["cpu_num"][VAL];
388                if (!$cpus) $cpus=1;
389                $load_one = $metrics[$this->hostname]["load_one"][VAL];
390                $load = ((float) $load_one)/$cpus;
391
392                $this->drawNode( $load );
393        }
394}
395
396class ClusterImage {
397
398        var $dataget, $image;
399
400        function ClusterImage() {
401                $this->dataget = new DataGatherer();
402        }
403
404        function draw() {
405                $mydatag = $this->dataget;
406                $mydatag->parseXML();
407
408                $max_width = 150;
409                $node_width = 12;
410
411                $nodes = $mydatag->getNodes();
412
413                $nodes_nr = count( $nodes );
414                $node_keys = array_keys( $nodes );
415
416                $nodes_size = $nodes_nr*$node_width;
417                $node_rows = 0;
418
419                if( $nodes_size > $max_width ) {
420                        $nodes_per_row = ( (int) ($max_width/$node_width) );
421                } else {
422                        $nodes_per_row = $nodes_size;
423                        $node_rows = 1;
424                }
425
426                if( $nodes_per_row < $nodes_nr ) {
427                        $node_rows = ( (int) ($nodes_nr/$nodes_per_row) );
428                        $node_rest = fmod( $nodes_nr, $nodes_per_row );
429                        //printf( "nodesnr %d noderest %f\n", $nodes_nr, $node_rest );
430                        if( $node_rest > 0 ) {
431                                $node_rows++;
432                                //printf( "noderows %d\n", $node_rows );
433                        }
434                }
435
436                //printf( "imagecreate: %dx%d", ($nodes_per_row*$node_width), ($node_rows*$node_width) );
437                $image = imageCreateTrueColor( ($nodes_per_row*$node_width), ($node_rows*$node_width) );
438                $colorwhite = imageColorAllocate( $image, 255, 255, 255 );
439                imageFill( $image, 0, 0, $colorwhite );
440
441                for( $n = 0; $n < $node_rows; $n++ ) {
442                       
443                        for( $m = 0; $m < $nodes_per_row; $m++ ) {
444                       
445                                $x = ($m * $node_width);
446                                $y = ($n * $node_width);
447
448                                $cur_node = ($n * $nodes_per_row) + ($m + 1);
449                                $host = $node_keys[$cur_node];
450
451                                if( isset( $nodes[$host] ) and ($cur_node <= $nodes_nr) ) {
452                                        $node = new NodeImage( $image, $x, $y );
453                                        $node->draw();
454                                        //$nodes[$host]->setCoords( $x, $y );
455                                        //$nodes[$host]->setImage( &$image );
456                                        //$nodes[$host]->draw();
457                                        //$cur_node++;
458                                }
459                        }
460                }
461               
462                header( 'Content-type: image/png' );
463                imagePNG( $image );
464                imageDestroy( $image );
465        }
466}
467
468//$my_data = new DataGatherer();
469//$my_data->parseXML();
470//$my_data->printInfo();
471
472$ic = new ClusterImage();
473$ic->draw();
474?>
Note: See TracBrowser for help on using the repository browser.