use wolfram_expr::{expr, from_wxf, to_wxf};
use wolfram_expr::{Association, ByteArray, Expr, ExprKind, NumericArray, RuleEntry};
#[path = "fixtures/wxf_kernel_fixtures.rs"]
mod fix;
#[track_caller]
fn assert_parses_to(bytes: &[u8], expected: Expr) {
let parsed: Expr = from_wxf(bytes).expect("deserialize kernel WXF");
assert_eq!(parsed, expected);
}
#[track_caller]
fn assert_serializes_to(expr: Expr, fixture: &[u8]) {
let bytes = to_wxf(&expr, None).expect("serialize WXF");
assert_eq!(
bytes.as_slice(),
fixture,
"serialized bytes don't match kernel fixture"
);
}
#[test]
fn integer() {
assert_parses_to(fix::INTEGER_42, Expr::from(42i64));
assert_parses_to(fix::INTEGER_NEG_LARGE, Expr::from(-1_234_567_890i64));
}
#[test]
fn real() {
assert_parses_to(fix::REAL_3_5, Expr::real(3.5));
}
#[test]
fn string() {
assert_parses_to(fix::STRING_HELLO, Expr::from("hello"));
}
#[test]
fn symbol() {
assert_parses_to(fix::SYMBOL_PLUS, expr!(::Plus));
assert_parses_to(fix::SYMBOL_MYPKG_X, expr!(MyPkg::x));
}
#[test]
fn list() {
assert_parses_to(fix::LIST_INTS, expr!(::List[1, 2, 3]));
assert_parses_to(fix::LIST_EMPTY, expr!(::List[]));
assert_parses_to(fix::LIST_MIXED, expr!(::List["a", 1, 2.5]));
}
#[test]
fn function_user_context() {
assert_parses_to(fix::FUNCTION_MYPKG, expr!(MyPkg::myFunc[1, 2, 3]));
}
#[test]
fn association_plain() {
let a: Association = vec![
RuleEntry::rule(Expr::from("a"), Expr::from(1)),
RuleEntry::rule(Expr::from("b"), Expr::from(2)),
];
assert_parses_to(fix::ASSOCIATION_PLAIN, Expr::from(a));
}
#[test]
fn association_with_delayed_rule() {
let a: Association = vec![
RuleEntry::rule(Expr::from("a"), Expr::from(1)),
RuleEntry::rule_delayed(Expr::from("b"), Expr::from(2)),
];
assert_parses_to(fix::ASSOCIATION_DELAYED, Expr::from(a));
}
#[test]
fn byte_array() {
let ba = Expr::from(ByteArray::from(vec![0u8, 1, 2, 0xff, 0x80]));
assert_parses_to(fix::BYTE_ARRAY, ba);
}
#[test]
fn numeric_array_int32() {
let arr = Expr::from(NumericArray::from_slice::<i32>(vec![3], &[10, 20, 30]));
assert_parses_to(fix::NUMERIC_ARRAY_INT32, arr);
}
#[test]
fn expr_macro_integers() {
assert_serializes_to(expr!(42), fix::INTEGER_42);
assert_serializes_to(expr!(-1_234_567_890i64), fix::INTEGER_NEG_LARGE);
}
#[test]
fn expr_macro_real() {
assert_serializes_to(expr!(3.5f64), fix::REAL_3_5);
}
#[test]
fn expr_macro_string() {
assert_serializes_to(expr!("hello"), fix::STRING_HELLO);
}
#[test]
fn expr_macro_association() {
assert_serializes_to(expr!({ "a" -> 1, "b" -> 2 }), fix::ASSOCIATION_PLAIN);
}
#[test]
fn expr_macro_byte_array() {
let ba = ByteArray::from(vec![0u8, 1, 2, 0xff, 0x80]);
assert_serializes_to(expr!(ba), fix::BYTE_ARRAY);
}
#[test]
fn expr_macro_numeric_array() {
let arr = NumericArray::from_slice::<i32>(vec![3], &[10, 20, 30]);
assert_serializes_to(expr!(arr), fix::NUMERIC_ARRAY_INT32);
}
#[test]
fn compressed_range_100() {
let parsed: Expr =
from_wxf(fix::COMPRESSED_RANGE_100).expect("deserialize compressed kernel WXF");
let ExprKind::PackedArray(arr) = parsed.kind() else {
panic!("Range[100] should land as a PackedArray, got {:?}", parsed);
};
assert_eq!(arr.dimensions(), &[100]);
assert_eq!(
arr.try_as_slice::<i8>(),
Some((1..=100i8).collect::<Vec<_>>().as_slice())
);
}