use super::*;
use ink_primitives::Key;
use scale_info::Path;
#[test]
fn layout_key_works() {
let layout_key = LayoutKey::from(&1);
let json = serde_json::to_string(&layout_key).unwrap();
assert_eq!(json, "\"0x01000000\"",);
}
fn named_fields_struct_layout(key: &Key) -> Layout {
StructLayout::new(
"Struct",
vec![
FieldLayout::new("a", LeafLayout::from_key::<i32>(LayoutKey::from(key))),
FieldLayout::new("b", LeafLayout::from_key::<i64>(LayoutKey::from(key))),
],
)
.into()
}
#[test]
fn named_fields_work() {
let layout = named_fields_struct_layout(&345);
let mut registry = Registry::new();
let compacted = layout.into_portable(&mut registry);
let json = serde_json::to_value(&compacted).unwrap();
let expected = serde_json::json! {
{
"struct": {
"fields": [
{
"layout": {
"leaf": {
"key": "0x59010000",
"ty": 0,
}
},
"name": "a",
},
{
"layout": {
"leaf": {
"key": "0x59010000",
"ty": 1,
}
},
"name": "b",
}
],
"name": "Struct",
}
}
};
assert_eq!(json, expected);
}
fn tuple_struct_layout(key: &Key) -> Layout {
StructLayout::new(
"(A, B)",
vec![
FieldLayout::new("0", LeafLayout::from_key::<i32>(LayoutKey::from(key))),
FieldLayout::new("1", LeafLayout::from_key::<i64>(LayoutKey::from(key))),
],
)
.into()
}
#[test]
fn tuple_struct_work() {
let layout = tuple_struct_layout(&234);
let mut registry = Registry::new();
let compacted = layout.into_portable(&mut registry);
let json = serde_json::to_value(&compacted).unwrap();
let expected = serde_json::json! {
{
"struct": {
"fields": [
{
"layout": {
"leaf": {
"key": "0xea000000",
"ty": 0,
}
},
"name": "0",
},
{
"layout": {
"leaf": {
"key": "0xea000000",
"ty": 1,
}
},
"name": "1",
}
],
"name": "(A, B)",
}
}
};
assert_eq!(json, expected);
}
fn clike_enum_layout(key: &Key) -> Layout {
EnumLayout::new(
"Enum",
key,
vec![
(Discriminant(0), StructLayout::new("Struct0", vec![])),
(Discriminant(1), StructLayout::new("Struct1", vec![])),
(Discriminant(2), StructLayout::new("Struct2", vec![])),
],
)
.into()
}
#[test]
fn clike_enum_work() {
let layout = clike_enum_layout(&123);
let mut registry = Registry::new();
let compacted = layout.into_portable(&mut registry);
let json = serde_json::to_value(&compacted).unwrap();
let expected = serde_json::json! {
{
"enum": {
"dispatchKey": "0x7b000000",
"name": "Enum",
"variants": {
"0": {
"fields": [],
"name": "Struct0",
},
"1": {
"fields": [],
"name": "Struct1",
},
"2": {
"fields": [],
"name": "Struct2",
},
}
}
}
};
assert_eq!(json, expected);
}
fn mixed_enum_layout(key: &Key) -> Layout {
EnumLayout::new(
"Enum",
*key,
vec![
(Discriminant(0), StructLayout::new("Struct0", vec![])),
{
let variant_key = key;
(
Discriminant(1),
StructLayout::new(
"Struct1",
vec![
FieldLayout::new(
"0",
LeafLayout::from_key::<i32>(LayoutKey::from(variant_key)),
),
FieldLayout::new(
"1",
LeafLayout::from_key::<i64>(LayoutKey::from(variant_key)),
),
],
),
)
},
{
let variant_key = key;
(
Discriminant(2),
StructLayout::new(
"Struct2",
vec![
FieldLayout::new(
"a",
LeafLayout::from_key::<i32>(LayoutKey::from(variant_key)),
),
FieldLayout::new(
"b",
LeafLayout::from_key::<i64>(LayoutKey::from(variant_key)),
),
],
),
)
},
],
)
.into()
}
#[test]
fn mixed_enum_work() {
let layout = mixed_enum_layout(&456);
let mut registry = Registry::new();
let compacted = layout.into_portable(&mut registry);
let json = serde_json::to_value(&compacted).unwrap();
let expected = serde_json::json! {
{
"enum": {
"dispatchKey": "0xc8010000",
"name": "Enum",
"variants": {
"0": {
"fields": [],
"name": "Struct0",
},
"1": {
"fields": [
{
"layout": {
"leaf": {
"key": "0xc8010000",
"ty": 0,
}
},
"name": "0",
},
{
"layout": {
"leaf": {
"key": "0xc8010000",
"ty": 1,
}
},
"name": "1",
}
],
"name": "Struct1",
},
"2": {
"fields": [
{
"layout": {
"leaf": {
"key": "0xc8010000",
"ty": 0,
}
},
"name": "a",
},
{
"layout": {
"leaf": {
"key": "0xc8010000",
"ty": 1,
}
},
"name": "b",
}
],
"name": "Struct2",
},
}
}
}
};
assert_eq!(json, expected);
}
fn unbounded_hashing_layout(key: &Key) -> Layout {
let root_key = key;
HashLayout::new(
root_key,
HashingStrategy::new(
CryptoHasher::Blake2x256,
b"ink storage hashmap".to_vec(),
Vec::new(),
),
LeafLayout::from_key::<(i32, bool)>(LayoutKey::from(root_key)),
)
.into()
}
#[test]
fn unbounded_layout_works() {
let layout = unbounded_hashing_layout(&567);
let mut registry = Registry::new();
let compacted = layout.into_portable(&mut registry);
let json = serde_json::to_value(&compacted).unwrap();
let expected = serde_json::json! {
{
"hash": {
"layout": {
"leaf": {
"key": "0x37020000",
"ty": 0
}
},
"offset": "0x37020000",
"strategy": {
"hasher": "Blake2x256",
"prefix": "0x696e6b2073746f7261676520686173686d6170",
"postfix": "",
}
}
}
};
assert_eq!(json, expected);
}
#[test]
fn runtime_storage_layout_works() {
let key = LayoutKey::new(0u32);
let leaf: LeafLayout<PortableForm> = LeafLayout::new(key, 123.into());
let path: Path<PortableForm> = Path::from_segments_unchecked(["Storage".to_string()]);
let root_layout = Layout::Struct(StructLayout::new(
path.ident().unwrap(),
[FieldLayout::new("Field", leaf)],
));
let json = serde_json::to_value(&root_layout).unwrap();
let expected = serde_json::json!(
{
"struct": {
"name": "Storage",
"fields": [
{
"name": "Field",
"layout": {
"leaf": {
"key": "0x00000000",
"ty": 123
}
}
}
]
}
}
);
assert_eq!(json, expected);
}
#[test]
fn ensure_portable_root_layout_are_supported() {
let root_key = LayoutKey::new(0u32);
let layout = Layout::Struct(StructLayout::new(String::new(), Vec::new()));
let ty = 0.into();
let _: RootLayout<PortableForm> = RootLayout::new(root_key, layout, ty);
}