mod test_utils;
use test_utils::*;
#[test]
fn test_external_data_basic() {
let graph = load_onnx("external_data.onnx");
assert_eq!(graph.inputs.len(), 1, "Expected 1 input");
assert_eq!(graph.outputs.len(), 1, "Expected 1 output");
assert!(!graph.nodes.is_empty(), "Graph should have nodes");
}
#[test]
fn test_external_data_values() {
let graph = load_onnx("external_data.onnx");
for node in &graph.nodes {
if let onnx_ir::ir::Node::Constant(const_node) = node {
if let Some(output) = const_node.outputs.first()
&& let Some(data) = output.value()
{
let shape = data.shape.clone();
if shape == burn_tensor::Shape::new([4, 4]) {
let values: Vec<f32> = data.as_slice().unwrap().to_vec();
assert_eq!(values[0], 1.0, "weight[0,0] should be 1.0");
assert_eq!(values[5], 2.0, "weight[1,1] should be 2.0");
assert_eq!(values[10], 3.0, "weight[2,2] should be 3.0");
assert_eq!(values[15], 4.0, "weight[3,3] should be 4.0");
}
if shape == burn_tensor::Shape::new([4]) {
let values: Vec<f32> = data.as_slice().unwrap().to_vec();
assert!((values[0] - 0.1).abs() < 1e-6, "bias[0] should be 0.1");
assert!((values[1] - 0.2).abs() < 1e-6, "bias[1] should be 0.2");
assert!((values[2] - 0.3).abs() < 1e-6, "bias[2] should be 0.3");
assert!((values[3] - 0.4).abs() < 1e-6, "bias[3] should be 0.4");
}
}
}
}
}
#[test]
fn test_external_data_with_offset() {
let graph = load_onnx("external_data_offset.onnx");
assert_eq!(graph.inputs.len(), 1, "Expected 1 input");
assert_eq!(graph.outputs.len(), 1, "Expected 1 output");
assert!(has_node_type(&graph, |n| matches!(
n,
onnx_ir::ir::Node::Add { .. }
)));
let const_count = count_constant_nodes(&graph);
assert_eq!(const_count, 1, "Expected 1 constant node");
for node in &graph.nodes {
if let onnx_ir::ir::Node::Constant(const_node) = node
&& let Some(output) = const_node.outputs.first()
&& let Some(data) = output.value()
{
assert_eq!(
data.shape,
burn_tensor::Shape::new([2, 3]),
"Expected shape [2, 3]"
);
let values: Vec<f32> = data.as_slice().unwrap().to_vec();
assert_eq!(values, vec![1.0, 2.0, 3.0, 4.0, 5.0, 6.0]);
}
}
}
#[test]
fn test_mixed_embedded_and_external_data() {
let graph = load_onnx("mixed_data.onnx");
assert_eq!(graph.inputs.len(), 1, "Expected 1 input");
assert_eq!(graph.outputs.len(), 1, "Expected 1 output");
assert!(!graph.nodes.is_empty(), "Graph should have nodes");
}
#[test]
#[should_panic(expected = "external data")]
fn test_external_data_from_bytes_panics() {
use std::fs;
let model_path = get_model_path("external_data.onnx");
let bytes = fs::read(&model_path).expect("Failed to read model file");
let _ = onnx_ir::OnnxGraphBuilder::new()
.simplify(false)
.parse_bytes(&bytes);
}
#[test]
fn test_multiple_external_files() {
let graph = load_onnx("multi_external_files.onnx");
assert_eq!(graph.inputs.len(), 1, "Expected 1 input");
assert_eq!(graph.outputs.len(), 1, "Expected 1 output");
assert!(!graph.nodes.is_empty(), "Graph should have nodes");
let mut found_weight = false;
let mut found_bias = false;
for node in &graph.nodes {
if let onnx_ir::ir::Node::Constant(const_node) = node
&& let Some(output) = const_node.outputs.first()
&& let Some(data) = output.value()
{
let shape = data.shape.clone();
if shape == burn_tensor::Shape::new([4, 4]) {
let values: Vec<f32> = data.as_slice().unwrap().to_vec();
assert_eq!(values[0], 1.0, "weight[0,0] should be 1.0");
assert_eq!(values[5], 2.0, "weight[1,1] should be 2.0");
assert_eq!(values[10], 3.0, "weight[2,2] should be 3.0");
assert_eq!(values[15], 4.0, "weight[3,3] should be 4.0");
found_weight = true;
}
if shape == burn_tensor::Shape::new([4]) {
let values: Vec<f32> = data.as_slice().unwrap().to_vec();
assert!((values[0] - 0.5).abs() < 1e-6, "bias[0] should be 0.5");
assert!((values[1] - 0.5).abs() < 1e-6, "bias[1] should be 0.5");
assert!((values[2] - 0.5).abs() < 1e-6, "bias[2] should be 0.5");
assert!((values[3] - 0.5).abs() < 1e-6, "bias[3] should be 0.5");
found_bias = true;
}
}
}
assert!(
found_weight || found_bias || !graph.nodes.is_empty(),
"Should successfully parse model with multiple external files"
);
}