Skip to content

Commit

Permalink
Moved to Severity level based schema
Browse files Browse the repository at this point in the history
  • Loading branch information
lishid committed Mar 28, 2014
1 parent ea53263 commit 38e7081
Show file tree
Hide file tree
Showing 32 changed files with 703 additions and 525 deletions.
5 changes: 2 additions & 3 deletions app/com/linkedin/drelephant/DrElephant.java
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@
import com.linkedin.drelephant.hadoop.HadoopJobData;
import org.apache.hadoop.mapred.JobID;

import java.io.File;
import java.io.IOException;

public class DrElephant extends Thread {
Expand All @@ -23,8 +22,8 @@ public static void analyse(String jobId) throws IOException {
ElephantFetcher fetcher = new ElephantFetcher();
HadoopJobData jobData = fetcher.getJobData(job_id);
ElephantAnalyser analyser = new ElephantAnalyser();
HeuristicResult result = analyser.analyse(jobData);
System.out.println(result.getMessage());
HeuristicResult[] result = analyser.analyse(jobData);
//System.out.println(result);
}

public DrElephant() throws IOException {
Expand Down
28 changes: 12 additions & 16 deletions app/com/linkedin/drelephant/ElephantAnalyser.java
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

import com.linkedin.drelephant.analysis.Heuristic;
import com.linkedin.drelephant.analysis.HeuristicResult;
import com.linkedin.drelephant.analysis.Severity;
import com.linkedin.drelephant.analysis.heuristics.*;
import com.linkedin.drelephant.hadoop.HadoopJobData;
import org.apache.log4j.Logger;
Expand All @@ -13,35 +14,30 @@ public class ElephantAnalyser {
private static final Logger logger = Logger.getLogger(ElephantAnalyser.class);
private static final ElephantAnalyser instance = new ElephantAnalyser();

private HeuristicResult nodata;
private List<Heuristic> heuristics = new ArrayList<Heuristic>();


public ElephantAnalyser() {
nodata = new HeuristicResult("No data received", Severity.LOW);
heuristics.add(new MapperDataSkewHeuristic());
heuristics.add(new ReducerDataSkewHeuristic());
heuristics.add(new UnsplittableFilesHeuristic());
heuristics.add(new SmallFilesHeuristic());
heuristics.add(new GeneralMapperSlowHeuristic());
heuristics.add(new ReducerRuntimeTooShortHeuristic());
heuristics.add(new ReducerRuntimeTooLongHeuristic());
heuristics.add(new SlowShuffleSortHeuristic());
heuristics.add(new MapperInputSizeHeuristic());
heuristics.add(new MapperSpeedHeuristic());
heuristics.add(new ReducerTimeHeuristic());
heuristics.add(new ShuffleSortHeuristic());
}

public HeuristicResult analyse(HadoopJobData data) {
public HeuristicResult[] analyse(HadoopJobData data) {
if (data.getMapperData().length == 0 && data.getReducerData().length == 0) {
return new HeuristicResult("No mapper/reducer data received", true);
return new HeuristicResult[]{nodata};
}

HeuristicResult result = null;
List<HeuristicResult> results = new ArrayList<HeuristicResult>();
for (Heuristic heuristic : heuristics) {
//Apply each heuristic
result = heuristic.apply(data);
//Cannot continue, return the response
if (!result.succeeded()) {
break;
}
results.add(heuristic.apply(data));
}
return result;
return results.toArray(new HeuristicResult[results.size()]);
}

public static ElephantAnalyser instance() {
Expand Down
37 changes: 25 additions & 12 deletions app/com/linkedin/drelephant/ElephantRunner.java
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,15 @@

import com.linkedin.drelephant.analysis.Constants;
import com.linkedin.drelephant.analysis.HeuristicResult;
import com.linkedin.drelephant.analysis.Severity;
import com.linkedin.drelephant.hadoop.HadoopJobData;
import model.AnalysisResult;
import model.JobHeuristicResult;
import model.JobResult;
import org.apache.hadoop.mapred.JobID;
import org.apache.hadoop.mapred.JobStatus;
import org.apache.log4j.Logger;

import java.io.File;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.Set;
import java.util.concurrent.atomic.AtomicBoolean;
Expand Down Expand Up @@ -91,7 +93,7 @@ private Set<JobID> filterPreviousJobs(Set<JobID> jobs, Set<JobID> previousJobs)
if (firstRun) {
Set<JobID> newJobs = new HashSet<JobID>();
for (JobID jobId : jobs) {
AnalysisResult prevResult = AnalysisResult.find.byId(jobId.toString());
JobResult prevResult = JobResult.find.byId(jobId.toString());
if (prevResult == null) {
//Job not found, add to new jobs list
newJobs.add(jobId);
Expand Down Expand Up @@ -121,29 +123,40 @@ private void analyzeJob(ElephantFetcher fetcher, JobID jobId) throws Exception {
return;
}

HeuristicResult analysisResult = ElephantAnalyser.instance().analyse(jobData);
HeuristicResult[] analysisResults = ElephantAnalyser.instance().analyse(jobData);

//Save to DB
AnalysisResult result = new AnalysisResult();
JobResult result = new JobResult();
result.job_id = jobId.toString();
result.success = analysisResult.succeeded();
result.url = jobData.getUrl();
result.username = jobData.getUsername();
result.message = analysisResult.getMessage();
result.data = analysisResult.getDetailsCSV();
result.dataColumns = analysisResult.getDetailsColumns();
result.startTime = jobData.getStartTime();
result.analysisTime = System.currentTimeMillis();
result.jobName = jobData.getJobName();

//Truncate long names
if (result.jobName.length() > 100) {
result.jobName = result.jobName.substring(0, 97) + "...";
}

if (result.dataColumns < 1) {
result.dataColumns = 1;
result.heuristicResults = new ArrayList<JobHeuristicResult>();

Severity worstSeverity = Severity.NONE;

for (HeuristicResult heuristicResult : analysisResults) {
JobHeuristicResult detail = new JobHeuristicResult();
detail.analysisName = heuristicResult.getAnalysis();
detail.data = heuristicResult.getDetailsCSV();
detail.dataColumns = heuristicResult.getDetailsColumns();
detail.severity = heuristicResult.getSeverity();
if (detail.dataColumns < 1) {
detail.dataColumns = 1;
}
result.heuristicResults.add(detail);
worstSeverity = Severity.max(worstSeverity, detail.severity);
}

result.severity = worstSeverity;

result.save();
}

Expand Down
56 changes: 11 additions & 45 deletions app/com/linkedin/drelephant/analysis/HeuristicResult.java
Original file line number Diff line number Diff line change
@@ -1,61 +1,27 @@
package com.linkedin.drelephant.analysis;

import java.util.*;
import java.util.ArrayList;
import java.util.List;

public class HeuristicResult {
public static final HeuristicResult SUCCESS = new HeuristicResult("Everything looks good", true);
public static final List<String> possibleResults = new ArrayList<String>();
public static final Set<String> possibleResultsSet = new HashSet<String>();

public static String addPossibleMapperResult(String message) {
return addPossibleResult(MapReduceSide.MAP, message);
}

public static String addPossibleReducerResult(String message) {
return addPossibleResult(MapReduceSide.REDUCE, message);
}

private static String addPossibleResult(MapReduceSide side, String message) {
message = side.getName() + message;
possibleResultsSet.add(message);
possibleResults.clear();
possibleResults.addAll(possibleResultsSet);
Collections.sort(possibleResults);
return message;
}

private static enum MapReduceSide {
MAP("Mapper side "),
REDUCE("Reducer side ");

private String name;

MapReduceSide(String name) {
this.name = name;
}

public String getName() {
return name;
}
}

private String message;
private String analysis;
private Severity severity;
private List<String> details;
private int detailsColumns = 0;
private boolean success;

public HeuristicResult(String message, boolean success) {
this.message = message;
public HeuristicResult(String analysis, Severity severity) {
this.analysis = analysis;
this.severity = severity;
this.details = new ArrayList<String>();
this.success = success;
}

public boolean succeeded() {
return success;
public String getAnalysis() {
return analysis;
}

public String getMessage() {
return message;
public Severity getSeverity() {
return severity;
}

/**
Expand Down
105 changes: 105 additions & 0 deletions app/com/linkedin/drelephant/analysis/Severity.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,105 @@
package com.linkedin.drelephant.analysis;

import com.avaje.ebean.annotation.EnumValue;

public enum Severity {
@EnumValue("4")
CRITICAL(4, "Critical", "danger"),

@EnumValue("3")
SEVERE(3, "Severe", "severe"),

@EnumValue("2")
MODERATE(2, "Moderate", "warning"),

@EnumValue("1")
LOW(1, "Low", "success"),

@EnumValue("0")
NONE(0, "None", "success");

private int value;
private String text;
private String color;

Severity(int value, String text, String color) {
this.value = value;
this.text = text;
this.color = color;
}

public int getValue() {
return value;
}

public String getText() {
return text;
}

public String getColor() {
return color;
}

public static Severity byValue(int value) {
for (Severity severity : values()) {
if (severity.value == value) {
return severity;
}
}
return NONE;
}

public static Severity max(Severity a, Severity b) {
if (a.value > b.value) {
return a;
}
return b;
}

public static Severity max(Severity... severities) {
Severity currentSeverity = NONE;
for (Severity severity : severities) {
currentSeverity = max(currentSeverity, severity);
}
return currentSeverity;
}

public static Severity min(Severity a, Severity b) {
if (a.value < b.value) {
return a;
}
return b;
}

public static Severity getSeverityAscending(long value, long low, long moderate, long severe, long critical) {
if (value >= critical) {
return CRITICAL;
}
if (value >= severe) {
return SEVERE;
}
if (value >= moderate) {
return MODERATE;
}
if (value >= low) {
return LOW;
}
return NONE;
}

public static Severity getSeverityDescending(long value, long low, long moderate, long severe, long critical) {
if (value <= critical) {
return CRITICAL;
}
if (value <= severe) {
return SEVERE;
}
if (value <= moderate) {
return MODERATE;
}
if (value <= low) {
return LOW;
}
return NONE;
}
}

This file was deleted.

Loading

0 comments on commit 38e7081

Please sign in to comment.