From 49642b4b11e7ca28725c112b8d9381edaf8373c6 Mon Sep 17 00:00:00 2001 From: Raphael Taylor-Davies Date: Fri, 2 Jan 2026 16:02:32 +0000 Subject: [PATCH 1/3] Seal Array trait --- arrow-array/src/array/boolean_array.rs | 2 ++ arrow-array/src/array/byte_array.rs | 2 ++ arrow-array/src/array/byte_view_array.rs | 2 ++ arrow-array/src/array/dictionary_array.rs | 4 ++++ arrow-array/src/array/fixed_size_binary_array.rs | 2 ++ arrow-array/src/array/fixed_size_list_array.rs | 2 ++ arrow-array/src/array/list_array.rs | 2 ++ arrow-array/src/array/list_view_array.rs | 2 ++ arrow-array/src/array/map_array.rs | 2 ++ arrow-array/src/array/mod.rs | 10 +++++++++- arrow-array/src/array/null_array.rs | 2 ++ arrow-array/src/array/primitive_array.rs | 2 ++ arrow-array/src/array/run_array.rs | 4 ++++ arrow-array/src/array/struct_array.rs | 2 ++ arrow-array/src/array/union_array.rs | 2 ++ 15 files changed, 41 insertions(+), 1 deletion(-) diff --git a/arrow-array/src/array/boolean_array.rs b/arrow-array/src/array/boolean_array.rs index 530121ea7853..acea680ae374 100644 --- a/arrow-array/src/array/boolean_array.rs +++ b/arrow-array/src/array/boolean_array.rs @@ -286,6 +286,8 @@ impl BooleanArray { } } +impl super::private::Sealed for BooleanArray {} + impl Array for BooleanArray { fn as_any(&self) -> &dyn Any { self diff --git a/arrow-array/src/array/byte_array.rs b/arrow-array/src/array/byte_array.rs index fbd8458846fc..bd85bffcfe44 100644 --- a/arrow-array/src/array/byte_array.rs +++ b/arrow-array/src/array/byte_array.rs @@ -462,6 +462,8 @@ impl std::fmt::Debug for GenericByteArray { } } +impl super::private::Sealed for GenericByteArray {} + impl Array for GenericByteArray { fn as_any(&self) -> &dyn Any { self diff --git a/arrow-array/src/array/byte_view_array.rs b/arrow-array/src/array/byte_view_array.rs index f677c4ae6757..b31c76ab5a27 100644 --- a/arrow-array/src/array/byte_view_array.rs +++ b/arrow-array/src/array/byte_view_array.rs @@ -854,6 +854,8 @@ impl Debug for GenericByteViewArray { } } +impl super::private::Sealed for GenericByteViewArray {} + impl Array for GenericByteViewArray { fn as_any(&self) -> &dyn Any { self diff --git a/arrow-array/src/array/dictionary_array.rs b/arrow-array/src/array/dictionary_array.rs index 5243218392f6..be7703b13c5c 100644 --- a/arrow-array/src/array/dictionary_array.rs +++ b/arrow-array/src/array/dictionary_array.rs @@ -697,6 +697,8 @@ impl<'a, T: ArrowDictionaryKeyType> FromIterator<&'a str> for DictionaryArray } } +impl super::private::Sealed for DictionaryArray {} + impl Array for DictionaryArray { fn as_any(&self) -> &dyn Any { self @@ -856,6 +858,8 @@ impl<'a, K: ArrowDictionaryKeyType, V> TypedDictionaryArray<'a, K, V> { } } +impl super::private::Sealed for TypedDictionaryArray<'_, K, V> {} + impl Array for TypedDictionaryArray<'_, K, V> { fn as_any(&self) -> &dyn Any { self.dictionary diff --git a/arrow-array/src/array/fixed_size_binary_array.rs b/arrow-array/src/array/fixed_size_binary_array.rs index d13cecb18027..b94e168cfe7c 100644 --- a/arrow-array/src/array/fixed_size_binary_array.rs +++ b/arrow-array/src/array/fixed_size_binary_array.rs @@ -602,6 +602,8 @@ impl std::fmt::Debug for FixedSizeBinaryArray { } } +impl super::private::Sealed for FixedSizeBinaryArray {} + impl Array for FixedSizeBinaryArray { fn as_any(&self) -> &dyn Any { self diff --git a/arrow-array/src/array/fixed_size_list_array.rs b/arrow-array/src/array/fixed_size_list_array.rs index fca92a64812c..3d5e8a0787c2 100644 --- a/arrow-array/src/array/fixed_size_list_array.rs +++ b/arrow-array/src/array/fixed_size_list_array.rs @@ -462,6 +462,8 @@ impl From for ArrayData { } } +impl super::private::Sealed for FixedSizeListArray {} + impl Array for FixedSizeListArray { fn as_any(&self) -> &dyn Any { self diff --git a/arrow-array/src/array/list_array.rs b/arrow-array/src/array/list_array.rs index 32add1abf557..225be14ae365 100644 --- a/arrow-array/src/array/list_array.rs +++ b/arrow-array/src/array/list_array.rs @@ -525,6 +525,8 @@ impl GenericListArray { } } +impl super::private::Sealed for GenericListArray {} + impl Array for GenericListArray { fn as_any(&self) -> &dyn Any { self diff --git a/arrow-array/src/array/list_view_array.rs b/arrow-array/src/array/list_view_array.rs index 867dcf955be7..52c88d581d20 100644 --- a/arrow-array/src/array/list_view_array.rs +++ b/arrow-array/src/array/list_view_array.rs @@ -415,6 +415,8 @@ impl ArrayAccessor for &GenericListViewArray super::private::Sealed for GenericListViewArray {} + impl Array for GenericListViewArray { fn as_any(&self) -> &dyn Any { self diff --git a/arrow-array/src/array/map_array.rs b/arrow-array/src/array/map_array.rs index b5e611a92b57..86608d586f34 100644 --- a/arrow-array/src/array/map_array.rs +++ b/arrow-array/src/array/map_array.rs @@ -361,6 +361,8 @@ impl MapArray { } } +impl super::private::Sealed for MapArray {} + impl Array for MapArray { fn as_any(&self) -> &dyn Any { self diff --git a/arrow-array/src/array/mod.rs b/arrow-array/src/array/mod.rs index bb114be95045..40d9732fb7a6 100644 --- a/arrow-array/src/array/mod.rs +++ b/arrow-array/src/array/mod.rs @@ -78,8 +78,14 @@ pub use list_view_array::*; use crate::iterator::ArrayIter; +mod private { + pub trait Sealed {} + + impl Sealed for &T {} +} + /// An array in the [arrow columnar format](https://arrow.apache.org/docs/format/Columnar.html) -pub trait Array: std::fmt::Debug + Send + Sync { +pub trait Array: std::fmt::Debug + Send + Sync + private::Sealed { /// Returns the array as [`Any`] so that it can be /// downcasted to a specific implementation. /// @@ -341,6 +347,8 @@ pub trait Array: std::fmt::Debug + Send + Sync { /// A reference-counted reference to a generic `Array` pub type ArrayRef = Arc; +impl private::Sealed for ArrayRef {} + /// Ergonomics: Allow use of an ArrayRef as an `&dyn Array` impl Array for ArrayRef { fn as_any(&self) -> &dyn Any { diff --git a/arrow-array/src/array/null_array.rs b/arrow-array/src/array/null_array.rs index 72556a92a3bc..b682466b6738 100644 --- a/arrow-array/src/array/null_array.rs +++ b/arrow-array/src/array/null_array.rs @@ -76,6 +76,8 @@ impl NullArray { } } +impl super::private::Sealed for NullArray {} + impl Array for NullArray { fn as_any(&self) -> &dyn Any { self diff --git a/arrow-array/src/array/primitive_array.rs b/arrow-array/src/array/primitive_array.rs index e71f4d47193f..457c2428145e 100644 --- a/arrow-array/src/array/primitive_array.rs +++ b/arrow-array/src/array/primitive_array.rs @@ -1190,6 +1190,8 @@ impl From> for ArrayData { } } +impl super::private::Sealed for PrimitiveArray {} + impl Array for PrimitiveArray { fn as_any(&self) -> &dyn Any { self diff --git a/arrow-array/src/array/run_array.rs b/arrow-array/src/array/run_array.rs index ddc99f8e172d..5254a0ed3cdc 100644 --- a/arrow-array/src/array/run_array.rs +++ b/arrow-array/src/array/run_array.rs @@ -260,6 +260,8 @@ impl From> for ArrayData { } } +impl super::private::Sealed for RunArray {} + impl Array for RunArray { fn as_any(&self) -> &dyn Any { self @@ -519,6 +521,8 @@ impl<'a, R: RunEndIndexType, V> TypedRunArray<'a, R, V> { } } +impl super::private::Sealed for TypedRunArray<'_, R, V> {} + impl Array for TypedRunArray<'_, R, V> { fn as_any(&self) -> &dyn Any { self.run_array diff --git a/arrow-array/src/array/struct_array.rs b/arrow-array/src/array/struct_array.rs index 5b18bd35d026..6ad1ead0d250 100644 --- a/arrow-array/src/array/struct_array.rs +++ b/arrow-array/src/array/struct_array.rs @@ -401,6 +401,8 @@ impl TryFrom> for StructArray { } } +impl super::private::Sealed for StructArray {} + impl Array for StructArray { fn as_any(&self) -> &dyn Any { self diff --git a/arrow-array/src/array/union_array.rs b/arrow-array/src/array/union_array.rs index 934107d075f7..e08542bc8638 100644 --- a/arrow-array/src/array/union_array.rs +++ b/arrow-array/src/array/union_array.rs @@ -738,6 +738,8 @@ impl From for ArrayData { } } +impl super::private::Sealed for UnionArray {} + impl Array for UnionArray { fn as_any(&self) -> &dyn Any { self From f6d9565ae8943ed723e56a0bbb0e60b63a98976d Mon Sep 17 00:00:00 2001 From: Raphael Taylor-Davies <1781103+tustvold@users.noreply.github.com> Date: Mon, 5 Jan 2026 14:06:56 +0000 Subject: [PATCH 2/3] Update arrow-array/src/array/mod.rs Co-authored-by: Andrew Lamb --- arrow-array/src/array/mod.rs | 1 + 1 file changed, 1 insertion(+) diff --git a/arrow-array/src/array/mod.rs b/arrow-array/src/array/mod.rs index 40d9732fb7a6..6cc40e25314d 100644 --- a/arrow-array/src/array/mod.rs +++ b/arrow-array/src/array/mod.rs @@ -79,6 +79,7 @@ pub use list_view_array::*; use crate::iterator::ArrayIter; mod private { + /// Private marker trait to ensure [`Array`] can not be implemented outside this crate pub trait Sealed {} impl Sealed for &T {} From 6d5172969e7332fa79e5ee7845b6e8e2638576ca Mon Sep 17 00:00:00 2001 From: Raphael Taylor-Davies Date: Mon, 5 Jan 2026 14:13:28 +0000 Subject: [PATCH 3/3] Docs --- arrow-array/src/array/mod.rs | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/arrow-array/src/array/mod.rs b/arrow-array/src/array/mod.rs index 6cc40e25314d..75e32d57e89c 100644 --- a/arrow-array/src/array/mod.rs +++ b/arrow-array/src/array/mod.rs @@ -79,13 +79,16 @@ pub use list_view_array::*; use crate::iterator::ArrayIter; mod private { - /// Private marker trait to ensure [`Array`] can not be implemented outside this crate + /// Private marker trait to ensure [`super::Array`] can not be implemented outside this crate pub trait Sealed {} impl Sealed for &T {} } /// An array in the [arrow columnar format](https://arrow.apache.org/docs/format/Columnar.html) +/// +/// This trait is sealed as it is not intended for custom array types, rather only +/// those defined in this crate. pub trait Array: std::fmt::Debug + Send + Sync + private::Sealed { /// Returns the array as [`Any`] so that it can be /// downcasted to a specific implementation.