2
2
// Licensed under the MIT License.
3
3
4
4
import {
5
+ CancellationError ,
5
6
CancellationToken ,
6
7
l10n ,
7
8
LanguageModelTool ,
@@ -12,7 +13,7 @@ import {
12
13
Uri ,
13
14
workspace ,
14
15
} from 'vscode' ;
15
- import { PythonExtension } from '../api/types' ;
16
+ import { PythonExtension , ResolvedEnvironment } from '../api/types' ;
16
17
import { IServiceContainer } from '../ioc/types' ;
17
18
import { ICodeExecutionService } from '../terminals/types' ;
18
19
import { TerminalCodeExecutionProvider } from '../terminals/codeExecution/terminalCodeExecution' ;
@@ -26,7 +27,7 @@ import {
26
27
} from './utils' ;
27
28
import { resolveFilePath } from './utils' ;
28
29
import { ITerminalHelper } from '../common/terminal/types' ;
29
- import { raceTimeout } from '../common/utils/async' ;
30
+ import { raceTimeout , sleep } from '../common/utils/async' ;
30
31
import { IInterpreterPathService } from '../common/types' ;
31
32
import { DisposableStore } from '../common/utils/resourceLifecycle' ;
32
33
import { IRecommendedEnvironmentService } from '../interpreter/configuration/types' ;
@@ -36,7 +37,8 @@ import { convertEnvInfoToPythonEnvironment } from '../pythonEnvironments/legacyI
36
37
import { sortInterpreters } from '../interpreter/helpers' ;
37
38
import { isStableVersion } from '../pythonEnvironments/info/pythonVersion' ;
38
39
import { createVirtualEnvironment } from '../pythonEnvironments/creation/createEnvApi' ;
39
- import { traceError , traceWarn } from '../logging' ;
40
+ import { traceError , traceVerbose , traceWarn } from '../logging' ;
41
+ import { StopWatch } from '../common/utils/stopWatch' ;
40
42
41
43
export class CreateVirtualEnvTool implements LanguageModelTool < IResourceReference > {
42
44
private readonly terminalExecutionService : TerminalCodeExecutionProvider ;
@@ -62,12 +64,12 @@ export class CreateVirtualEnvTool implements LanguageModelTool<IResourceReferenc
62
64
async invoke (
63
65
options : LanguageModelToolInvocationOptions < IResourceReference > ,
64
66
token : CancellationToken ,
65
- ) : Promise < LanguageModelToolResult | undefined > {
67
+ ) : Promise < LanguageModelToolResult > {
66
68
const resource = resolveFilePath ( options . input . resourcePath ) ;
67
69
let info = await this . getPreferredEnvForCreation ( resource ) ;
68
70
if ( ! info ) {
69
- traceWarn ( `${ CreateVirtualEnvTool . toolName } tool not invoked, no preferred environment found.` ) ;
70
- return ;
71
+ traceWarn ( `Called ${ CreateVirtualEnvTool . toolName } tool not invoked, no preferred environment found.` ) ;
72
+ throw new CancellationError ( ) ;
71
73
}
72
74
const { workspaceFolder, preferredGlobalPythonEnv } = info ;
73
75
const interpreterPathService = this . serviceContainer . get < IInterpreterPathService > ( IInterpreterPathService ) ;
@@ -85,16 +87,30 @@ export class CreateVirtualEnvTool implements LanguageModelTool<IResourceReferenc
85
87
token ,
86
88
) ;
87
89
if ( ! created ?. path ) {
88
- traceWarn ( `${ CreateVirtualEnvTool . toolName } tool not invoked, no preferred environment found .` ) ;
89
- return ;
90
+ traceWarn ( `${ CreateVirtualEnvTool . toolName } tool not invoked, virtual env not created .` ) ;
91
+ throw new CancellationError ( ) ;
90
92
}
93
+
91
94
// Wait a few secs to ensure the env is selected as the active environment..
92
95
// If this doesn't work, then something went wrong.
93
96
await raceTimeout ( 5_000 , interpreterChanged ) ;
94
- const env = await this . api . resolveEnvironment ( created . path ) ;
97
+
98
+ const stopWatch = new StopWatch ( ) ;
99
+ let env : ResolvedEnvironment | undefined ;
100
+ while ( stopWatch . elapsedTime < 5_000 || ! env ) {
101
+ env = await this . api . resolveEnvironment ( created . path ) ;
102
+ if ( env ) {
103
+ break ;
104
+ } else {
105
+ traceVerbose (
106
+ `${ CreateVirtualEnvTool . toolName } tool invoked, env created but not yet resolved, waiting...` ,
107
+ ) ;
108
+ await sleep ( 200 ) ;
109
+ }
110
+ }
95
111
if ( ! env ) {
96
- traceError ( `${ CreateVirtualEnvTool . toolName } tool not invoked, no preferred environment found .` ) ;
97
- return ;
112
+ traceError ( `${ CreateVirtualEnvTool . toolName } tool invoked, env created but unable to resolve details .` ) ;
113
+ throw new CancellationError ( ) ;
98
114
}
99
115
return await getEnvDetailsForResponse (
100
116
env ,
0 commit comments