Skip to content
This repository was archived by the owner on Oct 3, 2023. It is now read-only.

Commit 8a0a133

Browse files
Switch to CircleCi machine build type (#16)
1 parent 29aaad1 commit 8a0a133

8 files changed

Lines changed: 250 additions & 174 deletions

File tree

.circleci/config.yml

Lines changed: 1 addition & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -11,33 +11,8 @@ release_tags: &release_tags
1111
version: 2.0
1212
jobs:
1313
build:
14-
docker:
15-
# specify the version you desire here
16-
- image: circleci/node:10-browsers
17-
18-
# Specify service dependencies here if necessary
19-
# CircleCI maintains a library of pre-built images
20-
# documented at https://circleci.com/docs/2.0/circleci-images/
21-
# - image: circleci/mongo:3.4.4
22-
23-
working_directory: ~/repo
24-
14+
machine: true
2515
steps:
2616
- checkout
27-
28-
# Download and cache dependencies
29-
- restore_cache:
30-
keys:
31-
- v1-dependencies-{{ checksum "package.json" }}
32-
# fallback to using the latest cache if no exact match is found
33-
- v1-dependencies-
34-
3517
- run: npm install
36-
37-
- save_cache:
38-
paths:
39-
- node_modules
40-
key: v1-dependencies-{{ checksum "package.json" }}
41-
42-
# run tests!
4318
- run: npm test

packages/opencensus-web-core/package-lock.json

Lines changed: 3 additions & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

packages/opencensus-web-core/test/test-span.ts

Lines changed: 20 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@
1616

1717
import {LinkType, MessageEventType} from '../src/trace/model/enums';
1818
import {Span} from '../src/trace/model/span';
19+
import {mockGetterOrValue, restoreGetterOrValue} from './util';
1920

2021
describe('Span', () => {
2122
let span: Span;
@@ -33,17 +34,27 @@ describe('Span', () => {
3334
expect(span.id).toBe('000000000000000b');
3435
});
3536

36-
it('calculates time fields based on startPerfTime/endPerfTime', () => {
37-
expect(span.ended).toBe(false);
37+
describe('time fields', () => {
38+
let realTimeOrigin: number;
39+
beforeEach(() => {
40+
realTimeOrigin = performance.timeOrigin;
41+
});
42+
afterEach(() => {
43+
restoreGetterOrValue(performance, 'timeOrigin', realTimeOrigin);
44+
});
3845

39-
spyOnProperty(performance, 'timeOrigin').and.returnValue(1548000000000);
40-
span.startPerfTime = 2;
41-
span.endPerfTime = 4.5;
46+
it('calculates them based on startPerfTime/endPerfTime', () => {
47+
expect(span.ended).toBe(false);
4248

43-
expect(span.ended).toBe(true);
44-
expect(span.startTime.getTime()).toBe(1548000000002);
45-
expect(span.endTime.getTime()).toBe(1548000000004);
46-
expect(span.duration).toBe(2.5);
49+
mockGetterOrValue(performance, 'timeOrigin', 1548000000000);
50+
span.startPerfTime = 2;
51+
span.endPerfTime = 4.5;
52+
53+
expect(span.ended).toBe(true);
54+
expect(span.startTime.getTime()).toBe(1548000000002);
55+
expect(span.endTime.getTime()).toBe(1548000000004);
56+
expect(span.duration).toBe(2.5);
57+
});
4758
});
4859

4960
it('calculates isRootSpan based on parentSpanId', () => {

packages/opencensus-web-core/test/test-time-util.ts

Lines changed: 87 additions & 82 deletions
Original file line numberDiff line numberDiff line change
@@ -15,99 +15,104 @@
1515
*/
1616

1717
import {adjustPerfTimeOrigin, getDateForPerfTime, getIsoDateStrForPerfTime, getPerfTimeOrigin, TEST_ONLY} from '../src/common/time-util';
18+
import {mockGetterOrValue, restoreGetterOrValue} from './util';
1819

19-
describe('getPerfTimeOrigin', () => {
20-
it('returns `performance.timeOrigin` if set', () => {
21-
spyOnProperty(performance, 'timeOrigin').and.returnValue(1548000000000);
22-
23-
expect(getPerfTimeOrigin()).toBe(1548000000000);
24-
});
25-
26-
it('calculates via polyfill if `performance.timeOrigin` unset', () => {
27-
spyOnProperty(performance, 'timeOrigin').and.returnValue(undefined);
28-
spyOn(Date, 'now').and.returnValue(1548000009999);
29-
spyOn(performance, 'now').and.returnValue(9999);
30-
31-
expect(getPerfTimeOrigin()).toBe(1548000000000);
32-
});
33-
});
34-
35-
describe('adjustPerfTimeOrigin', () => {
36-
const CLIENT_TIME_ORIGIN = 1548000000000;
20+
describe('time utils', () => {
21+
let realTimeOrigin: number;
3722
beforeEach(() => {
38-
spyOnProperty(performance, 'timeOrigin')
39-
.and.returnValue(CLIENT_TIME_ORIGIN);
23+
realTimeOrigin = performance.timeOrigin;
4024
});
4125
afterEach(() => {
42-
TEST_ONLY.clearAdjustedPerfTime();
26+
restoreGetterOrValue(performance, 'timeOrigin', realTimeOrigin);
4327
});
4428

45-
it('keeps client time origin if no performance timing missing', () => {
46-
spyOnProperty(performance, 'timing').and.returnValue(undefined);
47-
adjustPerfTimeOrigin(1548000001000.2, 5.1);
48-
expect(getPerfTimeOrigin()).toBe(CLIENT_TIME_ORIGIN);
29+
describe('getPerfTimeOrigin', () => {
30+
it('returns `performance.timeOrigin` if set', () => {
31+
mockGetterOrValue(performance, 'timeOrigin', 1548000000000);
32+
expect(getPerfTimeOrigin()).toBe(1548000000000);
33+
});
34+
35+
it('calculates via polyfill if `performance.timeOrigin` unset', () => {
36+
mockGetterOrValue(performance, 'timeOrigin', undefined);
37+
spyOn(Date, 'now').and.returnValue(1548000009999);
38+
spyOn(performance, 'now').and.returnValue(9999);
39+
});
4940
});
5041

51-
it('keeps client time origin if server time longer than client', () => {
52-
// Client nav fetch duration is 5ms
53-
spyOnProperty(performance.timing, 'requestStart').and.returnValue(10.1);
54-
spyOnProperty(performance.timing, 'responseStart').and.returnValue(15.1);
55-
56-
// Server nav fetch duration is 10ms
57-
adjustPerfTimeOrigin(1548000001000.2, /* serverNavFetchDuration */ 10);
58-
59-
expect(getPerfTimeOrigin()).toBe(CLIENT_TIME_ORIGIN);
42+
describe('adjustPerfTimeOrigin', () => {
43+
const CLIENT_TIME_ORIGIN = 1548000000000;
44+
beforeEach(() => {
45+
mockGetterOrValue(performance, 'timeOrigin', CLIENT_TIME_ORIGIN);
46+
});
47+
afterEach(() => {
48+
TEST_ONLY.clearAdjustedPerfTime();
49+
});
50+
51+
it('keeps client time origin if performance timing missing', () => {
52+
spyOnProperty(performance, 'timing').and.returnValue(undefined);
53+
adjustPerfTimeOrigin(1548000001000.2, 5.1);
54+
expect(getPerfTimeOrigin()).toBe(CLIENT_TIME_ORIGIN);
55+
});
56+
57+
it('keeps client time origin if server time longer than client', () => {
58+
// Client nav fetch duration is 5ms
59+
spyOnProperty(performance.timing, 'requestStart').and.returnValue(10.1);
60+
spyOnProperty(performance.timing, 'responseStart').and.returnValue(15.1);
61+
62+
// Server nav fetch duration is 10ms
63+
adjustPerfTimeOrigin(1548000001000.2, /* serverNavFetchDuration */ 10);
64+
65+
expect(getPerfTimeOrigin()).toBe(CLIENT_TIME_ORIGIN);
66+
});
67+
68+
it('adjusts origin to center server span in client span', () => {
69+
const clientNavFetchStartInPerfTime = 10; // Performance clock millis.
70+
spyOnProperty(performance.timing, 'requestStart')
71+
.and.returnValue(clientNavFetchStartInPerfTime);
72+
const clientNavFetchEndInPerfTime = 18; // Performance clock millis.
73+
spyOnProperty(performance.timing, 'responseStart')
74+
.and.returnValue(clientNavFetchEndInPerfTime);
75+
76+
const serverNavFetchStartEpochMillis = 1500000001000; // Epoch millis.
77+
const serverNavFetchDuration = 6; // Duration millis
78+
adjustPerfTimeOrigin(
79+
serverNavFetchStartEpochMillis, serverNavFetchDuration);
80+
81+
// Calculations to make the expectation clearer:
82+
const clientNavFetchDuration =
83+
clientNavFetchEndInPerfTime - clientNavFetchStartInPerfTime;
84+
expect(clientNavFetchDuration).toBe(8); // Duration millis
85+
const networkTime = clientNavFetchDuration - serverNavFetchDuration;
86+
expect(networkTime).toBe(2); // Duration millis
87+
const clientNavStartInEpochMillis =
88+
serverNavFetchStartEpochMillis - networkTime / 2;
89+
expect(clientNavStartInEpochMillis).toBe(1500000000999);
90+
const perfOriginInEpochMillis =
91+
clientNavStartInEpochMillis - clientNavFetchStartInPerfTime;
92+
expect(perfOriginInEpochMillis).toBe(1500000000989);
93+
94+
expect(getPerfTimeOrigin()).toBe(perfOriginInEpochMillis);
95+
});
6096
});
6197

62-
it('adjusts origin to center server span in client span', () => {
63-
const clientNavFetchStartInPerfTime = 10; // Performance clock millis.
64-
spyOnProperty(performance.timing, 'requestStart')
65-
.and.returnValue(clientNavFetchStartInPerfTime);
66-
const clientNavFetchEndInPerfTime = 18; // Performance clock millis.
67-
spyOnProperty(performance.timing, 'responseStart')
68-
.and.returnValue(clientNavFetchEndInPerfTime);
69-
70-
const serverNavFetchStartEpochMillis = 1500000001000; // Epoch millis.
71-
const serverNavFetchDuration = 6; // Duration millis
72-
adjustPerfTimeOrigin(
73-
serverNavFetchStartEpochMillis, serverNavFetchDuration);
74-
75-
// Calculations to make the expectation clearer:
76-
const clientNavFetchDuration =
77-
clientNavFetchEndInPerfTime - clientNavFetchStartInPerfTime;
78-
expect(clientNavFetchDuration).toBe(8); // Duration millis
79-
const networkTime = clientNavFetchDuration - serverNavFetchDuration;
80-
expect(networkTime).toBe(2); // Duration millis
81-
const clientNavStartInEpochMillis =
82-
serverNavFetchStartEpochMillis - networkTime / 2;
83-
expect(clientNavStartInEpochMillis).toBe(1500000000999);
84-
const perfOriginInEpochMillis =
85-
clientNavStartInEpochMillis - clientNavFetchStartInPerfTime;
86-
expect(perfOriginInEpochMillis).toBe(1500000000989);
87-
88-
expect(getPerfTimeOrigin()).toBe(perfOriginInEpochMillis);
98+
describe('getDateForPerfTime', () => {
99+
it('calculates date for perf time based on time origin', () => {
100+
mockGetterOrValue(performance, 'timeOrigin', 1548000000000);
101+
expect(getDateForPerfTime(999.6).getTime()).toBe(1548000000999);
102+
});
89103
});
90-
});
91-
92-
describe('getDateForPerfTime', () => {
93-
it('calculates date for perf time based on time origin', () => {
94-
spyOnProperty(performance, 'timeOrigin').and.returnValue(1548000000000);
95-
96-
expect(getDateForPerfTime(999.6).getTime()).toBe(1548000000999);
97-
});
98-
});
99-
100-
describe('getIsoDateStrForPerfTime', () => {
101-
it('converts perf time to nanosecond-precise ISO date string', () => {
102-
spyOnProperty(performance, 'timeOrigin').and.returnValue(1535683887001);
103-
expect(getIsoDateStrForPerfTime(0.000001))
104-
.toEqual('2018-08-31T02:51:27.001000001Z');
105-
});
106-
107-
it('accurately combines milliseconds from origin and perf times', () => {
108-
spyOnProperty(performance, 'timeOrigin').and.returnValue(1535683887441.586);
109104

110-
expect(getIsoDateStrForPerfTime(658867.8000000073))
111-
.toEqual('2018-08-31T03:02:26.309385938Z');
105+
describe('getIsoDateStrForPerfTime', () => {
106+
it('converts perf time to nanosecond-precise ISO date string', () => {
107+
mockGetterOrValue(performance, 'timeOrigin', 1535683887001);
108+
expect(getIsoDateStrForPerfTime(0.000001))
109+
.toEqual('2018-08-31T02:51:27.001000001Z');
110+
});
111+
112+
it('accurately combines milliseconds from origin and perf times', () => {
113+
mockGetterOrValue(performance, 'timeOrigin', 1535683887441.586);
114+
expect(getIsoDateStrForPerfTime(658867.8000000073))
115+
.toEqual('2018-08-31T03:02:26.309385938Z');
116+
});
112117
});
113118
});
Lines changed: 64 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,64 @@
1+
/**
2+
* Copyright 2019, OpenCensus Authors
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
/** Enables setting arbitrary properties on an object. */
18+
interface IndexableObject {
19+
[key: string]: unknown;
20+
}
21+
22+
/**
23+
* This mocks an object value that can either be a getter property, or just a
24+
* regular object value. The reason this is needed it because certain browser
25+
* APIs (such as `performance.timeOrigin`) may be modeled as a getter in some
26+
* browsers but not in others.
27+
*
28+
* If the property is a getter, this will use Jasmine's `spyOnProperty`, and for
29+
* normal values it just sets the object property directly to the mock value.
30+
*
31+
* @param object The object whose property to set with a mock value
32+
* @param property Name of the property to set
33+
* @mockValue Value to set. Should keep the real value first to restory it with
34+
* `restoreGetterOrValue` below.
35+
*/
36+
export function mockGetterOrValue<T>(
37+
object: T, property: keyof T, mockValue: unknown) {
38+
if (isGetter(object, property)) {
39+
spyOnProperty(object, property).and.returnValue(mockValue);
40+
} else {
41+
// Allow forcing mock values that violate the type signature. This allows
42+
// mocking `undefined` for browser APIs that are not available in all
43+
// browsers.
44+
(object as IndexableObject)[property as string] = mockValue;
45+
}
46+
}
47+
48+
/**
49+
* Restores an object's previously mocked property (getter or normal value)
50+
* to a real value that was saved before the mocking was done.
51+
* This is a no-op for getter properties since Jasmine's `spyOnProperty` is
52+
* restored automatically. For normal values, this just sets the value.
53+
*/
54+
export function restoreGetterOrValue<T, K extends keyof T>(
55+
object: T, property: K, value: T[K]) {
56+
if (isGetter(object, property)) return;
57+
object[property] = value;
58+
}
59+
60+
function isGetter<T>(object: T, property: keyof T) {
61+
const prototype = Object.getPrototypeOf(object);
62+
const descriptor = Object.getOwnPropertyDescriptor(prototype, property);
63+
return descriptor && descriptor.hasOwnProperty('get');
64+
}

packages/opencensus-web-exporter-ocagent/test/test-adapters.ts

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,13 +19,22 @@ import * as webTypes from '@opencensus/web-core';
1919
import {adaptRootSpan} from '../src/adapters';
2020
import * as apiTypes from '../src/api-types';
2121
import {MockRootSpan, MockSpan} from './mock-trace-types';
22+
import {mockGetterOrValue, restoreGetterOrValue} from './util';
2223

2324
const API_SPAN_KIND_UNSPECIFIED: apiTypes.SpanKindUnspecified = 0;
2425
const API_SPAN_KIND_SERVER: apiTypes.SpanKindServer = 1;
2526
const API_LINK_TYPE_CHILD_LINKED_SPAN: apiTypes.LinkTypeChildLinkedSpan = 1;
2627
const API_MESSAGE_EVENT_TYPE_SENT: apiTypes.MessageEventTypeSent = 1;
2728

2829
describe('Core to API Span adapters', () => {
30+
let realTimeOrigin: number;
31+
beforeEach(() => {
32+
realTimeOrigin = performance.timeOrigin;
33+
});
34+
afterEach(() => {
35+
restoreGetterOrValue(performance, 'timeOrigin', realTimeOrigin);
36+
});
37+
2938
it('adapts @opencensus/core span to grpc-gateway properties', () => {
3039
const coreRootSpan: coreTypes.RootSpan = new MockRootSpan(
3140
{
@@ -173,7 +182,7 @@ describe('Core to API Span adapters', () => {
173182
});
174183

175184
it('adapts perf times of web spans as high-res timestamps', () => {
176-
spyOnProperty(performance, 'timeOrigin').and.returnValue(1548000000000);
185+
mockGetterOrValue(performance, 'timeOrigin', 1548000000000);
177186
const tracer = new webTypes.Tracer();
178187
const webSpan1 = new webTypes.Span();
179188
webSpan1.id = '000000000000000a';

0 commit comments

Comments
 (0)