@@ -41,6 +41,10 @@ pub struct Opts {
41
41
#[ structopt( short = "p" , long = "package" , value_name = "package" ) ]
42
42
packages : Vec < String > ,
43
43
44
+ /// Specify path to Cargo.toml
45
+ #[ structopt( long = "manifest-path" , value_name = "manifest-path" ) ]
46
+ manifest_path : Option < String > ,
47
+
44
48
/// Options passed to rustfmt
45
49
// 'raw = true' to make `--` explicit.
46
50
#[ structopt( name = "rustfmt_options" , raw( raw = "true" ) ) ]
@@ -90,7 +94,27 @@ fn execute() -> i32 {
90
94
91
95
let strategy = CargoFmtStrategy :: from_opts ( & opts) ;
92
96
93
- handle_command_status ( format_crate ( verbosity, & strategy, opts. rustfmt_options ) )
97
+ if opts. manifest_path . is_some ( ) {
98
+ let specified_manifest_path = opts. manifest_path . unwrap ( ) ;
99
+ if !specified_manifest_path. ends_with ( "Cargo.toml" ) {
100
+ print_usage_to_stderr ( "the manifest-path must be a path to a Cargo.toml file" ) ;
101
+ return FAILURE ;
102
+ }
103
+ let manifest_path = PathBuf :: from ( specified_manifest_path) ;
104
+ handle_command_status ( format_crate (
105
+ verbosity,
106
+ & strategy,
107
+ opts. rustfmt_options ,
108
+ Some ( & manifest_path) ,
109
+ ) )
110
+ } else {
111
+ handle_command_status ( format_crate (
112
+ verbosity,
113
+ & strategy,
114
+ opts. rustfmt_options ,
115
+ None ,
116
+ ) )
117
+ }
94
118
}
95
119
96
120
fn print_usage_to_stderr ( reason : & str ) {
@@ -142,14 +166,15 @@ fn format_crate(
142
166
verbosity : Verbosity ,
143
167
strategy : & CargoFmtStrategy ,
144
168
rustfmt_args : Vec < String > ,
169
+ manifest_path : Option < & Path > ,
145
170
) -> Result < i32 , io:: Error > {
146
171
let targets = if rustfmt_args
147
172
. iter ( )
148
173
. any ( |s| [ "--print-config" , "-h" , "--help" , "-V" , "--version" ] . contains ( & s. as_str ( ) ) )
149
174
{
150
175
BTreeSet :: new ( )
151
176
} else {
152
- get_targets ( strategy) ?
177
+ get_targets ( strategy, manifest_path ) ?
153
178
} ;
154
179
155
180
// Currently only bin and lib files get formatted.
@@ -227,13 +252,20 @@ impl CargoFmtStrategy {
227
252
}
228
253
229
254
/// Based on the specified `CargoFmtStrategy`, returns a set of main source files.
230
- fn get_targets ( strategy : & CargoFmtStrategy ) -> Result < BTreeSet < Target > , io:: Error > {
255
+ fn get_targets (
256
+ strategy : & CargoFmtStrategy ,
257
+ manifest_path : Option < & Path > ,
258
+ ) -> Result < BTreeSet < Target > , io:: Error > {
231
259
let mut targets = BTreeSet :: new ( ) ;
232
260
233
261
match * strategy {
234
- CargoFmtStrategy :: Root => get_targets_root_only ( & mut targets) ?,
235
- CargoFmtStrategy :: All => get_targets_recursive ( None , & mut targets, & mut BTreeSet :: new ( ) ) ?,
236
- CargoFmtStrategy :: Some ( ref hitlist) => get_targets_with_hitlist ( hitlist, & mut targets) ?,
262
+ CargoFmtStrategy :: Root => get_targets_root_only ( manifest_path, & mut targets) ?,
263
+ CargoFmtStrategy :: All => {
264
+ get_targets_recursive ( manifest_path, & mut targets, & mut BTreeSet :: new ( ) ) ?
265
+ }
266
+ CargoFmtStrategy :: Some ( ref hitlist) => {
267
+ get_targets_with_hitlist ( manifest_path, hitlist, & mut targets) ?
268
+ }
237
269
}
238
270
239
271
if targets. is_empty ( ) {
@@ -246,12 +278,22 @@ fn get_targets(strategy: &CargoFmtStrategy) -> Result<BTreeSet<Target>, io::Erro
246
278
}
247
279
}
248
280
249
- fn get_targets_root_only ( targets : & mut BTreeSet < Target > ) -> Result < ( ) , io:: Error > {
250
- let metadata = get_cargo_metadata ( None , false ) ?;
251
- let current_dir = env:: current_dir ( ) ?. canonicalize ( ) ?;
252
- let current_dir_manifest = current_dir. join ( "Cargo.toml" ) ;
281
+ fn get_targets_root_only (
282
+ manifest_path : Option < & Path > ,
283
+ targets : & mut BTreeSet < Target > ,
284
+ ) -> Result < ( ) , io:: Error > {
285
+ let metadata = get_cargo_metadata ( manifest_path, false ) ?;
253
286
let workspace_root_path = PathBuf :: from ( & metadata. workspace_root ) . canonicalize ( ) ?;
254
- let in_workspace_root = workspace_root_path == current_dir;
287
+ let ( in_workspace_root, current_dir_manifest) = if manifest_path. is_some ( ) {
288
+ let target_manifest = manifest_path. unwrap ( ) . canonicalize ( ) ?;
289
+ ( workspace_root_path == target_manifest, target_manifest)
290
+ } else {
291
+ let current_dir = env:: current_dir ( ) ?. canonicalize ( ) ?;
292
+ (
293
+ workspace_root_path == current_dir,
294
+ current_dir. join ( "Cargo.toml" ) ,
295
+ )
296
+ } ;
255
297
256
298
let package_targets = match metadata. packages . len ( ) {
257
299
1 => metadata. packages . into_iter ( ) . next ( ) . unwrap ( ) . targets ,
@@ -319,10 +361,11 @@ fn get_targets_recursive(
319
361
}
320
362
321
363
fn get_targets_with_hitlist (
364
+ manifest_path : Option < & Path > ,
322
365
hitlist : & [ String ] ,
323
366
targets : & mut BTreeSet < Target > ,
324
367
) -> Result < ( ) , io:: Error > {
325
- let metadata = get_cargo_metadata ( None , false ) ?;
368
+ let metadata = get_cargo_metadata ( manifest_path , false ) ?;
326
369
327
370
let mut workspace_hitlist: BTreeSet < & String > = BTreeSet :: from_iter ( hitlist) ;
328
371
0 commit comments