All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.perf4j.LogParser Maven / Gradle / Ivy

Go to download

Performance statistics logging and monitoring toolkit extension to log4j and the java.util.logging framework.

There is a newer version: 0.9.16
Show newest version
/* Copyright (c) 2008-2009 HomeAway, Inc.
 * All rights reserved.  http://www.perf4j.org
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package org.perf4j;

import org.perf4j.helpers.GroupingStatisticsIterator;
import org.perf4j.helpers.StopWatchLogIterator;
import org.perf4j.helpers.StatsValueRetriever;
import org.perf4j.chart.StatisticsChartGenerator;
import org.perf4j.chart.GoogleChartGenerator;

import java.io.*;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Iterator;
import java.util.List;

/**
 * LogParser provides the main method for reading a log of StopWatch output and generating statistics and graphs
 * from that output. Run "java -cp pathToPerf4jJar org.per4j.LogParser --help" for instructions.
 *
 * @author Alex Devine
 */
public class LogParser {
    /**
     * The input log that is being parsed.
     */
    private Reader inputLog;
    /**
     * The stream where the GroupedTimingStatistics data will be printed - if null, no statistics will be printed
     */
    private PrintStream statisticsOutput;
    /**
     * The stream where graphing output will be printed - if null, no graphing output will be printed. May be the
     * same stream as statisticsOutput.
     */
    private PrintStream graphingOutput;
    /**
     * The chart generator used to send the mean time graph to graphingOutput.
     */
    private StatisticsChartGenerator meanTimeChartGenerator;
    /**
     * The chart generator used to send the TPS graph to graphingOutput.
     */
    private StatisticsChartGenerator tpsChartGenerator;
    /**
     * The length of time, in milliseconds, of the timeslice of each GroupedTimingStatistics.
     */
    private long timeSlice;
    /**
     * Whether or not "rollup statistics" should be created for each GroupedTimingStatistics created.
     */
    private boolean createRollupStatistics;

    // --- Constructors ---
    /**
     * Default constructor reads input from standard in, writes statistics output to standard out, does not write
     * graph output, has a time slice window of 30 seconds, and does not create rollup statistics.
     */
    public LogParser() {
        this(new InputStreamReader(System.in), System.out, null, 30000L, false);
    }

    /**
     * Creates a new LogParser to parse log data from the input.
     *
     * @param inputLog               The log being parsed, which should contain {@link org.perf4j.StopWatch} log messages.
     * @param statisticsOutput       The stream where calculated statistics information should be written - if null,
     *                               statistics data is not written.
     * @param graphingOutput         The stream where graphing data should be written - if null, graphs are not written.
     * @param timeSlice              The length of time, in milliseconds, of the timeslice of each statistics data created.
     * @param createRollupStatistics Whether or not "rollup statistics" should be created for each timeslice of data.
     */
    public LogParser(Reader inputLog, PrintStream statisticsOutput, PrintStream graphingOutput,
                     long timeSlice, boolean createRollupStatistics) {
        this.inputLog = inputLog;
        this.statisticsOutput = statisticsOutput;
        this.graphingOutput = graphingOutput;
        this.timeSlice = timeSlice;
        this.createRollupStatistics = createRollupStatistics;
        if (graphingOutput != null) {
            this.meanTimeChartGenerator = newMeanTimeChartGenerator();
            this.tpsChartGenerator = newTpsChartGenerator();
        }
    }

    // --- Instance Methods ---

    /**
     * Reads all the data from the inputLog, parses it, and writes the statistics data and graphing data as desired
     * to the output streams.
     */
    public void parseLog() {

        Iterator stopWatchIter = new StopWatchLogIterator(inputLog);

        int i = 0;
        for (GroupingStatisticsIterator statsIter = new GroupingStatisticsIterator(stopWatchIter,
                                                                                   timeSlice,
                                                                                   createRollupStatistics);
             statsIter.hasNext();) {
            GroupedTimingStatistics statistics = statsIter.next();

            if (statisticsOutput != null) {
                statisticsOutput.println(statistics.toString());
            }

            if (graphingOutput != null) {
                meanTimeChartGenerator.appendData(statistics);
                tpsChartGenerator.appendData(statistics);
                if ((++i % StatisticsChartGenerator.DEFAULT_MAX_DATA_POINTS == 0) ||
                    (!statsIter.hasNext())) {
                    printGraphOutput();
                }
            }
        }
    }

    protected StatisticsChartGenerator newMeanTimeChartGenerator() {
        return new GoogleChartGenerator();
    }

    protected StatisticsChartGenerator newTpsChartGenerator() {
        return new GoogleChartGenerator(StatsValueRetriever.TPS_VALUE_RETRIEVER);
    }

