Pārlūkot izejas kodu

YARN-5650. Render Application Timeout value in web UI. Contributed by Akhil PB.

Sunil G 8 gadi atpakaļ
vecāks
revīzija
d5271b03d3

+ 60 - 0
hadoop-yarn-project/hadoop-yarn/hadoop-yarn-ui/src/main/webapp/app/components/app-timeout-bar.js

@@ -0,0 +1,60 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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.
+ */
+
+import Ember from 'ember';
+import Converter from 'yarn-ui/utils/converter';
+
+export default Ember.Component.extend({
+  app: null,
+
+  appTimeoutValue: function() {
+    var timeoutValueInSecs = this.get("app.remainingTimeoutInSeconds");
+    if (timeoutValueInSecs > -1) {
+      return Converter.msToElapsedTime(timeoutValueInSecs * 1000);
+    } else {
+      return timeoutValueInSecs;
+    }
+  }.property("app.remainingTimeoutInSeconds"),
+
+  isAppTimedOut: function() {
+    if (this.get("app.remainingTimeoutInSeconds") > 0) {
+      return false;
+    } else {
+      return true;
+    }
+  }.property("app.remainingTimeoutInSeconds"),
+
+  appTimeoutBarStyle: function() {
+    var remainingInSecs = this.get("app.remainingTimeoutInSeconds"),
+        expiryTimestamp = Converter.dateToTimeStamp(this.get("app.applicationExpiryTime")),
+        expiryInSecs = expiryTimestamp / 1000,
+        startTimestamp = Converter.dateToTimeStamp(this.get("app.startTime")),
+        startInSecs = startTimestamp / 1000,
+        totalRunInSecs = 0,
+        appRunDurationInSecs = 0,
+        width = 0;
+
+    if (remainingInSecs > 0) {
+      totalRunInSecs = expiryInSecs - startInSecs;
+      appRunDurationInSecs = totalRunInSecs - remainingInSecs;
+      width = appRunDurationInSecs / totalRunInSecs * 100;
+    }
+
+    return "width: " + width + "%";
+  }.property("app.remainingTimeoutInSeconds", "app.applicationExpiryTime", "app.startTime")
+});

+ 2 - 0
hadoop-yarn-project/hadoop-yarn/hadoop-yarn-ui/src/main/webapp/app/models/yarn-app.js

