@@ -125,15 +125,21 @@ fn parse_recursive(
125125 // Provide GARDEN_ROOT.
126126 config. variables . insert (
127127 string ! ( constants:: GARDEN_ROOT ) ,
128- model:: Variable :: from_expr ( config. root . get_expr ( ) . to_string ( ) ) ,
128+ model:: Variable :: from_expr (
129+ constants:: GARDEN_ROOT . to_string ( ) ,
130+ config. root . get_expr ( ) . to_string ( ) ,
131+ ) ,
129132 ) ;
130133
131134 if let Some ( config_path_raw) = config. dirname . as_ref ( ) {
132135 // Calculate an absolute path for GARDEN_CONFIG_DIR.
133136 if let Ok ( config_path) = path:: canonicalize ( config_path_raw) {
134137 config. variables . insert (
135138 string ! ( constants:: GARDEN_CONFIG_DIR ) ,
136- model:: Variable :: from_expr ( config_path. to_string_lossy ( ) . to_string ( ) ) ,
139+ model:: Variable :: from_expr (
140+ constants:: GARDEN_CONFIG_DIR . to_string ( ) ,
141+ config_path. to_string_lossy ( ) . to_string ( ) ,
142+ ) ,
137143 ) ;
138144 }
139145 }
@@ -156,6 +162,7 @@ fn parse_recursive(
156162 // override the same variables when also defined in an included garden file.
157163 let mut config_includes = Vec :: new ( ) ;
158164 if get_vec_variables (
165+ constants:: INCLUDES ,
159166 & doc[ constants:: GARDEN ] [ constants:: INCLUDES ] ,
160167 & mut config_includes,
161168 ) {
@@ -375,13 +382,13 @@ fn get_indexset_str(yaml: &Yaml, values: &mut StringSet) -> bool {
375382}
376383
377384/// Construct a model::Variable from a ran YAML object.
378- fn variable_from_yaml ( yaml : & Yaml ) -> Option < model:: Variable > {
385+ fn variable_from_yaml ( name : String , yaml : & Yaml ) -> Option < model:: Variable > {
379386 match yaml {
380- Yaml :: String ( yaml_str) => Some ( model:: Variable :: from_expr ( yaml_str. to_string ( ) ) ) ,
387+ Yaml :: String ( yaml_str) => Some ( model:: Variable :: from_expr ( name , yaml_str. to_string ( ) ) ) ,
381388 Yaml :: Array ( yaml_array) => {
382389 // If we see an array we loop over so that the first value wins.
383- for array_value in yaml_array. iter ( ) . rev ( ) {
384- return variable_from_yaml ( array_value) ;
390+ if let Some ( array_value) = yaml_array. iter ( ) . next_back ( ) {
391+ return variable_from_yaml ( name , array_value) ;
385392 }
386393
387394 None
@@ -390,13 +397,30 @@ fn variable_from_yaml(yaml: &Yaml) -> Option<model::Variable> {
390397 // Integers are already resolved.
391398 let int_value = yaml_int. to_string ( ) ;
392399
393- Some ( model:: Variable :: from_resolved_expr ( int_value) )
400+ Some ( model:: Variable :: from_resolved_expr ( name , int_value) )
394401 }
395402 Yaml :: Boolean ( yaml_bool) => {
396403 // Booleans are already resolved.
397404 let bool_value = syntax:: bool_to_string ( * yaml_bool) ;
398405
399- Some ( model:: Variable :: from_resolved_expr ( bool_value) )
406+ Some ( model:: Variable :: from_resolved_expr ( name, bool_value) )
407+ }
408+ Yaml :: Hash ( yaml_hash) => {
409+ let required = yaml_hash
410+ . get ( & Yaml :: String ( constants:: REQUIRED . to_string ( ) ) )
411+ . and_then ( |v| v. as_bool ( ) )
412+ . unwrap_or ( false ) ;
413+ let value = yaml_hash
414+ . get ( & Yaml :: String ( constants:: VALUE . to_string ( ) ) )
415+ . and_then ( |v| v. as_str ( ) )
416+ . unwrap_or_default ( )
417+ . to_string ( ) ;
418+
419+ if required {
420+ Some ( model:: Variable :: from_required_expr ( name, value) )
421+ } else {
422+ Some ( model:: Variable :: from_expr ( name, value) )
423+ }
400424 }
401425 _ => {
402426 // dump_node(yaml, 1, "");
@@ -406,8 +430,8 @@ fn variable_from_yaml(yaml: &Yaml) -> Option<model::Variable> {
406430}
407431
408432// Extract a `Variable` from `yaml`. Return `false` when `yaml` is not a `Yaml::String`.
409- fn get_variable ( yaml : & Yaml , value : & mut model:: Variable ) -> bool {
410- if let Some ( variable) = variable_from_yaml ( yaml) {
433+ fn get_variable ( name : String , yaml : & Yaml , value : & mut model:: Variable ) -> bool {
434+ if let Some ( variable) = variable_from_yaml ( name , yaml) {
411435 * value = variable;
412436
413437 true
@@ -417,17 +441,17 @@ fn get_variable(yaml: &Yaml, value: &mut model::Variable) -> bool {
417441}
418442
419443/// Promote `Yaml::String` or `Yaml::Array<Yaml::String>` into a `Vec<Variable>`.
420- fn get_vec_variables ( yaml : & Yaml , vec : & mut Vec < model:: Variable > ) -> bool {
444+ fn get_vec_variables ( name : & str , yaml : & Yaml , vec : & mut Vec < model:: Variable > ) -> bool {
421445 if let Yaml :: Array ( yaml_array) = yaml {
422446 for value in yaml_array {
423- if let Some ( variable) = variable_from_yaml ( value) {
447+ if let Some ( variable) = variable_from_yaml ( name . to_string ( ) , value) {
424448 vec. push ( variable) ;
425449 }
426450 }
427451 return true ;
428452 }
429453
430- if let Some ( variable) = variable_from_yaml ( yaml) {
454+ if let Some ( variable) = variable_from_yaml ( name . to_string ( ) , yaml) {
431455 vec. push ( variable) ;
432456 return true ;
433457 }
@@ -447,7 +471,7 @@ fn get_variables_map(yaml: &Yaml, map: &mut model::VariableMap) -> bool {
447471 continue ;
448472 }
449473 } ;
450- if let Some ( variable) = variable_from_yaml ( v) {
474+ if let Some ( variable) = variable_from_yaml ( key . to_string ( ) , v) {
451475 map. insert ( key, variable) ;
452476 }
453477 }
@@ -469,15 +493,15 @@ fn get_multivariables(yaml: &Yaml, vec: &mut Vec<model::MultiVariable>) -> bool
469493 if let Yaml :: Array ( yaml_array) = v {
470494 let mut variables = Vec :: new ( ) ;
471495 for value in yaml_array {
472- if let Some ( variable) = variable_from_yaml ( value) {
496+ if let Some ( variable) = variable_from_yaml ( key . to_string ( ) , value) {
473497 variables. push ( variable) ;
474498 }
475499 }
476500 vec. push ( model:: MultiVariable :: new ( key, variables) ) ;
477501 continue ;
478502 }
479503
480- if let Some ( variable) = variable_from_yaml ( v) {
504+ if let Some ( variable) = variable_from_yaml ( key . to_string ( ) , v) {
481505 let variables = vec ! [ variable] ;
482506 vec. push ( model:: MultiVariable :: new ( key, variables) ) ;
483507 }
@@ -501,15 +525,15 @@ fn get_multivariables_map(yaml: &Yaml, multivariables: &mut model::MultiVariable
501525 if let Yaml :: Array ( yaml_array) = v {
502526 let mut variables = Vec :: new ( ) ;
503527 for value in yaml_array {
504- if let Some ( variable) = variable_from_yaml ( value) {
528+ if let Some ( variable) = variable_from_yaml ( key . to_string ( ) , value) {
505529 variables. push ( variable) ;
506530 }
507531 }
508532 multivariables. insert ( key, variables) ;
509533 continue ;
510534 }
511535
512- if let Some ( variable) = variable_from_yaml ( v) {
536+ if let Some ( variable) = variable_from_yaml ( key . to_string ( ) , v) {
513537 let variables = vec ! [ variable] ;
514538 multivariables. insert ( key, variables) ;
515539 }
@@ -561,19 +585,19 @@ fn get_template(
561585 // templates:
562586 // example: git://git.example.org/example/repo.git
563587 if get_str ( value, & mut url) {
564- template
565- . tree
566- . remotes
567- . insert ( string ! ( constants :: ORIGIN ) , model :: Variable :: from_expr ( url ) ) ;
588+ template. tree . remotes . insert (
589+ constants :: ORIGIN . to_string ( ) ,
590+ model :: Variable :: from_expr ( constants :: ORIGIN . to_string ( ) , url ) ,
591+ ) ;
568592 return template;
569593 }
570594 // If a `<url>` is configured then populate the "origin" remote.
571595 // The first remote is "origin" by convention.
572596 if get_str ( & value[ constants:: URL ] , & mut url) {
573- template
574- . tree
575- . remotes
576- . insert ( string ! ( constants :: ORIGIN ) , model :: Variable :: from_expr ( url ) ) ;
597+ template. tree . remotes . insert (
598+ string ! ( constants :: ORIGIN ) ,
599+ model :: Variable :: from_expr ( constants :: URL . to_string ( ) , url ) ,
600+ ) ;
577601 }
578602 }
579603
@@ -671,8 +695,8 @@ fn get_tree_from_url(name: &Yaml, url: &str) -> model::Tree {
671695 tree. is_bare_repository = true ;
672696 }
673697 tree. remotes . insert (
674- string ! ( constants:: ORIGIN ) ,
675- model:: Variable :: from_expr ( url. to_string ( ) ) ,
698+ constants:: ORIGIN . to_string ( ) ,
699+ model:: Variable :: from_expr ( constants :: ORIGIN . to_string ( ) , url. to_string ( ) ) ,
676700 ) ;
677701
678702 tree
@@ -686,15 +710,27 @@ fn get_tree_fields(value: &Yaml, tree: &mut model::Tree) {
686710 get_str ( & value[ constants:: DEFAULT_REMOTE ] , & mut tree. default_remote ) ;
687711 get_str_trimmed ( & value[ constants:: DESCRIPTION ] , & mut tree. description ) ;
688712 get_str_variables_map ( & value[ constants:: REMOTES ] , & mut tree. remotes ) ;
689- get_vec_variables ( & value[ constants:: LINKS ] , & mut tree. links ) ;
713+ get_vec_variables ( constants :: LINKS , & value[ constants:: LINKS ] , & mut tree. links ) ;
690714
691715 get_multivariables ( & value[ constants:: ENVIRONMENT ] , & mut tree. environment ) ;
692716 get_multivariables_map ( & value[ constants:: COMMANDS ] , & mut tree. commands ) ;
693717
694- get_variable ( & value[ constants:: BRANCH ] , & mut tree. branch ) ;
718+ get_variable (
719+ constants:: BRANCH . to_string ( ) ,
720+ & value[ constants:: BRANCH ] ,
721+ & mut tree. branch ,
722+ ) ;
695723 get_variables_map ( & value[ constants:: BRANCHES ] , & mut tree. branches ) ;
696- get_variable ( & value[ constants:: SYMLINK ] , & mut tree. symlink ) ;
697- get_variable ( & value[ constants:: WORKTREE ] , & mut tree. worktree ) ;
724+ get_variable (
725+ constants:: SYMLINK . to_string ( ) ,
726+ & value[ constants:: SYMLINK ] ,
727+ & mut tree. symlink ,
728+ ) ;
729+ get_variable (
730+ constants:: WORKTREE . to_string ( ) ,
731+ & value[ constants:: WORKTREE ] ,
732+ & mut tree. worktree ,
733+ ) ;
698734
699735 get_i64 ( & value[ constants:: DEPTH ] , & mut tree. clone_depth ) ;
700736 get_bool ( & value[ constants:: BARE ] , & mut tree. is_bare_repository ) ;
@@ -706,7 +742,7 @@ fn get_tree_fields(value: &Yaml, tree: &mut model::Tree) {
706742 if get_str ( & value[ constants:: URL ] , & mut url) {
707743 tree. remotes . insert (
708744 tree. default_remote . to_string ( ) ,
709- model:: Variable :: from_expr ( url) ,
745+ model:: Variable :: from_expr ( constants :: URL . to_string ( ) , url) ,
710746 ) ;
711747 }
712748 }
@@ -803,7 +839,7 @@ fn get_str_variables_map(yaml: &Yaml, remotes: &mut model::VariableMap) {
803839 if let ( Some ( name_str) , Some ( value_str) ) = ( name. as_str ( ) , value. as_str ( ) ) {
804840 remotes. insert (
805841 name_str. to_string ( ) ,
806- model:: Variable :: from_expr ( value_str. to_string ( ) ) ,
842+ model:: Variable :: from_expr ( name_str . to_string ( ) , value_str. to_string ( ) ) ,
807843 ) ;
808844 }
809845 }
0 commit comments