1- /// This module represents the RLS view of the Cargo project model:
2- /// a graph of interdependent packages.
1+ //! This module represents the RLS view of the Cargo project model:
2+ //! a graph of interdependent packages.
33use std:: {
44 collections:: HashMap ,
55 sync:: Arc ,
@@ -20,6 +20,7 @@ use racer;
2020
2121#[ derive( Debug ) ]
2222pub struct ProjectModel {
23+ manifest_to_id : HashMap < PathBuf , Package > ,
2324 packages : Vec < PackageData > ,
2425}
2526
@@ -28,8 +29,7 @@ pub struct Package(usize);
2829
2930#[ derive( Debug ) ]
3031struct PackageData {
31- manifest : PathBuf ,
32- lib : Option < PathBuf > ,
32+ lib : Option < ( PathBuf , String ) > ,
3333 deps : Vec < Dep > ,
3434}
3535
@@ -40,12 +40,12 @@ pub struct Dep {
4040}
4141
4242impl ProjectModel {
43- pub fn load ( manifest : & Path , vfs : & Vfs ) -> Result < ProjectModel , failure:: Error > {
44- assert ! ( manifest . ends_with( "Cargo.toml" ) ) ;
43+ pub fn load ( ws_manifest : & Path , vfs : & Vfs ) -> Result < ProjectModel , failure:: Error > {
44+ assert ! ( ws_manifest . ends_with( "Cargo.toml" ) ) ;
4545 let mut config = Config :: default ( ) ?;
46- // frozen=true , locked=true
47- config. configure ( 0 , Some ( true ) , & None , true , true , & None , & [ ] ) ?;
48- let ws = Workspace :: new ( & manifest , & config) ?;
46+ // frozen = false , locked = false
47+ config. configure ( 0 , Some ( true ) , & None , false , false , & None , & [ ] ) ?;
48+ let ws = Workspace :: new ( & ws_manifest , & config) ?;
4949 // get resolve from lock file
5050 let prev = {
5151 let lock_path = ws. root ( ) . to_owned ( ) . join ( "Cargo.lock" ) ;
@@ -55,30 +55,33 @@ impl ProjectModel {
5555 let v: EncodableResolve = resolve. try_into ( ) ?;
5656 Some ( v. into_resolve ( & ws) ?)
5757 }
58- _ => None
58+ _ => None ,
5959 }
6060 } ;
61- // then resolve precisely and add overrides
6261 let mut registry = PackageRegistry :: new ( ws. config ( ) ) ?;
6362 let resolve = resolve_with_prev ( & mut registry, & ws, prev. as_ref ( ) ) ?;
6463 let cargo_packages = {
6564 let ids: Vec < PackageId > = resolve. iter ( ) . cloned ( ) . collect ( ) ;
6665 registry. get ( & ids)
6766 } ;
68-
6967 let mut pkg_id_to_pkg = HashMap :: new ( ) ;
68+ let mut manifest_to_id = HashMap :: new ( ) ;
7069 let mut packages = Vec :: new ( ) ;
7170 for ( idx, pkg_id) in resolve. iter ( ) . enumerate ( ) {
7271 let pkg = Package ( idx) ;
7372 pkg_id_to_pkg. insert ( pkg_id. clone ( ) , pkg) ;
7473 let cargo_pkg = cargo_packages. get ( pkg_id) ?;
74+ let manifest = cargo_pkg. manifest_path ( ) . to_owned ( ) ;
7575 packages. push ( PackageData {
76- manifest : cargo_pkg. manifest_path ( ) . to_owned ( ) ,
77- lib : cargo_pkg. targets ( ) . iter ( )
76+ lib : cargo_pkg
77+ . targets ( )
78+ . iter ( )
7879 . find ( |t| t. is_lib ( ) )
79- . map ( |t| t. src_path ( ) . to_owned ( ) ) ,
80+ // racer expect name 'underscored'(crate) name
81+ . map ( |t| ( t. src_path ( ) . to_owned ( ) , t. name ( ) . replace ( '-' , "_" ) ) ) ,
8082 deps : Vec :: new ( ) ,
81- } )
83+ } ) ;
84+ manifest_to_id. insert ( manifest, pkg) ;
8285 }
8386 for pkg_id in resolve. iter ( ) {
8487 for ( dep_id, _) in resolve. deps ( & pkg_id) {
@@ -99,28 +102,31 @@ impl ProjectModel {
99102 }
100103 }
101104 }
102- Ok ( ProjectModel { packages } )
105+ Ok ( ProjectModel {
106+ manifest_to_id,
107+ packages,
108+ } )
103109 }
104110
105111 pub fn package_for_manifest ( & self , manifest_path : & Path ) -> Option < Package > {
106- self . packages . iter ( )
107- . enumerate ( )
108- . find ( |( _idx, p) | p. manifest == manifest_path)
109- . map ( |( idx, _p) | Package ( idx) )
112+ self . manifest_to_id . get ( manifest_path) . map ( |& x| x)
110113 }
111114
112115 fn get ( & self , pkg : Package ) -> & PackageData {
113116 & self . packages [ pkg. 0 ]
114117 }
115118
119+ fn get_lib ( & self , pkg : Package ) -> Option < & ( PathBuf , String ) > {
120+ self . packages [ pkg. 0 ] . lib . as_ref ( )
121+ }
116122}
117123
118124impl Package {
119125 pub fn deps ( self , project : & ProjectModel ) -> & [ Dep ] {
120126 & project. get ( self ) . deps
121127 }
122128 pub fn lib_root ( self , project : & ProjectModel ) -> Option < & Path > {
123- project. get ( self ) . lib . as_ref ( ) . map ( |p| p. as_path ( ) )
129+ project. get ( self ) . lib . as_ref ( ) . map ( |p| p. 0 . as_path ( ) )
124130 }
125131}
126132
@@ -141,6 +147,13 @@ impl racer::ProjectModelProvider for RacerProjectModel {
141147 }
142148 fn resolve_dependency ( & self , manifest : & Path , libname : & str ) -> Option < PathBuf > {
143149 let pkg = self . 0 . package_for_manifest ( manifest) ?;
150+ // if current package has a library target, we have to provide its own name
151+ // in examples/tests/benches directory
152+ if let Some ( lib) = self . 0 . get_lib ( pkg) {
153+ if lib. 1 == libname {
154+ return Some ( lib. 0 . clone ( ) ) ;
155+ }
156+ }
144157 let dep = pkg. deps ( & self . 0 )
145158 . iter ( )
146159 . find ( |dep| dep. crate_name == libname) ?
0 commit comments