Skip to content

Commit

Permalink
Move flattened_union_builder tests to test_with_arrow directory
Browse files Browse the repository at this point in the history
  • Loading branch information
raj-nimble committed Oct 22, 2024
1 parent 6a02592 commit bf3f789
Show file tree
Hide file tree
Showing 4 changed files with 159 additions and 141 deletions.
2 changes: 1 addition & 1 deletion serde_arrow/src/internal/schema/tracer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,7 @@ impl Tracer {
let root = self.to_field()?;

if root.nullable {
fail!("The root type cannot be nullable");
fail!("The root type cannot be nullable: {root:#?}");
}

let tracing_mode = dispatch_tracer!(self, tracer => tracer.options.tracing_mode);
Expand Down
140 changes: 0 additions & 140 deletions serde_arrow/src/internal/serialization/flattened_union_builder.rs
Original file line number Diff line number Diff line change
Expand Up @@ -118,143 +118,3 @@ impl SimpleSerializer for FlattenedUnionBuilder {
.ctx(&ctx)
}
}

#[cfg(test)]
mod tests {
use std::collections::HashMap;

use crate::{
internal::{
array_builder::ArrayBuilder,
arrow::{DataType, Field},
serialization::{self, outer_sequence_builder::build_builder},
},
schema::SerdeArrowSchema,
Serializer,
};
use serde::{Deserialize, Serialize};

#[derive(Serialize, Deserialize)]
struct Number {
v: Value,
}

#[derive(Serialize, Deserialize)]
enum Value {
Real { value: f32 },
Complex { i: f32, j: f32 },
Whole { value: usize },
}

fn number_field() -> Field {
Field {
name: "v".to_string(),
data_type: DataType::Struct(vec![
Field {
name: "Complex::i".to_string(),
data_type: DataType::Float32,
nullable: true,
metadata: HashMap::new(),
},
Field {
name: "Complex::j".to_string(),
data_type: DataType::Float32,
nullable: true,
metadata: HashMap::new(),
},
Field {
name: "Real::value".to_string(),
data_type: DataType::Float32,
nullable: true,
metadata: HashMap::new(),
},
Field {
name: "Whole::value".to_string(),
data_type: DataType::UInt64,
nullable: true,
metadata: HashMap::new(),
},
]),
nullable: false,
metadata: HashMap::from([(
"SERDE_ARROW:strategy".to_string(),
"EnumsWithNamedFieldsAsStructs".to_string(),
)]),
}
}

fn number_data() -> Vec<Number> {
vec![
Number {
v: Value::Real { value: 0.0 },
},
Number {
v: Value::Complex { i: 0.5, j: 0.5 },
},
Number {
v: Value::Whole { value: 5 },
},
]
}

#[test]
fn test_build_flattened_union_builder() {
let field = number_field();

let array_builder =
build_builder("$".to_string(), &field).expect("failed to build builder");

let serialization::ArrayBuilder::FlattenedUnion(builder) = array_builder else {
panic!("did not create correct builder");
};

// Should be 3 struct builders: one for Real, one for Complex, one for Whole
assert_eq!(
builder.fields.len(),
3,
"contained {} builder fields",
builder.fields.len()
);
assert!(
builder
.fields
.iter()
.all(|(inner, _)| matches!(inner, serialization::ArrayBuilder::Struct(_))),
"some inner builders were not Struct builders"
);
}

#[test]
fn test_serialize_flattened_union_builder() {
let field = number_field();
let data = number_data();
let schema = SerdeArrowSchema {
fields: vec![field],
};

let api_builder = ArrayBuilder::new(schema).expect("failed to create api array builder");
let serializer = Serializer::new(api_builder);
data.serialize(serializer)
.expect("failed to serialize")
.into_inner()
.to_arrow()
.expect("failed to serialize to arrow");
}

#[test]
fn test_record_batch_flattened_union_builder() {
let field = number_field();
let data = number_data();
let schema = SerdeArrowSchema {
fields: vec![field],
};

let api_builder = ArrayBuilder::new(schema).expect("failed to create api array builder");
let serializer = Serializer::new(api_builder);
data.serialize(serializer)
.expect("failed to serialize")
.into_inner()
.to_record_batch()
.expect("failed to create record batch");
}
}
157 changes: 157 additions & 0 deletions serde_arrow/src/test_with_arrow/impls/flattened_union.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,157 @@
use std::collections::HashMap;

