azkaban-aplcache

Combinging Execution and Executor Servlet. I don't know what

9/6/2012 8:01:06 PM

Details

diff --git a/src/java/azkaban/executor/ExecutorManager.java b/src/java/azkaban/executor/ExecutorManager.java
index 4419e70..993f3c5 100644
--- a/src/java/azkaban/executor/ExecutorManager.java
+++ b/src/java/azkaban/executor/ExecutorManager.java
@@ -455,19 +455,9 @@ public class ExecutorManager {
 		flow.setSubmitted(true);
 	}
 	
-	public long getExecutableFlowLog(ExecutableFlow flow, StringBuffer buffer, long startChar, long maxSize) throws ExecutorManagerException {
-		String path = flow.getExecutionPath();
-		File execPath = new File(path);
-		if (!execPath.exists()) {
-			logger.error("Execution dir for " + flow + " doesn't exist.");
-			return -1;
-		}
-		
-		String logFileName = "_flow." + flow.getExecutionId() + ".log";
-		File flowLogFile = new File(execPath, logFileName);
-		
-		if (!flowLogFile.exists()) {
-			logger.error("Execution log for " + flowLogFile + " doesn't exist.");
+	private long readLog(File logFile, StringBuffer buffer, long startChar, long maxSize) {
+		if (!logFile.exists()) {
+			logger.error("Execution log for " + logFile + " doesn't exist.");
 			return -1;
 		}
 		
@@ -476,7 +466,7 @@ public class ExecutorManager {
 		char[] charBuffer = new char[LOG_BUFFER_READ_SIZE];
 		
 		try {
-			fileReader = new FileReader(flowLogFile);
+			fileReader = new FileReader(logFile);
 		} catch (FileNotFoundException e) {
 			e.printStackTrace();
 		}
@@ -514,6 +504,46 @@ public class ExecutorManager {
 		return charPosition;
 	}
 	
+	public long getExecutionJobLog(ExecutableFlow flow, String jobid, StringBuffer buffer, long startChar, long maxSize) throws ExecutorManagerException {
+		String path = flow.getExecutionPath();
+		File execPath = new File(path);
+		if (!execPath.exists()) {
+			logger.error("Execution dir for " + flow + " doesn't exist.");
+			return -1;
+		}
+		
+		String logFileName = "_job." + flow.getExecutionId() + "." + jobid + ".log";
+		File logFile = new File(execPath, logFileName);
+		
+		if (!logFile.exists()) {
+			logger.error("Execution log for " + logFile + " doesn't exist.");
+			return -1;
+		}
+
+		long charPosition = readLog(logFile, buffer, startChar, maxSize);
+		return charPosition;
+	}
+	
+	public long getExecutableFlowLog(ExecutableFlow flow, StringBuffer buffer, long startChar, long maxSize) throws ExecutorManagerException {
+		String path = flow.getExecutionPath();
+		File execPath = new File(path);
+		if (!execPath.exists()) {
+			logger.error("Execution dir for " + flow + " doesn't exist.");
+			return -1;
+		}
+		
+		String logFileName = "_flow." + flow.getExecutionId() + ".log";
+		File flowLogFile = new File(execPath, logFileName);
+		
+		if (!flowLogFile.exists()) {
+			logger.error("Execution log for " + flowLogFile + " doesn't exist.");
+			return -1;
+		}
+
+		long charPosition = readLog(flowLogFile, buffer, startChar, maxSize);
+		return charPosition;
+	}
+	
 	public void cleanupAll(ExecutableFlow exflow) throws ExecutorManagerException{
 		String path = exflow.getExecutionPath();
 		File executionPath = new File(path);
diff --git a/src/java/azkaban/webapp/AzkabanWebServer.java b/src/java/azkaban/webapp/AzkabanWebServer.java
index 173379c..79a14fa 100644
--- a/src/java/azkaban/webapp/AzkabanWebServer.java
+++ b/src/java/azkaban/webapp/AzkabanWebServer.java
@@ -43,8 +43,7 @@ import azkaban.user.XmlUserManager;
 import azkaban.utils.Props;
 import azkaban.utils.Utils;
 import azkaban.webapp.servlet.AzkabanServletContextListener;
-import azkaban.webapp.servlet.ExecutionServlet;
-import azkaban.webapp.servlet.FlowExecutorServlet;
+import azkaban.webapp.servlet.ExecutorServlet;
 import azkaban.webapp.servlet.HistoryServlet;
 import azkaban.webapp.servlet.IndexServlet;
 import azkaban.webapp.servlet.ProjectManagerServlet;
@@ -347,8 +346,7 @@ public class AzkabanWebServer {
 		root.addServlet(staticServlet, "/favicon.ico");
 
 		root.addServlet(new ServletHolder(new ProjectManagerServlet()),"/manager");
-		root.addServlet(new ServletHolder(new FlowExecutorServlet()),"/executor");
-		root.addServlet(new ServletHolder(new ExecutionServlet()),"/executions");
+		root.addServlet(new ServletHolder(new ExecutorServlet()),"/executor");
 		root.addServlet(new ServletHolder(new HistoryServlet()), "/history");
 		
 		root.setAttribute(AzkabanServletContextListener.AZKABAN_SERVLET_CONTEXT_KEY, app);
diff --git a/src/java/azkaban/webapp/servlet/velocity/executingflowpage.vm b/src/java/azkaban/webapp/servlet/velocity/executingflowpage.vm
index 01c69b7..8fe3bf0 100644
--- a/src/java/azkaban/webapp/servlet/velocity/executingflowpage.vm
+++ b/src/java/azkaban/webapp/servlet/velocity/executingflowpage.vm
@@ -44,7 +44,7 @@
 
 				<div id="all-jobs-content">
 					<div class="section-hd flow-header">
-						<h2><a href="${context}/executions?execid=${execid}">Flow Execution <span>$execid</span></a></h2>
+						<h2><a href="${context}/executor?execid=${execid}">Flow Execution <span>$execid</span></a></h2>
 						<div class="section-sub-hd">
 							<h4><a href="${context}/manager?project=${projectName}">Project <span>$projectName</span></a></h4>
 							<h4 class="separator">&gt;</h4>
@@ -58,7 +58,7 @@
 							<li class="lidivider">|</li>
 							<li><a id="jobslistViewLink" href="#jobslist">Job List</a></li>
 							<li class="lidivider">|</li>
-							<li><a id="flowLogViewLink" href="#log">Log</a></li>
+							<li><a id="flowLogViewLink" href="#log">Flow Log</a></li>
 						</ul>
 						<ul id="actionsBtns" class="buttons">
 							<li><div id="pausebtn" class="btn2">Pause</div></li>
@@ -100,7 +100,7 @@
 							</tbody>
 						</table>
 					</div>
-					<div id="flowLogView">
+					<div id="flowLogView" class="logView">
 						<div class="logHeader"><div class="logButtonRow"><div id="updateLogBtn" class="btn7">Load More</div></div></div>
 						<div class="logViewer">
 							<pre id="logSection" class="log"></pre>
diff --git a/src/java/azkaban/webapp/servlet/velocity/executionspage.vm b/src/java/azkaban/webapp/servlet/velocity/executionspage.vm
index 3dd9c6f..2c04c8b 100644
--- a/src/java/azkaban/webapp/servlet/velocity/executionspage.vm
+++ b/src/java/azkaban/webapp/servlet/velocity/executionspage.vm
@@ -50,7 +50,7 @@
 #foreach($flow in $runningFlows)
 						<tr class="row" >
 							<td class="tb-name">
-								<a href="${context}/executions?execid=${flow.executionId}">$utils.extractNumericalId(${flow.executionId})</a>
+								<a href="${context}/executor?execid=${flow.executionId}">$utils.extractNumericalId(${flow.executionId})</a>
 							</td>
 							<td><a href="${context}/manager?project=${flow.projectId}&flow=${flow.flowId}">${flow.flowId}</a></td>
 							<td>
@@ -91,7 +91,7 @@
 #foreach($flow in $recentlyFinished)
 						<tr class="row" >
 							<td class="tb-name">
-								<a href="${context}/executions?execid=${flow.executionId}">$utils.extractNumericalId(${flow.executionId})</a>
+								<a href="${context}/executor?execid=${flow.executionId}">$utils.extractNumericalId(${flow.executionId})</a>
 							</td>
 							<td><a href="${context}/manager?project=${flow.projectId}&flow=${flow.flowId}">${flow.flowId}</a></td>
 							<td>
diff --git a/src/java/azkaban/webapp/servlet/velocity/historypage.vm b/src/java/azkaban/webapp/servlet/velocity/historypage.vm
index 7204cee..1a94a39 100644
--- a/src/java/azkaban/webapp/servlet/velocity/historypage.vm
+++ b/src/java/azkaban/webapp/servlet/velocity/historypage.vm
@@ -54,7 +54,7 @@
 #foreach($flow in $flowHistory)
 						<tr class="row" >
 							<td class="tb-name">
-								<a href="${context}/executions?execid=${flow.execId}">$utils.extractNumericalId(${flow.execId})</a>
+								<a href="${context}/executor?execid=${flow.execId}">$utils.extractNumericalId(${flow.execId})</a>
 							</td>
 							<td class="tb-name">
 								<a href="${context}/manager?project=${flow.projectId}&flow=${flow.flowId}">${flow.flowId}</a>
diff --git a/src/java/azkaban/webapp/servlet/velocity/joblogpage.vm b/src/java/azkaban/webapp/servlet/velocity/joblogpage.vm
new file mode 100644
index 0000000..dd9f233
--- /dev/null
+++ b/src/java/azkaban/webapp/servlet/velocity/joblogpage.vm
@@ -0,0 +1,69 @@
+<!DOCTYPE html> 
+<html>
+	<head>
+#parse( "azkaban/webapp/servlet/velocity/style.vm" )
+		<script type="text/javascript" src="${context}/js/jquery/jquery.js"></script>    
+		<script type="text/javascript" src="${context}/js/namespace.js"></script>
+		<script type="text/javascript" src="${context}/js/underscore-1.2.1-min.js"></script>
+		<script type="text/javascript" src="${context}/js/backbone-0.5.3-min.js"></script>
+		<script type="text/javascript" src="${context}/js/jquery.simplemodal.js"></script>
+		<script type="text/javascript" src="${context}/js/azkaban.ajax.utils.js"></script>
+		<script type="text/javascript" src="${context}/js/azkaban.nav.js"></script>
+		<script type="text/javascript" src="${context}/js/azkaban.joblog.view.js"></script>
+		<script type="text/javascript">
+			var contextURL = "${context}";
+			var currentTime = ${currentTime};
+			var timezone = "${timezone}";
+			var errorMessage = ${error_message};
+			var successMessage = ${success_message};
+			
+			var projectName = "${projectName}";
+			var flowName = "${flowid}";
+			var execId = "${execid}";
+			var jobId = "${jobid}";
+		</script>
+	</head>
+	<body>
+		#set($current_page="executing")
+#parse( "azkaban/webapp/servlet/velocity/nav.vm" )
+		<div class="content">
+#if($errorMsg)
+				<div class="box-error-message">$errorMsg</div>
+#else
+#if($error_message != "null")
+				<div class="box-error-message">$error_message</div>
+#elseif($success_message != "null")
+				<div class="box-success-message">$success_message</div>
+#end
+		
+			<div id="all-jobs-content">
+				<div class="section-hd flow-header">
+					<h2><a href="${context}/executor?execid=${execid}&job=${jobid}">Job Execution<span>$jobid</span></a></h2>
+					<div class="section-sub-hd">
+						<h4><a href="${context}/manager?project=${projectName}">Project <span>$projectName</span></a></h4>
+						<h4 class="separator">&gt;</h4>
+						<h4><a href="${context}/executor?execid=${execid}#jobslist">Execution <span>$execid</span></a></h4>
+						<h4 class="separator">&gt;</h4>
+						<h4><a href="${context}/manager?project=${projectName}&flow=${flowid}">Flow <span>$flowid</span></a></h4>
+						<h4 class="separator">&gt;</h4>
+						<h4><a href="${context}/manager?project=${projectName}&flow=${flowid}&job=$jobid">Job <span>$jobid</span></a></h4>
+					</div>
+				</div>
+			</div>
+			
+			<div id="headertabs" class="headertabs">
+				<ul>
+					<li><a id="logViewLink" href="#log">Log</a></li>
+				</ul>
+			</div>
+
+			<div id="jobLogView" class="logView">
+				<div class="logHeader"><div class="logButtonRow"><div id="updateLogBtn" class="btn7">Load More</div></div></div>
+				<div class="logViewer">
+					<pre id="logSection" class="log"></pre>
+				</div>
+			</div>
+#end
+		</div>
+	</body>
+</html>
\ No newline at end of file
diff --git a/src/java/azkaban/webapp/servlet/velocity/nav.vm b/src/java/azkaban/webapp/servlet/velocity/nav.vm
index 7999a7f..2517d8f 100644
--- a/src/java/azkaban/webapp/servlet/velocity/nav.vm
+++ b/src/java/azkaban/webapp/servlet/velocity/nav.vm
@@ -9,7 +9,7 @@
 			<ul id="nav" class="nav">
 				<li id="all-jobs-tab" #if($current_page == 'all')class="selected"#end onClick="navMenuClick('$!context/')"><a href="$!context/">Projects</a></li>
 				<li id="scheduled-jobs-tab" #if($current_page == 'schedule')class="scheduled"#end onClick="navMenuClick('$!context/schedule')"><a href="$!context/schedule">Scheduled</a></li>
-				<li id="executing-jobs-tab" #if($current_page == 'executing')class="selected"#end onClick="navMenuClick('$!context/executions')"><a href="$!context/executions">Executing</a></li>
+				<li id="executing-jobs-tab" #if($current_page == 'executing')class="selected"#end onClick="navMenuClick('$!context/executor')"><a href="$!context/executor">Executing</a></li>
 				<li id="history-jobs-tab" #if($current_page == 'history')class="selected"#end onClick="navMenuClick('$!context/history')"><a href="$!context/history">History</a></li>
 				<li><a href="$!context/fs">HDFS</a></li>
 			</ul>
diff --git a/src/web/css/azkaban.css b/src/web/css/azkaban.css
index fa0c773..449e05d 100644
--- a/src/web/css/azkaban.css
+++ b/src/web/css/azkaban.css
@@ -1166,7 +1166,7 @@ tr:hover td {
 	background: #E0E0E0;
 }
 
-#flowLogView {
+.logView {
 	position: absolute;
 	top: 210px;
 	bottom: 5px;
@@ -1175,6 +1175,16 @@ tr:hover td {
 	background: #E0E0E0;
 }
 
+#flowLogView {
+	top: 210px;
+	bottom: 5px;
+}
+
+#jobLogView {
+	top: 210px;
+	bottom: 5px;
+}
+
 .logHeader {
 	height: 30px;
 	margin: 0px;
@@ -1197,6 +1207,15 @@ tr:hover td {
 	overflow:scroll;
 }
 
+.logLink {
+	text-align: center;
+}
+
+.logLink a {
+	text-decoration: underline;
+	margin: 0px;
+}
+
 .log {
 	padding-left: 15px;
 	font-family: "courier";
diff --git a/src/web/js/azkaban.exflow.view.js b/src/web/js/azkaban.exflow.view.js
index 79ec6a4..8dbe54c 100644
--- a/src/web/js/azkaban.exflow.view.js
+++ b/src/web/js/azkaban.exflow.view.js
@@ -823,6 +823,13 @@ azkaban.ExecutionListView = Backbone.View.extend({
 		$(status).attr("id", node.id + "-status-div");
 		tdStatus.appendChild(status);
 
+		var logURL = contextURL + "/executor?execid=" + execId + "&flow=" + flowName + "&job=" + node.id;
+		var a = document.createElement("a");
+		$(a).attr("href", logURL);
+		$(a).text("Log");
+		$(tdLog).addClass("logLink");
+		$(tdLog).append(a);
+
 		executingBody.append(tr);
 	}
 });
diff --git a/src/web/js/azkaban.flow.view.js b/src/web/js/azkaban.flow.view.js
index 868d8d3..73c244f 100644
--- a/src/web/js/azkaban.flow.view.js
+++ b/src/web/js/azkaban.flow.view.js
@@ -641,7 +641,7 @@ azkaban.ExecutionsView = Backbone.View.extend({
 			
 			var tdId = document.createElement("td");
 			var execA = document.createElement("a");
-			$(execA).attr("href", contextURL + "/executions?execid=" + executions[i].execId);
+			$(execA).attr("href", contextURL + "/executor?execid=" + executions[i].execId);
 			$(execA).text(executions[i].execId);
 			tdId.appendChild(execA);
 			row.appendChild(tdId);
diff --git a/src/web/js/azkaban.joblog.view.js b/src/web/js/azkaban.joblog.view.js
new file mode 100644
index 0000000..1150736
--- /dev/null
+++ b/src/web/js/azkaban.joblog.view.js
@@ -0,0 +1,51 @@
+$.namespace('azkaban');
+
+var logModel;
+azkaban.LogModel = Backbone.Model.extend({});
+
+var jobLogView;
+azkaban.JobLogView = Backbone.View.extend({
+	events: {
+		"click #updateLogBtn" : "handleUpdate"
+	},
+	initialize: function(settings) {
+		this.model.set({"current": 0});
+		this.handleUpdate();
+	},
+	handleUpdate: function(evt) {
+		var current = this.model.get("current");
+		var requestURL = contextURL + "/executor"; 
+		var model = this.model;
+
+		ajaxCall(
+			requestURL,
+			{"execid": execId, "job": jobId, "ajax":"fetchExecJobLogs", "current": current, "max": 100000},
+			function(data) {
+	          console.log("fetchLogs");
+	          if (data.error) {
+	          	showDialog("Error", data.error);
+	          }
+	          else {
+	          	var log = $("#logSection").text();
+	          	if (!log) {
+	          		log = data.log;
+	          	}
+	          	else {
+	          		log += data.log;
+	          	}
+	          	
+	          	current = data.current;
+	          	$("#logSection").text(log);
+	          	model.set({"current": current, "log": log});
+	          }
+	      }
+	    );
+	}
+});
+
+$(function() {
+	var selected;
+
+	logModel = new azkaban.LogModel();
+	jobLogView = new azkaban.JobLogView({el:$('#jobLogView'), model: logModel});
+});