Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 0 additions & 1 deletion Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions api/src/tests/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ mod objects;
mod option_test;
mod resource_groups;
mod secp256k1_ecdsa;
mod signed_int_test;
mod simulation_test;
mod state_test;
mod string_resource_test;
Expand Down
134 changes: 134 additions & 0 deletions api/src/tests/signed_int_test.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,134 @@
// Copyright © Aptos Foundation
// Parts of the project are originally copyright © Meta Platforms, Inc.
// SPDX-License-Identifier: Apache-2.0

use super::new_test_context_with_orderless_flags;
use aptos_api_test_context::{current_function_name, TestContext};
use rstest::rstest;
use serde_json::json;
use std::path::PathBuf;

#[tokio::test(flavor = "multi_thread", worker_threads = 2)]
#[rstest(
use_txn_payload_v2_format,
use_orderless_transactions,
case(false, false),
case(true, false),
case(true, true)
)]
async fn test_signed_ints(use_txn_payload_v2_format: bool, use_orderless_transactions: bool) {
let mut context = new_test_context_with_orderless_flags(
current_function_name!(),
use_txn_payload_v2_format,
use_orderless_transactions,
);
let mut account = context.create_account().await;
let account_addr = account.address();

// Publish packages
let named_addresses = vec![("account".to_string(), account_addr)];
let txn = futures::executor::block_on(async move {
let path = PathBuf::from(std::env!("CARGO_MANIFEST_DIR"))
.join("../aptos-move/move-examples/signed_int/calculator");
TestContext::build_package_with_latest_language(path, named_addresses)
});

// Init state: `-1i64`
context.publish_package(&mut account, txn).await;
let state_resource = format!("{}::{}::{}", account_addr, "calculator", "State");
let state = &context
.gen_resource(&account_addr, &state_resource)
.await
.unwrap()["data"];
assert_eq!(state, &json!({"__variant__": "Value", "_0": "-1"}));

// Reset state: `0i64`
context
.api_execute_entry_function(
&mut account,
&format!("0x{}::calculator::number", account_addr.to_hex()),
json!([]),
json!(["0"]),
)
.await;
let state = &context
.gen_resource(&account_addr, &state_resource)
.await
.unwrap()["data"];
assert_eq!(state, &json!({"__variant__": "Value", "_0": "0"}));

// Add `2i8`
context
.api_execute_entry_function(
&mut account,
&format!("0x{}::calculator::add", account_addr.to_hex()),
json!([]),
json!([2]),
)
.await;
let state = &context
.gen_resource(&account_addr, &state_resource)
.await
.unwrap()["data"];
assert_eq!(state, &json!({"__variant__": "Value", "_0": "2"}));

// Sub `-2i16`
context
.api_execute_entry_function(
&mut account,
&format!("0x{}::calculator::sub", account_addr.to_hex()),
json!([]),
json!([-2]),
)
.await;
let state = &context
.gen_resource(&account_addr, &state_resource)
.await
.unwrap()["data"];
assert_eq!(state, &json!({"__variant__": "Value", "_0": "4"}));

// Mul `2i32`
context
.api_execute_entry_function(
&mut account,
&format!("0x{}::calculator::mul", account_addr.to_hex()),
json!([]),
json!([2]),
)
.await;
let state = &context
.gen_resource(&account_addr, &state_resource)
.await
.unwrap()["data"];
assert_eq!(state, &json!({"__variant__": "Value", "_0": "8"}));

// Div `2i128`
context
.api_execute_entry_function(
&mut account,
&format!("0x{}::calculator::div", account_addr.to_hex()),
json!([]),
json!(["2"]),
)
.await;
let state = &context
.gen_resource(&account_addr, &state_resource)
.await
.unwrap()["data"];
assert_eq!(state, &json!({"__variant__": "Value", "_0": "4"}));

// Mod `-3i256`
context
.api_execute_entry_function(
&mut account,
&format!("0x{}::calculator::mod", account_addr.to_hex()),
json!([]),
json!(["-3"]),
)
.await;
let state = &context
.gen_resource(&account_addr, &state_resource)
.await
.unwrap()["data"];
assert_eq!(state, &json!({"__variant__": "Value", "_0": "1"}));
}
15 changes: 6 additions & 9 deletions api/types/src/bytecode.rs
Original file line number Diff line number Diff line change
Expand Up @@ -85,6 +85,12 @@ pub trait Bytecode {
SignatureToken::U64 => MoveType::U64,
SignatureToken::U128 => MoveType::U128,
SignatureToken::U256 => MoveType::U256,
SignatureToken::I8 => MoveType::I8,
SignatureToken::I16 => MoveType::I16,
SignatureToken::I32 => MoveType::I32,
SignatureToken::I64 => MoveType::I64,
SignatureToken::I128 => MoveType::I128,
SignatureToken::I256 => MoveType::I256,
SignatureToken::Address => MoveType::Address,
SignatureToken::Signer => MoveType::Signer,
SignatureToken::Vector(t) => MoveType::Vector {
Expand Down Expand Up @@ -115,15 +121,6 @@ pub trait Bytecode {
abilities: *abilities,
}
},
SignatureToken::I8
| SignatureToken::I16
| SignatureToken::I32
| SignatureToken::I64
| SignatureToken::I128
| SignatureToken::I256 => {
// TODO(#17645): signed integers
MoveType::Unparsable("signed integer NYI".to_string())
},
}
}