    protected void printGraphOutput() {
        graphingOutput.println("

"); graphingOutput.println("

"); } // --- Main and Static Methods --- public static void main(String[] args) { System.exit(runMain(args)); } public static int runMain(String[] args) { try { List argsList = new ArrayList(Arrays.asList(args)); if (printUsage(argsList)) { return 0; } PrintStream statisticsOutput = openStatisticsOutput(argsList); PrintStream graphingOutput = openGraphingOutput(argsList); long timeSlice = getTimeSlice(argsList); boolean rollupStatistics = getRollupStatistics(argsList); Reader input = openInput(argsList); if (!argsList.isEmpty()) { printUnknownArgs(argsList); return 1; } new LogParser(input, statisticsOutput, graphingOutput, timeSlice, rollupStatistics).parseLog(); closeGraphingOutput(graphingOutput); } catch ( Exception e ) { e.printStackTrace(); return 1; } return 0; } protected static boolean printUsage(List argsList) { if (getIndexOfArg(argsList, false, "-h", "--help", "-?", "--usage") >= 0) { System.out.println("Usage: LogParser [-o|--out|--output outputFile] " + "[-g|--graph graphingOutputFile] " + "[-t|--timeslice timeslice] " + "[-r] [logInputFile]"); System.out.println("Arguments:"); System.out.println(" logInputFile - The log file to be parsed. If not specified, log data is read from stdin."); System.out.println(" -o|--out|--output outputFile - The file where generated statistics should be written." + " If not specified, statistics are written to stdout."); System.out.println(" -g|--graph graphingOutputFile - The file where generated perf graphs should be written." + " If not specified, no graphs are written."); System.out.println(" -t|--timeslice timeslice - The length of time (in ms) of each timeslice for which" + " statistics should be generated. Defaults to 30000 ms."); System.out.println(" -r - Whether or not statistics rollups should be generated." + " If not specified, rollups are not generated."); System.out.println(); System.out.println("Note that out, stdout, err and stderr can be used as aliases to the standard output" + " streams when specifying output files."); return true; } return false; } protected static PrintStream openStatisticsOutput(List argsList) throws IOException { int indexOfOut = getIndexOfArg(argsList, true, "-o", "--output", "--out"); if (indexOfOut >= 0) { String fileName = argsList.remove(indexOfOut + 1); argsList.remove(indexOfOut); return openStream(fileName); } else { return System.out; } } protected static PrintStream openGraphingOutput(List argsList) throws IOException { int indexOfOut = getIndexOfArg(argsList, true, "-g", "--graph"); if (indexOfOut >= 0) { String fileName = argsList.remove(indexOfOut + 1); argsList.remove(indexOfOut); PrintStream retVal = openStream(fileName); retVal.println(""); retVal.println("<span class="hljs-string">Perf4J Performance Graphs</span>"); retVal.println(""); return retVal; } else { return null; } } protected static void closeGraphingOutput(PrintStream graphingOutput) throws IOException { if (graphingOutput != null) { graphingOutput.println(""); if (graphingOutput != System.out && graphingOutput != System.err) { graphingOutput.close(); } } } protected static long getTimeSlice(List argsList) { int indexOfOut = getIndexOfArg(argsList, true, "-t", "--timeslice"); if (indexOfOut >= 0) { String timeslice = argsList.remove(indexOfOut + 1); argsList.remove(indexOfOut); return Long.parseLong(timeslice); } else { return 30000L; } } protected static boolean getRollupStatistics(List argsList) { int indexOfOut = getIndexOfArg(argsList, false, "-r", "--rollup"); if (indexOfOut >= 0) { argsList.remove(indexOfOut); return true; } else { return false; } } protected static Reader openInput(List argsList) throws IOException { if (argsList.isEmpty()) { return new InputStreamReader(System.in); } else { String fileName = argsList.remove(0); return new BufferedReader(new FileReader(fileName)); } } protected static void printUnknownArgs(List argsList) { System.out.println("Unknown arguments: "); for (String arg : argsList) { System.out.print(arg + " "); } System.out.println(); } protected static int getIndexOfArg(List args, boolean needsParam, String... argNames) { int retVal = -1; boolean foundArg = false; for (String argName : argNames) { int argIndex = args.indexOf(argName); if (argIndex >= 0) { if (foundArg) { throw new IllegalArgumentException("You must specify only one of " + Arrays.toString(argNames)); } retVal = argIndex; foundArg = true; } } if ((retVal >= 0) && needsParam && (retVal == args.size() - 1)) { throw new IllegalArgumentException("You must specify a parameter for the " + args.get(retVal) + " arg"); } return retVal; } protected static PrintStream openStream(String fileName) throws IOException { if ("stdout".equals(fileName) || "out".equals(fileName)) { return System.out; } else if ("stderr".equals(fileName) || "err".equals(fileName)) { return System.err; } else { return new PrintStream(new FileOutputStream(fileName), true); } } }




© 2015 - 2025 Weber Informatics LLC | Privacy Policy