This is an automated email from the ASF dual-hosted git repository.

alamb pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/arrow-rs.git


The following commit(s) were added to refs/heads/main by this push:
     new 800425cee0 refactor: improve display formatting for Union (#8529)
800425cee0 is described below

commit 800425cee0cfed63b581c5bb216e8bc65fdcb956
Author: Alex Huang <[email protected]>
AuthorDate: Sat Oct 4 13:32:47 2025 +0300

    refactor: improve display formatting for Union (#8529)
    
    # Which issue does this PR close?
    
    - Parts of #8351
    
    # Rationale for this change
    Support more human readable display in `Union`
    
    # What changes are included in this PR?
    
    
    # Are these changes tested?
    
    Yes
    
    # Are there any user-facing changes?
    
    No
    
    ---------
    
    Co-authored-by: Andrew Lamb <[email protected]>
---
 arrow-schema/src/datatype_display.rs | 84 +++++++++++++++++++++++++++++++++++-
 1 file changed, 83 insertions(+), 1 deletion(-)

diff --git a/arrow-schema/src/datatype_display.rs 
b/arrow-schema/src/datatype_display.rs
index 73ceb3f680..6e9501777a 100644
--- a/arrow-schema/src/datatype_display.rs
+++ b/arrow-schema/src/datatype_display.rs
@@ -132,7 +132,24 @@ impl fmt::Display for DataType {
                 Ok(())
             }
             Self::Union(union_fields, union_mode) => {
-                write!(f, "Union({union_fields:?}, {union_mode:?})")
+                write!(f, "Union({union_mode:?}, ")?;
+                if !union_fields.is_empty() {
+                    let fields_str = union_fields
+                        .iter()
+                        .map(|v| {
+                            let type_id = v.0;
+                            let field = v.1;
+                            let maybe_nullable = if field.is_nullable() { 
"nullable " } else { "" };
+                            let data_type = field.data_type();
+                            let metadata_str = 
format_metadata(field.metadata());
+                            format!("{type_id:?}: 
{maybe_nullable}{data_type}{metadata_str}")
+                        })
+                        .collect::<Vec<_>>()
+                        .join(", ");
+                    write!(f, "{fields_str}")?;
+                }
+                write!(f, ")")?;
+                Ok(())
             }
             Self::Dictionary(data_type, data_type1) => {
                 write!(f, "Dictionary({data_type}, {data_type1})")
@@ -248,4 +265,69 @@ mod tests {
             "FixedSizeList(4 x nullable Int32, metadata: {\"key2\": 
\"value2\"})";
         assert_eq!(fixed_size_metadata_string, expected_metadata_string);
     }
+
+    #[test]
+    fn test_display_struct() {
+        let fields = vec![
+            Field::new("a", DataType::Int32, false),
+            Field::new("b", DataType::Utf8, true),
+        ];
+        let struct_data_type = DataType::Struct(fields.into());
+        let struct_data_type_string = struct_data_type.to_string();
+        let expected_string = "Struct(\"a\": Int32, \"b\": nullable Utf8)";
+        assert_eq!(struct_data_type_string, expected_string);
+
+        // Test with metadata
+        let mut field_with_metadata = Field::new("b", DataType::Utf8, true);
+        let metadata = HashMap::from([("key".to_string(), 
"value".to_string())]);
+        field_with_metadata.set_metadata(metadata);
+        let struct_fields_with_metadata =
+            vec![Field::new("a", DataType::Int32, false), field_with_metadata];
+        let struct_data_type_with_metadata = 
DataType::Struct(struct_fields_with_metadata.into());
+        let struct_data_type_with_metadata_string = 
struct_data_type_with_metadata.to_string();
+        let expected_string_with_metadata =
+            "Struct(\"a\": Int32, \"b\": nullable Utf8, metadata: {\"key\": 
\"value\"})";
+        assert_eq!(
+            struct_data_type_with_metadata_string,
+            expected_string_with_metadata
+        );
+    }
+
+    #[test]
+    fn test_display_union() {
+        let fields = vec![
+            Field::new("a", DataType::Int32, false),
+            Field::new("b", DataType::Utf8, true),
+        ];
+        let type_ids = vec![0, 1];
+        let union_fields = type_ids
+            .into_iter()
+            .zip(fields.into_iter().map(Arc::new))
+            .collect();
+
+        let union_data_type = DataType::Union(union_fields, 
crate::UnionMode::Sparse);
+        let union_data_type_string = union_data_type.to_string();
+        let expected_string = "Union(Sparse, 0: Int32, 1: nullable Utf8)";
+        assert_eq!(union_data_type_string, expected_string);
+
+        // Test with metadata
+        let mut field_with_metadata = Field::new("b", DataType::Utf8, true);
+        let metadata = HashMap::from([("key".to_string(), 
"value".to_string())]);
+        field_with_metadata.set_metadata(metadata);
+        let union_fields_with_metadata = vec![
+            (0, Arc::new(Field::new("a", DataType::Int32, false))),
+            (1, Arc::new(field_with_metadata)),
+        ]
+        .into_iter()
+        .collect();
+        let union_data_type_with_metadata =
+            DataType::Union(union_fields_with_metadata, 
crate::UnionMode::Sparse);
+        let union_data_type_with_metadata_string = 
union_data_type_with_metadata.to_string();
+        let expected_string_with_metadata =
+            "Union(Sparse, 0: Int32, 1: nullable Utf8, metadata: {\"key\": 
\"value\"})";
+        assert_eq!(
+            union_data_type_with_metadata_string,
+            expected_string_with_metadata
+        );
+    }
 }

Reply via email to