You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@tez.apache.org by sr...@apache.org on 2016/03/25 19:53:36 UTC
tez git commit: TEZ-3171. Tez UI 2: Swimlane - Tooltip,
zoom & redirection (sree)
Repository: tez
Updated Branches:
refs/heads/master 8a233ecc1 -> 182c9970a
TEZ-3171. Tez UI 2: Swimlane - Tooltip, zoom & redirection (sree)
Project: http://git-wip-us.apache.org/repos/asf/tez/repo
Commit: http://git-wip-us.apache.org/repos/asf/tez/commit/182c9970
Tree: http://git-wip-us.apache.org/repos/asf/tez/tree/182c9970
Diff: http://git-wip-us.apache.org/repos/asf/tez/diff/182c9970
Branch: refs/heads/master
Commit: 182c9970a792cb47b958daff5e64a89a3b6174b6
Parents: 8a233ec
Author: Sreenath Somarajapuram <sr...@apache.org>
Authored: Sat Mar 26 00:20:14 2016 +0530
Committer: Sreenath Somarajapuram <sr...@apache.org>
Committed: Sat Mar 26 00:20:14 2016 +0530
----------------------------------------------------------------------
CHANGES.txt | 1 +
.../components/em-swimlane-blocking-event.js | 16 ++
.../app/components/em-swimlane-event-bar.js | 23 ++-
.../webapp/app/components/em-swimlane-event.js | 21 ++-
.../app/components/em-swimlane-process-line.js | 54 +++++++
.../app/components/em-swimlane-process-name.js | 19 ++-
.../components/em-swimlane-process-visual.js | 42 ++++-
.../main/webapp/app/components/em-swimlane.js | 23 ++-
.../main/webapp/app/components/em-tooltip.js | 158 +++++++++++++++++++
.../main/webapp/app/controllers/dag/swimlane.js | 98 ++++++++++--
tez-ui2/src/main/webapp/app/styles/app.less | 1 +
.../src/main/webapp/app/styles/em-swimlane.less | 77 ++++-----
.../src/main/webapp/app/styles/em-tooltip.less | 117 ++++++++++++++
.../main/webapp/app/styles/swimlane-page.less | 17 ++
.../templates/components/em-swimlane-event.hbs | 2 +-
.../components/em-swimlane-process-line.hbs | 19 +++
.../components/em-swimlane-process-visual.hbs | 32 +++-
.../app/templates/components/em-swimlane.hbs | 30 ++--
.../app/templates/components/em-tooltip.hbs | 54 +++++++
.../main/webapp/app/templates/dag/swimlane.hbs | 7 +
tez-ui2/src/main/webapp/app/utils/process.js | 7 +
.../src/main/webapp/app/utils/vertex-process.js | 51 +++++-
.../components/em-swimlane-process-line-test.js | 65 ++++++++
.../em-swimlane-process-visual-test.js | 3 +-
.../integration/components/em-swimlane-test.js | 7 +
.../integration/components/em-tooltip-test.js | 80 ++++++++++
.../webapp/tests/unit/utils/process-test.js | 1 +
.../tests/unit/utils/vertex-process-test.js | 80 ++++++++++
28 files changed, 1022 insertions(+), 83 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/CHANGES.txt
----------------------------------------------------------------------
diff --git a/CHANGES.txt b/CHANGES.txt
index 7c4939c..4b1e91c 100644
--- a/CHANGES.txt
+++ b/CHANGES.txt
@@ -1891,6 +1891,7 @@ ALL CHANGES
TEZ-3160. Tez UI 2: Swimlane - Create swimlane page & component (sree)
TEZ-3170. Tez UI 2: Swimlane - Display computed events, event bars & dependencies (sree)
TEZ-3152. Tez UI 2: Build fails when run by multiple users or when node_modules is old (sree)
+ TEZ-3171. Tez UI 2: Swimlane - Tooltip, zoom & redirection (sree)
Release 0.2.0-incubating: 2013-11-30
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/components/em-swimlane-blocking-event.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/components/em-swimlane-blocking-event.js b/tez-ui2/src/main/webapp/app/components/em-swimlane-blocking-event.js
index a58ded8..c40bec9 100644
--- a/tez-ui2/src/main/webapp/app/components/em-swimlane-blocking-event.js
+++ b/tez-ui2/src/main/webapp/app/components/em-swimlane-blocking-event.js
@@ -47,4 +47,20 @@ export default Ember.Component.extend({
});
}),
+ sendMouseAction: function (name, mouseEvent) {
+ this.sendAction(name, "blocking-event", this.get("process"), {
+ mouseEvent: mouseEvent,
+ blocking: this.get("blocking"),
+ blockingEvent: this.get("blockingEvent")
+ });
+ },
+
+ mouseEnter: function (mouseEvent) {
+ this.sendMouseAction("showTooltip", mouseEvent);
+ },
+
+ mouseLeave: function (mouseEvent) {
+ this.sendMouseAction("hideTooltip", mouseEvent);
+ },
+
});
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/components/em-swimlane-event-bar.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/components/em-swimlane-event-bar.js b/tez-ui2/src/main/webapp/app/components/em-swimlane-event-bar.js
index e0e835e..7afb312 100644
--- a/tez-ui2/src/main/webapp/app/components/em-swimlane-event-bar.js
+++ b/tez-ui2/src/main/webapp/app/components/em-swimlane-event-bar.js
@@ -62,6 +62,27 @@ export default Ember.Component.extend({
else {
this.$().hide();
}
- })
+ }),
+
+ sendMouseAction: function (name, mouseEvent) {
+ this.sendAction(name, "event-bar", this.get("process"), {
+ mouseEvent: mouseEvent,
+ bar: this.get("bar"),
+ fromEvent: this.get("fromEvent"),
+ toEvent: this.get("toEvent")
+ });
+ },
+
+ mouseEnter: function (mouseEvent) {
+ this.sendMouseAction("showTooltip", mouseEvent);
+ },
+
+ mouseLeave: function (mouseEvent) {
+ this.sendMouseAction("hideTooltip", mouseEvent);
+ },
+
+ mouseUp: function (mouseEvent) {
+ this.sendMouseAction("click", mouseEvent);
+ }
});
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/components/em-swimlane-event.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/components/em-swimlane-event.js b/tez-ui2/src/main/webapp/app/components/em-swimlane-event.js
index 5eb6f0a..c4d31ca 100644
--- a/tez-ui2/src/main/webapp/app/components/em-swimlane-event.js
+++ b/tez-ui2/src/main/webapp/app/components/em-swimlane-event.js
@@ -35,10 +35,23 @@ export default Ember.Component.extend({
this.$(".event-bubble").css("border-color", color);
}),
- actions: {
- showTooltip: function () {
- console.log(this.get("event.name"));
- }
+ sendMouseAction: function (name, mouseEvent) {
+ this.sendAction(name, "event", this.get("process"), {
+ mouseEvent: mouseEvent,
+ events: [this.get("event")]
+ });
+ },
+
+ mouseEnter: function (mouseEvent) {
+ this.sendMouseAction("showTooltip", mouseEvent);
+ },
+
+ mouseLeave: function (mouseEvent) {
+ this.sendMouseAction("hideTooltip", mouseEvent);
+ },
+
+ mouseUp: function (mouseEvent) {
+ this.sendMouseAction("click", mouseEvent);
}
});
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/components/em-swimlane-process-line.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/components/em-swimlane-process-line.js b/tez-ui2/src/main/webapp/app/components/em-swimlane-process-line.js
new file mode 100644
index 0000000..ab4972b
--- /dev/null
+++ b/tez-ui2/src/main/webapp/app/components/em-swimlane-process-line.js
@@ -0,0 +1,54 @@
+/**
+ * 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';
+
+export default Ember.Component.extend({
+
+ process: null,
+ startEvent: null,
+ endEvent: null,
+
+ didInsertElement: Ember.observer("startEvent.pos", "endEvent.pos", function () {
+ this.$(".process-line").css({
+ left: this.get("startEvent.pos") + "%",
+ right: (100 - this.get("endEvent.pos")) + "%",
+ "background-color": this.get("process").getColor()
+ });
+ }),
+
+ sendMouseAction: function (name, mouseEvent) {
+ this.sendAction(name, "process-line", this.get("process"), {
+ mouseEvent: mouseEvent,
+ });
+ },
+
+ mouseEnter: function (mouseEvent) {
+ this.sendMouseAction("showTooltip", mouseEvent);
+ },
+
+ mouseLeave: function (mouseEvent) {
+ this.sendMouseAction("hideTooltip", mouseEvent);
+ },
+
+ mouseUp: function (mouseEvent) {
+ this.sendMouseAction("click", mouseEvent);
+ }
+
+
+});
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/components/em-swimlane-process-name.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/components/em-swimlane-process-name.js b/tez-ui2/src/main/webapp/app/components/em-swimlane-process-name.js
index f2b7ca9..eea897d 100644
--- a/tez-ui2/src/main/webapp/app/components/em-swimlane-process-name.js
+++ b/tez-ui2/src/main/webapp/app/components/em-swimlane-process-name.js
@@ -21,8 +21,25 @@ import Ember from 'ember';
export default Ember.Component.extend({
process: null,
- definition: null,
classNames: ["em-swimlane-process-name"],
+ sendMouseAction: function (name, mouseEvent) {
+ this.sendAction(name, "process-name", this.get("process"), {
+ mouseEvent: mouseEvent,
+ });
+ },
+
+ mouseEnter: function (mouseEvent) {
+ this.sendMouseAction("showTooltip", mouseEvent);
+ },
+
+ mouseLeave: function (mouseEvent) {
+ this.sendMouseAction("hideTooltip", mouseEvent);
+ },
+
+ mouseUp: function (mouseEvent) {
+ this.sendMouseAction("click", mouseEvent);
+ }
+
});
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/components/em-swimlane-process-visual.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/components/em-swimlane-process-visual.js b/tez-ui2/src/main/webapp/app/components/em-swimlane-process-visual.js
index 5942cf1..caa7603 100644
--- a/tez-ui2/src/main/webapp/app/components/em-swimlane-process-visual.js
+++ b/tez-ui2/src/main/webapp/app/components/em-swimlane-process-visual.js
@@ -18,6 +18,8 @@
import Ember from 'ember';
+const BUBBLE_RADIUS = 8; // Same as that in css
+
export default Ember.Component.extend({
process: null,
definition: null,
@@ -71,12 +73,38 @@ export default Ember.Component.extend({
});
}),
- drawEventWindow: Ember.observer("startEvent.pos", "endEvent.pos", function () {
- this.$(".event-window-line").css({
- left: this.get("startEvent.pos") + "%",
- right: (100 - this.get("endEvent.pos")) + "%",
- "background-color": this.get("process").getColor()
- });
- })
+ actions: {
+ showTooltip: function(type, process, options) {
+
+ if(type === "event") {
+ let mouseEvent = options.mouseEvent,
+ normalizedEvents = this.get("normalizedEvents"),
+ events = [];
+
+ this.$(".em-swimlane-event").each(function (index) {
+ var offset = Ember.$(this).offset();
+
+ if(mouseEvent.clientX >= offset.left - BUBBLE_RADIUS &&
+ mouseEvent.clientX <= offset.left + BUBBLE_RADIUS &&
+ mouseEvent.clientY >= offset.top - BUBBLE_RADIUS &&
+ mouseEvent.clientY <= offset.top + BUBBLE_RADIUS) {
+ events.push(normalizedEvents[index]);
+ }
+ });
+
+ if(events.length) {
+ options.events = events;
+ }
+ }
+
+ this.sendAction("showTooltip", type, process, options);
+ },
+ hideTooltip: function(type, process, options) {
+ this.sendAction("hideTooltip", type, process, options);
+ },
+ click: function (type, process, options) {
+ this.sendAction("click", type, process, options);
+ }
+ }
});
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/components/em-swimlane.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/components/em-swimlane.js b/tez-ui2/src/main/webapp/app/components/em-swimlane.js
index 3f22c50..c05461f 100644
--- a/tez-ui2/src/main/webapp/app/components/em-swimlane.js
+++ b/tez-ui2/src/main/webapp/app/components/em-swimlane.js
@@ -44,6 +44,15 @@ export default Ember.Component.extend({
eventBars: [],
+ tooltipContents: null,
+
+ zoom: 100,
+
+ didInsertElement: Ember.observer("zoom", function () {
+ var zoom = this.get("zoom");
+ this.$(".zoom-panel").css("width", `${zoom}%`);
+ }),
+
timeWindow: Ember.computed("startTime", "endTime", function () {
return Math.max(0, this.get("endTime") - this.get("startTime"));
}),
@@ -111,6 +120,18 @@ export default Ember.Component.extend({
});
return Ember.A(normalizedProcesses);
- })
+ }),
+
+ actions: {
+ showTooltip: function (type, process, options) {
+ this.set("tooltipContents", process.getTooltipContents(type, options));
+ },
+ hideTooltip: function () {
+ this.set("tooltipContents", null);
+ },
+ click: function (type, process, options) {
+ this.sendAction("click", type, process, options);
+ }
+ }
});
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/components/em-tooltip.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/components/em-tooltip.js b/tez-ui2/src/main/webapp/app/components/em-tooltip.js
new file mode 100644
index 0000000..093ca3d
--- /dev/null
+++ b/tez-ui2/src/main/webapp/app/components/em-tooltip.js
@@ -0,0 +1,158 @@
+/**
+ * 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';
+
+const TIP_PADDING = 10, // As in em-tooltip.css
+ FADE_TIME = 150;
+
+export default Ember.Component.extend({
+
+ title: null,
+ description: null,
+ properties: null,
+ contents: null,
+
+ classNames: ["em-tooltip"],
+ classNameBindings: ["aboveOrBelow"],
+
+ x: 0,
+ y: 0,
+
+ _contents: null,
+ show: false,
+ aboveOrBelow: null,
+
+ window: null,
+ tip: null,
+ bubbles: null,
+
+ _contentObserver: Ember.on("init", Ember.observer("title", "description", "properties", "contents", function () {
+ var contents,
+ tip = this.get("tip");
+
+ if(this.get("title") || this.get("description") || this.get("properties")){
+ contents = [{
+ title: this.get("title"),
+ description: this.get("description"),
+ properties: this.get("properties"),
+ }];
+ }
+ else if(Array.isArray(this.get("contents"))){
+ contents = this.get("contents");
+ }
+
+ this.set("show", false);
+ if(contents) {
+ if(tip) {
+ tip.hide();
+ }
+ this.set("_contents", contents);
+
+ Ember.run.later(this, function () {
+ this.set("bubbles", this.$(".bubble"));
+ this.set("show", true);
+ this.renderTip();
+ });
+ }
+ else if(tip){
+ tip.stop(true).fadeOut(FADE_TIME);
+ }
+ })),
+
+ didInsertElement: function () {
+ this.setProperties({
+ window: Ember.$(window),
+ tip: this.$(),
+ });
+ Ember.$(document).on("mousemove", this, this.onMouseMove);
+ },
+
+ willDestroyElement: function () {
+ Ember.$(document).off("mousemove", this.onMouseMove);
+ },
+
+ onMouseMove: function (event) {
+ event.data.setProperties({
+ x: event.clientX,
+ y: event.clientY
+ });
+
+ if(Ember.get(event, "data.tip")) {
+ event.data.renderTip();
+ }
+ },
+
+ getBubbleOffset: function (x, bubbleElement, winWidth) {
+ var bubbleWidth = bubbleElement.width(),
+ bubbleOffset = (bubbleWidth - TIP_PADDING) >> 1;
+
+ if(bubbleWidth < 0) {
+ bubbleWidth = 0;
+ }
+
+ if(x - bubbleOffset < 0) {
+ bubbleOffset = x;
+ }
+ else if(x + TIP_PADDING + bubbleOffset > winWidth) {
+ bubbleOffset = x - (winWidth - bubbleWidth);
+ }
+
+ return -bubbleOffset;
+ },
+
+ renderTip: function () {
+ if(this.get("show")) {
+ let x = this.get("x"),
+ y = this.get("y"),
+
+ winHeight = this.get("window").height(),
+ winWidth = this.get("window").width(),
+
+ showAbove = y < (winHeight >> 1),
+
+ that = this,
+ tip = this.get("tip");
+
+ if(!showAbove) {
+ y -= tip.height();
+ this.set("aboveOrBelow", "below");
+ }
+ else {
+ this.set("aboveOrBelow", "above");
+ }
+
+ tip.css({
+ left: `${x}px`,
+ top: `${y}px`,
+ });
+
+ tip.fadeIn({
+ duration: FADE_TIME,
+ start: function () {
+ that.get("bubbles").each(function () {
+ var bubble = Ember.$(this),
+ bubbleOffset = that.getBubbleOffset(x, bubble, winWidth);
+ bubble.css("left", `${bubbleOffset}px`);
+ });
+ }
+ });
+ }
+ }
+
+});
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/controllers/dag/swimlane.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/controllers/dag/swimlane.js b/tez-ui2/src/main/webapp/app/controllers/dag/swimlane.js
index 1699708..cf69e1f 100644
--- a/tez-ui2/src/main/webapp/app/controllers/dag/swimlane.js
+++ b/tez-ui2/src/main/webapp/app/controllers/dag/swimlane.js
@@ -25,32 +25,96 @@ import VertexProcess from '../../utils/vertex-process';
import fullscreen from 'em-tgraph/utils/fullscreen';
export default MultiTableController.extend({
+
+ zoom: 100,
+
breadcrumbs: [{
text: "Vertex Swimlane",
routeName: "dag.swimlane",
}],
- columns: ColumnDefinition.make([]),
-
- actions: {
- toggleFullscreen: function () {
- var swimlaneElement = Ember.$(".swimlane-page")[0];
- if(swimlaneElement){
- fullscreen.toggle(swimlaneElement);
- }
+ columns: ColumnDefinition.make([{
+ id: 'entityID',
+ headerTitle: 'Vertex Id',
+ contentPath: 'entityID'
+ },{
+ id: 'status',
+ headerTitle: 'Status',
+ contentPath: 'status',
+ },{
+ id: 'progress',
+ headerTitle: 'Progress',
+ contentPath: 'progress',
+ cellDefinition: {
+ type: 'number',
+ format: '0%'
+ }
+ },{
+ id: 'startTime',
+ headerTitle: 'Start Time',
+ contentPath: 'startTime',
+ cellDefinition: {
+ type: 'date'
+ }
+ },{
+ id: 'endTime',
+ headerTitle: 'End Time',
+ contentPath: 'endTime',
+ cellDefinition: {
+ type: 'date'
+ }
+ },{
+ id: 'duration',
+ headerTitle: 'Duration',
+ contentPath: 'duration',
+ cellDefinition: {
+ type: 'duration'
}
- },
+ },{
+ id: 'firstTaskStartTime',
+ headerTitle: 'First Task Start Time',
+ contentPath: 'firstTaskStartTime',
+ cellDefinition: {
+ type: 'date'
+ }
+ },{
+ id: 'totalTasks',
+ headerTitle: 'Tasks',
+ contentPath: 'totalTasks',
+ },{
+ id: 'succeededTasks',
+ headerTitle: 'Succeeded Tasks',
+ contentPath: 'succeededTasks',
+ },{
+ id: 'runningTasks',
+ headerTitle: 'Running Tasks',
+ contentPath: 'runningTasks',
+ },{
+ id: 'pendingTasks',
+ headerTitle: 'Pending Tasks',
+ contentPath: 'pendingTasks',
+ },{
+ id: 'processorClassName',
+ headerTitle: 'Processor Class',
+ contentPath: 'processorClassName',
+ }]),
processes: Ember.computed("model", function () {
var processes = [],
processHash = {},
- dagPlanEdges = this.get("model.firstObject.dag.edges");
+ dagPlanEdges = this.get("model.firstObject.dag.edges"),
+
+ that = this,
+ getVisibleProps = function () {
+ return that.get("visibleColumns");
+ };
// Create process instances for each vertices
this.get("model").forEach(function (vertex) {
var process = VertexProcess.create({
vertex: vertex,
+ getVisibleProps: getVisibleProps,
blockers: Ember.A()
});
processHash[vertex.get("name")] = process;
@@ -74,5 +138,17 @@ export default MultiTableController.extend({
}, {
fromEvent: "BLOCKING_VERTICES_COMPLETE",
toEvent: "VERTEX_TASK_FINISH",
- }]
+ }],
+
+ actions: {
+ toggleFullscreen: function () {
+ var swimlaneElement = Ember.$(".swimlane-page")[0];
+ if(swimlaneElement){
+ fullscreen.toggle(swimlaneElement);
+ }
+ },
+ click: function (type, process) {
+ this.transitionToRoute('vertex.index', process.get('vertex.entityID'));
+ }
+ }
});
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/styles/app.less
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/styles/app.less b/tez-ui2/src/main/webapp/app/styles/app.less
index 0202486..7275650 100644
--- a/tez-ui2/src/main/webapp/app/styles/app.less
+++ b/tez-ui2/src/main/webapp/app/styles/app.less
@@ -30,6 +30,7 @@
@import "caller-info";
@import "date-formatter";
@import "em-swimlane";
+@import "em-tooltip";
// Modals
@import "column-selector";
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/styles/em-swimlane.less
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/styles/em-swimlane.less b/tez-ui2/src/main/webapp/app/styles/em-swimlane.less
index a982712..2deb4db 100644
--- a/tez-ui2/src/main/webapp/app/styles/em-swimlane.less
+++ b/tez-ui2/src/main/webapp/app/styles/em-swimlane.less
@@ -28,10 +28,13 @@
border-right: 1px solid @border-color;
}
.process-visuals {
+ .force-scrollbar;
+
position: absolute;
left: 100px;
right: 0px;
top: 0px;
+ overflow: auto;
}
}
@@ -51,9 +54,11 @@
position: relative;
height: 30px;
- margin-left: 10px;
+ margin: 0px 10px;
- cursor: pointer;
+ .process-line, .event-bar, .event-bubble {
+ cursor: pointer;
+ }
.base-line {
position: relative;
@@ -63,7 +68,7 @@
border-top: 1px dotted @border-color;
}
- .event-window-line {
+ .process-line {
position: absolute;
top: unit(unit(@process-height) * 0.5 - 1, get-unit(@process-height));
height: 3px;
@@ -78,48 +83,46 @@
border: 1px solid;
margin-right: -1px;
}
-}
-.em-swimlane-event {
- position: absolute;
- top: unit(unit(@process-height) * 0.5, get-unit(@process-height));
-
- .event-line {
+ .em-swimlane-event {
position: absolute;
- top: -9px;
- height: 18px;
- border-left: 1px solid;
- }
+ top: unit(unit(@process-height) * 0.5, get-unit(@process-height));
- .event-bubble {
- position: absolute;
- top: 0;
- right: 0;
- bottom: 0;
- left: 0;
-
- -webkit-transition: top .2s, right .2s, bottom .2s, left .2s, border-width .2s; /* Safari */
- transition: top .2s, right .2s, bottom .2s, left .2s, border-width .2s;
- transition-timing-function: cubic-bezier(1.44);
-
- border-radius: 7px;
- border: 0px solid;
- background-color: white;
- }
-}
+ .event-line {
+ position: absolute;
+ top: -9px;
+ height: 18px;
+ border-left: 1px solid;
+ }
-.em-swimlane-blocking-event {
- position: absolute;
- top: unit(unit(@process-height) * 0.5, get-unit(@process-height));
+ .event-bubble {
+ position: absolute;
+ top: 0;
+ right: 0;
+ bottom: 0;
+ left: 0;
+
+ -webkit-transition: top .2s, right .2s, bottom .2s, left .2s, border-width .2s; /* Safari */
+ transition: top .2s, right .2s, bottom .2s, left .2s, border-width .2s;
+ transition-timing-function: cubic-bezier(1.44);
+
+ border-radius: 7px;
+ border: 0px solid;
+ background-color: white;
+ }
+ }
- .event-line {
+ .em-swimlane-blocking-event {
position: absolute;
- top: 0px;
- border-left: 1px solid;
+ top: unit(unit(@process-height) * 0.5, get-unit(@process-height));
+
+ .event-line {
+ position: absolute;
+ top: 0px;
+ border-left: 1px solid;
+ }
}
-}
-.em-swimlane-process-visual {
&:hover {
.event-bubble {
top: -7px;
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/styles/em-tooltip.less
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/styles/em-tooltip.less b/tez-ui2/src/main/webapp/app/styles/em-tooltip.less
new file mode 100644
index 0000000..ab2a19e
--- /dev/null
+++ b/tez-ui2/src/main/webapp/app/styles/em-tooltip.less
@@ -0,0 +1,117 @@
+/**
+ * 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.
+ */
+
+.em-tooltip {
+ .no-select;
+ .no-mouse;
+
+ position: fixed;
+ width: 820px; //2 * (td width + padding)
+
+ top: 10px;
+ left: 20px;
+
+ .bubble-container {
+ margin-bottom: 5px;
+
+ .bubble {
+ display: inline-block;
+ max-width: 820px;
+ margin-left: -11px; // Border radius + arrow margin-left
+
+ position: relative;
+ padding: 10px;
+
+ font-family: helvetica;
+ background: rgba(0, 0, 0, 0.8);
+ color: #fff;
+ border-radius: 5px;
+
+ .tip-title, .tip-desc, .tip-props {
+ border-top: 1px solid rgba(255, 255, 255, 0.4);
+ text-align: center;
+
+ padding: 0px 2px;
+
+ &:first-child {
+ border-top: none;
+ }
+ }
+
+ .tip-title {
+ font-size: 1.1em;
+ }
+
+ .tip-props {
+ table {
+ display: inline;
+ table-layout:fixed;
+
+ td {
+ overflow: hidden;
+ white-space: nowrap;
+ text-overflow: ellipsis;
+ max-width: 400px;
+
+ text-align: right;
+ }
+ td:nth-child(1) {
+ padding-right: 10px;
+ text-align: left;
+ }
+ td:nth-child(2) {
+ text-align: right;
+ padding-left: 10px;
+ border-left: 1px solid rgba(255, 255, 255, 0.4);
+ }
+ }
+ }
+ }
+ }
+
+ &.below:after, &.above:before {
+ display: block;
+ box-sizing: border-box;
+
+ font-size: 12px;
+ line-height: 9px;
+
+ color: rgba(0, 0, 0, 0.8);
+ margin-left: -6px; // Half of font size
+ }
+
+ &.above {
+ margin-top: 20px;
+
+ &:before {
+ margin-bottom: -2px;
+ content: "\25B2";
+ }
+ }
+
+ &.below {
+ .bubble-container {
+ margin-top: 5px;
+ margin-bottom: 0px;
+ }
+
+ &:after {
+ content: "\25BC";
+ }
+ }
+}
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/styles/swimlane-page.less
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/styles/swimlane-page.less b/tez-ui2/src/main/webapp/app/styles/swimlane-page.less
index e31371f..c9ae374 100644
--- a/tez-ui2/src/main/webapp/app/styles/swimlane-page.less
+++ b/tez-ui2/src/main/webapp/app/styles/swimlane-page.less
@@ -41,6 +41,23 @@
}
}
+ .zoom-range {
+ .no-wrap;
+ display: inline-block;
+ width: 300px;
+
+ margin-right: 5px;
+ padding-right: 5px;
+ border-right: 1px solid @border-color;
+
+ input {
+ width: 200px;
+ display: inline-block;
+ margin-top: 5px;
+ vertical-align: text-bottom;
+ }
+ }
+
.fa-compress {
display: none;
}
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/templates/components/em-swimlane-event.hbs
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/templates/components/em-swimlane-event.hbs b/tez-ui2/src/main/webapp/app/templates/components/em-swimlane-event.hbs
index 9b6330f..e5ddfa9 100644
--- a/tez-ui2/src/main/webapp/app/templates/components/em-swimlane-event.hbs
+++ b/tez-ui2/src/main/webapp/app/templates/components/em-swimlane-event.hbs
@@ -17,4 +17,4 @@
}}
<div class="event-line"></div>
-<div class="event-bubble" {{action "showTooltip" on="mouseEnter"}}></div>
\ No newline at end of file
+<div class="event-bubble"></div>
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/templates/components/em-swimlane-process-line.hbs
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/templates/components/em-swimlane-process-line.hbs b/tez-ui2/src/main/webapp/app/templates/components/em-swimlane-process-line.hbs
new file mode 100644
index 0000000..bd790fa
--- /dev/null
+++ b/tez-ui2/src/main/webapp/app/templates/components/em-swimlane-process-line.hbs
@@ -0,0 +1,19 @@
+{{!
+ * 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="process-line"></div>
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/templates/components/em-swimlane-process-visual.hbs
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/templates/components/em-swimlane-process-visual.hbs b/tez-ui2/src/main/webapp/app/templates/components/em-swimlane-process-visual.hbs
index 6e4603d..cbb025c 100644
--- a/tez-ui2/src/main/webapp/app/templates/components/em-swimlane-process-visual.hbs
+++ b/tez-ui2/src/main/webapp/app/templates/components/em-swimlane-process-visual.hbs
@@ -17,9 +17,23 @@
}}
<div class="base-line"></div>
-<div class="event-window-line"></div>
+{{em-swimlane-process-line
+ process=process
+ startEvent=startEvent
+ endEvent=endEvent
+ showTooltip="showTooltip"
+ hideTooltip="hideTooltip"
+ click="click"
+}}
{{#each process.blocking as |blocking|}}
- {{em-swimlane-blocking-event process=process blocking=blocking events=normalizedEvents}}
+ {{em-swimlane-blocking-event
+ process=process
+ blocking=blocking
+ events=normalizedEvents
+ showTooltip="showTooltip"
+ hideTooltip="hideTooltip"
+ click="click"
+ }}
{{/each}}
{{#each eventBars as |bar index|}}
{{em-swimlane-event-bar
@@ -27,8 +41,18 @@
bar=bar
barIndex=index
bars=eventBars
- process=process}}
+ process=process
+ showTooltip="showTooltip"
+ hideTooltip="hideTooltip"
+ click="click"
+ }}
{{/each}}
{{#each normalizedEvents as |event|}}
- {{em-swimlane-event process=process event=event}}
+ {{em-swimlane-event
+ process=process
+ event=event
+ showTooltip="showTooltip"
+ hideTooltip="hideTooltip"
+ click="click"
+ }}
{{/each}}
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/templates/components/em-swimlane.hbs
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/templates/components/em-swimlane.hbs b/tez-ui2/src/main/webapp/app/templates/components/em-swimlane.hbs
index a4777f0..ad0cbe2 100644
--- a/tez-ui2/src/main/webapp/app/templates/components/em-swimlane.hbs
+++ b/tez-ui2/src/main/webapp/app/templates/components/em-swimlane.hbs
@@ -18,17 +18,27 @@
<div class="process-names">
{{#each normalizedProcesses as |process|}}
- {{em-swimlane-process-name process=process definition=processDefinition}}
- {{/each}}
-</div><div class="process-visuals">
- {{#each normalizedProcesses as |process|}}
- {{em-swimlane-process-visual
+ {{em-swimlane-process-name
process=process
- definition=processDefinition
- eventBars=eventBars
- startTime=startTime
- endTime=endTime
- timeWindow=timeWindow
+ click="click"
}}
{{/each}}
+</div><div class="process-visuals">
+ <div class="zoom-panel">
+ {{#each normalizedProcesses as |process|}}
+ {{em-swimlane-process-visual
+ process=process
+ definition=processDefinition
+ eventBars=eventBars
+ startTime=startTime
+ endTime=endTime
+ timeWindow=timeWindow
+ showTooltip="showTooltip"
+ hideTooltip="hideTooltip"
+ click="click"
+ }}
+ {{/each}}
+ </div>
</div>
+
+{{em-tooltip contents=tooltipContents}}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/templates/components/em-tooltip.hbs
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/templates/components/em-tooltip.hbs b/tez-ui2/src/main/webapp/app/templates/components/em-tooltip.hbs
new file mode 100644
index 0000000..65f33db
--- /dev/null
+++ b/tez-ui2/src/main/webapp/app/templates/components/em-tooltip.hbs
@@ -0,0 +1,54 @@
+{{!
+ * 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.
+}}
+
+{{#each _contents as |content|}}
+
+ <div class="bubble-container">
+ <div class="bubble">
+ {{#if content.title}}{{show_}}
+ <div class="tip-title">{{content.title}}</div>
+ {{/if}}
+ {{#if content.description}}
+ <div class="tip-desc">{{content.description}}</div>
+ {{/if}}
+ {{#if content.properties}}
+ <div class="tip-props">
+ <table>
+ {{#each content.properties as |prop|}}
+ <tr>
+ <td>
+ {{prop.name}}
+ </td>
+ <td>
+ {{txt prop.value
+ type=prop.type
+ format=prop.format
+ timeZone=prop.timeZone
+ valueFormat=prop.valueFormat
+ valueTimeZone=prop.valueTimeZone
+ valueUnit=prop.valueUnit}}
+ </td>
+ </tr>
+ {{/each}}
+ </table>
+ </div>
+ {{/if}}
+ </div>
+ </div>
+
+{{/each}}
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/templates/dag/swimlane.hbs
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/templates/dag/swimlane.hbs b/tez-ui2/src/main/webapp/app/templates/dag/swimlane.hbs
index a2b2cbe..6d9b885 100644
--- a/tez-ui2/src/main/webapp/app/templates/dag/swimlane.hbs
+++ b/tez-ui2/src/main/webapp/app/templates/dag/swimlane.hbs
@@ -19,6 +19,11 @@
{{#if loaded}}
<div class="swimlane-page">
<div class="button-panel">
+ <div class="zoom-range">
+ {{zoom}}%
+ {{input type="range" value=zoom min=100 max=1000}}
+ </div>
+ <i class='fa fa-cog fa-border' {{action 'openColumnSelector'}} title="Customize vertex tooltip"></i>
<i class='fa fa-expand fa-border' {{action 'toggleFullscreen'}} title="Toggle fullscreen"></i>
<i class='fa fa-compress fa-border' {{action 'toggleFullscreen'}} title="Toggle fullscreen"></i>
</div>
@@ -29,6 +34,8 @@
eventBars=eventBars
startTime=model.firstObject.dag.startTime
endTime=model.firstObject.dag.endTime
+ zoom=zoom
+ click="click"
}}
</div>
{{else}}
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/utils/process.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/utils/process.js b/tez-ui2/src/main/webapp/app/utils/process.js
index eba3e72..d0f06a7 100644
--- a/tez-ui2/src/main/webapp/app/utils/process.js
+++ b/tez-ui2/src/main/webapp/app/utils/process.js
@@ -96,6 +96,13 @@ export default Ember.Object.extend({
parentHash[currentId] = false;
return blockers;
+ },
+
+ getTooltipContents: function (type/*, options*/) {
+ return [{
+ title: this.get("name"),
+ description: "Mouse on : " + type
+ }];
}
});
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/app/utils/vertex-process.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/app/utils/vertex-process.js b/tez-ui2/src/main/webapp/app/utils/vertex-process.js
index e48532d..b99c822 100644
--- a/tez-ui2/src/main/webapp/app/utils/vertex-process.js
+++ b/tez-ui2/src/main/webapp/app/utils/vertex-process.js
@@ -36,6 +36,8 @@ export default Process.extend({
blockingEventName: "VERTEX_FINISHED",
+ getVisibleProps: null,
+
events: Ember.computed(
"vertex.events.@each.timestamp",
"vertex.firstTaskStartTime",
@@ -45,7 +47,7 @@ export default Process.extend({
var events = this.get("vertex.events").map(function (event) {
return {
name: event.eventtype,
- test: EVENT_TEXTS[event.eventtype],
+ text: EVENT_TEXTS[event.eventtype],
time: event.timestamp
};
}),
@@ -57,7 +59,7 @@ export default Process.extend({
let type = "VERTEX_TASK_START";
events.push({
name: type,
- test: EVENT_TEXTS[type],
+ text: EVENT_TEXTS[type],
time: firstTaskStartTime
});
}
@@ -66,7 +68,7 @@ export default Process.extend({
let type = "VERTEX_TASK_FINISH";
events.push({
name: type,
- test: EVENT_TEXTS[type],
+ text: EVENT_TEXTS[type],
time: lastTaskFinishTime
});
}
@@ -75,7 +77,7 @@ export default Process.extend({
let type = "BLOCKING_VERTICES_COMPLETE";
events.push({
name: type,
- test: EVENT_TEXTS[type],
+ text: EVENT_TEXTS[type],
time: unblockTime
});
}
@@ -106,4 +108,45 @@ export default Process.extend({
return time;
}),
+ getTooltipContents: function (type, options) {
+ var contents,
+ that = this;
+
+ switch(type) {
+ case "event-bar":
+ case "process-line":
+ let properties = this.getVisibleProps().map(function (definition) {
+ return {
+ name: definition.get("headerTitle"),
+ value: that.get("vertex").get(definition.get("contentPath")),
+ type: Ember.get(definition, "cellDefinition.type"),
+ format: Ember.get(definition, "cellDefinition.format")
+ };
+ });
+
+ contents = [{
+ title: this.get("name"),
+ properties: properties
+ }];
+ break;
+ case "event":
+ contents = options.events.map(function (event) {
+ return {
+ title: event.text,
+ properties: [{
+ name: "Type",
+ value: event.name,
+ }, {
+ name: "Time",
+ value: event.time,
+ type: "date"
+ }]
+ };
+ });
+ break;
+ }
+
+ return contents;
+ }
+
});
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/tests/integration/components/em-swimlane-process-line-test.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/tests/integration/components/em-swimlane-process-line-test.js b/tez-ui2/src/main/webapp/tests/integration/components/em-swimlane-process-line-test.js
new file mode 100644
index 0000000..0dd8ead
--- /dev/null
+++ b/tez-ui2/src/main/webapp/tests/integration/components/em-swimlane-process-line-test.js
@@ -0,0 +1,65 @@
+/**
+ * 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';
+
+import wait from 'ember-test-helpers/wait';
+import Ember from 'ember';
+
+import Process from 'tez-ui/utils/process';
+
+moduleForComponent('em-swimlane-process-line', 'Integration | Component | em swimlane process line', {
+ integration: true
+});
+
+test('Basic creation test', function(assert) {
+ this.set("process", Process.create());
+
+ this.render(hbs`{{em-swimlane-process-line process=process}}`);
+
+ assert.equal(this.$().text().trim(), '');
+
+ // Template block usage:" + EOL +
+ this.render(hbs`
+ {{#em-swimlane-process-line process=process}}
+ template block text
+ {{/em-swimlane-process-line}}
+ `);
+
+ assert.equal(this.$().text().trim(), '');
+});
+
+test('start-end event test', function(assert) {
+ var startEvent = Ember.Object.create({
+ pos: 50
+ }),
+ endEvent = Ember.Object.create({
+ pos: 70
+ });
+
+ this.set("process", Process.create());
+ this.set("startEvent", startEvent);
+ this.set("endEvent", endEvent);
+
+ this.render(hbs`{{em-swimlane-process-line process=process startEvent=startEvent endEvent=endEvent}}`);
+
+ return wait().then(() => {
+ assert.equal(this.$(".process-line").eq(0).attr("style").trim(), "left: 50%; right: 30%;", "process-line");
+ });
+});
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/tests/integration/components/em-swimlane-process-visual-test.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/tests/integration/components/em-swimlane-process-visual-test.js b/tez-ui2/src/main/webapp/tests/integration/components/em-swimlane-process-visual-test.js
index ffc7b56..4eb6b1b 100644
--- a/tez-ui2/src/main/webapp/tests/integration/components/em-swimlane-process-visual-test.js
+++ b/tez-ui2/src/main/webapp/tests/integration/components/em-swimlane-process-visual-test.js
@@ -60,11 +60,10 @@ test('Events test', function(assert) {
return wait().then(() => {
var events = this.$(".em-swimlane-event");
-
assert.equal(events.length, 2);
assert.equal(events.eq(0).attr("style").trim(), "left: 50%;", "em-swimlane-event 1 left");
assert.equal(events.eq(1).attr("style").trim(), "left: 70%;", "em-swimlane-event 2 left");
- assert.equal(this.$(".event-window-line").eq(0).attr("style").trim(), "left: 50%; right: 30%;", "event-window-line");
+ assert.equal(this.$(".process-line").eq(0).attr("style").trim(), "left: 50%; right: 30%;", "process-line");
});
});
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/tests/integration/components/em-swimlane-test.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/tests/integration/components/em-swimlane-test.js b/tez-ui2/src/main/webapp/tests/integration/components/em-swimlane-test.js
index 59e543d..e0ab7c7 100644
--- a/tez-ui2/src/main/webapp/tests/integration/components/em-swimlane-test.js
+++ b/tez-ui2/src/main/webapp/tests/integration/components/em-swimlane-test.js
@@ -84,3 +84,10 @@ test('Normalization (Blocker based sorting) test - On a graph', function(assert)
assert.equal(names.eq(3).text().trim(), p3.name);
assert.equal(names.eq(4).text().trim(), p5.name);
});
+
+test('Zoom test', function(assert) {
+ this.set("processes", [Process.create()]);
+
+ this.render(hbs`{{em-swimlane processes=processes zoom=500}}`);
+ assert.equal(this.$(".zoom-panel").attr("style").trim(), "width: 500%;");
+});
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/tests/integration/components/em-tooltip-test.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/tests/integration/components/em-tooltip-test.js b/tez-ui2/src/main/webapp/tests/integration/components/em-tooltip-test.js
new file mode 100644
index 0000000..73a957b
--- /dev/null
+++ b/tez-ui2/src/main/webapp/tests/integration/components/em-tooltip-test.js
@@ -0,0 +1,80 @@
+/**
+ * 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('em-tooltip', 'Integration | Component | em tooltip', {
+ integration: true
+});
+
+test('Basic creation test', function(assert) {
+
+ this.render(hbs`{{em-tooltip}}`);
+
+ assert.equal(this.$().text().trim(), '');
+
+ // Template block usage:" + EOL +
+ this.render(hbs`
+ {{#em-tooltip}}
+ template block text
+ {{/em-tooltip}}
+ `);
+
+ assert.equal(this.$().text().trim(), '');
+});
+
+test('Title test', function(assert) {
+ this.set("title", "TestTitle");
+ this.render(hbs`{{em-tooltip title=title}}`);
+
+ assert.equal(this.$().text().trim(), 'TestTitle');
+});
+
+test('Description test', function(assert) {
+ this.set("desc", "TestDesc");
+ this.render(hbs`{{em-tooltip description=desc}}`);
+
+ assert.equal(this.$().text().trim(), 'TestDesc');
+});
+
+test('Properties test', function(assert) {
+ this.set("properties", [{
+ name: "p1", value: "v1"
+ }, {
+ name: "p2", value: "v2"
+ }]);
+ this.render(hbs`{{em-tooltip properties=properties}}`);
+
+ assert.equal(this.$("tr").length, 2);
+});
+
+test('Contents test', function(assert) {
+ this.set("contents", [{
+ title: "p1",
+ properties: [{}, {}]
+ }, {
+ title: "p2",
+ properties: [{}, {}, {}]
+ }]);
+
+ this.render(hbs`{{em-tooltip contents=contents}}`);
+
+ assert.equal(this.$(".bubble").length, 2);
+ assert.equal(this.$("tr").length, 2 + 3);
+});
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/tests/unit/utils/process-test.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/tests/unit/utils/process-test.js b/tez-ui2/src/main/webapp/tests/unit/utils/process-test.js
index ffab868..6069d7b 100644
--- a/tez-ui2/src/main/webapp/tests/unit/utils/process-test.js
+++ b/tez-ui2/src/main/webapp/tests/unit/utils/process-test.js
@@ -29,6 +29,7 @@ test('Basic creation test', function(assert) {
assert.ok(process.startEvent);
assert.ok(process.endEvent);
assert.ok(process.getAllBlockers);
+ assert.ok(process.getTooltipContents);
});
test('getColor test', function(assert) {
http://git-wip-us.apache.org/repos/asf/tez/blob/182c9970/tez-ui2/src/main/webapp/tests/unit/utils/vertex-process-test.js
----------------------------------------------------------------------
diff --git a/tez-ui2/src/main/webapp/tests/unit/utils/vertex-process-test.js b/tez-ui2/src/main/webapp/tests/unit/utils/vertex-process-test.js
index 85c0d0f..05ffc40 100644
--- a/tez-ui2/src/main/webapp/tests/unit/utils/vertex-process-test.js
+++ b/tez-ui2/src/main/webapp/tests/unit/utils/vertex-process-test.js
@@ -34,6 +34,8 @@ test('Basic creation test', function(assert) {
assert.ok(process.events);
assert.ok(process.unblockTime);
+
+ assert.ok(process.getTooltipContents);
});
test('unblockTime test', function(assert) {
@@ -96,3 +98,81 @@ test('events test', function(assert) {
assert.equal(process.get("events.length"), 5);
assert.equal(process.get("events.4.time"), 30);
});
+
+test('getTooltipContents-event test', function(assert) {
+ var process = VertexProcess.create();
+
+ var eventTooltip = process.getTooltipContents("event", {
+ events: [{
+ text: "TestEventText1",
+ name: "TestEventName1",
+ time: 10
+ }, {
+ text: "TestEventText2",
+ name: "TestEventName2",
+ time: 20
+ }]
+ });
+
+ assert.equal(eventTooltip.length, 2);
+
+ assert.equal(eventTooltip[0].title, "TestEventText1");
+ assert.equal(eventTooltip[0].properties.length, 2);
+ assert.equal(eventTooltip[0].properties[0].name, "Type");
+ assert.equal(eventTooltip[0].properties[0].value, "TestEventName1");
+ assert.equal(eventTooltip[0].properties[1].name, "Time");
+ assert.equal(eventTooltip[0].properties[1].value, 10);
+
+ assert.equal(eventTooltip[1].title, "TestEventText2");
+ assert.equal(eventTooltip[1].properties.length, 2);
+ assert.equal(eventTooltip[1].properties[0].name, "Type");
+ assert.equal(eventTooltip[1].properties[0].value, "TestEventName2");
+ assert.equal(eventTooltip[1].properties[1].name, "Time");
+ assert.equal(eventTooltip[1].properties[1].value, 20);
+
+});
+
+test('getTooltipContents-process test', function(assert) {
+ var process = VertexProcess.create({
+ name: "TestName",
+ vertex: Ember.Object.create({
+ prop1: "val1",
+ prop2: "val2",
+ prop3: "val3"
+ }),
+ getVisibleProps: function () {
+ return [Ember.Object.create({
+ id: "prop1",
+ headerTitle: "Prop 1",
+ contentPath: "prop1"
+ }), Ember.Object.create({
+ id: "prop2",
+ headerTitle: "Prop 2",
+ contentPath: "prop2"
+ })];
+ }
+ });
+
+ var processTooltip = process.getTooltipContents("event-bar")[0];
+ assert.equal(processTooltip.title, "TestName");
+
+ assert.equal(processTooltip.properties.length, 2);
+
+ assert.equal(processTooltip.properties[0].name, "Prop 1");
+ assert.equal(processTooltip.properties[0].value, "val1");
+
+ assert.equal(processTooltip.properties[1].name, "Prop 2");
+ assert.equal(processTooltip.properties[1].value, "val2");
+
+ processTooltip = process.getTooltipContents("process-line")[0];
+ assert.equal(processTooltip.title, "TestName");
+
+ assert.equal(processTooltip.properties.length, 2);
+
+ assert.equal(processTooltip.properties[0].name, "Prop 1");
+ assert.equal(processTooltip.properties[0].value, "val1");
+
+ assert.equal(processTooltip.properties[1].name, "Prop 2");
+ assert.equal(processTooltip.properties[1].value, "val2");
+
+});