Expand Down
15 changes: 6 additions & 9 deletions api/types/src/convert.rs
Original file line number Diff line number Diff line change
Expand Up @@ -916,6 +916,12 @@ impl<'a, S: StateView> MoveConverter<'a, S> {
MoveTypeLayout::U64 => serde_json::from_value::<crate::U64>(val)?.into(),
MoveTypeLayout::U128 => serde_json::from_value::<crate::U128>(val)?.into(),
MoveTypeLayout::U256 => serde_json::from_value::<crate::U256>(val)?.into(),
MoveTypeLayout::I8 => I8(serde_json::from_value::<i8>(val)?),
MoveTypeLayout::I16 => I16(serde_json::from_value::<i16>(val)?),
MoveTypeLayout::I32 => I32(serde_json::from_value::<i32>(val)?),
MoveTypeLayout::I64 => serde_json::from_value::<crate::I64>(val)?.into(),
MoveTypeLayout::I128 => serde_json::from_value::<crate::I128>(val)?.into(),
MoveTypeLayout::I256 => serde_json::from_value::<crate::I256>(val)?.into(),
MoveTypeLayout::Address => serde_json::from_value::<crate::Address>(val)?.into(),
MoveTypeLayout::Vector(item_layout) => {
self.try_into_vm_value_vector(item_layout.as_ref(), val)?
Expand All @@ -935,15 +941,6 @@ impl<'a, S: StateView> MoveConverter<'a, S> {
MoveTypeLayout::Signer | MoveTypeLayout::Native(..) => {
bail!("unexpected move type {:?} for value {:?}", layout, val)
},
MoveTypeLayout::I8
| MoveTypeLayout::I16
| MoveTypeLayout::I32
| MoveTypeLayout::I64
| MoveTypeLayout::I128
| MoveTypeLayout::I256 => {
// TODO(#17645): signed integers
bail!("unimplemented support for signed integers")
},
})
}

