1
1
use std:: collections:: HashMap ;
2
- use std:: io:: prelude:: * ;
3
- use std:: fs:: File ;
4
2
use std:: path:: Path ;
3
+ use std:: str;
5
4
6
5
use serde_json;
7
6
8
7
use core:: dependency:: { Dependency , DependencyInner , Kind } ;
9
8
use core:: { SourceId , Summary , PackageId , Registry } ;
10
9
use sources:: registry:: { RegistryPackage , RegistryDependency , INDEX_LOCK } ;
10
+ use sources:: registry:: RegistryData ;
11
11
use util:: { CargoResult , ChainError , internal, Filesystem , Config } ;
12
+ use util:: human;
12
13
13
14
pub struct RegistryIndex < ' cfg > {
14
15
source_id : SourceId ,
@@ -23,7 +24,8 @@ impl<'cfg> RegistryIndex<'cfg> {
23
24
pub fn new ( id : & SourceId ,
24
25
path : & Filesystem ,
25
26
config : & ' cfg Config ,
26
- locked : bool ) -> RegistryIndex < ' cfg > {
27
+ locked : bool )
28
+ -> RegistryIndex < ' cfg > {
27
29
RegistryIndex {
28
30
source_id : id. clone ( ) ,
29
31
path : path. clone ( ) ,
@@ -35,13 +37,16 @@ impl<'cfg> RegistryIndex<'cfg> {
35
37
}
36
38
37
39
/// Return the hash listed for a specified PackageId.
38
- pub fn hash ( & mut self , pkg : & PackageId ) -> CargoResult < String > {
40
+ pub fn hash ( & mut self ,
41
+ pkg : & PackageId ,
42
+ load : & mut RegistryData )
43
+ -> CargoResult < String > {
39
44
let key = ( pkg. name ( ) . to_string ( ) , pkg. version ( ) . to_string ( ) ) ;
40
45
if let Some ( s) = self . hashes . get ( & key) {
41
46
return Ok ( s. clone ( ) )
42
47
}
43
48
// Ok, we're missing the key, so parse the index file to load it.
44
- self . summaries ( pkg. name ( ) ) ?;
49
+ self . summaries ( pkg. name ( ) , load ) ?;
45
50
self . hashes . get ( & key) . chain_error ( || {
46
51
internal ( format ! ( "no hash listed for {}" , pkg) )
47
52
} ) . map ( |s| s. clone ( ) )
@@ -51,20 +56,26 @@ impl<'cfg> RegistryIndex<'cfg> {
51
56
///
52
57
/// Returns a list of pairs of (summary, yanked) for the package name
53
58
/// specified.
54
- pub fn summaries ( & mut self , name : & str ) -> CargoResult < & Vec < ( Summary , bool ) > > {
59
+ pub fn summaries ( & mut self ,
60
+ name : & str ,
61
+ load : & mut RegistryData )
62
+ -> CargoResult < & Vec < ( Summary , bool ) > > {
55
63
if self . cache . contains_key ( name) {
56
64
return Ok ( & self . cache [ name] ) ;
57
65
}
58
- let summaries = self . load_summaries ( name) ?;
66
+ let summaries = self . load_summaries ( name, load ) ?;
59
67
let summaries = summaries. into_iter ( ) . filter ( |summary| {
60
68
summary. 0 . package_id ( ) . name ( ) == name
61
69
} ) . collect ( ) ;
62
70
self . cache . insert ( name. to_string ( ) , summaries) ;
63
71
Ok ( & self . cache [ name] )
64
72
}
65
73
66
- fn load_summaries ( & mut self , name : & str ) -> CargoResult < Vec < ( Summary , bool ) > > {
67
- let ( path, _lock) = if self . locked {
74
+ fn load_summaries ( & mut self ,
75
+ name : & str ,
76
+ load : & mut RegistryData )
77
+ -> CargoResult < Vec < ( Summary , bool ) > > {
78
+ let ( root, _lock) = if self . locked {
68
79
let lock = self . path . open_ro ( Path :: new ( INDEX_LOCK ) ,
69
80
self . config ,
70
81
"the registry index" ) ;
@@ -84,25 +95,32 @@ impl<'cfg> RegistryIndex<'cfg> {
84
95
85
96
// see module comment for why this is structured the way it is
86
97
let path = match fs_name. len ( ) {
87
- 1 => path. join ( "1" ) . join ( & fs_name) ,
88
- 2 => path. join ( "2" ) . join ( & fs_name) ,
89
- 3 => path. join ( "3" ) . join ( & fs_name[ ..1 ] ) . join ( & fs_name) ,
90
- _ => path. join ( & fs_name[ 0 ..2 ] )
91
- . join ( & fs_name[ 2 ..4 ] )
92
- . join ( & fs_name) ,
98
+ 1 => format ! ( "1/{}" , fs_name) ,
99
+ 2 => format ! ( "2/{}" , fs_name) ,
100
+ 3 => format ! ( "3/{}/{}" , & fs_name[ ..1 ] , fs_name) ,
101
+ _ => format ! ( "{}/{}/{}" , & fs_name[ 0 ..2 ] , & fs_name[ 2 ..4 ] , fs_name) ,
102
+ // 1 => Path::new("1").join(fs_name),
103
+ // 2 => Path::new("2").join(fs_name),
104
+ // 3 => Path::new("3").join(&fs_name[..1]).join(fs_name),
105
+ // _ => Path::new(&fs_name[0..2]).join(&fs_name[2..4]).join(fs_name),
93
106
} ;
94
- match File :: open ( & path) {
95
- Ok ( mut f) => {
96
- let mut contents = String :: new ( ) ;
97
- f. read_to_string ( & mut contents) ?;
98
- let ret: CargoResult < Vec < ( Summary , bool ) > > ;
99
- ret = contents. lines ( ) . filter ( |l| !l. trim ( ) . is_empty ( ) )
100
- . map ( |l| self . parse_registry_package ( l) )
101
- . collect ( ) ;
102
- ret. chain_error ( || {
103
- internal ( format ! ( "failed to parse registry's information \
104
- for: {}", name) )
105
- } )
107
+ match load. load ( & root, Path :: new ( & path) ) {
108
+ Ok ( contents) => {
109
+ let contents = str:: from_utf8 ( & contents) . map_err ( |_| {
110
+ human ( "registry index file was not valid utf-8" )
111
+ } ) ?;
112
+ let lines = contents. lines ( )
113
+ . map ( |s| s. trim ( ) )
114
+ . filter ( |l| !l. is_empty ( ) ) ;
115
+
116
+ // Attempt forwards-compatibility on the index by ignoring
117
+ // everything that we ourselves don't understand, that should
118
+ // allow future cargo implementations to break the
119
+ // interpretation of each line here and older cargo will simply
120
+ // ignore the new lines.
121
+ Ok ( lines. filter_map ( |line| {
122
+ self . parse_registry_package ( line) . ok ( )
123
+ } ) . collect ( ) )
106
124
}
107
125
Err ( ..) => Ok ( Vec :: new ( ) ) ,
108
126
}
@@ -161,12 +179,13 @@ impl<'cfg> RegistryIndex<'cfg> {
161
179
. set_kind ( kind)
162
180
. into_dependency ( ) )
163
181
}
164
- }
165
182
166
- impl < ' cfg > Registry for RegistryIndex < ' cfg > {
167
- fn query ( & mut self , dep : & Dependency ) -> CargoResult < Vec < Summary > > {
183
+ pub fn query ( & mut self ,
184
+ dep : & Dependency ,
185
+ load : & mut RegistryData )
186
+ -> CargoResult < Vec < Summary > > {
168
187
let mut summaries = {
169
- let summaries = self . summaries ( dep. name ( ) ) ?;
188
+ let summaries = self . summaries ( dep. name ( ) , load ) ?;
170
189
summaries. iter ( ) . filter ( |& & ( _, yanked) | {
171
190
dep. source_id ( ) . precise ( ) . is_some ( ) || !yanked
172
191
} ) . map ( |s| s. 0 . clone ( ) ) . collect :: < Vec < _ > > ( )
@@ -188,8 +207,4 @@ impl<'cfg> Registry for RegistryIndex<'cfg> {
188
207
} ) ;
189
208
summaries. query ( dep)
190
209
}
191
-
192
- fn supports_checksums ( & self ) -> bool {
193
- true
194
- }
195
210
}
0 commit comments