use crate::{
internal::{
array_builder::ArrayBuilder,
arrow::{Array, DataType, Field},
schema::{SchemaLike, TracingOptions},
},
schema::SerdeArrowSchema,
Serializer,
};
use serde::{Deserialize, Serialize};

#[derive(Serialize, Deserialize)]
struct Number {
v: Value,
}

#[derive(Serialize, Deserialize)]
enum Value {
Real { value: f32 },
Complex { i: f32, j: f32 },
Whole { value: usize },
}

fn number_field() -> Field {
Field {
name: "v".to_string(),
data_type: DataType::Struct(vec![
Field {
name: "Complex::i".to_string(),
data_type: DataType::Float32,
nullable: true,
metadata: HashMap::new(),
},
Field {
name: "Complex::j".to_string(),
data_type: DataType::Float32,
nullable: true,
metadata: HashMap::new(),
},
Field {
name: "Real::value".to_string(),
data_type: DataType::Float32,
nullable: true,
metadata: HashMap::new(),
},
Field {
name: "Whole::value".to_string(),
data_type: DataType::UInt64,
nullable: true,
metadata: HashMap::new(),
},
]),
nullable: false,
metadata: HashMap::from([(
"SERDE_ARROW:strategy".to_string(),
"EnumsWithNamedFieldsAsStructs".to_string(),
)]),
}
}

fn number_schema() -> SerdeArrowSchema {
let options = TracingOptions::default()
.allow_null_fields(true)
.enums_with_named_fields_as_structs(true);

SerdeArrowSchema::from_type::<Number>(options).unwrap()
}

fn number_data() -> Vec<Number> {
vec![
Number {
v: Value::Real { value: 0.0 },
},
Number {
v: Value::Complex { i: 0.5, j: 0.5 },
},
Number {
v: Value::Whole { value: 5 },
},
]
}

#[test]
fn test_build_flattened_union_builder() {
let mut builder = ArrayBuilder::new(number_schema()).unwrap();

// One struct in the array
let arrays = builder.build_arrays().unwrap();

assert_eq!(arrays.len(), 1);

let array = &arrays[0];

let Array::Struct(ref struct_array) = array else {
panic!("expected a struct array, found {array:#?}");
};

// Should be a single struct array with 4 fields: Complex::i, Complex::j, Real::value, Whole::value
assert_eq!(
struct_array.fields.len(),
4,
"contained {} fields",
struct_array.fields.len()
);

let (first_field, meta) = &struct_array.fields[0];
assert_eq!(meta.name, "Complex::i");
assert!(matches!(first_field, Array::Float32(_)));

let (second_field, meta) = &struct_array.fields[1];
assert_eq!(meta.name, "Complex::j");
assert!(matches!(second_field, Array::Float32(_)));

let (third_field, meta) = &struct_array.fields[2];
assert_eq!(meta.name, "Real::value");
assert!(matches!(third_field, Array::Float32(_)));

let (fourth_field, meta) = &struct_array.fields[3];
assert_eq!(meta.name, "Whole::value");
assert!(matches!(fourth_field, Array::UInt64(_)));
}

#[test]
fn test_serialize_flattened_union_builder() {
let field = number_field();
let data = number_data();
let schema = SerdeArrowSchema {
fields: vec![field],
};

let api_builder = ArrayBuilder::new(schema).expect("failed to create api array builder");
let serializer = Serializer::new(api_builder);
data.serialize(serializer)
.expect("failed to serialize")
.into_inner()
.to_arrow()
.expect("failed to serialize to arrow");
}

#[test]
fn test_record_batch_flattened_union_builder() {
let field = number_field();
let data = number_data();
let schema = SerdeArrowSchema {
fields: vec![field],
};

let api_builder = ArrayBuilder::new(schema).expect("failed to create api array builder");
let serializer = Serializer::new(api_builder);
data.serialize(serializer)
.expect("failed to serialize")
.into_inner()
.to_record_batch()
.expect("failed to create record batch");
}
1 change: 1 addition & 0 deletions serde_arrow/src/test_with_arrow/impls/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ mod chrono;
mod dictionary;
mod examples;
mod fixed_size_list;
mod flattened_union;
mod jiff;
mod json_values;
mod list;
Expand Down

0 comments on commit bf3f789

Please sign in to comment.