@@ -50,6 +50,8 @@ export default DS.Model.extend({
   clusterUsagePercentage: DS.attr('number'),
   queueUsagePercentage: DS.attr('number'),
   currentAppAttemptId: DS.attr('string'),
+  remainingTimeoutInSeconds: DS.attr('number'),
+  applicationExpiryTime: DS.attr('string'),
 
   isFailed: function() {
     return this.get('finalStatus') == "FAILED"

+ 16 - 5
hadoop-yarn-project/hadoop-yarn/hadoop-yarn-ui/src/main/webapp/app/serializers/yarn-app.js

@@ -23,9 +23,18 @@ export default DS.JSONAPISerializer.extend({
     internalNormalizeSingleResponse(store, primaryModelClass, payload, id,
       requestType) {
       if (payload.app) {
-        payload = payload.app;  
+        payload = payload.app;
       }
-      
+
+      var timeoutInSecs = -1;
+      var appExpiryTime = Converter.timeStampToDate(payload.finishedTime);
+      if (payload.timeouts && payload.timeouts.timeout && payload.timeouts.timeout[0]) {
+        timeoutInSecs = payload.timeouts.timeout[0].remainingTimeInSeconds;
+        if (timeoutInSecs > -1) {
+          appExpiryTime = Converter.isoDateToDate(payload.timeouts.timeout[0].expiryTime);
+        }
+      }
+
       var fixedPayload = {
         id: id,
         type: primaryModelClass.modelName, // yarn-app
@@ -58,7 +67,9 @@ export default DS.JSONAPISerializer.extend({
           numAMContainerPreempted: payload.numAMContainerPreempted,
           clusterUsagePercentage: payload.clusterUsagePercentage,
           queueUsagePercentage: payload.queueUsagePercentage,
-          currentAppAttemptId: payload.currentAppAttemptId
+          currentAppAttemptId: payload.currentAppAttemptId,
+          remainingTimeoutInSeconds: timeoutInSecs,
+          applicationExpiryTime: appExpiryTime
         }
       };
 
@@ -67,7 +78,7 @@ export default DS.JSONAPISerializer.extend({
 
     normalizeSingleResponse(store, primaryModelClass, payload, id,
       requestType) {
-      var p = this.internalNormalizeSingleResponse(store, 
+      var p = this.internalNormalizeSingleResponse(store,
         primaryModelClass, payload, id, requestType);
       return { data: p };
     },
@@ -90,4 +101,4 @@ export default DS.JSONAPISerializer.extend({
 
       return normalizedArrayResponse;
     }
-});
+});

+ 34 - 0
hadoop-yarn-project/hadoop-yarn/hadoop-yarn-ui/src/main/webapp/app/templates/components/app-timeout-bar.hbs

@@ -0,0 +1,34 @@
+{{!
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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.
+}}
+
+<div class="app-timeout-wrapper">
+  {{#unless isAppTimedOut}}
+    <div class="panel panel-default">
+      <div class="panel-body">
+        <label>Application will be timed out after <span class="text-danger">{{appTimeoutValue}}</span></label>
+        <div class="progress">
+          <div class="progress-bar progress-bar-danger progress-bar-striped active" style="{{appTimeoutBarStyle}}"></div>
+        </div>
+        <div>
+          <label class="pull-left">{{app.startTime}}</label>
+          <label class="pull-right">{{app.applicationExpiryTime}}</label>
+        </div>
+      </div>
+    </div>
+  {{/unless}}
+</div>

+ 8 - 2
hadoop-yarn-project/hadoop-yarn/hadoop-yarn-ui/src/main/webapp/app/templates/yarn-app.hbs

@@ -45,6 +45,12 @@
     </div>
 
     <div class="col-md-10 container-fluid">
+      <div class="row">
+        <div class="col-md-12">
+          {{app-timeout-bar app=model.app}}
+        </div>
+      </div>
+
       <div class="row">
         <div class="col-md-12 container-fluid">
           <div class="panel panel-default">
@@ -116,10 +122,10 @@
               </div>
             {{else}}
               <div class="panel panel-default">
-                <div class="panel-body">
+                <div class="panel-heading">
                   Diagnostics
                 </div>
-                <div class="panel-footer">{{model.app.diagnostics}}</div>
+                <div class="panel-body">{{model.app.diagnostics}}</div>
               </div>
             {{/if}}
           </div>

+ 3 - 0
hadoop-yarn-project/hadoop-yarn/hadoop-yarn-ui/src/main/webapp/app/utils/converter.js

@@ -91,6 +91,9 @@ export default {
       return ts;
     }
   },
+  isoDateToDate: function(isoDate) {
+    return moment(isoDate).format("YYYY/MM/DD HH:mm:ss");
+  },
   splitForContainerLogs: function(id) {
     if (id) {
       var splits = id.split(Constants.PARAM_SEPARATOR);

+ 34 - 0
hadoop-yarn-project/hadoop-yarn/hadoop-yarn-ui/src/main/webapp/tests/integration/components/app-timeout-bar-test.js

@@ -0,0 +1,34 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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.
+ */
+
+import { moduleForComponent, test } from 'ember-qunit';
+import hbs from 'htmlbars-inline-precompile';
+
+moduleForComponent('app-timeout-bar', 'Integration | Component | app timeout bar', {
+  integration: true
+});
+
+test('it renders', function(assert) {
+
+  // Set any properties with this.set('myProperty', 'value');
+  // Handle any actions with this.on('myAction', function(val) { ... });" + EOL + EOL +
+
+  this.render(hbs`{{app-timeout-bar}}`);
+
+  assert.equal(this.$().text().trim(), '');
+});