Skip to content

Commit 4465d16

Browse files
authored
telemetry(inline-suggestion): Fix incorrect clientComponentLatency@preprocessLatency (#6320)
## Problem t1: user trigger inline suggestion either automatically or manually t2: start building request with editor context t3: done building request t4: call service API PreprocessLatency is supposed to denote `t3 - t1`, whereas current implementation isn't which has been using `codewhispererPreprocessingLatency: session.fetchCredentialStartTime - session.invokeSuggestionStartTime,` ## Solution --- - Treat all work as PUBLIC. Private `feature/x` branches will not be squash-merged at release time. - Your code changes must meet the guidelines in [CONTRIBUTING.md](https://github.com/aws/aws-toolkit-vscode/blob/master/CONTRIBUTING.md#guidelines). - License: I confirm that my contribution is made under the terms of the Apache 2.0 license.
1 parent 2c01b0d commit 4465d16

File tree

4 files changed

+81
-19
lines changed

4 files changed

+81
-19
lines changed

packages/amazonq/test/unit/codewhisperer/util/telemetryHelper.test.ts

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ import {
1111
CodewhispererSuggestionState,
1212
CodewhispererUserDecision,
1313
} from 'aws-core-vscode/shared'
14+
import sinon from 'sinon'
1415

1516
// TODO: improve and move the following test utils to codewhisperer/testUtils.ts
1617
function aUserDecision(
@@ -38,6 +39,47 @@ function aCompletion(): Completion {
3839
}
3940

4041
describe('telemetryHelper', function () {
42+
describe('clientComponentLatency', function () {
43+
let sut: TelemetryHelper
44+
45+
beforeEach(function () {
46+
sut = new TelemetryHelper()
47+
})
48+
49+
afterEach(function () {
50+
sinon.restore()
51+
})
52+
53+
it('resetClientComponentLatencyTime should reset state variables', function () {
54+
session.invokeSuggestionStartTime = 100
55+
session.preprocessEndTime = 200
56+
session.sdkApiCallStartTime = 300
57+
session.fetchCredentialStartTime = 400
58+
session.firstSuggestionShowTime = 500
59+
60+
sut.setSdkApiCallEndTime()
61+
sut.setAllPaginationEndTime()
62+
sut.setFirstResponseRequestId('aFakeRequestId')
63+
64+
sut.resetClientComponentLatencyTime()
65+
66+
assert.strictEqual(session.invokeSuggestionStartTime, 0)
67+
assert.strictEqual(session.preprocessEndTime, 0)
68+
assert.strictEqual(session.sdkApiCallStartTime, 0)
69+
assert.strictEqual(session.fetchCredentialStartTime, 0)
70+
assert.strictEqual(session.firstSuggestionShowTime, 0)
71+
assert.strictEqual(sut.sdkApiCallEndTime, 0)
72+
assert.strictEqual(sut.allPaginationEndTime, 0)
73+
assert.strictEqual(sut.firstResponseRequestId, '')
74+
})
75+
76+
it('setInvocationSuggestionStartTime should call resetClientComponentLatencyTime', function () {
77+
const resetStub = sinon.stub(sut, 'resetClientComponentLatencyTime')
78+
sut.setInvokeSuggestionStartTime()
79+
assert.ok(resetStub.calledOnce)
80+
})
81+
})
82+
4183
describe('aggregateUserDecisionByRequest', function () {
4284
let sut: TelemetryHelper
4385

packages/core/src/codewhisperer/service/recommendationHandler.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -207,6 +207,8 @@ export class RecommendationHandler {
207207
session.requestContext = await EditorContext.buildGenerateRecommendationRequest(editor as vscode.TextEditor)
208208
}
209209
const request = session.requestContext.request
210+
// record preprocessing end time
211+
TelemetryHelper.instance.setPreprocessEndTime()
210212

211213
// set start pos for non pagination call or first pagination call
212214
if (!pagination || (pagination && page === 0)) {

packages/core/src/codewhisperer/util/codeWhispererSession.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,7 @@ class CodeWhispererSession {
4141
fetchCredentialStartTime = 0
4242
sdkApiCallStartTime = 0
4343
invokeSuggestionStartTime = 0
44+
preprocessEndTime = 0
4445
timeToFirstRecommendation = 0
4546
firstSuggestionShowTime = 0
4647
perceivedLatency = 0

packages/core/src/codewhisperer/util/telemetryHelper.ts

Lines changed: 36 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -31,9 +31,18 @@ import { Session } from '../../amazonqTest/chat/session/session'
3131

3232
export class TelemetryHelper {
3333
// Some variables for client component latency
34-
private sdkApiCallEndTime = 0
35-
private allPaginationEndTime = 0
36-
private firstResponseRequestId = ''
34+
private _sdkApiCallEndTime = 0
35+
get sdkApiCallEndTime(): number {
36+
return this._sdkApiCallEndTime
37+
}
38+
private _allPaginationEndTime = 0
39+
get allPaginationEndTime(): number {
40+
return this._allPaginationEndTime
41+
}
42+
private _firstResponseRequestId = ''
43+
get firstResponseRequestId(): string {
44+
return this._firstResponseRequestId
45+
}
3746
// variables for user trigger decision
3847
// these will be cleared after a invocation session
3948
private sessionDecisions: CodewhispererUserTriggerDecision[] = []
@@ -582,12 +591,20 @@ export class TelemetryHelper {
582591

583592
public resetClientComponentLatencyTime() {
584593
session.invokeSuggestionStartTime = 0
594+
session.preprocessEndTime = 0
585595
session.sdkApiCallStartTime = 0
586-
this.sdkApiCallEndTime = 0
596+
this._sdkApiCallEndTime = 0
587597
session.fetchCredentialStartTime = 0
588598
session.firstSuggestionShowTime = 0
589-
this.allPaginationEndTime = 0
590-
this.firstResponseRequestId = ''
599+
this._allPaginationEndTime = 0
600+
this._firstResponseRequestId = ''
601+
}
602+
603+
public setPreprocessEndTime() {
604+
if (session.preprocessEndTime !== 0) {
605+
getLogger().warn(`inline completion preprocessEndTime has been set and not reset correctly`)
606+
}
607+
session.preprocessEndTime = performance.now()
591608
}
592609

593610
/** This method is assumed to be invoked first at the start of execution **/
@@ -597,46 +614,46 @@ export class TelemetryHelper {
597614
}
598615

599616
public setSdkApiCallEndTime() {
600-
if (this.sdkApiCallEndTime === 0 && session.sdkApiCallStartTime !== 0) {
601-
this.sdkApiCallEndTime = performance.now()
617+
if (this._sdkApiCallEndTime === 0 && session.sdkApiCallStartTime !== 0) {
618+
this._sdkApiCallEndTime = performance.now()
602619
}
603620
}
604621

605622
public setAllPaginationEndTime() {
606-
if (this.allPaginationEndTime === 0 && this.sdkApiCallEndTime !== 0) {
607-
this.allPaginationEndTime = performance.now()
623+
if (this._allPaginationEndTime === 0 && this._sdkApiCallEndTime !== 0) {
624+
this._allPaginationEndTime = performance.now()
608625
}
609626
}
610627

611628
public setFirstSuggestionShowTime() {
612-
if (session.firstSuggestionShowTime === 0 && this.sdkApiCallEndTime !== 0) {
629+
if (session.firstSuggestionShowTime === 0 && this._sdkApiCallEndTime !== 0) {
613630
session.firstSuggestionShowTime = performance.now()
614631
}
615632
}
616633

617634
public setFirstResponseRequestId(requestId: string) {
618-
if (this.firstResponseRequestId === '') {
619-
this.firstResponseRequestId = requestId
635+
if (this._firstResponseRequestId === '') {
636+
this._firstResponseRequestId = requestId
620637
}
621638
}
622639

623640
// report client component latency after all pagination call finish
624641
// and at least one suggestion is shown to the user
625642
public tryRecordClientComponentLatency() {
626-
if (session.firstSuggestionShowTime === 0 || this.allPaginationEndTime === 0) {
643+
if (session.firstSuggestionShowTime === 0 || this._allPaginationEndTime === 0) {
627644
return
628645
}
629646
telemetry.codewhisperer_clientComponentLatency.emit({
630-
codewhispererAllCompletionsLatency: this.allPaginationEndTime - session.sdkApiCallStartTime,
647+
codewhispererAllCompletionsLatency: this._allPaginationEndTime - session.sdkApiCallStartTime,
631648
codewhispererCompletionType: 'Line',
632649
codewhispererCredentialFetchingLatency: session.sdkApiCallStartTime - session.fetchCredentialStartTime,
633650
codewhispererCustomizationArn: getSelectedCustomization().arn,
634651
codewhispererEndToEndLatency: session.firstSuggestionShowTime - session.invokeSuggestionStartTime,
635-
codewhispererFirstCompletionLatency: this.sdkApiCallEndTime - session.sdkApiCallStartTime,
652+
codewhispererFirstCompletionLatency: this._sdkApiCallEndTime - session.sdkApiCallStartTime,
636653
codewhispererLanguage: session.language,
637-
codewhispererPostprocessingLatency: session.firstSuggestionShowTime - this.sdkApiCallEndTime,
638-
codewhispererPreprocessingLatency: session.fetchCredentialStartTime - session.invokeSuggestionStartTime,
639-
codewhispererRequestId: this.firstResponseRequestId,
654+
codewhispererPostprocessingLatency: session.firstSuggestionShowTime - this._sdkApiCallEndTime,
655+
codewhispererPreprocessingLatency: session.preprocessEndTime - session.invokeSuggestionStartTime,
656+
codewhispererRequestId: this._firstResponseRequestId,
640657
codewhispererSessionId: session.sessionId,
641658
codewhispererTriggerType: session.triggerType,
642659
credentialStartUrl: AuthUtil.instance.startUrl,

0 commit comments

Comments
 (0)