diff --git a/src/vs/workbench/contrib/chat/browser/chatEditing/chatEditingSession.ts b/src/vs/workbench/contrib/chat/browser/chatEditing/chatEditingSession.ts index 8552946891ff1..134c3de87edb3 100644 --- a/src/vs/workbench/contrib/chat/browser/chatEditing/chatEditingSession.ts +++ b/src/vs/workbench/contrib/chat/browser/chatEditing/chatEditingSession.ts @@ -18,7 +18,6 @@ import { ITextModel } from '../../../../../editor/common/model.js'; import { IModelService } from '../../../../../editor/common/services/model.js'; import { ITextModelService } from '../../../../../editor/common/services/resolverService.js'; import { localize } from '../../../../../nls.js'; -import { IFileDialogService } from '../../../../../platform/dialogs/common/dialogs.js'; import { EditorActivation } from '../../../../../platform/editor/common/editor.js'; import { IFileService } from '../../../../../platform/files/common/files.js'; import { IInstantiationService } from '../../../../../platform/instantiation/common/instantiation.js'; @@ -29,12 +28,10 @@ import { IEditorGroupsService } from '../../../../services/editor/common/editorG import { IEditorService } from '../../../../services/editor/common/editorService.js'; import { MultiDiffEditor } from '../../../multiDiffEditor/browser/multiDiffEditor.js'; import { MultiDiffEditorInput } from '../../../multiDiffEditor/browser/multiDiffEditorInput.js'; -import { ChatAgentLocation, IChatAgentService } from '../../common/chatAgents.js'; import { ChatEditingSessionChangeType, ChatEditingSessionState, ChatEditKind, getMultiDiffSourceUri, IChatEditingSession, IModifiedFileEntry, WorkingSetDisplayMetadata, WorkingSetEntryRemovalReason, WorkingSetEntryState } from '../../common/chatEditingService.js'; import { IChatResponseModel } from '../../common/chatModel.js'; import { ChatEditingModifiedFileEntry, IModifiedEntryTelemetryInfo, ISnapshotEntry } from './chatEditingModifiedFileEntry.js'; import { ChatEditingTextModelContentProvider } from './chatEditingTextModelContentProviders.js'; -import { Schemas } from '../../../../../base/common/network.js'; import { isEqual, joinPath } from '../../../../../base/common/resources.js'; import { StringSHA1 } from '../../../../../base/common/hash.js'; import { IEnvironmentService } from '../../../../../platform/environment/common/environment.js'; @@ -94,7 +91,6 @@ export class ChatEditingSession extends Disposable implements IChatEditingSessio * Contains the contents of a file when the AI first began doing edits to it. */ private readonly _initialFileContents = new ResourceMap(); - private readonly _filesToSkipCreating = new ResourceSet(); private readonly _entriesObs = observableValue(this, []); public get entries(): IObservable { @@ -174,10 +170,6 @@ export class ChatEditingSession extends Disposable implements IChatEditingSessio @IBulkEditService public readonly _bulkEditService: IBulkEditService, @IEditorGroupsService private readonly _editorGroupsService: IEditorGroupsService, @IEditorService private readonly _editorService: IEditorService, - @IWorkspaceContextService private readonly _workspaceContextService: IWorkspaceContextService, - @IFileService private readonly _fileService: IFileService, - @IFileDialogService private readonly _dialogService: IFileDialogService, - @IChatAgentService private readonly _chatAgentService: IChatAgentService, @IChatService private readonly _chatService: IChatService, @INotebookService private readonly _notebookService: INotebookService, ) { @@ -187,9 +179,6 @@ export class ChatEditingSession extends Disposable implements IChatEditingSessio public async init(): Promise { const restoredSessionState = await this._instantiationService.createInstance(ChatEditingSessionStorage, this.chatSessionId).restoreState(); if (restoredSessionState) { - for (const uri of restoredSessionState.filesToSkipCreating) { - this._filesToSkipCreating.add(uri); - } for (const [uri, content] of restoredSessionState.initialFileContents) { this._initialFileContents.set(uri, content); } @@ -225,7 +214,6 @@ export class ChatEditingSession extends Disposable implements IChatEditingSessio public storeState(): Promise { const storage = this._instantiationService.createInstance(ChatEditingSessionStorage, this.chatSessionId); const state: StoredSessionState = { - filesToSkipCreating: [...this._filesToSkipCreating], initialFileContents: this._initialFileContents, pendingSnapshot: this._pendingSnapshot, recentSnapshot: this._createSnapshot(undefined), @@ -625,26 +613,11 @@ export class ChatEditingSession extends Disposable implements IChatEditingSessio } private async _acceptTextEdits(resource: URI, textEdits: TextEdit[], isLastEdits: boolean, responseModel: IChatResponseModel): Promise { - if (this._filesToSkipCreating.has(resource)) { - return; - } - if (!this._entriesObs.get().find(e => isEqual(e.modifiedURI, resource)) && this._entriesObs.get().length >= (await this.editingSessionFileLimitPromise)) { // Do not create files in a single editing session that would be in excess of our limit return; } - if (resource.scheme !== Schemas.untitled && !this._workspaceContextService.getWorkspaceFolder(resource) && !(await this._fileService.exists(resource))) { - // if the file doesn't exist yet and is outside the workspace, prompt the user for a location to save it to - const saveLocation = await this._dialogService.showSaveDialog({ title: localize('chatEditing.fileSave', '{0} wants to create a file. Choose where it should be saved.', this._chatAgentService.getDefaultAgent(ChatAgentLocation.EditingSession)?.fullName ?? 'Chat') }); - if (!saveLocation) { - // don't ask the user to create the file again when the next text edit for this same resource streams in - this._filesToSkipCreating.add(resource); - return; - } - resource = saveLocation; - } - // Make these getters because the response result is not available when the file first starts to be edited const telemetryInfo = new class { get agentId() { return responseModel.agent?.id; } @@ -730,7 +703,6 @@ export class ChatEditingSession extends Disposable implements IChatEditingSessio } interface StoredSessionState { - readonly filesToSkipCreating: URI[]; readonly initialFileContents: ResourceMap; readonly pendingSnapshot?: IChatEditingSessionSnapshot; readonly recentSnapshot: IChatEditingSessionSnapshot; @@ -801,7 +773,6 @@ class ChatEditingSessionStorage { } const linearHistory = await Promise.all(data.linearHistory.map(deserializeChatEditingSessionSnapshot)); - const filesToSkipCreating = data.filesToSkipCreating.map((uriStr: string) => URI.parse(uriStr)); const initialFileContents = new ResourceMap(); for (const fileContentDTO of data.initialFileContents) { @@ -811,7 +782,6 @@ class ChatEditingSessionStorage { const recentSnapshot = await deserializeChatEditingSessionSnapshot(data.recentSnapshot); return { - filesToSkipCreating, initialFileContents, pendingSnapshot, recentSnapshot, @@ -889,7 +859,6 @@ class ChatEditingSessionStorage { initialFileContents: serializeResourceMap(state.initialFileContents, value => addFileContent(value)), pendingSnapshot: state.pendingSnapshot ? serializeChatEditingSessionSnapshot(state.pendingSnapshot) : undefined, recentSnapshot: serializeChatEditingSessionSnapshot(state.recentSnapshot), - filesToSkipCreating: state.filesToSkipCreating.map(uri => uri.toString()), } satisfies IChatEditingSessionDTO; this._logService.debug(`chatEditingSession: Storing editing session at ${storageFolder.toString()}: ${fileContents.size} files`); @@ -959,5 +928,4 @@ interface IChatEditingSessionDTO { readonly linearHistoryIndex: number; readonly pendingSnapshot: IChatEditingSessionSnapshotDTO | undefined; readonly initialFileContents: ResourceMapDTO; - readonly filesToSkipCreating: string[]; }