Skip to content

Commit aceebe1

Browse files
authored
fix(cwl): Hide LiveTail CodeLenses and display info message when closing session (#6063)
## Problem Currently after closing a session in a way that leaves the TextDocument open (`Stop tailing` CodeLens), the codeLenses remain visible. This means a user could click `Stop tailing` again, and receive an error for not being able to find the running LiveTail session for the given document. Additionally, there is no feedback when a session is closed. Clicking `Stop tailing` doesn't signal to the user that the session was actually stopped. ## Solution * Provide a `refresh` method in the LiveTail CodeLens provider. This fires an event to force recomputing the CodeLenses on a document. * Modify LiveTail Lens provider to return no Lenses if the session is not running (in the registry) * Display an information window when a Session is stopped * Changes wording/placement on some log statements for consistency.
1 parent 833cc7f commit aceebe1

File tree

5 files changed

+43
-19
lines changed

5 files changed

+43
-19
lines changed

packages/core/src/awsService/cloudWatchLogs/activation.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,7 @@ export async function activate(context: vscode.ExtensionContext, configuration:
3434

3535
const documentProvider = new LogDataDocumentProvider(registry)
3636
const liveTailDocumentProvider = new LiveTailDocumentProvider()
37-
37+
const liveTailCodeLensProvider = new LiveTailCodeLensProvider(liveTailRegistry)
3838
context.subscriptions.push(
3939
vscode.languages.registerCodeLensProvider(
4040
{
@@ -55,7 +55,7 @@ export async function activate(context: vscode.ExtensionContext, configuration:
5555
language: 'log',
5656
scheme: cloudwatchLogsLiveTailScheme,
5757
},
58-
new LiveTailCodeLensProvider()
58+
liveTailCodeLensProvider
5959
)
6060
)
6161

@@ -121,11 +121,11 @@ export async function activate(context: vscode.ExtensionContext, configuration:
121121
? { regionName: node.regionCode, groupName: node.logGroup.logGroupName! }
122122
: undefined
123123
const source = node ? (logGroupInfo ? 'ExplorerLogGroupNode' : 'ExplorerServiceNode') : 'Command'
124-
await tailLogGroup(liveTailRegistry, source, logGroupInfo)
124+
await tailLogGroup(liveTailRegistry, source, liveTailCodeLensProvider, logGroupInfo)
125125
}),
126126

127127
Commands.register('aws.cwl.stopTailingLogGroup', async (document: vscode.TextDocument, source: string) => {
128-
closeSession(document.uri, liveTailRegistry, source)
128+
closeSession(document.uri, liveTailRegistry, source, liveTailCodeLensProvider)
129129
}),
130130

131131
Commands.register('aws.cwl.clearDocument', async (document: vscode.TextDocument) => {

packages/core/src/awsService/cloudWatchLogs/commands/tailLogGroup.ts

Lines changed: 18 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -16,10 +16,12 @@ import {
1616
} from '@aws-sdk/client-cloudwatch-logs'
1717
import { getLogger, globals, ToolkitError } from '../../../shared'
1818
import { uriToKey } from '../cloudWatchLogsUtils'
19+
import { LiveTailCodeLensProvider } from '../document/liveTailCodeLensProvider'
1920

2021
export async function tailLogGroup(
2122
registry: LiveTailSessionRegistry,
2223
source: string,
24+
codeLensProvider: LiveTailCodeLensProvider,
2325
logData?: { regionName: string; groupName: string }
2426
): Promise<void> {
2527
await telemetry.cwlLiveTail_Start.run(async (span) => {
@@ -55,9 +57,11 @@ export async function tailLogGroup(
5557
const document = await prepareDocument(session)
5658

5759
hideShowStatusBarItemsOnActiveEditor(session, document)
58-
registerTabChangeCallback(session, registry, document)
60+
registerTabChangeCallback(session, registry, document, codeLensProvider)
5961

6062
const stream = await session.startLiveTailSession()
63+
getLogger().info(`LiveTail session started: ${uriToKey(session.uri)}`)
64+
6165
span.record({
6266
source: source,
6367
result: 'Succeeded',
@@ -69,14 +73,21 @@ export async function tailLogGroup(
6973
})
7074
}
7175

72-
export function closeSession(sessionUri: vscode.Uri, registry: LiveTailSessionRegistry, source: string) {
76+
export function closeSession(
77+
sessionUri: vscode.Uri,
78+
registry: LiveTailSessionRegistry,
79+
source: string,
80+
codeLensProvider: LiveTailCodeLensProvider
81+
) {
7382
telemetry.cwlLiveTail_Stop.run((span) => {
7483
const session = registry.get(uriToKey(sessionUri))
7584
if (session === undefined) {
76-
throw new ToolkitError(`No LiveTail session found for URI: ${sessionUri.toString()}`)
85+
throw new ToolkitError(`No LiveTail session found for URI: ${uriToKey(sessionUri)}`)
7786
}
7887
session.stopLiveTailSession()
7988
registry.delete(uriToKey(sessionUri))
89+
void vscode.window.showInformationMessage(`Stopped LiveTail session: ${uriToKey(sessionUri)}`)
90+
codeLensProvider.refresh()
8091
span.record({
8192
result: 'Succeeded',
8293
source: source,
@@ -130,7 +141,7 @@ async function handleSessionStream(
130141
//AbortSignal interrupts the LiveTail stream, causing error to be thrown here.
131142
//Can assume that stopLiveTailSession() has already been called - AbortSignal is only
132143
//exposed through that method.
133-
getLogger().info(`Session stopped: ${uriToKey(session.uri)}`)
144+
getLogger().info(`LiveTail session stopped: ${uriToKey(session.uri)}`)
134145
} else {
135146
//Unexpected exception.
136147
session.stopLiveTailSession()
@@ -233,12 +244,13 @@ function hideShowStatusBarItemsOnActiveEditor(session: LiveTailSession, document
233244
function registerTabChangeCallback(
234245
session: LiveTailSession,
235246
registry: LiveTailSessionRegistry,
236-
document: vscode.TextDocument
247+
document: vscode.TextDocument,
248+
codeLensProvider: LiveTailCodeLensProvider
237249
) {
238250
vscode.window.tabGroups.onDidChangeTabs((tabEvent) => {
239251
const isOpen = isLiveTailSessionOpenInAnyTab(session)
240252
if (!isOpen) {
241-
closeSession(session.uri, registry, 'ClosedEditors')
253+
closeSession(session.uri, registry, 'ClosedEditors', codeLensProvider)
242254
void clearDocument(document)
243255
}
244256
})

packages/core/src/awsService/cloudWatchLogs/document/liveTailCodeLensProvider.ts

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,16 +5,22 @@
55

66
import * as vscode from 'vscode'
77
import { cloudwatchLogsLiveTailScheme } from '../../../shared/constants'
8+
import { LiveTailSessionRegistry } from '../registry/liveTailSessionRegistry'
9+
import { uriToKey } from '../cloudWatchLogsUtils'
810

911
export class LiveTailCodeLensProvider implements vscode.CodeLensProvider {
10-
onDidChangeCodeLenses?: vscode.Event<void> | undefined
12+
private _onDidChangeCodeLenses: vscode.EventEmitter<void> = new vscode.EventEmitter<void>()
13+
public readonly onDidChangeCodeLenses: vscode.Event<void> = this._onDidChangeCodeLenses.event
1114

12-
provideCodeLenses(
15+
public constructor(private readonly registry: LiveTailSessionRegistry) {}
16+
17+
public provideCodeLenses(
1318
document: vscode.TextDocument,
1419
token: vscode.CancellationToken
1520
): vscode.ProviderResult<vscode.CodeLens[]> {
1621
const uri = document.uri
17-
if (uri.scheme !== cloudwatchLogsLiveTailScheme) {
22+
//if registry does not contain session, it is assumed to have been stopped, thus, hide lenses.
23+
if (uri.scheme !== cloudwatchLogsLiveTailScheme || !this.registry.has(uriToKey(uri))) {
1824
return []
1925
}
2026
const codeLenses: vscode.CodeLens[] = []
@@ -23,6 +29,10 @@ export class LiveTailCodeLensProvider implements vscode.CodeLensProvider {
2329
return codeLenses
2430
}
2531

32+
public refresh() {
33+
this._onDidChangeCodeLenses.fire()
34+
}
35+
2636
private buildClearDocumentCodeLens(document: vscode.TextDocument): vscode.CodeLens {
2737
const range = this.getBottomOfDocumentRange(document)
2838
const command: vscode.Command = {

packages/core/src/awsService/cloudWatchLogs/registry/liveTailSession.ts

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -10,8 +10,8 @@ import {
1010
StartLiveTailResponseStream,
1111
} from '@aws-sdk/client-cloudwatch-logs'
1212
import { LogStreamFilterResponse } from '../wizard/liveTailLogStreamSubmenu'
13-
import { CloudWatchLogsSettings, uriToKey } from '../cloudWatchLogsUtils'
14-
import { getLogger, globals, Settings, ToolkitError } from '../../../shared'
13+
import { CloudWatchLogsSettings } from '../cloudWatchLogsUtils'
14+
import { globals, Settings, ToolkitError } from '../../../shared'
1515
import { createLiveTailURIFromArgs } from './liveTailSessionRegistry'
1616
import { getUserAgent } from '../../../shared/telemetry/util'
1717
import { convertToTimeString } from '../../../shared/datetime'
@@ -98,7 +98,6 @@ export class LiveTailSession {
9898
this.statusBarUpdateTimer = globals.clock.setInterval(() => {
9999
this.updateStatusBarItemText()
100100
}, 500)
101-
getLogger().info(`LiveTail session started: ${uriToKey(this.uri)}`)
102101
return commandOutput.responseStream
103102
}
104103

packages/core/src/test/awsService/cloudWatchLogs/commands/tailLogGroup.test.ts

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ import { getTestWindow } from '../../../shared/vscode/window'
2121
import { CloudWatchLogsSettings, uriToKey } from '../../../../awsService/cloudWatchLogs/cloudWatchLogsUtils'
2222
import { installFakeClock } from '../../../testUtil'
2323
import { DefaultAwsContext, ToolkitError } from '../../../../shared'
24+
import { LiveTailCodeLensProvider } from '../../../../awsService/cloudWatchLogs/document/liveTailCodeLensProvider'
2425

2526
describe('TailLogGroup', function () {
2627
const testLogGroup = 'test-log-group'
@@ -32,6 +33,7 @@ describe('TailLogGroup', function () {
3233

3334
let sandbox: sinon.SinonSandbox
3435
let registry: LiveTailSessionRegistry
36+
let codeLensProvider: LiveTailCodeLensProvider
3537
let startLiveTailSessionSpy: sinon.SinonSpy
3638
let stopLiveTailSessionSpy: sinon.SinonSpy
3739
let cloudwatchSettingsSpy: sinon.SinonSpy
@@ -47,6 +49,7 @@ describe('TailLogGroup', function () {
4749
clock.reset()
4850
sandbox = sinon.createSandbox()
4951
registry = new LiveTailSessionRegistry()
52+
codeLensProvider = new LiveTailCodeLensProvider(registry)
5053
})
5154

5255
after(function () {
@@ -94,7 +97,7 @@ describe('TailLogGroup', function () {
9497
cloudwatchSettingsSpy = sandbox.stub(CloudWatchLogsSettings.prototype, 'get').callsFake(() => {
9598
return 1
9699
})
97-
await tailLogGroup(registry, testSource, {
100+
await tailLogGroup(registry, testSource, codeLensProvider, {
98101
groupName: testLogGroup,
99102
regionName: testRegion,
100103
})
@@ -132,7 +135,7 @@ describe('TailLogGroup', function () {
132135
return getTestWizardResponse()
133136
})
134137
await assert.rejects(async () => {
135-
await tailLogGroup(registry, testSource, {
138+
await tailLogGroup(registry, testSource, codeLensProvider, {
136139
groupName: testLogGroup,
137140
regionName: testRegion,
138141
})
@@ -153,7 +156,7 @@ describe('TailLogGroup', function () {
153156
})
154157
registry.set(uriToKey(session.uri), session)
155158

156-
closeSession(session.uri, registry, testSource)
159+
closeSession(session.uri, registry, testSource, codeLensProvider)
157160
assert.strictEqual(0, registry.size)
158161
assert.strictEqual(true, stopLiveTailSessionSpy.calledOnce)
159162
assert.strictEqual(0, clock.countTimers())

0 commit comments

Comments
 (0)