function getChartData(array &$chartData, array &$contents, $patchIt = true) { //need to know depth of log file (numer of data points) $depth = $this->logFileDepth; //select 6,12 or 24 hour charts, 24 is default $dataSet = LoadAvg::$_settings->general['settings']['chart_type']; //echo 'dataSet ' . $dataSet . '<br>'; // this is based on logger interval of 5, 5 min = 300 aprox we add 100 to be safe //$interval = 360; // 5 minutes is 300 seconds + slippage of 20% aprox $interval = $this->getLoggerInterval(); $interval = $interval * 1.2; //add 20% to interval for system lag //get size of array for parsing $totalContents = (int) count($contents); //echo 'TOTAL ' . $totalContents; //trim the dataset if we are only reading 6 or 12 hours of info //revise for 6 and 12 hour charts if ($dataSet == 6 || $dataSet == 12) { //logger is every 5 min then $this->getLoggerInterval() / 60 = 5; //so 300 / 60 = 5 min; 60 / 5 = 12 datasets per hour $dataFrame = 60 / ($this->getLoggerInterval() / 60); $dataNeeded = $dataFrame * $dataSet; //TODO: only trim if there is more than we need... $contents = array_slice($contents, $totalContents - $dataNeeded); } //contents is a array of strings for the dataset/logfile with the charts log data //we explode each value in each line of the array into datapoints in chartData //and send it back as a array! $patch = $chartData = array(); $numPatches = 0; //delimiter is based on logger type used to explode data $delimiter = LoadUtility::getDelimiter(); //if there is only one item in data set then we just chart it and return if ($totalContents == 1) { $data = explode($delimiter, $contents[0]); LoadUtility::cleanDataPoint($data, $depth); $chartData[0] = $data; } else { //subtract one from totalContents as arrays start at 0 not 1 for ($i = 0; $i < $totalContents; ++$i) { //grab the first dataset $data = explode($delimiter, $contents[$i]); LoadUtility::cleanDataPoint($data, $depth); $chartData[$i] = $data; /* * if there is more than one item in dataset then we can check for downtime between points * and patch the dataset so they render ok * this is becuase when rendering we connect lines in the chart (prev to next) * and so downtime comes across as span not a null or 0 * * check if difference is more than logging interval and patch for when server is offline * we patch for time between last data (system went down) and next data (system came up) * need to check if we need the nextData patch as well ie if system came up within * the next interval time * * for local data we dont check the first value in the data set as if its there it means it was up */ if ($i > 0 && $i < $totalContents - 1) { //dont do this for last value in dataset! as it will have no difference $nextData = explode($delimiter, $contents[$i + 1]); //difference in timestamps $difference = $nextData[0] - $data[0]; //if more time that the logging interval has passed it means //the system was down as logger should send data every interval if ($difference >= $interval) { //$chartData[$i-1]['redline'] = true; //echo 'patch difference:' . $difference; //patches are spans ie fall between datapoints //so each patch has a start and end $patch[$numPatches] = array($data[0] + $interval, "REDLINE", $i); $patch[$numPatches + 1] = array($nextData[0] - $interval / 2, "REDLINE", $i); $numPatches += 2; } } } } //if there are patches to be applied, we iterate through the patcharray //and patch the dataset by inserting patch spans into it based on time $totalPatch = (int) count($patch); if ($totalPatch > 0 && $patchIt == true) { //echo "PATCHCOUNT: " . $totalPatch . "<br>"; for ($i = 0; $i < $totalPatch; ++$i) { //patch time is really patch key position in array $patch_key_position = $patch[$i][2] + $i; $newdata[0] = strval($patch[$i][0]); $thepatch[0] = array_pad($newdata, $depth + 1, '0.0'); $thepatch[0]['redline'] = true; //echo '<pre>patch'; var_dump ($thepatch); echo '</pre>'; array_splice($chartData, $patch_key_position, 0, $thepatch); //echo "PATCHED: " . $patch_key_position . " count: " . count( $chartData ) . "<br>"; } } //echo '<pre>'; var_dump ($chartData); echo '</pre>'; }
/** * getUsageData * * Gets data from logfile, formats and parses it to pass it to the chart generating function * * @return array $return data retrived from logfile * */ public function getUsageData($logfile) { $class = __CLASS__; $settings = LoadPlugins::$_settings->{$class}; //define some core variables here $dataArray = $dataArrayLabel = array(); $dataRedline = $usage = array(); /* * grab the log file data needed for the charts as array of strings * takes logfiles(s) and gives us back contents */ $contents = array(); $logStatus = LoadUtility::parseLogFileData($logfile, $contents); //echo '<pre> :: '; var_dump ($contents); echo '</pre>'; /* * build the chartArray array here as array of arrays needed for charting * takes in contents and gives us back chartArray */ $chartArray = array(); $sizeofChartArray = 0; $chartData = array(); //delimiter is based on logger type used to explode data $delimiter = LoadUtility::getDelimiter(); $delimiter = "|"; //takes the log file and parses it into chartable data //echo '<pre> :: <br>'; if ($logStatus) { //$this->getChartData ($chartArray, $contents, false ); $totalContents = (int) count($contents); for ($i = 0; $i < $totalContents; ++$i) { //grab the first dataset $data = explode($delimiter, $contents[$i]); //echo $data[0] . " " . $data[1] . " " . $data[2] . "<br>"; $chartData[$i] = $data; } } return $chartData; }
/** * parseComplexLogFiles * * when dealing with complex log files ie log data split across multiple files * we need to read in all parts, parse to arrays and then merge them togeather * into a single array as loadavg charts work with a single array of log data only! * currently a bit of a mission! * */ public static function parseComplexLogFiles($mycontents, $arraysize) { //fist we have to loop through each data set in each log file //as per the depth of the array (number of files) parse it and then //stitch it back up into the newDataArray //now we loop through multiple mycontents array break out data values $thenewarray = array(); //delimiter is based on logger type $delimiter = LoadUtility::getDelimiter(); //main loop is number of datasets to me merged togeather for ($dataloop = 0; $dataloop < $arraysize; $dataloop++) { $finaldata = ""; //this builds the array $loop = 0; foreach ($mycontents[$dataloop] as &$value) { $thedata = explode($delimiter, $value); //for first data set grab timestamp if ($dataloop == 0) { $thenewarray[0][$loop] = isset($thedata[0]) ? $thedata[0] : null; } //all other data sets its the 2nd value $thenewarray[$dataloop + 1][$loop] = isset($thedata[1]) ? $thedata[1] : null; $loop++; } unset($value); } //now rebuild data into $thenewarray as a single array - stitch it back up $loop = 0; foreach ($thenewarray[0] as &$value) { $dataString = ""; for ($dataloop = 0; $dataloop <= $arraysize; $dataloop++) { $dataString .= $thenewarray[$dataloop][$loop] . ","; } //need to kill the last "," here as its not needed ? $dataString = substr($dataString, 0, -1); $finaldata[$loop] = $dataString; $loop++; } unset($value); return $finaldata; }