Add a compare_properties variant with support for additional properties.
This commit is contained in:
		
							parent
							
								
									b385270d7b
								
							
						
					
					
						commit
						275ed87c3f
					
				| @ -542,11 +542,10 @@ fn new_compare_heading<'b, 's>( | ||||
|     let mut child_status = Vec::new(); | ||||
|     let mut message = None; | ||||
| 
 | ||||
|     let additional_property_names = rust | ||||
|     let additional_property_names: Vec<String> = rust | ||||
|         .get_additional_properties() | ||||
|         .map(|node_property| EmacsField::Required(node_property.property_name)); | ||||
| 
 | ||||
|     // TODO: This needs to support additional properties from the property drawer
 | ||||
|         .map(|node_property| format!(":{}", node_property.property_name)) | ||||
|         .collect(); | ||||
| 
 | ||||
|     compare_children( | ||||
|         source, | ||||
| @ -561,6 +560,10 @@ fn new_compare_heading<'b, 's>( | ||||
|         source, | ||||
|         emacs, | ||||
|         rust, | ||||
|         additional_property_names | ||||
|             .iter() | ||||
|             .map(String::as_str) | ||||
|             .map(EmacsField::Required), | ||||
|         ( | ||||
|             EmacsField::Required(":level"), | ||||
|             |r| Some(r.level), | ||||
|  | ||||
| @ -96,6 +96,90 @@ macro_rules! compare_properties { | ||||
|             new_status | ||||
|         } | ||||
|     }; | ||||
|     // Specifies additional properties
 | ||||
|     ($source:expr, $emacs:expr, $rust:expr, $additionalproperties: expr, $(($emacs_field:expr, $rust_value_getter:expr, $compare_fn: expr)),+) => { | ||||
|         { | ||||
|             let mut new_status = Vec::new(); | ||||
|             let children = $emacs.as_list()?; | ||||
|             let attributes_child = children | ||||
|             .iter() | ||||
|             .nth(1) | ||||
|             .ok_or("Should have an attributes child.")?; | ||||
|             let attributes_map = attributes_child.as_map()?; | ||||
|             let mut emacs_keys: BTreeSet<&str> = attributes_map.keys().map(|s| *s).collect(); | ||||
|             if emacs_keys.contains(":standard-properties") { | ||||
|                 emacs_keys.remove(":standard-properties"); | ||||
|             } else { | ||||
|                 new_status.push(ComparePropertiesResult::SelfChange(DiffStatus::Bad, Some(format!( | ||||
|                     "Emacs token lacks :standard-properties field.", | ||||
|                 )))); | ||||
|             } | ||||
|             for additional_field in $additionalproperties { | ||||
|                 match additional_field { | ||||
|                     EmacsField::Required(name) if emacs_keys.contains(name) => { | ||||
|                         emacs_keys.remove(name); | ||||
|                     }, | ||||
|                     EmacsField::Optional(name) if emacs_keys.contains(name) => { | ||||
|                         emacs_keys.remove(name); | ||||
|                     }, | ||||
|                     EmacsField::Required(name) => { | ||||
|                         new_status.push(ComparePropertiesResult::SelfChange(DiffStatus::Bad, Some(format!( | ||||
|                             "Emacs token lacks required field: {}", | ||||
|                             name | ||||
|                         )))); | ||||
|                     }, | ||||
|                     EmacsField::Optional(_name) => {}, | ||||
|                 } | ||||
|             } | ||||
|             $( | ||||
|             match $emacs_field { | ||||
|                 EmacsField::Required(name) if emacs_keys.contains(name) => { | ||||
|                     emacs_keys.remove(name); | ||||
|                 }, | ||||
|                 EmacsField::Optional(name) if emacs_keys.contains(name) => { | ||||
|                     emacs_keys.remove(name); | ||||
|                 }, | ||||
|                 EmacsField::Required(name) => { | ||||
|                     new_status.push(ComparePropertiesResult::SelfChange(DiffStatus::Bad, Some(format!( | ||||
|                         "Emacs token lacks required field: {}", | ||||
|                         name | ||||
|                     )))); | ||||
|                 }, | ||||
|                 EmacsField::Optional(_name) => {}, | ||||
|             } | ||||
|             )+ | ||||
| 
 | ||||
|             if !emacs_keys.is_empty() { | ||||
|                 let unexpected_keys: Vec<&str> = emacs_keys.into_iter().collect(); | ||||
|                 let unexpected_keys = unexpected_keys.join(", "); | ||||
|                 new_status.push(ComparePropertiesResult::SelfChange(DiffStatus::Bad, Some(format!( | ||||
|                     "Emacs token had extra field(s): {}", | ||||
|                     unexpected_keys | ||||
|                 )))); | ||||
|             } | ||||
| 
 | ||||
|             $( | ||||
|             let emacs_name = match $emacs_field { | ||||
|                 EmacsField::Required(name) => { | ||||
|                     name | ||||
|                 }, | ||||
|                 EmacsField::Optional(name) => { | ||||
|                     name | ||||
|                 }, | ||||
|             }; | ||||
|             let result = $compare_fn($source, $emacs, $rust, emacs_name, $rust_value_getter)?; | ||||
|             match result { | ||||
|                 ComparePropertiesResult::SelfChange(DiffStatus::Good, _) => unreachable!("No comparison functions should return SelfChange() when DiffStatus is good."), | ||||
|                 ComparePropertiesResult::NoChange => {}, | ||||
|                 result => { | ||||
|                     new_status.push(result); | ||||
|                 } | ||||
|             } | ||||
|             )+ | ||||
| 
 | ||||
|             new_status | ||||
|         } | ||||
|     }; | ||||
|     // Default case for when there are no expected properties except for :standard-properties
 | ||||
|     ($emacs:expr) => { | ||||
|         { | ||||
|  | ||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user
	 Tom Alexander
						Tom Alexander