@@ -5,7 +5,7 @@ use conda_info::CondaInfo;
55use env_variables:: EnvVariables ;
66use environment_locations:: { get_conda_environment_paths, get_environments} ;
77use environments:: { get_conda_environment_info, CondaEnvironment } ;
8- use log:: { error, warn } ;
8+ use log:: error;
99use manager:: CondaManager ;
1010use pet_core:: {
1111 os_environment:: Environment ,
@@ -20,6 +20,7 @@ use std::{
2020 sync:: { Arc , Mutex } ,
2121 thread,
2222} ;
23+ use telemetry:: report_missing_envs;
2324use utils:: { is_conda_env, is_conda_install} ;
2425
2526mod conda_info;
@@ -29,11 +30,16 @@ pub mod environment_locations;
2930pub mod environments;
3031pub mod manager;
3132pub mod package;
33+ mod telemetry;
3234pub mod utils;
3335
3436pub trait CondaLocator : Send + Sync {
3537 fn find_in ( & self , path : & Path ) -> Option < LocatorResult > ;
36- fn find_with_conda_executable ( & self , conda_executable : Option < PathBuf > ) -> Option < ( ) > ;
38+ fn find_and_report_missing_envs (
39+ & self ,
40+ reporter : & dyn Reporter ,
41+ conda_executable : Option < PathBuf > ,
42+ ) -> Option < ( ) > ;
3743}
3844pub struct Conda {
3945 /// Directories where conda environments are found (env_dirs returned from `conda info --json`)
@@ -55,11 +61,29 @@ impl Conda {
5561}
5662
5763impl CondaLocator for Conda {
58- fn find_with_conda_executable ( & self , conda_executable : Option < PathBuf > ) -> Option < ( ) > {
59- let info = CondaInfo :: from ( conda_executable) ?;
60- // Have we seen these envs, if yes, then nothing to do
64+ fn find_and_report_missing_envs (
65+ & self ,
66+ reporter : & dyn Reporter ,
67+ conda_executable : Option < PathBuf > ,
68+ ) -> Option < ( ) > {
69+ // Look for environments that we couldn't find without spawning conda.
70+ let user_provided_conda_exe = conda_executable. is_some ( ) ;
71+ let conda_info = CondaInfo :: from ( conda_executable) ?;
72+
73+ // Keep track of these directories for next refresh
74+ // This way we can search these directories again and they will be reported.
75+ {
76+ let mut env_dirs = self . env_dirs . lock ( ) . unwrap ( ) ;
77+ env_dirs. append ( & mut conda_info. envs_dirs . clone ( ) ) ;
78+ conda_info. envs_dirs . iter ( ) . for_each ( |p| {
79+ if !env_dirs. contains ( p) {
80+ env_dirs. push ( p. clone ( ) ) ;
81+ }
82+ } ) ;
83+ }
84+
6185 let environments = self . environments . lock ( ) . unwrap ( ) . clone ( ) ;
62- let mut new_envs = info
86+ let new_envs = conda_info
6387 . envs
6488 . clone ( )
6589 . into_iter ( )
@@ -68,61 +92,57 @@ impl CondaLocator for Conda {
6892 if new_envs. is_empty ( ) {
6993 return None ;
7094 }
95+ let environments = environments
96+ . into_values ( )
97+ . collect :: < Vec < PythonEnvironment > > ( ) ;
7198
72- // Oh oh, we have new envs, lets find them.
73- let manager = CondaManager :: from_info ( & info. executable , & info) ?;
74- for path in new_envs. iter ( ) {
75- let mgr = manager. clone ( ) ;
76- if let Some ( env) = get_conda_environment_info ( path, & Some ( mgr. clone ( ) ) ) {
77- warn ! (
78- "Found a conda env {:?} using the conda exe {:?}" ,
79- env. prefix, info. executable
80- ) ;
81- }
82- }
83-
84- // Also keep track of these directories for next time
85- let mut env_dirs = self . env_dirs . lock ( ) . unwrap ( ) ;
86- env_dirs. append ( & mut new_envs) ;
87-
88- // Send telemetry
99+ let _ = report_missing_envs (
100+ reporter,
101+ & self . env_vars ,
102+ & new_envs,
103+ & environments,
104+ & conda_info,
105+ user_provided_conda_exe,
106+ ) ;
89107
90108 Some ( ( ) )
91109 }
110+
92111 fn find_in ( & self , conda_dir : & Path ) -> Option < LocatorResult > {
93112 if !is_conda_install ( conda_dir) {
94113 return None ;
95114 }
96115 if let Some ( manager) = CondaManager :: from ( conda_dir) {
97- let conda_dir = manager. conda_dir . clone ( ) ;
98- // Keep track to search again later.
99- // Possible we'll find environments in other directories created using this manager
100- let mut managers = self . managers . lock ( ) . unwrap ( ) ;
101- // Keep track to search again later.
102- // Possible we'll find environments in other directories created using this manager
103- managers. insert ( conda_dir. clone ( ) , manager. clone ( ) ) ;
104- drop ( managers) ;
116+ if let Some ( conda_dir) = manager. conda_dir . clone ( ) {
117+ // Keep track to search again later.
118+ // Possible we'll find environments in other directories created using this manager
119+ let mut managers = self . managers . lock ( ) . unwrap ( ) ;
120+ // Keep track to search again later.
121+ // Possible we'll find environments in other directories created using this manager
122+ managers. insert ( conda_dir. clone ( ) , manager. clone ( ) ) ;
123+ drop ( managers) ;
105124
106- let mut new_environments = vec ! [ ] ;
125+ let mut new_environments = vec ! [ ] ;
107126
108- // Find all the environments in the conda install folder. (under `envs` folder)
109- for conda_env in
110- get_conda_environments ( & get_environments ( & conda_dir) , & manager. clone ( ) . into ( ) )
111- {
112- let mut environments = self . environments . lock ( ) . unwrap ( ) ;
113- if environments. contains_key ( & conda_env. prefix ) {
114- continue ;
127+ // Find all the environments in the conda install folder. (under `envs` folder)
128+ for conda_env in
129+ get_conda_environments ( & get_environments ( & conda_dir) , & manager. clone ( ) . into ( ) )
130+ {
131+ let mut environments = self . environments . lock ( ) . unwrap ( ) ;
132+ if environments. contains_key ( & conda_env. prefix ) {
133+ continue ;
134+ }
135+ let env = conda_env
136+ . to_python_environment ( Some ( conda_dir. clone ( ) ) , Some ( manager. to_manager ( ) ) ) ;
137+ environments. insert ( conda_env. prefix . clone ( ) , env. clone ( ) ) ;
138+ new_environments. push ( env) ;
115139 }
116- let env = conda_env
117- . to_python_environment ( Some ( conda_dir. clone ( ) ) , Some ( manager. to_manager ( ) ) ) ;
118- environments. insert ( conda_env. prefix . clone ( ) , env. clone ( ) ) ;
119- new_environments. push ( env) ;
120- }
121140
122- return Some ( LocatorResult {
123- environments : new_environments,
124- managers : vec ! [ manager. to_manager( ) ] ,
125- } ) ;
141+ return Some ( LocatorResult {
142+ environments : new_environments,
143+ managers : vec ! [ manager. to_manager( ) ] ,
144+ } ) ;
145+ }
126146 }
127147 None
128148 }
@@ -279,7 +299,7 @@ impl Locator for Conda {
279299 // 5. Report this env.
280300 if let Some ( manager) = manager {
281301 let env = env. to_python_environment (
282- Some ( manager. conda_dir . clone ( ) ) ,
302+ manager. conda_dir . clone ( ) ,
283303 Some ( manager. to_manager ( ) ) ,
284304 ) ;
285305 let mut environments = self . environments . lock ( ) . unwrap ( ) ;
0 commit comments