Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 12 additions & 6 deletions src/vs/sessions/contrib/sessions/browser/sessionHoverContent.ts
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,7 @@ export function getSessionSummaryHoverData(
const mainWorkspace = mainChat?.workspace.get() ?? sessionWorkspace;
const topPullRequestRefs = getPullRequestRefs([isMultiFolder ? mainWorkspace : sessionWorkspace]);
return {
...getProviderDetails(session, sessionsProvidersService),
title: session.title.get() || getUntitledSessionTitle(session.isQuickChat?.get() ?? false),
...(includeUpdatedAt ? { updatedAt: session.updatedAt.get() } : {}),
location: getLocation(
Expand All @@ -60,7 +61,6 @@ export function getSessionSummaryHoverData(
pullRequests: toHoverPullRequests(topPullRequestRefs.values(), openerService),
createdBy,
externalSession: getExternalSession(session, preferencesService),
providerLabel: getProviderLabel(session, sessionsProvidersService),
...(sessionWorkspace && isMultiFolder ? {
sessionSummary: {
workspaces: getWorkspaceSummaries(sessionWorkspace, session.worktreePending?.get() ?? false, labelService),
Expand All @@ -87,6 +87,7 @@ export function getChatSummaryHoverData(
includeUpdatedAt = false,
): ISessionSummaryHoverData {
return {
...getProviderDetails(session, sessionsProvidersService),
title: chat.title.get().trim() || localize('untitledChat', "Untitled Chat"),
...(includeUpdatedAt ? { updatedAt: chat.updatedAt.get() } : {}),
location: getLocation(
Expand All @@ -98,7 +99,6 @@ export function getChatSummaryHoverData(
pullRequests: getPullRequests(chat.workspace.get(), openerService),
createdBy,
externalSession: getExternalSession(session, preferencesService),
providerLabel: getProviderLabel(session, sessionsProvidersService),
};
}

Expand Down Expand Up @@ -253,11 +253,17 @@ function getExternalSession(session: ISession, preferencesService: IPreferencesS
};
}

/** The kind of agent serving the session, e.g. "Claude". */
function getProviderLabel(session: ISession, sessionsProvidersService: ISessionsProvidersService): string | undefined {
function getProviderDetails(
session: ISession,
sessionsProvidersService: ISessionsProvidersService,
): Pick<ISessionSummaryHoverData, 'providerLabel' | 'remoteName'> {
const provider = sessionsProvidersService.getProvider(session.providerId);
if (!provider) {
return undefined;
return {};
}
return provider.sessionTypes.find(type => type.id === session.sessionType)?.label ?? provider.label;
const providerLabel = provider.sessionTypes.find(type => type.id === session.sessionType)?.label ?? provider.label;
return {
providerLabel,
...(session.remoteConnectionStatus && providerLabel !== provider.label ? { remoteName: provider.label } : {}),
};
}
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@ import { IStorageService, StorageScope, StorageTarget } from '../../../../../pla
import { IAutomationRun } from '../../../../../workbench/contrib/chat/common/automations/automation.js';
import { IAutomationService } from '../../../../../workbench/contrib/chat/common/automations/automationService.js';
import { ChatAutomationsEnabledContext } from '../../../../../workbench/contrib/chat/common/automations/automationsEnabled.js';
import { SessionSummaryHoverWidget } from '../../../../../workbench/contrib/chat/browser/agentSessions/sessionSummaryHover.js';
import { AICustomizationManagementEditorInput } from '../../../../../workbench/contrib/chat/browser/aiCustomization/aiCustomizationManagementEditorInput.js';
import { IEditorService } from '../../../../../workbench/services/editor/common/editorService.js';
import { IPreferencesService, IOpenSettingsOptions } from '../../../../../workbench/services/preferences/common/preferences.js';
Expand All @@ -57,7 +58,7 @@ import type { ICustomViewDescriptor } from '../../../../services/customView/brow
import { ISessionsListModelService, SessionsListModelService } from '../../../../services/sessions/browser/sessionsListModelService.js';
import { ISessionGroup, ISessionGroupsChangeEvent, ISessionGroupsService } from '../../../../services/sessions/browser/sessionGroupsService.js';
import { ISessionsService } from '../../../../services/sessions/browser/sessionsService.js';
import { BRANCH_CHANGES_CHANGESET_ID, ChatInteractivity, ChatOriginKind, IChat, ISession, ISessionChangeset, ISessionChangesSummary, ISessionFileChange, ISessionFolder, SessionStatus } from '../../../../services/sessions/common/session.js';
import { BRANCH_CHANGES_CHANGESET_ID, ChatInteractivity, ChatOriginKind, IChat, ISession, ISessionChangeset, ISessionChangesSummary, ISessionFileChange, ISessionFolder, ISessionType, SessionStatus } from '../../../../services/sessions/common/session.js';
import { IActiveSession, ISessionsManagementService } from '../../../../services/sessions/common/sessionsManagement.js';
import { ISessionsProvider } from '../../../../services/sessions/common/sessionsProvider.js';
import { ISessionsProvidersService } from '../../../../services/sessions/browser/sessionsProvidersService.js';
Expand Down Expand Up @@ -1940,6 +1941,53 @@ suite('Sessions - SessionsList', () => {
});
});

test('remote session hover shows the remote name after the session type', () => {
const localSession = createSession('Fix remote reconnection', { workspaceLabel: 'Workspace' });
const remoteSession: ISession = {
...localSession,
remoteConnectionStatus: constObservable({ kind: 'connected' }),
};
const provider = upcastPartial<ISessionsProvider>({
label: 'Remote Mac',
sessionTypes: [upcastPartial<ISessionType>({ id: 'test', label: 'Copilot CLI' })],
});
const createProvidersService = (provider: ISessionsProvider) => new class extends mock<ISessionsProvidersService>() {
override getProvider<T extends ISessionsProvider>(): T | undefined {
return provider as T;
}
};
const providersService = createProvidersService(provider);
const createHoverData = (session: ISession) => getSessionSummaryHoverData(
session,
providersService,
upcastPartial<IOpenerService>({}),
upcastPartial<ILabelService>({}),
upcastPartial<IPreferencesService>({}),
);
const remoteData = createHoverData(remoteSession);
const titleLine = new SessionSummaryHoverWidget(remoteData).domNode.querySelector('.session-summary-hover-title')?.textContent;
const disconnectedData = getSessionSummaryHoverData(
remoteSession,
createProvidersService({ ...provider, sessionTypes: [] }),
upcastPartial<IOpenerService>({}),
upcastPartial<ILabelService>({}),
upcastPartial<IPreferencesService>({}),
);
const disconnectedTitleLine = new SessionSummaryHoverWidget(disconnectedData).domNode.querySelector('.session-summary-hover-title')?.textContent;

assert.deepStrictEqual({
titleLine,
remoteName: remoteData.remoteName,
disconnectedTitleLine,
localRemoteName: createHoverData(localSession).remoteName,
}, {
titleLine: 'Fix remote reconnection · Copilot CLI · Remote Mac',
remoteName: 'Remote Mac',
disconnectedTitleLine: 'Fix remote reconnection · Remote Mac',
localRemoteName: undefined,
});
});

test('external session hover leads to the setting that governs external sessions', () => {
const queries: (string | undefined)[] = [];
const hoverFor = (isExternal: boolean) => getSessionSummaryHoverData(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,8 @@ export interface ISessionSummaryHoverData {
* title as "Fix the redirect loop · Claude".
*/
readonly providerLabel?: string;
/** The remote host serving the session, shown after {@link providerLabel} when present. */
readonly remoteName?: string;
/** Session that created this session, when available. */
readonly createdBy?: {
readonly title: string;
Expand Down Expand Up @@ -149,6 +151,10 @@ export class SessionSummaryHoverWidget {
appendSeparator(this._title);
dom.append(this._title, dom.$('span.session-summary-hover-provider', undefined, data.providerLabel));
}
if (data.remoteName) {
appendSeparator(this._title);
dom.append(this._title, dom.$('span.session-summary-hover-provider', undefined, data.remoteName));
}
if (data.updatedAt) {
appendSeparator(this._title);
dom.append(this._title, dom.$('span.session-summary-hover-provider', undefined, fromNow(data.updatedAt, true)));
Expand Down
Loading