style(vscode-ide-companion): adjust chat session initialization logic and optimize tool invocation component style

This commit is contained in:
yiliang114
2025-12-06 22:44:31 +08:00
15 changed files with 373 additions and 387 deletions

View File

@@ -26,8 +26,6 @@ export class WebViewProvider {
private authStateManager: AuthStateManager;
private disposables: vscode.Disposable[] = [];
private agentInitialized = false; // Track if agent has been initialized
// Control whether to auto-restore last session on the very first connect of this panel
private autoRestoreOnFirstConnect = true;
constructor(
context: vscode.ExtensionContext,
@@ -242,13 +240,6 @@ export class WebViewProvider {
);
}
/**
* Suppress auto-restore once for this panel (used by "New Chat Tab").
*/
suppressAutoRestoreOnce(): void {
this.autoRestoreOnFirstConnect = false;
}
async show(): Promise<void> {
const panel = this.panelManager.getPanel();
@@ -383,6 +374,22 @@ export class WebViewProvider {
type: 'activeEditorChanged',
data: { fileName, filePath, selection: selectionInfo },
});
// Surface available modes and current mode (from ACP initialize)
this.agentManager.onModeInfo((info) => {
this.sendMessageToWebView({
type: 'modeInfo',
data: info || {},
});
});
// Surface mode changes (from ACP or immediate set_mode response)
this.agentManager.onModeChanged((modeId) => {
this.sendMessageToWebView({
type: 'modeChanged',
data: { modeId },
});
});
}
});
this.disposables.push(selectionChangeDisposable);
@@ -681,199 +688,40 @@ export class WebViewProvider {
/**
* Load messages from current Qwen session
* Attempts to restore an existing session before creating a new one
* Skips session restoration and creates a new session directly
*/
private async loadCurrentSessionMessages(): Promise<void> {
try {
console.log(
'[WebViewProvider] Initializing with session restoration attempt',
'[WebViewProvider] Initializing with new session (skipping restoration)',
);
const workspaceFolder = vscode.workspace.workspaceFolders?.[0];
const workingDir = workspaceFolder?.uri.fsPath || process.cwd();
// First, try to restore an existing session if we have cached auth
if (this.authStateManager) {
const hasValidAuth = await this.authStateManager.hasValidAuth(
// Skip session restoration entirely and create a new session directly
try {
await this.agentManager.createNewSession(
workingDir,
authMethod,
this.authStateManager,
);
if (hasValidAuth) {
const allowAutoRestore = this.autoRestoreOnFirstConnect;
// Reset for subsequent connects (only once per panel lifecycle unless set again)
this.autoRestoreOnFirstConnect = true;
console.log('[WebViewProvider] ACP session created successfully');
if (allowAutoRestore) {
console.log(
'[WebViewProvider] Valid auth found, attempting auto-restore of last session...',
);
try {
const page = await this.agentManager.getSessionListPaged({
size: 1,
});
const item = page.sessions[0] as
| { sessionId?: string; id?: string; cwd?: string }
| undefined;
if (item && (item.sessionId || item.id)) {
const targetId = (item.sessionId || item.id) as string;
await this.agentManager.loadSessionViaAcp(
targetId,
(item.cwd as string | undefined) ?? workingDir,
);
this.messageHandler.setCurrentConversationId(targetId);
const messages =
await this.agentManager.getSessionMessages(targetId);
// Even if messages array is empty, we should still switch to the session
// This ensures we don't lose the session context
this.sendMessageToWebView({
type: 'qwenSessionSwitched',
data: { sessionId: targetId, messages },
});
console.log(
'[WebViewProvider] Auto-restored last session:',
targetId,
);
// Ensure auth state is saved after successful session restore
if (this.authStateManager) {
await this.authStateManager.saveAuthState(
workingDir,
authMethod,
);
console.log(
'[WebViewProvider] Auth state saved after session restore',
);
}
return;
}
console.log(
'[WebViewProvider] No sessions to auto-restore, creating new session',
);
} catch (restoreError) {
console.warn(
'[WebViewProvider] Auto-restore failed, will create a new session:',
restoreError,
);
// Try to get session messages anyway, even if loadSessionViaAcp failed
// This can happen if the session exists locally but failed to load in the CLI
try {
const page = await this.agentManager.getSessionListPaged({
size: 1,
});
const item = page.sessions[0] as
| { sessionId?: string; id?: string }
| undefined;
if (item && (item.sessionId || item.id)) {
const targetId = (item.sessionId || item.id) as string;
const messages =
await this.agentManager.getSessionMessages(targetId);
// Switch to the session with whatever messages we could get
this.messageHandler.setCurrentConversationId(targetId);
this.sendMessageToWebView({
type: 'qwenSessionSwitched',
data: { sessionId: targetId, messages },
});
console.log(
'[WebViewProvider] Partially restored last session:',
targetId,
);
// Ensure auth state is saved after partial session restore
if (this.authStateManager) {
await this.authStateManager.saveAuthState(
workingDir,
authMethod,
);
console.log(
'[WebViewProvider] Auth state saved after partial session restore',
);
}
return;
}
} catch (fallbackError) {
console.warn(
'[WebViewProvider] Fallback session restore also failed:',
fallbackError,
);
}
}
} else {
console.log(
'[WebViewProvider] Auto-restore suppressed for this panel',
);
}
// Create a fresh ACP session (no auto-restore or restore failed)
try {
await this.agentManager.createNewSession(
workingDir,
this.authStateManager,
);
console.log('[WebViewProvider] ACP session created successfully');
// Ensure auth state is saved after successful session creation
if (this.authStateManager) {
await this.authStateManager.saveAuthState(workingDir, authMethod);
console.log(
'[WebViewProvider] Auth state saved after session creation',
);
}
} catch (sessionError) {
console.error(
'[WebViewProvider] Failed to create ACP session:',
sessionError,
);
vscode.window.showWarningMessage(
`Failed to create ACP session: ${sessionError}. You may need to authenticate first.`,
);
}
} else {
// Ensure auth state is saved after successful session creation
if (this.authStateManager) {
await this.authStateManager.saveAuthState(workingDir, authMethod);
console.log(
'[WebViewProvider] No valid cached auth found, creating new session',
'[WebViewProvider] Auth state saved after session creation',
);
// No valid auth, create a new session (will trigger auth if needed)
try {
await this.agentManager.createNewSession(
workingDir,
this.authStateManager,
);
console.log('[WebViewProvider] ACP session created successfully');
} catch (sessionError) {
console.error(
'[WebViewProvider] Failed to create ACP session:',
sessionError,
);
vscode.window.showWarningMessage(
`Failed to create ACP session: ${sessionError}. You may need to authenticate first.`,
);
}
}
} else {
// No auth state manager, create a new session
console.log(
'[WebViewProvider] No auth state manager, creating new session',
} catch (sessionError) {
console.error(
'[WebViewProvider] Failed to create ACP session:',
sessionError,
);
vscode.window.showWarningMessage(
`Failed to create ACP session: ${sessionError}. You may need to authenticate first.`,
);
try {
await this.agentManager.createNewSession(
workingDir,
this.authStateManager,
);
console.log('[WebViewProvider] ACP session created successfully');
} catch (sessionError) {
console.error(
'[WebViewProvider] Failed to create ACP session:',
sessionError,
);
vscode.window.showWarningMessage(
`Failed to create ACP session: ${sessionError}. You may need to authenticate first.`,
);
}
}
await this.initializeEmptyConversation();