Merge remote-tracking branch 'github-open/open115b' into open-master
This commit is contained in:
@@ -34,6 +34,10 @@
|
|||||||
{
|
{
|
||||||
"key": "time",
|
"key": "time",
|
||||||
"name": "Time"
|
"name": "Time"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"key": "yesterday",
|
||||||
|
"name": "Yesterday"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"ranges": [
|
"ranges": [
|
||||||
@@ -61,4 +65,4 @@
|
|||||||
}
|
}
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -29,23 +29,25 @@ define(
|
|||||||
function () {
|
function () {
|
||||||
"use strict";
|
"use strict";
|
||||||
|
|
||||||
var firstObservedTime = Math.floor(Date.now() / 1000);
|
var ONE_DAY = 60 * 60 * 24,
|
||||||
|
firstObservedTime = Math.floor(Date.now() / 1000) - ONE_DAY;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* @constructor
|
* @constructor
|
||||||
*/
|
*/
|
||||||
function SinewaveTelemetrySeries(request) {
|
function SinewaveTelemetrySeries(request) {
|
||||||
var latestObservedTime = Math.floor(Date.now() / 1000),
|
var timeOffset = (request.domain === 'yesterday') ? ONE_DAY : 0,
|
||||||
|
latestTime = Math.floor(Date.now() / 1000) - timeOffset,
|
||||||
|
firstTime = firstObservedTime - timeOffset,
|
||||||
endTime = (request.end !== undefined) ?
|
endTime = (request.end !== undefined) ?
|
||||||
Math.floor(request.end / 1000) : latestObservedTime,
|
Math.floor(request.end / 1000) : latestTime,
|
||||||
count =
|
count = Math.min(endTime, latestTime) - firstTime,
|
||||||
Math.min(endTime, latestObservedTime) - firstObservedTime,
|
period = +request.period || 30,
|
||||||
period = request.period || 30,
|
|
||||||
generatorData = {},
|
generatorData = {},
|
||||||
offset = (request.start !== undefined) ?
|
requestStart = (request.start === undefined) ? firstTime :
|
||||||
Math.floor(request.start / 1000) - firstObservedTime :
|
Math.max(Math.floor(request.start / 1000), firstTime),
|
||||||
0;
|
offset = requestStart - firstTime;
|
||||||
|
|
||||||
if (request.size !== undefined) {
|
if (request.size !== undefined) {
|
||||||
offset = Math.max(offset, count - request.size);
|
offset = Math.max(offset, count - request.size);
|
||||||
@@ -56,8 +58,8 @@ define(
|
|||||||
};
|
};
|
||||||
|
|
||||||
generatorData.getDomainValue = function (i, domain) {
|
generatorData.getDomainValue = function (i, domain) {
|
||||||
return (i + offset) * 1000 +
|
return (i + offset) * 1000 + firstTime * 1000 -
|
||||||
(domain !== 'delta' ? (firstObservedTime * 1000) : 0);
|
(domain === 'yesterday' ? ONE_DAY : 0);
|
||||||
};
|
};
|
||||||
|
|
||||||
generatorData.getRangeValue = function (i, range) {
|
generatorData.getRangeValue = function (i, range) {
|
||||||
|
|||||||
@@ -23,7 +23,23 @@
|
|||||||
{
|
{
|
||||||
"key": "conductorService",
|
"key": "conductorService",
|
||||||
"implementation": "ConductorService.js",
|
"implementation": "ConductorService.js",
|
||||||
"depends": [ "now" ]
|
"depends": [ "now", "TIME_CONDUCTOR_DOMAINS" ]
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"templates": [
|
||||||
|
{
|
||||||
|
"key": "time-conductor",
|
||||||
|
"templateUrl": "templates/time-conductor.html"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"constants": [
|
||||||
|
{
|
||||||
|
"key": "TIME_CONDUCTOR_DOMAINS",
|
||||||
|
"value": [
|
||||||
|
{ "key": "time", "name": "Time" },
|
||||||
|
{ "key": "yesterday", "name": "Yesterday" }
|
||||||
|
],
|
||||||
|
"comment": "Placeholder; to be replaced by inspection of available domains."
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,10 @@
|
|||||||
|
<mct-include key="'time-controller'"
|
||||||
|
ng-model='ngModel.conductor'>
|
||||||
|
</mct-include>
|
||||||
|
<mct-control key="'select'"
|
||||||
|
ng-model='ngModel'
|
||||||
|
field="'domain'"
|
||||||
|
options="ngModel.options"
|
||||||
|
style="position: absolute; right: 0px; bottom: 46px;"
|
||||||
|
>
|
||||||
|
</mct-control>
|
||||||
@@ -28,7 +28,7 @@ define(
|
|||||||
|
|
||||||
var CONDUCTOR_HEIGHT = "100px",
|
var CONDUCTOR_HEIGHT = "100px",
|
||||||
TEMPLATE = [
|
TEMPLATE = [
|
||||||
"<mct-include key=\"'time-controller'\" ng-model='conductor'>",
|
"<mct-include key=\"'time-conductor'\" ng-model='ngModel'>",
|
||||||
"</mct-include>"
|
"</mct-include>"
|
||||||
].join(''),
|
].join(''),
|
||||||
THROTTLE_MS = 200,
|
THROTTLE_MS = 200,
|
||||||
@@ -78,7 +78,8 @@ define(
|
|||||||
function bounds(start, end) {
|
function bounds(start, end) {
|
||||||
return {
|
return {
|
||||||
start: conductor.displayStart(),
|
start: conductor.displayStart(),
|
||||||
end: conductor.displayEnd()
|
end: conductor.displayEnd(),
|
||||||
|
domain: conductor.domain()
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -89,12 +90,30 @@ define(
|
|||||||
}
|
}
|
||||||
|
|
||||||
function updateConductorInner() {
|
function updateConductorInner() {
|
||||||
conductor.displayStart(conductorScope.conductor.inner.start);
|
var innerBounds = conductorScope.ngModel.conductor.inner;
|
||||||
conductor.displayEnd(conductorScope.conductor.inner.end);
|
conductor.displayStart(innerBounds.start);
|
||||||
|
conductor.displayEnd(innerBounds.end);
|
||||||
lastObservedBounds = lastObservedBounds || bounds();
|
lastObservedBounds = lastObservedBounds || bounds();
|
||||||
broadcastBounds();
|
broadcastBounds();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function updateDomain(value) {
|
||||||
|
conductor.domain(value);
|
||||||
|
repScope.$broadcast('telemetry:display:bounds', bounds(
|
||||||
|
conductor.displayStart(),
|
||||||
|
conductor.displayEnd(),
|
||||||
|
conductor.domain()
|
||||||
|
));
|
||||||
|
}
|
||||||
|
|
||||||
|
// telemetry domain metadata -> option for a select control
|
||||||
|
function makeOption(domainOption) {
|
||||||
|
return {
|
||||||
|
name: domainOption.name,
|
||||||
|
value: domainOption.key
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
broadcastBounds = this.throttle(function () {
|
broadcastBounds = this.throttle(function () {
|
||||||
var newlyObservedBounds = bounds();
|
var newlyObservedBounds = bounds();
|
||||||
|
|
||||||
@@ -107,12 +126,19 @@ define(
|
|||||||
}
|
}
|
||||||
}, THROTTLE_MS);
|
}, THROTTLE_MS);
|
||||||
|
|
||||||
conductorScope.conductor = { outer: bounds(), inner: bounds() };
|
conductorScope.ngModel = {};
|
||||||
|
conductorScope.ngModel.conductor =
|
||||||
|
{ outer: bounds(), inner: bounds() };
|
||||||
|
conductorScope.ngModel.options =
|
||||||
|
conductor.domainOptions().map(makeOption);
|
||||||
|
conductorScope.ngModel.domain = conductor.domain();
|
||||||
|
|
||||||
conductorScope
|
conductorScope
|
||||||
.$watch('conductor.inner.start', updateConductorInner);
|
.$watch('ngModel.conductor.inner.start', updateConductorInner);
|
||||||
conductorScope
|
conductorScope
|
||||||
.$watch('conductor.inner.end', updateConductorInner);
|
.$watch('ngModel.conductor.inner.end', updateConductorInner);
|
||||||
|
conductorScope
|
||||||
|
.$watch('ngModel.domain', updateDomain);
|
||||||
|
|
||||||
repScope.$on('telemetry:view', updateConductorInner);
|
repScope.$on('telemetry:view', updateConductorInner);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -39,12 +39,15 @@ define(
|
|||||||
* @param {Function} now a function which returns the current time
|
* @param {Function} now a function which returns the current time
|
||||||
* as a UNIX timestamp, in milliseconds
|
* as a UNIX timestamp, in milliseconds
|
||||||
*/
|
*/
|
||||||
function ConductorService(now) {
|
function ConductorService(now, domains) {
|
||||||
var initialEnd =
|
var initialEnd =
|
||||||
Math.ceil(now() / SIX_HOURS_IN_MS) * SIX_HOURS_IN_MS;
|
Math.ceil(now() / SIX_HOURS_IN_MS) * SIX_HOURS_IN_MS;
|
||||||
|
|
||||||
this.conductor =
|
this.conductor = new TimeConductor(
|
||||||
new TimeConductor(initialEnd - ONE_DAY_IN_MS, initialEnd);
|
initialEnd - ONE_DAY_IN_MS,
|
||||||
|
initialEnd,
|
||||||
|
domains
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -44,12 +44,14 @@ define(
|
|||||||
ConductorTelemetryDecorator.prototype.amendRequests = function (requests) {
|
ConductorTelemetryDecorator.prototype.amendRequests = function (requests) {
|
||||||
var conductor = this.conductorService.getConductor(),
|
var conductor = this.conductorService.getConductor(),
|
||||||
start = conductor.displayStart(),
|
start = conductor.displayStart(),
|
||||||
end = conductor.displayEnd();
|
end = conductor.displayEnd(),
|
||||||
|
domain = conductor.domain();
|
||||||
|
|
||||||
function amendRequest(request) {
|
function amendRequest(request) {
|
||||||
request = request || {};
|
request = request || {};
|
||||||
request.start = start;
|
request.start = start;
|
||||||
request.end = end;
|
request.end = end;
|
||||||
|
request.domain = domain;
|
||||||
return request;
|
return request;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -40,8 +40,10 @@ define(
|
|||||||
* @param {number} start the initial start time
|
* @param {number} start the initial start time
|
||||||
* @param {number} end the initial end time
|
* @param {number} end the initial end time
|
||||||
*/
|
*/
|
||||||
function TimeConductor(start, end) {
|
function TimeConductor(start, end, domains) {
|
||||||
this.range = { start: start, end: end };
|
this.range = { start: start, end: end };
|
||||||
|
this.domains = domains;
|
||||||
|
this.activeDomain = domains[0].key;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -68,6 +70,34 @@ define(
|
|||||||
return this.range.end;
|
return this.range.end;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get available domain options which can be used to bound time
|
||||||
|
* selection.
|
||||||
|
* @returns {TelemetryDomain[]} available domains
|
||||||
|
*/
|
||||||
|
TimeConductor.prototype.domainOptions = function () {
|
||||||
|
return this.domains;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get or set (if called with an argument) the active domain.
|
||||||
|
* @param {string} [key] the key identifying the domain choice
|
||||||
|
* @returns {TelemetryDomain} the active telemetry domain
|
||||||
|
*/
|
||||||
|
TimeConductor.prototype.domain = function (key) {
|
||||||
|
function matchesKey(domain) {
|
||||||
|
return domain.key === key;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (arguments.length > 0) {
|
||||||
|
if (!this.domains.some(matchesKey)) {
|
||||||
|
throw new Error("Unknown domain " + key);
|
||||||
|
}
|
||||||
|
this.activeDomain = key;
|
||||||
|
}
|
||||||
|
return this.activeDomain;
|
||||||
|
};
|
||||||
|
|
||||||
return TimeConductor;
|
return TimeConductor;
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -21,12 +21,9 @@
|
|||||||
*****************************************************************************/
|
*****************************************************************************/
|
||||||
/*global define,describe,it,expect,beforeEach,waitsFor,afterEach,jasmine*/
|
/*global define,describe,it,expect,beforeEach,waitsFor,afterEach,jasmine*/
|
||||||
|
|
||||||
/**
|
|
||||||
* EventSpec. Created by vwoeltje on 11/6/14. Modified by shale on 06/23/2015.
|
|
||||||
*/
|
|
||||||
define(
|
define(
|
||||||
["../src/ConductorRepresenter"],
|
["../src/ConductorRepresenter", "./TestTimeConductor"],
|
||||||
function (ConductorRepresenter) {
|
function (ConductorRepresenter, TestTimeConductor) {
|
||||||
"use strict";
|
"use strict";
|
||||||
|
|
||||||
var SCOPE_METHODS = [
|
var SCOPE_METHODS = [
|
||||||
@@ -77,10 +74,7 @@ define(
|
|||||||
testViews = [ { someKey: "some value" } ];
|
testViews = [ { someKey: "some value" } ];
|
||||||
mockScope = jasmine.createSpyObj('scope', SCOPE_METHODS);
|
mockScope = jasmine.createSpyObj('scope', SCOPE_METHODS);
|
||||||
mockElement = jasmine.createSpyObj('element', ELEMENT_METHODS);
|
mockElement = jasmine.createSpyObj('element', ELEMENT_METHODS);
|
||||||
mockConductor = jasmine.createSpyObj(
|
mockConductor = new TestTimeConductor();
|
||||||
'conductor',
|
|
||||||
[ 'displayStart', 'displayEnd' ]
|
|
||||||
);
|
|
||||||
mockCompiledTemplate = jasmine.createSpy('template');
|
mockCompiledTemplate = jasmine.createSpy('template');
|
||||||
mockNewScope = jasmine.createSpyObj('newScope', SCOPE_METHODS);
|
mockNewScope = jasmine.createSpyObj('newScope', SCOPE_METHODS);
|
||||||
mockNewElement = jasmine.createSpyObj('newElement', ELEMENT_METHODS);
|
mockNewElement = jasmine.createSpyObj('newElement', ELEMENT_METHODS);
|
||||||
@@ -135,11 +129,12 @@ define(
|
|||||||
it("exposes conductor state in scope", function () {
|
it("exposes conductor state in scope", function () {
|
||||||
mockConductor.displayStart.andReturn(1977);
|
mockConductor.displayStart.andReturn(1977);
|
||||||
mockConductor.displayEnd.andReturn(1984);
|
mockConductor.displayEnd.andReturn(1984);
|
||||||
|
mockConductor.domain.andReturn('d');
|
||||||
representer.represent(testViews[0], {});
|
representer.represent(testViews[0], {});
|
||||||
|
|
||||||
expect(mockNewScope.conductor).toEqual({
|
expect(mockNewScope.ngModel.conductor).toEqual({
|
||||||
inner: { start: 1977, end: 1984 },
|
inner: { start: 1977, end: 1984, domain: 'd' },
|
||||||
outer: { start: 1977, end: 1984 }
|
outer: { start: 1977, end: 1984, domain: 'd' }
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -151,17 +146,27 @@ define(
|
|||||||
|
|
||||||
representer.represent(testViews[0], {});
|
representer.represent(testViews[0], {});
|
||||||
|
|
||||||
mockNewScope.conductor = testState;
|
mockNewScope.ngModel.conductor = testState;
|
||||||
|
|
||||||
fireWatch(mockNewScope, 'conductor.inner.start', testState.inner.start);
|
fireWatch(
|
||||||
|
mockNewScope,
|
||||||
|
'ngModel.conductor.inner.start',
|
||||||
|
testState.inner.start
|
||||||
|
);
|
||||||
expect(mockConductor.displayStart).toHaveBeenCalledWith(42);
|
expect(mockConductor.displayStart).toHaveBeenCalledWith(42);
|
||||||
|
|
||||||
fireWatch(mockNewScope, 'conductor.inner.end', testState.inner.end);
|
fireWatch(
|
||||||
|
mockNewScope,
|
||||||
|
'ngModel.conductor.inner.end',
|
||||||
|
testState.inner.end
|
||||||
|
);
|
||||||
expect(mockConductor.displayEnd).toHaveBeenCalledWith(1984);
|
expect(mockConductor.displayEnd).toHaveBeenCalledWith(1984);
|
||||||
});
|
});
|
||||||
|
|
||||||
describe("when bounds are changing", function () {
|
describe("when bounds are changing", function () {
|
||||||
var mockThrottledFn = jasmine.createSpy('throttledFn'),
|
var startWatch = "ngModel.conductor.inner.start",
|
||||||
|
endWatch = "ngModel.conductor.inner.end",
|
||||||
|
mockThrottledFn = jasmine.createSpy('throttledFn'),
|
||||||
testBounds;
|
testBounds;
|
||||||
|
|
||||||
function fireThrottledFn() {
|
function fireThrottledFn() {
|
||||||
@@ -172,7 +177,7 @@ define(
|
|||||||
mockThrottle.andReturn(mockThrottledFn);
|
mockThrottle.andReturn(mockThrottledFn);
|
||||||
representer.represent(testViews[0], {});
|
representer.represent(testViews[0], {});
|
||||||
testBounds = { start: 0, end: 1000 };
|
testBounds = { start: 0, end: 1000 };
|
||||||
mockNewScope.conductor.inner = testBounds;
|
mockNewScope.ngModel.conductor.inner = testBounds;
|
||||||
mockConductor.displayStart.andCallFake(function () {
|
mockConductor.displayStart.andCallFake(function () {
|
||||||
return testBounds.start;
|
return testBounds.start;
|
||||||
});
|
});
|
||||||
@@ -184,14 +189,14 @@ define(
|
|||||||
it("does not broadcast while bounds are changing", function () {
|
it("does not broadcast while bounds are changing", function () {
|
||||||
expect(mockScope.$broadcast).not.toHaveBeenCalled();
|
expect(mockScope.$broadcast).not.toHaveBeenCalled();
|
||||||
testBounds.start = 100;
|
testBounds.start = 100;
|
||||||
fireWatch(mockNewScope, 'conductor.inner.start', testBounds.start);
|
fireWatch(mockNewScope, startWatch, testBounds.start);
|
||||||
testBounds.end = 500;
|
testBounds.end = 500;
|
||||||
fireWatch(mockNewScope, 'conductor.inner.end', testBounds.end);
|
fireWatch(mockNewScope, endWatch, testBounds.end);
|
||||||
fireThrottledFn();
|
fireThrottledFn();
|
||||||
testBounds.start = 200;
|
testBounds.start = 200;
|
||||||
fireWatch(mockNewScope, 'conductor.inner.start', testBounds.start);
|
fireWatch(mockNewScope, startWatch, testBounds.start);
|
||||||
testBounds.end = 400;
|
testBounds.end = 400;
|
||||||
fireWatch(mockNewScope, 'conductor.inner.end', testBounds.end);
|
fireWatch(mockNewScope, endWatch, testBounds.end);
|
||||||
fireThrottledFn();
|
fireThrottledFn();
|
||||||
expect(mockScope.$broadcast).not.toHaveBeenCalled();
|
expect(mockScope.$broadcast).not.toHaveBeenCalled();
|
||||||
});
|
});
|
||||||
@@ -199,17 +204,56 @@ define(
|
|||||||
it("does broadcast when bounds have stabilized", function () {
|
it("does broadcast when bounds have stabilized", function () {
|
||||||
expect(mockScope.$broadcast).not.toHaveBeenCalled();
|
expect(mockScope.$broadcast).not.toHaveBeenCalled();
|
||||||
testBounds.start = 100;
|
testBounds.start = 100;
|
||||||
fireWatch(mockNewScope, 'conductor.inner.start', testBounds.start);
|
fireWatch(mockNewScope, startWatch, testBounds.start);
|
||||||
testBounds.end = 500;
|
testBounds.end = 500;
|
||||||
fireWatch(mockNewScope, 'conductor.inner.end', testBounds.end);
|
fireWatch(mockNewScope, endWatch, testBounds.end);
|
||||||
fireThrottledFn();
|
fireThrottledFn();
|
||||||
fireWatch(mockNewScope, 'conductor.inner.start', testBounds.start);
|
fireWatch(mockNewScope, startWatch, testBounds.start);
|
||||||
fireWatch(mockNewScope, 'conductor.inner.end', testBounds.end);
|
fireWatch(mockNewScope, endWatch, testBounds.end);
|
||||||
fireThrottledFn();
|
fireThrottledFn();
|
||||||
expect(mockScope.$broadcast).toHaveBeenCalled();
|
expect(mockScope.$broadcast).toHaveBeenCalled();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it("exposes domain selection in scope", function () {
|
||||||
|
representer.represent(testViews[0], null);
|
||||||
|
|
||||||
|
expect(mockNewScope.ngModel.domain)
|
||||||
|
.toEqual(mockConductor.domain());
|
||||||
|
});
|
||||||
|
|
||||||
|
it("exposes domain options in scope", function () {
|
||||||
|
representer.represent(testViews[0], null);
|
||||||
|
|
||||||
|
mockConductor.domainOptions().forEach(function (option, i) {
|
||||||
|
expect(mockNewScope.ngModel.options[i].value)
|
||||||
|
.toEqual(option.key);
|
||||||
|
expect(mockNewScope.ngModel.options[i].name)
|
||||||
|
.toEqual(option.name);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it("updates domain selection from scope", function () {
|
||||||
|
var choice;
|
||||||
|
representer.represent(testViews[0], null);
|
||||||
|
|
||||||
|
// Choose a domain that isn't currently selected
|
||||||
|
mockNewScope.ngModel.options.forEach(function (option) {
|
||||||
|
if (option.value !== mockNewScope.ngModel.domain) {
|
||||||
|
choice = option.value;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(mockConductor.domain)
|
||||||
|
.not.toHaveBeenCalledWith(choice);
|
||||||
|
|
||||||
|
mockNewScope.ngModel.domain = choice;
|
||||||
|
fireWatch(mockNewScope, "ngModel.domain", choice);
|
||||||
|
|
||||||
|
expect(mockConductor.domain)
|
||||||
|
.toHaveBeenCalledWith(choice);
|
||||||
|
});
|
||||||
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -21,9 +21,6 @@
|
|||||||
*****************************************************************************/
|
*****************************************************************************/
|
||||||
/*global define,describe,it,expect,beforeEach,waitsFor,jasmine*/
|
/*global define,describe,it,expect,beforeEach,waitsFor,jasmine*/
|
||||||
|
|
||||||
/**
|
|
||||||
* EventSpec. Created by vwoeltje on 11/6/14. Modified by shale on 06/23/2015.
|
|
||||||
*/
|
|
||||||
define(
|
define(
|
||||||
["../src/ConductorService"],
|
["../src/ConductorService"],
|
||||||
function (ConductorService) {
|
function (ConductorService) {
|
||||||
@@ -38,7 +35,10 @@ define(
|
|||||||
beforeEach(function () {
|
beforeEach(function () {
|
||||||
mockNow = jasmine.createSpy('now');
|
mockNow = jasmine.createSpy('now');
|
||||||
mockNow.andReturn(TEST_NOW);
|
mockNow.andReturn(TEST_NOW);
|
||||||
conductorService = new ConductorService(mockNow);
|
conductorService = new ConductorService(mockNow, [
|
||||||
|
{ key: "d1", name: "Domain #1" },
|
||||||
|
{ key: "d2", name: "Domain #2" }
|
||||||
|
]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("initializes a time conductor around the current time", function () {
|
it("initializes a time conductor around the current time", function () {
|
||||||
|
|||||||
@@ -23,8 +23,8 @@
|
|||||||
|
|
||||||
|
|
||||||
define(
|
define(
|
||||||
["../src/ConductorTelemetryDecorator"],
|
["../src/ConductorTelemetryDecorator", "./TestTimeConductor"],
|
||||||
function (ConductorTelemetryDecorator) {
|
function (ConductorTelemetryDecorator, TestTimeConductor) {
|
||||||
"use strict";
|
"use strict";
|
||||||
|
|
||||||
describe("ConductorTelemetryDecorator", function () {
|
describe("ConductorTelemetryDecorator", function () {
|
||||||
@@ -54,10 +54,7 @@ define(
|
|||||||
'conductorService',
|
'conductorService',
|
||||||
['getConductor']
|
['getConductor']
|
||||||
);
|
);
|
||||||
mockConductor = jasmine.createSpyObj(
|
mockConductor = new TestTimeConductor();
|
||||||
'conductor',
|
|
||||||
[ 'queryStart', 'queryEnd', 'displayStart', 'displayEnd' ]
|
|
||||||
);
|
|
||||||
mockPromise = jasmine.createSpyObj(
|
mockPromise = jasmine.createSpyObj(
|
||||||
'promise',
|
'promise',
|
||||||
['then']
|
['then']
|
||||||
@@ -78,10 +75,9 @@ define(
|
|||||||
return j * j * j;
|
return j * j * j;
|
||||||
});
|
});
|
||||||
|
|
||||||
mockConductor.queryStart.andReturn(-12321);
|
|
||||||
mockConductor.queryEnd.andReturn(-12321);
|
|
||||||
mockConductor.displayStart.andReturn(42);
|
mockConductor.displayStart.andReturn(42);
|
||||||
mockConductor.displayEnd.andReturn(1977);
|
mockConductor.displayEnd.andReturn(1977);
|
||||||
|
mockConductor.domain.andReturn("testDomain");
|
||||||
|
|
||||||
decorator = new ConductorTelemetryDecorator(
|
decorator = new ConductorTelemetryDecorator(
|
||||||
mockConductorService,
|
mockConductorService,
|
||||||
@@ -89,24 +85,72 @@ define(
|
|||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("adds display start/end times to historical requests", function () {
|
|
||||||
|
describe("decorates historical requests", function () {
|
||||||
|
var request;
|
||||||
|
|
||||||
|
beforeEach(function () {
|
||||||
|
decorator.requestTelemetry([{ someKey: "some value" }]);
|
||||||
|
request = mockTelemetryService.requestTelemetry
|
||||||
|
.mostRecentCall.args[0][0];
|
||||||
|
});
|
||||||
|
|
||||||
|
it("with start times", function () {
|
||||||
|
expect(request.start).toEqual(mockConductor.displayStart());
|
||||||
|
});
|
||||||
|
|
||||||
|
it("with end times", function () {
|
||||||
|
expect(request.end).toEqual(mockConductor.displayEnd());
|
||||||
|
});
|
||||||
|
|
||||||
|
it("with domain selection", function () {
|
||||||
|
expect(request.domain).toEqual(mockConductor.domain());
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe("decorates subscription requests", function () {
|
||||||
|
var request;
|
||||||
|
|
||||||
|
beforeEach(function () {
|
||||||
|
var mockCallback = jasmine.createSpy('callback');
|
||||||
|
decorator.subscribe(mockCallback, [{ someKey: "some value" }]);
|
||||||
|
request = mockTelemetryService.subscribe
|
||||||
|
.mostRecentCall.args[1][0];
|
||||||
|
});
|
||||||
|
|
||||||
|
it("with start times", function () {
|
||||||
|
expect(request.start).toEqual(mockConductor.displayStart());
|
||||||
|
});
|
||||||
|
|
||||||
|
it("with end times", function () {
|
||||||
|
expect(request.end).toEqual(mockConductor.displayEnd());
|
||||||
|
});
|
||||||
|
|
||||||
|
it("with domain selection", function () {
|
||||||
|
expect(request.domain).toEqual(mockConductor.domain());
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it("adds display start/end times & domain selection to historical requests", function () {
|
||||||
decorator.requestTelemetry([{ someKey: "some value" }]);
|
decorator.requestTelemetry([{ someKey: "some value" }]);
|
||||||
expect(mockTelemetryService.requestTelemetry)
|
expect(mockTelemetryService.requestTelemetry)
|
||||||
.toHaveBeenCalledWith([{
|
.toHaveBeenCalledWith([{
|
||||||
someKey: "some value",
|
someKey: "some value",
|
||||||
start: mockConductor.displayStart(),
|
start: mockConductor.displayStart(),
|
||||||
end: mockConductor.displayEnd()
|
end: mockConductor.displayEnd(),
|
||||||
|
domain: jasmine.any(String)
|
||||||
}]);
|
}]);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("adds display start/end times to subscription requests", function () {
|
it("adds display start/end times & domain selection to subscription requests", function () {
|
||||||
var mockCallback = jasmine.createSpy('callback');
|
var mockCallback = jasmine.createSpy('callback');
|
||||||
decorator.subscribe(mockCallback, [{ someKey: "some value" }]);
|
decorator.subscribe(mockCallback, [{ someKey: "some value" }]);
|
||||||
expect(mockTelemetryService.subscribe)
|
expect(mockTelemetryService.subscribe)
|
||||||
.toHaveBeenCalledWith(jasmine.any(Function), [{
|
.toHaveBeenCalledWith(jasmine.any(Function), [{
|
||||||
someKey: "some value",
|
someKey: "some value",
|
||||||
start: mockConductor.displayStart(),
|
start: mockConductor.displayStart(),
|
||||||
end: mockConductor.displayEnd()
|
end: mockConductor.displayEnd(),
|
||||||
|
domain: jasmine.any(String)
|
||||||
}]);
|
}]);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
50
platform/features/conductor/test/TestTimeConductor.js
Normal file
50
platform/features/conductor/test/TestTimeConductor.js
Normal file
@@ -0,0 +1,50 @@
|
|||||||
|
/*****************************************************************************
|
||||||
|
* Open MCT Web, Copyright (c) 2014-2015, United States Government
|
||||||
|
* as represented by the Administrator of the National Aeronautics and Space
|
||||||
|
* Administration. All rights reserved.
|
||||||
|
*
|
||||||
|
* Open MCT Web is 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.
|
||||||
|
*
|
||||||
|
* Open MCT Web includes source code licensed under additional open source
|
||||||
|
* licenses. See the Open Source Licenses file (LICENSES.md) included with
|
||||||
|
* this source code distribution or the Licensing information page available
|
||||||
|
* at runtime from the About dialog for additional information.
|
||||||
|
*****************************************************************************/
|
||||||
|
/*global define,describe,it,expect,beforeEach,waitsFor,jasmine,spyOn*/
|
||||||
|
|
||||||
|
define(
|
||||||
|
["../src/TimeConductor"],
|
||||||
|
function (TimeConductor) {
|
||||||
|
'use strict';
|
||||||
|
|
||||||
|
function TestTimeConductor() {
|
||||||
|
var self = this;
|
||||||
|
|
||||||
|
TimeConductor.apply(this, [
|
||||||
|
402514200000,
|
||||||
|
444546000000,
|
||||||
|
[
|
||||||
|
{ key: "domain0", name: "Domain #1" },
|
||||||
|
{ key: "domain1", name: "Domain #2" }
|
||||||
|
]
|
||||||
|
]);
|
||||||
|
|
||||||
|
Object.keys(TimeConductor.prototype).forEach(function (method) {
|
||||||
|
spyOn(self, method).andCallThrough();
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
TestTimeConductor.prototype = TimeConductor.prototype;
|
||||||
|
|
||||||
|
return TestTimeConductor;
|
||||||
|
}
|
||||||
|
);
|
||||||
@@ -21,9 +21,6 @@
|
|||||||
*****************************************************************************/
|
*****************************************************************************/
|
||||||
/*global define,describe,it,expect,beforeEach,waitsFor,jasmine*/
|
/*global define,describe,it,expect,beforeEach,waitsFor,jasmine*/
|
||||||
|
|
||||||
/**
|
|
||||||
* EventSpec. Created by vwoeltje on 11/6/14. Modified by shale on 06/23/2015.
|
|
||||||
*/
|
|
||||||
define(
|
define(
|
||||||
["../src/TimeConductor"],
|
["../src/TimeConductor"],
|
||||||
function (TimeConductor) {
|
function (TimeConductor) {
|
||||||
@@ -32,12 +29,17 @@ define(
|
|||||||
describe("TimeConductor", function () {
|
describe("TimeConductor", function () {
|
||||||
var testStart,
|
var testStart,
|
||||||
testEnd,
|
testEnd,
|
||||||
|
testDomains,
|
||||||
conductor;
|
conductor;
|
||||||
|
|
||||||
beforeEach(function () {
|
beforeEach(function () {
|
||||||
testStart = 42;
|
testStart = 42;
|
||||||
testEnd = 12321;
|
testEnd = 12321;
|
||||||
conductor = new TimeConductor(testStart, testEnd);
|
testDomains = [
|
||||||
|
{ key: "d1", name: "Domain #1" },
|
||||||
|
{ key: "d2", name: "Domain #2" }
|
||||||
|
];
|
||||||
|
conductor = new TimeConductor(testStart, testEnd, testDomains);
|
||||||
});
|
});
|
||||||
|
|
||||||
it("provides accessors for query/display start/end times", function () {
|
it("provides accessors for query/display start/end times", function () {
|
||||||
@@ -52,6 +54,25 @@ define(
|
|||||||
expect(conductor.displayEnd()).toEqual(4);
|
expect(conductor.displayEnd()).toEqual(4);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it("exposes domain options", function () {
|
||||||
|
expect(conductor.domainOptions()).toEqual(testDomains);
|
||||||
|
});
|
||||||
|
|
||||||
|
it("exposes the current domain choice", function () {
|
||||||
|
expect(conductor.domain()).toEqual(testDomains[0].key);
|
||||||
|
});
|
||||||
|
|
||||||
|
it("allows the domain choice to be changed", function () {
|
||||||
|
conductor.domain(testDomains[1].key);
|
||||||
|
expect(conductor.domain()).toEqual(testDomains[1].key);
|
||||||
|
});
|
||||||
|
|
||||||
|
it("throws an error on attempts to set an invalid domain", function () {
|
||||||
|
expect(function () {
|
||||||
|
conductor.domain("invalid-domain");
|
||||||
|
}).toThrow();
|
||||||
|
});
|
||||||
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -105,11 +105,13 @@ define(
|
|||||||
index
|
index
|
||||||
);
|
);
|
||||||
|
|
||||||
setDisplayedValue(
|
if (index >= 0) {
|
||||||
telemetryObject,
|
setDisplayedValue(
|
||||||
telemetrySeries.getRangeValue(index),
|
telemetryObject,
|
||||||
limit && datum && limit.evaluate(datum)
|
telemetrySeries.getRangeValue(index),
|
||||||
);
|
limit && datum && limit.evaluate(datum)
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Update the displayed value for this object
|
// Update the displayed value for this object
|
||||||
|
|||||||
@@ -110,20 +110,23 @@ define(
|
|||||||
* Get the latest telemetry datum for this domain object. This
|
* Get the latest telemetry datum for this domain object. This
|
||||||
* will be from real-time telemetry, unless an index is specified,
|
* will be from real-time telemetry, unless an index is specified,
|
||||||
* in which case it will be pulled from the historical telemetry
|
* in which case it will be pulled from the historical telemetry
|
||||||
* series at the specified index.
|
* series at the specified index. If there is no latest available
|
||||||
|
* datum, this will return undefined.
|
||||||
*
|
*
|
||||||
* @param {DomainObject} domainObject the object of interest
|
* @param {DomainObject} domainObject the object of interest
|
||||||
* @param {number} [index] the index of the data of interest
|
* @param {number} [index] the index of the data of interest
|
||||||
* @returns {TelemetryDatum} the most recent datum
|
* @returns {TelemetryDatum} the most recent datum
|
||||||
*/
|
*/
|
||||||
self.getDatum = function (telemetryObject, index) {
|
self.getDatum = function (telemetryObject, index) {
|
||||||
|
function makeNewDatum(series) {
|
||||||
|
return series ?
|
||||||
|
subscription.makeDatum(telemetryObject, series, index) :
|
||||||
|
undefined;
|
||||||
|
}
|
||||||
|
|
||||||
return typeof index !== 'number' ?
|
return typeof index !== 'number' ?
|
||||||
subscription.getDatum(telemetryObject) :
|
subscription.getDatum(telemetryObject) :
|
||||||
subscription.makeDatum(
|
makeNewDatum(this.getSeries(telemetryObject));
|
||||||
telemetryObject,
|
|
||||||
this.getSeries(telemetryObject),
|
|
||||||
index
|
|
||||||
);
|
|
||||||
};
|
};
|
||||||
|
|
||||||
return self;
|
return self;
|
||||||
|
|||||||
Reference in New Issue
Block a user