11use super :: disk_usage:: { file_size:: DiskUsage , units:: PrefixKind } ;
22use crate :: tty;
3- use clap:: { parser:: ValueSource , ArgMatches , CommandFactory , FromArgMatches , Parser } ;
3+ use args:: Reconciler ;
4+ use clap:: { FromArgMatches , Parser } ;
45use color:: Coloring ;
56use error:: Error ;
67use ignore:: {
@@ -11,12 +12,15 @@ use regex::Regex;
1112use std:: {
1213 borrow:: Borrow ,
1314 convert:: From ,
14- ffi:: { OsStr , OsString } ,
1515 num:: NonZeroUsize ,
1616 path:: { Path , PathBuf } ,
1717 thread:: available_parallelism,
1818} ;
1919
20+ /// Concerned with figuring out how to reconcile arguments provided via the command-line with
21+ /// arguments that come from a config file.
22+ pub mod args;
23+
2024/// Operations to load in defaults from configuration file.
2125pub mod config;
2226
@@ -253,73 +257,8 @@ impl Context {
253257 /// Initializes [Context], optionally reading in the configuration file to override defaults.
254258 /// Arguments provided will take precedence over config.
255259 pub fn try_init ( ) -> Result < Self , Error > {
256- // User-provided arguments from command-line.
257- let user_args = Self :: command ( ) . args_override_self ( true ) . get_matches ( ) ;
258-
259- // User provides `--no-config`.
260- if user_args. get_one :: < bool > ( "no_config" ) . is_some_and ( |b| * b) {
261- return Self :: from_arg_matches ( & user_args) . map_err ( Error :: ArgParse ) ;
262- }
263-
264- // Load in `.erdtreerc` or `.erdtree.toml`.
265- let config_args = if let Some ( config) = config:: rc:: read_config_to_string ( ) {
266- let raw_args = config:: rc:: parse ( & config) ;
267-
268- Self :: command ( ) . get_matches_from ( raw_args)
269- } else if let Ok ( config) = config:: toml:: load ( ) {
270- let named_table = user_args. get_one :: < String > ( "config" ) ;
271- let raw_args = config:: toml:: parse ( config, named_table. map ( String :: as_str) ) ?;
272-
273- Self :: command ( ) . get_matches_from ( raw_args)
274- } else {
275- return Self :: from_arg_matches ( & user_args) . map_err ( Error :: ArgParse ) ;
276- } ;
277-
278- // If the user did not provide any arguments just read from config.
279- if !user_args. args_present ( ) {
280- return Self :: from_arg_matches ( & config_args) . map_err ( Error :: Config ) ;
281- }
282-
283- let mut args = vec ! [ OsString :: from( "--" ) ] ;
284-
285- let ids = Self :: command ( )
286- . get_arguments ( )
287- . map ( |arg| arg. get_id ( ) . clone ( ) )
288- . collect :: < Vec < _ > > ( ) ;
289-
290- for id in ids {
291- let id_str = id. as_str ( ) ;
292-
293- if id_str == "dir" {
294- if let Ok ( Some ( dir) ) = user_args. try_get_one :: < PathBuf > ( id_str) {
295- args. push ( dir. as_os_str ( ) . to_owned ( ) ) ;
296- continue ;
297- }
298- }
299-
300- let Some ( source) = user_args. value_source ( id_str) else {
301- if let Some ( params) = Self :: extract_args_from ( id_str, & config_args) {
302- args. extend ( params) ;
303- }
304- continue ;
305- } ;
306-
307- let higher_precedent = match source {
308- // User provided argument takes precedent over argument from config
309- ValueSource :: CommandLine => & user_args,
310-
311- // otherwise prioritize argument from the config
312- _ => & config_args,
313- } ;
314-
315- if let Some ( params) = Self :: extract_args_from ( id_str, higher_precedent) {
316- args. extend ( params) ;
317- }
318- }
319-
320- let clargs = Self :: command ( ) . get_matches_from ( args) ;
321-
322- Self :: from_arg_matches ( & clargs) . map_err ( Error :: Config )
260+ let args = Self :: compute_args ( ) ?;
261+ Self :: from_arg_matches ( & args) . map_err ( Error :: Config )
323262 }
324263
325264 /// Determines whether or not it's appropriate to display color in output based on
@@ -373,26 +312,6 @@ impl Context {
373312 self . file_type . unwrap_or_default ( )
374313 }
375314
376- /// Used to pick either from config or user args when constructing [Context].
377- #[ inline]
378- fn extract_args_from ( id : & str , matches : & ArgMatches ) -> Option < Vec < OsString > > {
379- let Ok ( Some ( raw) ) = matches. try_get_raw ( id) else {
380- return None
381- } ;
382-
383- let kebap = format ! ( "--{}" , id. replace( '_' , "-" ) ) ;
384-
385- let raw_args = raw
386- . map ( OsStr :: to_owned)
387- . map ( |s| [ OsString :: from ( & kebap) , s] )
388- . filter ( |[ _key, val] | val != "false" )
389- . flatten ( )
390- . filter ( |s| s != "true" )
391- . collect :: < Vec < _ > > ( ) ;
392-
393- Some ( raw_args)
394- }
395-
396315 /// Predicate used for filtering via regular expressions and file-type. When matching regular
397316 /// files, directories will always be included since matched files will need to be bridged back
398317 /// to the root node somehow. Empty sets not producing an output is handled by [`Tree`].
@@ -428,11 +347,11 @@ impl Context {
428347 match file_type {
429348 file:: Type :: File if entry_type. map_or ( true , |ft| !ft. is_file ( ) ) => {
430349 return false
431- }
350+ } ,
432351 file:: Type :: Link if entry_type. map_or ( true , |ft| !ft. is_symlink ( ) ) => {
433352 return false
434- }
435- _ => { }
353+ } ,
354+ _ => { } ,
436355 }
437356 let file_name = dir_entry. file_name ( ) . to_string_lossy ( ) ;
438357 re. is_match ( & file_name)
@@ -497,11 +416,11 @@ impl Context {
497416 match file_type {
498417 file:: Type :: File if entry_type. map_or ( true , |ft| !ft. is_file ( ) ) => {
499418 return false
500- }
419+ } ,
501420 file:: Type :: Link if entry_type. map_or ( true , |ft| !ft. is_symlink ( ) ) => {
502421 return false
503- }
504- _ => { }
422+ } ,
423+ _ => { } ,
505424 }
506425
507426 let matched = overrides. matched ( dir_entry. path ( ) , false ) ;
0 commit comments