mirror of
https://github.com/microsoft/vscode.git
synced 2026-04-17 23:35:54 +01:00
Sessions - changes view improvements (#301485)
* Sessions - changes view improvements * Fix compilation
This commit is contained in:
@@ -52,13 +52,12 @@ import { AgentSessionProviders } from '../../../../workbench/contrib/chat/browse
|
||||
import { ChatContextKeys } from '../../../../workbench/contrib/chat/common/actions/chatContextKeys.js';
|
||||
import { IChatSessionFileChange, IChatSessionFileChange2, isIChatSessionFileChange2 } from '../../../../workbench/contrib/chat/common/chatSessionsService.js';
|
||||
import { chatEditingWidgetFileStateContextKey, hasAppliedChatEditsContextKey, hasUndecidedChatEditingResourceContextKey, IChatEditingService, ModifiedFileEntryState } from '../../../../workbench/contrib/chat/common/editing/chatEditingService.js';
|
||||
import { getChatSessionType } from '../../../../workbench/contrib/chat/common/model/chatUri.js';
|
||||
import { createFileIconThemableTreeContainerScope } from '../../../../workbench/contrib/files/browser/views/explorerView.js';
|
||||
import { IActivityService, NumberBadge } from '../../../../workbench/services/activity/common/activity.js';
|
||||
import { IEditorService, MODAL_GROUP, SIDE_GROUP } from '../../../../workbench/services/editor/common/editorService.js';
|
||||
import { IExtensionService } from '../../../../workbench/services/extensions/common/extensions.js';
|
||||
import { IWorkbenchLayoutService } from '../../../../workbench/services/layout/browser/layoutService.js';
|
||||
import { ISessionsManagementService } from '../../sessions/browser/sessionsManagementService.js';
|
||||
import { IActiveSessionItem, ISessionsManagementService } from '../../sessions/browser/sessionsManagementService.js';
|
||||
import { GITHUB_REMOTE_FILE_SCHEME } from '../../fileTreeView/browser/githubFileSystemProvider.js';
|
||||
import { CodeReviewStateKind, getCodeReviewFilesFromSessionChanges, getCodeReviewVersion, ICodeReviewService, PRReviewStateKind } from '../../codeReview/browser/codeReviewService.js';
|
||||
import { IGitRepository, IGitService } from '../../../../workbench/contrib/git/common/gitService.js';
|
||||
@@ -117,13 +116,6 @@ interface IChangesFolderItem {
|
||||
readonly name: string;
|
||||
}
|
||||
|
||||
interface IActiveSession {
|
||||
readonly resource: URI;
|
||||
readonly sessionType: string;
|
||||
readonly repository: URI | undefined;
|
||||
readonly worktree: URI | undefined;
|
||||
}
|
||||
|
||||
type ChangesTreeElement = IChangesFileItem | IChangesFolderItem;
|
||||
|
||||
function isChangesFileItem(element: ChangesTreeElement): element is IChangesFileItem {
|
||||
@@ -261,7 +253,7 @@ export class ChangesViewPane extends ViewPane {
|
||||
}
|
||||
|
||||
// Track the active session used by this view
|
||||
private readonly activeSession: IObservableWithChange<IActiveSession | undefined>;
|
||||
private readonly activeSession: IObservableWithChange<IActiveSessionItem | undefined>;
|
||||
private readonly activeSessionFileCountObs: IObservableWithChange<number>;
|
||||
private readonly activeSessionHasChangesObs: IObservableWithChange<boolean>;
|
||||
private readonly activeSessionRepositoryChangesObs: IObservableWithChange<IChangesFileItem[] | undefined>;
|
||||
@@ -310,7 +302,7 @@ export class ChangesViewPane extends ViewPane {
|
||||
this.versionModeContextKey.set(ChangesVersionMode.AllChanges);
|
||||
|
||||
// Track active session from sessions management service
|
||||
this.activeSession = derivedOpts<IActiveSession | undefined>({
|
||||
this.activeSession = derivedOpts<IActiveSessionItem | undefined>({
|
||||
equalsFn: (a, b) => isEqual(a?.resource, b?.resource),
|
||||
}, reader => {
|
||||
const activeSession = this.sessionManagementService.activeSession.read(reader);
|
||||
@@ -318,12 +310,7 @@ export class ChangesViewPane extends ViewPane {
|
||||
return undefined;
|
||||
}
|
||||
|
||||
return {
|
||||
resource: activeSession.resource,
|
||||
repository: activeSession.repository,
|
||||
worktree: activeSession.worktree,
|
||||
sessionType: getChatSessionType(activeSession.resource),
|
||||
};
|
||||
return activeSession;
|
||||
}).recomputeInitiallyAndOnChange(this._store);
|
||||
|
||||
// Track active session repository changes
|
||||
@@ -381,7 +368,7 @@ export class ChangesViewPane extends ViewPane {
|
||||
const viewSessionTypeKey = this.scopedContextKeyService.createKey<string>(ChatContextKeys.agentSessionType.key, '');
|
||||
this._register(autorun(reader => {
|
||||
const activeSession = this.activeSession.read(reader);
|
||||
viewSessionTypeKey.set(activeSession?.sessionType ?? '');
|
||||
viewSessionTypeKey.set(activeSession?.providerType ?? '');
|
||||
}));
|
||||
}
|
||||
|
||||
@@ -411,10 +398,8 @@ export class ChangesViewPane extends ViewPane {
|
||||
return 0;
|
||||
}
|
||||
|
||||
const isBackgroundSession = activeSession.sessionType === AgentSessionProviders.Background;
|
||||
|
||||
let editingSessionCount = 0;
|
||||
if (!isBackgroundSession) {
|
||||
if (activeSession.providerType !== AgentSessionProviders.Background) {
|
||||
const sessions = this.chatEditingService.editingSessionsObs.read(reader);
|
||||
const session = sessions.find(candidate => isEqual(candidate.chatSessionResource, activeSession.resource));
|
||||
editingSessionCount = session ? session.entries.read(reader).length : 0;
|
||||
@@ -509,7 +494,7 @@ export class ChangesViewPane extends ViewPane {
|
||||
const activeSession = this.activeSession.read(reader);
|
||||
|
||||
// Background chat sessions render the working set based on the session files, not the editing session
|
||||
if (activeSession?.sessionType === AgentSessionProviders.Background) {
|
||||
if (activeSession?.providerType === AgentSessionProviders.Background) {
|
||||
return [];
|
||||
}
|
||||
|
||||
@@ -720,7 +705,7 @@ export class ChangesViewPane extends ViewPane {
|
||||
const chatSessionTypeKey = this.scopedContextKeyService.createKey<string>(ChatContextKeys.agentSessionType.key, '');
|
||||
this.renderDisposables.add(autorun(reader => {
|
||||
const activeSession = this.activeSession.read(reader);
|
||||
chatSessionTypeKey.set(activeSession?.sessionType ?? '');
|
||||
chatSessionTypeKey.set(activeSession?.providerType ?? '');
|
||||
}));
|
||||
|
||||
// Bind required context keys for the menu buttons
|
||||
@@ -757,8 +742,8 @@ export class ChangesViewPane extends ViewPane {
|
||||
this.renderDisposables.add(bindContextKey(hasUncommittedChangesContextKey, this.scopedContextKeyService, r => hasUncommittedChangesObs.read(r)));
|
||||
|
||||
const isMergeBaseBranchProtectedObs = derived(reader => {
|
||||
const state = this.activeSessionRepositoryObs.read(reader)?.state.read(reader);
|
||||
return state?.HEAD?.base?.isProtected === true;
|
||||
const activeSession = this.activeSession.read(reader);
|
||||
return activeSession?.worktreeBaseBranchProtected === true;
|
||||
});
|
||||
|
||||
this.renderDisposables.add(bindContextKey(isMergeBaseBranchProtectedContextKey, this.scopedContextKeyService, r => isMergeBaseBranchProtectedObs.read(r)));
|
||||
|
||||
@@ -87,6 +87,7 @@ suite('getGitHubContext', () => {
|
||||
repository: undefined,
|
||||
worktree: undefined,
|
||||
worktreeBranchName: undefined,
|
||||
worktreeBaseBranchProtected: undefined,
|
||||
providerType: 'copilot-cloud-agent',
|
||||
...overrides,
|
||||
};
|
||||
|
||||
@@ -54,6 +54,7 @@ export interface IActiveSessionItem {
|
||||
readonly repository: URI | undefined;
|
||||
readonly worktree: URI | undefined;
|
||||
readonly worktreeBranchName: string | undefined;
|
||||
readonly worktreeBaseBranchProtected: boolean | undefined;
|
||||
readonly providerType: string;
|
||||
}
|
||||
|
||||
@@ -205,10 +206,10 @@ export class SessionsManagementService extends Disposable implements ISessionsMa
|
||||
}
|
||||
}
|
||||
|
||||
private getRepositoryFromMetadata(session: IAgentSession): [URI | undefined, URI | undefined, string | undefined] {
|
||||
private getRepositoryFromMetadata(session: IAgentSession): [URI | undefined, URI | undefined, string | undefined, boolean | undefined] {
|
||||
const metadata = session.metadata;
|
||||
if (!metadata) {
|
||||
return [undefined, undefined, undefined];
|
||||
return [undefined, undefined, undefined, undefined];
|
||||
}
|
||||
|
||||
if (session.providerType === AgentSessionProviders.Cloud) {
|
||||
@@ -219,12 +220,12 @@ export class SessionsManagementService extends Disposable implements ISessionsMa
|
||||
authority: 'github',
|
||||
path: `/${metadata.owner}/${metadata.name}/${encodeURIComponent(branch)}`
|
||||
});
|
||||
return [repositoryUri, undefined, undefined];
|
||||
return [repositoryUri, undefined, undefined, undefined];
|
||||
}
|
||||
|
||||
const workingDirectoryPath = metadata?.workingDirectoryPath as string | undefined;
|
||||
if (workingDirectoryPath) {
|
||||
return [URI.file(workingDirectoryPath), undefined, undefined];
|
||||
return [URI.file(workingDirectoryPath), undefined, undefined, undefined];
|
||||
}
|
||||
|
||||
const repositoryPath = metadata?.repositoryPath as string | undefined;
|
||||
@@ -234,11 +235,13 @@ export class SessionsManagementService extends Disposable implements ISessionsMa
|
||||
const worktreePathUri = typeof worktreePath === 'string' ? URI.file(worktreePath) : undefined;
|
||||
|
||||
const worktreeBranchName = metadata?.branchName as string | undefined;
|
||||
const worktreeBaseBranchProtected = metadata?.baseBranchProtected as boolean | undefined;
|
||||
|
||||
return [
|
||||
URI.isUri(repositoryPathUri) ? repositoryPathUri : undefined,
|
||||
URI.isUri(worktreePathUri) ? worktreePathUri : undefined,
|
||||
worktreeBranchName];
|
||||
worktreeBranchName,
|
||||
worktreeBaseBranchProtected];
|
||||
}
|
||||
|
||||
getActiveSession(): IActiveSessionItem | undefined {
|
||||
@@ -460,7 +463,7 @@ export class SessionsManagementService extends Disposable implements ISessionsMa
|
||||
if (session) {
|
||||
if (isAgentSession(session)) {
|
||||
this.lastSelectedSession = session.resource;
|
||||
const [repository, worktree, worktreeBranchName] = this.getRepositoryFromMetadata(session);
|
||||
const [repository, worktree, worktreeBranchName, worktreeBaseBranchProtected] = this.getRepositoryFromMetadata(session);
|
||||
activeSessionItem = {
|
||||
isUntitled: false,
|
||||
label: session.label,
|
||||
@@ -468,6 +471,7 @@ export class SessionsManagementService extends Disposable implements ISessionsMa
|
||||
repository: repository,
|
||||
worktree,
|
||||
worktreeBranchName: worktreeBranchName,
|
||||
worktreeBaseBranchProtected: worktreeBaseBranchProtected === true,
|
||||
providerType: session.providerType,
|
||||
};
|
||||
} else {
|
||||
@@ -478,6 +482,7 @@ export class SessionsManagementService extends Disposable implements ISessionsMa
|
||||
repository: session.repoUri,
|
||||
worktree: undefined,
|
||||
worktreeBranchName: undefined,
|
||||
worktreeBaseBranchProtected: undefined,
|
||||
providerType: session.target,
|
||||
};
|
||||
this._newActiveSessionDisposables.clear();
|
||||
@@ -490,6 +495,7 @@ export class SessionsManagementService extends Disposable implements ISessionsMa
|
||||
repository: session.repoUri,
|
||||
worktree: undefined,
|
||||
worktreeBranchName: undefined,
|
||||
worktreeBaseBranchProtected: undefined,
|
||||
providerType: session.target,
|
||||
});
|
||||
}
|
||||
@@ -529,7 +535,8 @@ export class SessionsManagementService extends Disposable implements ISessionsMa
|
||||
a.repository?.toString() === b.repository?.toString() &&
|
||||
a.worktree?.toString() === b.worktree?.toString() &&
|
||||
a.worktreeBranchName === b.worktreeBranchName &&
|
||||
a.providerType === b.providerType
|
||||
a.providerType === b.providerType &&
|
||||
a.worktreeBaseBranchProtected === b.worktreeBaseBranchProtected
|
||||
);
|
||||
}
|
||||
|
||||
@@ -605,8 +612,9 @@ export class SessionsManagementService extends Disposable implements ISessionsMa
|
||||
repository,
|
||||
worktree,
|
||||
worktreeBranchName: undefined,
|
||||
worktreeBaseBranchProtected: undefined,
|
||||
providerType: agentSession.providerType,
|
||||
});
|
||||
} satisfies IActiveSessionItem);
|
||||
}
|
||||
|
||||
resolveSessionFileUri(sessionResource: URI, relativePath: string): URI | undefined {
|
||||
|
||||
Reference in New Issue
Block a user