Expand Down
63 changes: 58 additions & 5 deletions api/types/src/derives.rs
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@
use crate::{
move_types::{MoveAbility, MoveStructValue},
Address, AssetType, EntryFunctionId, HashValue, HexEncodedBytes, IdentifierWrapper,
MoveModuleId, MoveStructTag, MoveType, StateKeyWrapper, U128, U256, U64,
MoveModuleId, MoveStructTag, MoveType, StateKeyWrapper, I128, I256, I64, U128, U256, U64,
};
use aptos_openapi::{impl_poem_parameter, impl_poem_type};
use indoc::indoc;
Expand Down Expand Up @@ -177,9 +177,9 @@ impl_poem_type!(

Move `bool` type value is serialized into `boolean`.

Move `u8`, `u16` and `u32` type value is serialized into `integer`.
Move `u8`, `u16`, `u32`, `i8`, `i16`, and `i32` type value is serialized into `integer`.

Move `u64`, `u128` and `u256` type value is serialized into `string`.
Move `u64`, `u128`, `u256`, `i64`, `i128`, and `i256` type value is serialized into `string`.

Move `address` type value (32 byte Aptos account address) is serialized into a HexEncodedBytes string.
For example:
Expand Down Expand Up @@ -217,7 +217,7 @@ impl_poem_type!(
"string",
(
pattern =
Some("^(bool|u8|u64|u128|address|signer|vector<.+>|0x[0-9a-zA-Z:_<, >]+)$".to_string()),
Some("^(bool|u8|u16|u32|u64|u128|u256|i8|i16|i32|i64|i128|i256|address|signer|vector<.+>|0x[0-9a-zA-Z:_<, >]+)$".to_string()),
description = Some(indoc! {"
String representation of an on-chain Move type tag that is exposed in transaction payload.
Values:
Expand All @@ -228,6 +228,12 @@ impl_poem_type!(
- u64
- u128
- u256
- i8
- i16
- i32
- i64
- i128
- i256
- address
- signer
- vector: `vector<{non-reference MoveTypeId}>`
Expand Down Expand Up @@ -309,6 +315,51 @@ impl_poem_type!(
)
);

impl_poem_type!(
I64,
"string",
(
example = Some(serde_json::Value::String("-32425224034".to_string())),
format = Some("int64"),
description = Some(indoc! {"
A string containing a 64-bit signed integer.

We represent i64 values as a string to ensure compatibility with languages such
as JavaScript that do not parse i64s in JSON natively.
"})
)
);

impl_poem_type!(
I128,
"string",
(
example = Some(serde_json::Value::String("-32425224034".to_string())),
format = Some("int128"),
description = Some(indoc! {"
A string containing a 128-bit signed integer.

We represent i128 values as a string to ensure compatibility with languages such
as JavaScript that do not parse i128s in JSON natively.
"})
)
);

impl_poem_type!(
I256,
"string",
(
example = Some(serde_json::Value::String("-32425224034".to_string())),
format = Some("int256"),
description = Some(indoc! {"
A string containing a 256-bit signed integer.

We represent i256 values as a string to ensure compatibility with languages such
as JavaScript that do not parse i256s in JSON natively.
"})
)
);

impl_poem_parameter!(
Address,
AssetType,
Expand All @@ -318,5 +369,7 @@ impl_poem_parameter!(
MoveStructTag,
StateKeyWrapper,
U64,
U128
U128,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Curious why u256, u32 and u16 are not here?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I am not exactly sure why they are not here. I am suspecting that's because they were added later and somehow got omitted. I need to ask around.

I64,
I128
);
2 changes: 1 addition & 1 deletion api/types/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ pub use move_types::{
HexEncodedBytes, MoveAbility, MoveFunction, MoveFunctionGenericTypeParam,
MoveFunctionVisibility, MoveModule, MoveModuleBytecode, MoveModuleId, MoveResource,
MoveScriptBytecode, MoveStruct, MoveStructField, MoveStructTag, MoveType, MoveValue,
ResourceGroup, MAX_RECURSIVE_TYPES_ALLOWED, U128, U256, U64,
ResourceGroup, I128, I256, I64, MAX_RECURSIVE_TYPES_ALLOWED, U128, U256, U64,
};
use serde::{Deserialize, Deserializer};
pub use state::RawStateValueRequest;
Expand Down
Loading
Loading