Skip to content
Merged
Show file tree
Hide file tree
Changes from 3 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
3 changes: 3 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -46,3 +46,6 @@ logs
.qodo/
.vercel
.roo/mcp.json

# Qdrant
qdrant_storage/
20 changes: 15 additions & 5 deletions pnpm-lock.yaml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

97 changes: 70 additions & 27 deletions src/extension.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ try {
console.warn("Failed to load environment variables:", e)
}

import { CloudService, ExtensionBridgeService } from "@roo-code/cloud"
import { CloudService, ExtensionBridgeService, type CloudUserInfo } from "@roo-code/cloud"
import { TelemetryService, PostHogTelemetryClient } from "@roo-code/telemetry"

import "./utils/path" // Necessary to have access to String.prototype.toPosix.
Expand Down Expand Up @@ -51,6 +51,11 @@ import { initializeI18n } from "./i18n"

let outputChannel: vscode.OutputChannel
let extensionContext: vscode.ExtensionContext
let cloudService: CloudService | undefined

let authStateChangedHandler: (() => void) | undefined
let settingsUpdatedHandler: (() => void) | undefined
let userInfoHandler: ((data: { userInfo: CloudUserInfo }) => Promise<void>) | undefined

// This method is called when your extension is activated.
// Your extension is activated the very first time the command is executed.
Expand Down Expand Up @@ -94,27 +99,66 @@ export async function activate(context: vscode.ExtensionContext) {

const contextProxy = await ContextProxy.getInstance(context)

// Initialize code index managers for all workspace folders
// Initialize code index managers for all workspace folders.
const codeIndexManagers: CodeIndexManager[] = []

if (vscode.workspace.workspaceFolders) {
for (const folder of vscode.workspace.workspaceFolders) {
const manager = CodeIndexManager.getInstance(context, folder.uri.fsPath)

if (manager) {
codeIndexManagers.push(manager)

try {
await manager.initialize(contextProxy)
} catch (error) {
outputChannel.appendLine(
`[CodeIndexManager] Error during background CodeIndexManager configuration/indexing for ${folder.uri.fsPath}: ${error.message || error}`,
)
}

context.subscriptions.push(manager)
}
}
}

// Initialize the provider *before* the Roo Code Cloud service.
const provider = new ClineProvider(context, outputChannel, "sidebar", contextProxy, mdmService)

// Initialize Roo Code Cloud service.
const cloudService = await CloudService.createInstance(context, cloudLogger)
const postStateListener = () => ClineProvider.getVisibleInstance()?.postStateToWebview()
authStateChangedHandler = postStateListener
settingsUpdatedHandler = postStateListener

userInfoHandler = async ({ userInfo }: { userInfo: any }) => {
postStateListener()

if (!CloudService.instance.cloudAPI) {
cloudLogger("[CloudService] CloudAPI is not initialized")
return
}

try {
const config = await CloudService.instance.cloudAPI.bridgeConfig()

ExtensionBridgeService.handleRemoteControlState(
userInfo,
contextProxy.getValue("remoteControlEnabled"),
{ ...config, provider, sessionId: vscode.env.sessionId },
(message: string) => outputChannel.appendLine(message),
)
} catch (error) {
cloudLogger(
`[CloudService] Failed to fetch bridgeConfig: ${error instanceof Error ? error.message : String(error)}`,
)
}
}

cloudService = await CloudService.createInstance(context, cloudLogger, {
"auth-state-changed": authStateChangedHandler,
"settings-updated": settingsUpdatedHandler,
"user-info": userInfoHandler,
})

try {
if (cloudService.telemetryClient) {
Expand All @@ -126,33 +170,10 @@ export async function activate(context: vscode.ExtensionContext) {
)
}

const postStateListener = () => ClineProvider.getVisibleInstance()?.postStateToWebview()

cloudService.on("auth-state-changed", postStateListener)
cloudService.on("settings-updated", postStateListener)

cloudService.on("user-info", async ({ userInfo }) => {
postStateListener()

const bridgeConfig = await cloudService.cloudAPI?.bridgeConfig().catch(() => undefined)

if (!bridgeConfig) {
outputChannel.appendLine("[CloudService] Failed to get bridge config")
return
}

ExtensionBridgeService.handleRemoteControlState(
userInfo,
contextProxy.getValue("remoteControlEnabled"),
{ ...bridgeConfig, provider, sessionId: vscode.env.sessionId },
(message: string) => outputChannel.appendLine(message),
)
})

// Add to subscriptions for proper cleanup on deactivate.
context.subscriptions.push(cloudService)

const provider = new ClineProvider(context, outputChannel, "sidebar", contextProxy, mdmService)
// Finish initializing the provider.
TelemetryService.instance.setProvider(provider)

context.subscriptions.push(
Expand Down Expand Up @@ -280,6 +301,28 @@ export async function activate(context: vscode.ExtensionContext) {
export async function deactivate() {
outputChannel.appendLine(`${Package.name} extension deactivated`)

if (cloudService && CloudService.hasInstance()) {
try {
if (authStateChangedHandler) {
CloudService.instance.off("auth-state-changed", authStateChangedHandler)
}

if (settingsUpdatedHandler) {
CloudService.instance.off("settings-updated", settingsUpdatedHandler)
}

if (userInfoHandler) {
CloudService.instance.off("user-info", userInfoHandler as any)
}

outputChannel.appendLine("CloudService event handlers cleaned up")
} catch (error) {
outputChannel.appendLine(
`Failed to clean up CloudService event handlers: ${error instanceof Error ? error.message : String(error)}`,
)
}
}

const bridgeService = ExtensionBridgeService.getInstance()

if (bridgeService) {
Expand Down
3 changes: 2 additions & 1 deletion src/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -429,7 +429,7 @@
"@mistralai/mistralai": "^1.9.18",
"@modelcontextprotocol/sdk": "^1.9.0",
"@qdrant/js-client-rest": "^1.14.0",
"@roo-code/cloud": "^0.22.0",
"@roo-code/cloud": "^0.24.0",
"@roo-code/ipc": "workspace:^",
"@roo-code/telemetry": "workspace:^",
"@roo-code/types": "workspace:^",
Expand All @@ -455,6 +455,7 @@
"i18next": "^25.0.0",
"ignore": "^7.0.3",
"isbinaryfile": "^5.0.2",
"jwt-decode": "^4.0.0",
"lodash.debounce": "^4.0.8",
"mammoth": "^1.9.1",
"monaco-vscode-textmate-theme-converter": "^0.1.7",
Expand Down
2 changes: 0 additions & 2 deletions webview-ui/src/components/chat/ChatView.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -1787,8 +1787,6 @@ const ChatViewComponent: React.ForwardRefRenderFunction<ChatViewRef, ChatViewPro

const areButtonsVisible = showScrollToBottom || primaryButtonText || secondaryButtonText || isStreaming

console.log("ChatView - render()")

return (
<div
data-testid="chat-view"
Expand Down
Loading