Fix blueprint schema for tuples.

This commit is contained in:
KtorZ 2023-02-21 15:29:33 +01:00
parent e611d1ee7a
commit db0dfbbec1
No known key found for this signature in database
GPG Key ID: 33173CB6F77F4277
2 changed files with 56 additions and 18 deletions

View File

@ -44,11 +44,18 @@ pub enum Schema {
pub enum Data {
Integer,
Bytes,
List(Box<Data>),
List(Items<Data>),
Map(Box<Data>, Box<Data>),
AnyOf(Vec<Annotated<Constructor>>),
}
/// A structure that represents either one or many elements.
#[derive(Debug, PartialEq, Eq, Clone)]
pub enum Items<T> {
One(Box<T>),
Many(Vec<T>),
}
/// Captures a single UPLC constructor with its
#[derive(Debug, PartialEq, Eq, Clone)]
pub struct Constructor {
@ -195,10 +202,15 @@ impl Annotated<Schema> {
// as such. We don't have a concept of language maps in Aiken, so we simply
// make all types abide by this convention.
let data = match generic.annotated {
Schema::Pair(left, right) => Data::Map(Box::new(left), Box::new(right)),
Schema::Data(Some(Data::List(Items::Many(xs)))) if xs.len() == 2 => {
Data::Map(
Box::new(xs.first().unwrap().to_owned()),
Box::new(xs.last().unwrap().to_owned()),
)
}
_ => {
let inner = generic.into_data(type_info)?.annotated;
Data::List(Box::new(inner))
Data::List(Items::One(Box::new(inner)))
}
};
@ -247,7 +259,11 @@ impl Annotated<Schema> {
let right = Annotated::from_type(modules, right, type_parameters)?
.into_data(right)
.map_err(|e| e.backtrack(type_info))?;
Ok(Schema::Pair(left.annotated, right.annotated).into())
Ok(Schema::Data(Some(Data::List(Items::Many(vec![
left.annotated,
right.annotated,
]))))
.into())
}
_ => {
let elems = elems
@ -261,7 +277,7 @@ impl Annotated<Schema> {
Ok(Annotated {
title: Some("Tuple".to_owned()),
description: None,
annotated: Schema::List(elems),
annotated: Schema::Data(Some(Data::List(Items::Many(elems)))).into(),
})
}
},
@ -409,7 +425,13 @@ impl Serialize for Data {
s.serialize_field("dataType", "bytes")?;
s.end()
}
Data::List(items) => {
Data::List(Items::One(item)) => {
let mut s = serializer.serialize_struct("List", 2)?;
s.serialize_field("dataType", "list")?;
s.serialize_field("items", &item)?;
s.end()
}
Data::List(Items::Many(items)) => {
let mut s = serializer.serialize_struct("List", 2)?;
s.serialize_field("dataType", "list")?;
s.serialize_field("items", &items)?;
@ -624,7 +646,7 @@ pub mod test {
#[test]
fn serialize_data_list_1() {
let schema = Schema::Data(Some(Data::List(Box::new(Data::Integer))));
let schema = Schema::Data(Some(Data::List(Items::One(Box::new(Data::Integer)))));
assert_json(
&schema,
json!({
@ -638,8 +660,8 @@ pub mod test {
#[test]
fn serialize_data_list_2() {
let schema = Schema::Data(Some(Data::List(Box::new(Data::List(Box::new(
Data::Integer,
let schema = Schema::Data(Some(Data::List(Items::One(Box::new(Data::List(
Items::One(Box::new(Data::Integer)),
))))));
assert_json(
&schema,
@ -654,6 +676,24 @@ pub mod test {
);
}
#[test]
fn serialize_data_list_3() {
let schema = Schema::Data(Some(Data::List(Items::Many(vec![
Data::Integer,
Data::Bytes,
]))));
assert_json(
&schema,
json!({
"dataType": "list",
"items": [
{ "dataType": "integer" },
{ "dataType": "bytes" },
]
}),
);
}
#[test]
fn serialize_data_map_1() {
let schema = Schema::Data(Some(Data::Map(
@ -678,7 +718,7 @@ pub mod test {
fn serialize_data_map_2() {
let schema = Schema::Data(Some(Data::Map(
Box::new(Data::Bytes),
Box::new(Data::List(Box::new(Data::Integer))),
Box::new(Data::List(Items::One(Box::new(Data::Integer)))),
)));
assert_json(
&schema,

View File

@ -474,13 +474,11 @@ mod test {
"title": "test_module.spend",
"hash": "3c6766e7a36df2aa13c0e9e6e071317ed39d05f405771c4f1a81c6cc",
"datum": {
"dataType": "#pair",
"left": {
"dataType": "integer"
},
"right": {
"dataType": "bytes"
}
"dataType": "list",
"items": [
{ "dataType": "integer" },
{ "dataType": "bytes" }
]
},
"redeemer": {
"dataType": "#string"
@ -505,7 +503,7 @@ mod test {
"hash": "f335ce0436fd7df56e727a66ada7298534a27b98f887bc3b7947ee48",
"datum": {
"title": "Tuple",
"dataType": "#list",
"dataType": "list",
"items": [
{
"dataType": "integer"