mirror of
https://github.com/eth-act/ere.git
synced 2026-02-19 11:54:42 -05:00
add initial code for inputErased
This commit is contained in:
@@ -12,6 +12,10 @@ bincode = "1.3"
|
||||
indexmap = { version = "2.9.0", features = ["serde"] }
|
||||
thiserror = "2"
|
||||
auto_impl = "1.0"
|
||||
erased-serde = "0.4.6"
|
||||
|
||||
[dev-dependencies]
|
||||
serde_json = "1"
|
||||
|
||||
[lints]
|
||||
workspace = true
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
use erased_serde::Serialize as ErasedSerialize;
|
||||
use serde::Serialize;
|
||||
|
||||
/// Represents a builder for input data to be passed to a ZKVM guest program.
|
||||
/// Values are serialized sequentially into an internal byte buffer.
|
||||
#[derive(Debug, Default)]
|
||||
@@ -8,6 +8,24 @@ pub struct Input {
|
||||
ranges: Vec<(usize, usize)>,
|
||||
}
|
||||
|
||||
pub struct InputErased {
|
||||
buf: Vec<Box<dyn ErasedSerialize>>,
|
||||
}
|
||||
|
||||
impl InputErased {
|
||||
/// Create an empty input buffer.
|
||||
pub fn new() -> Self {
|
||||
Self {
|
||||
buf: Default::default(),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn write<T: Serialize + 'static>(&mut self, value: T) -> Result<(), bincode::Error> {
|
||||
self.buf.push(Box::new(value));
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
impl Input {
|
||||
/// Create an empty input buffer.
|
||||
pub fn new() -> Self {
|
||||
@@ -127,3 +145,177 @@ mod tests {
|
||||
assert_eq!(input.iter().count(), slice1.len() + slice2.len());
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod input_erased_tests {
|
||||
use super::*;
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq)]
|
||||
struct Person {
|
||||
name: String,
|
||||
age: u32,
|
||||
}
|
||||
|
||||
#[derive(Debug, Serialize, Deserialize, PartialEq)]
|
||||
struct Product {
|
||||
id: u64,
|
||||
name: String,
|
||||
price: f64,
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_new_creates_empty_buffer() {
|
||||
let input = InputErased::new();
|
||||
assert_eq!(input.buf.len(), 0);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_write_primitive_types() {
|
||||
let mut input = InputErased::new();
|
||||
|
||||
assert!(input.write(42i32).is_ok());
|
||||
assert!(input.write(3.14f64).is_ok());
|
||||
assert!(input.write(true).is_ok());
|
||||
assert!(input.write("hello".to_string()).is_ok());
|
||||
|
||||
assert_eq!(input.buf.len(), 4);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_write_custom_structs() {
|
||||
let mut input = InputErased::new();
|
||||
|
||||
let person = Person {
|
||||
name: "Alice".to_string(),
|
||||
age: 30,
|
||||
};
|
||||
|
||||
let product = Product {
|
||||
id: 123,
|
||||
name: "Widget".to_string(),
|
||||
price: 9.99,
|
||||
};
|
||||
|
||||
assert!(input.write(person).is_ok());
|
||||
assert!(input.write(product).is_ok());
|
||||
|
||||
assert_eq!(input.buf.len(), 2);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_write_collections() {
|
||||
let mut input = InputErased::new();
|
||||
|
||||
let vec_data = vec![1, 2, 3, 4, 5];
|
||||
let array_data = [10, 20, 30];
|
||||
|
||||
assert!(input.write(vec_data).is_ok());
|
||||
assert!(input.write(array_data).is_ok());
|
||||
|
||||
assert_eq!(input.buf.len(), 2);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_write_mixed_types() {
|
||||
let mut input = InputErased::new();
|
||||
|
||||
// Write different types to the same buffer
|
||||
assert!(input.write(42).is_ok());
|
||||
assert!(input.write("test".to_string()).is_ok());
|
||||
assert!(input.write(vec![1, 2, 3]).is_ok());
|
||||
assert!(
|
||||
input
|
||||
.write(Person {
|
||||
name: "Bob".to_string(),
|
||||
age: 25,
|
||||
})
|
||||
.is_ok()
|
||||
);
|
||||
|
||||
assert_eq!(input.buf.len(), 4);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_serialization_with_erased_serde() {
|
||||
let mut input = InputErased::new();
|
||||
|
||||
input.write(42i32).unwrap();
|
||||
input.write("hello".to_string()).unwrap();
|
||||
|
||||
// Test that we can serialize the stored items to a buffer
|
||||
for item in &input.buf {
|
||||
let mut buf = Vec::new();
|
||||
let mut serializer = serde_json::Serializer::new(&mut buf);
|
||||
let json_result = erased_serde::serialize(item.as_ref(), &mut serializer);
|
||||
// Just testing that serialization works without error
|
||||
assert!(json_result.is_ok());
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_write_returns_ok() {
|
||||
let mut input = InputErased::new();
|
||||
|
||||
// All these should return Ok(())
|
||||
let results = vec![
|
||||
input.write(1),
|
||||
input.write("test".to_string()),
|
||||
input.write(vec![1, 2, 3]),
|
||||
];
|
||||
|
||||
for result in results {
|
||||
assert!(result.is_ok());
|
||||
assert_eq!(result.unwrap(), ());
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_multiple_writes_increase_buffer_size() {
|
||||
let mut input = InputErased::new();
|
||||
|
||||
assert_eq!(input.buf.len(), 0);
|
||||
|
||||
input.write(1).unwrap();
|
||||
assert_eq!(input.buf.len(), 1);
|
||||
|
||||
input.write(2).unwrap();
|
||||
assert_eq!(input.buf.len(), 2);
|
||||
|
||||
input.write(3).unwrap();
|
||||
assert_eq!(input.buf.len(), 3);
|
||||
}
|
||||
|
||||
// Helper function to demonstrate actual serialization to bytes
|
||||
// (since the current implementation doesn't expose this)
|
||||
fn serialize_buffer_to_json(
|
||||
input: &InputErased,
|
||||
) -> Result<Vec<String>, Box<dyn std::error::Error>> {
|
||||
let mut results = Vec::new();
|
||||
|
||||
for item in &input.buf {
|
||||
let mut buf = Vec::new();
|
||||
let mut serializer = serde_json::Serializer::new(&mut buf);
|
||||
erased_serde::serialize(item.as_ref(), &mut serializer)?;
|
||||
results.push(String::from_utf8(buf)?);
|
||||
}
|
||||
|
||||
Ok(results)
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_actual_serialization_output() {
|
||||
let mut input = InputErased::new();
|
||||
|
||||
input.write(42).unwrap();
|
||||
input.write("hello".to_string()).unwrap();
|
||||
input.write(vec![1, 2, 3]).unwrap();
|
||||
|
||||
let serialized = serialize_buffer_to_json(&input).unwrap();
|
||||
|
||||
assert_eq!(serialized.len(), 3);
|
||||
assert_eq!(serialized[0], "42");
|
||||
assert_eq!(serialized[1], "\"hello\"");
|
||||
assert_eq!(serialized[2], "[1,2,3]");
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user