Skip to content

Commit

Permalink
feat(ITS): add chain name and token deploy salt and token sdk to ITS (#…
Browse files Browse the repository at this point in the history
  • Loading branch information
ahramy authored Dec 4, 2024
1 parent e63006a commit 017d421
Show file tree
Hide file tree
Showing 10 changed files with 85 additions and 12 deletions.
1 change: 1 addition & 0 deletions 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 Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ axelar-soroban-std = { version = "^0.1.0", path = "packages/axelar-soroban-std"
axelar-gas-service = { version = "^0.1.0", path = "contracts/axelar-gas-service" }
axelar-gateway = { version = "^0.1.0", path = "contracts/axelar-gateway" }
axelar-operators = { version = "^0.1.0", path = "contracts/axelar-operators" }
interchain-token = { version = "^0.1.0", path = "contracts/interchain-token" }
interchain-token-service = { version = "^0.1.0", path = "contracts/interchain-token-service" }
alloy-primitives = { version = "0.7.6", default-features = false, features = [
"std",
Expand Down
1 change: 1 addition & 0 deletions contracts/interchain-token-service/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ axelar-gas-service = { workspace = true, features = ["library"] }
axelar-gateway = { workspace = true, features = ["library"] }
axelar-soroban-std = { workspace = true }
soroban-sdk = { workspace = true, features = ["alloc"] }
soroban-token-sdk = { workspace = true }

[dev-dependencies]
axelar-gas-service = { workspace = true, features = ["testutils"] }
Expand Down
47 changes: 44 additions & 3 deletions contracts/interchain-token-service/src/contract.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
use axelar_soroban_std::types::Token;
use axelar_soroban_std::{ensure, interfaces};
use soroban_sdk::xdr::ToXdr;
use soroban_sdk::{bytes, contract, contractimpl, Address, Bytes, BytesN, Env, FromVal, String};

use crate::error::ContractError;
Expand All @@ -14,21 +15,42 @@ use axelar_gateway::AxelarGatewayMessagingClient;
use axelar_gateway::executable::AxelarExecutableInterface;
use axelar_soroban_std::interfaces::{MigratableInterface, OwnableInterface, UpgradableInterface};

const PREFIX_INTERCHAIN_TOKEN_SALT: &str = "interchain-token-salt";

#[contract]
pub struct InterchainTokenService;

#[contractimpl]
impl InterchainTokenService {
pub fn __constructor(env: Env, owner: Address, gateway: Address, gas_service: Address) {
pub fn __constructor(
env: Env,
owner: Address,
gateway: Address,
gas_service: Address,
chain_name: String,
) {
interfaces::set_owner(&env, &owner);
env.storage().instance().set(&DataKey::Gateway, &gateway);
env.storage()
.instance()
.set(&DataKey::GasService, &gas_service);
env.storage()
.instance()
.set(&DataKey::ChainName, &chain_name);
}

fn gas_service(env: &Env) -> Address {
env.storage().instance().get(&DataKey::GasService).unwrap()
env.storage()
.instance()
.get(&DataKey::GasService)
.expect("gas service not found")
}

fn chain_name(env: &Env) -> String {
env.storage()
.instance()
.get(&DataKey::ChainName)
.expect("chain name not found")
}

fn pay_gas_and_call_contract(
Expand Down Expand Up @@ -157,6 +179,22 @@ impl InterchainTokenServiceInterface for InterchainTokenService {
todo!()
}

fn interchain_token_deploy_salt(env: &Env, deployer: Address, salt: BytesN<32>) -> BytesN<32> {
let chain_name = Self::chain_name(env);
let chain_name_hash: BytesN<32> = env.crypto().keccak256(&(chain_name).to_xdr(env)).into();
env.crypto()
.keccak256(
&(
PREFIX_INTERCHAIN_TOKEN_SALT,
chain_name_hash,
deployer,
salt,
)
.to_xdr(env),
)
.into()
}

fn deploy_remote_interchain_token(
env: &Env,
caller: Address,
Expand Down Expand Up @@ -209,7 +247,10 @@ impl InterchainTokenServiceInterface for InterchainTokenService {
#[contractimpl]
impl AxelarExecutableInterface for InterchainTokenService {
fn gateway(env: &Env) -> Address {
env.storage().instance().get(&DataKey::Gateway).unwrap()
env.storage()
.instance()
.get(&DataKey::Gateway)
.expect("gateway not found")
}

fn execute(
Expand Down
4 changes: 3 additions & 1 deletion contracts/interchain-token-service/src/interface.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
use axelar_gateway::executable::AxelarExecutableInterface;
use axelar_soroban_std::types::Token;
use soroban_sdk::{contractclient, Address, Bytes, Env, String};
use soroban_sdk::{contractclient, Address, Bytes, BytesN, Env, String};

use crate::error::ContractError;

Expand All @@ -14,6 +14,8 @@ pub trait InterchainTokenServiceInterface: AxelarExecutableInterface {

fn remove_trusted_address(env: &Env, chain: String) -> Result<(), ContractError>;

fn interchain_token_deploy_salt(env: &Env, deployer: Address, salt: BytesN<32>) -> BytesN<32>;

fn deploy_interchain_token(
_env: &Env,
_caller: Address,
Expand Down
1 change: 1 addition & 0 deletions contracts/interchain-token-service/src/storage_types.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,4 +6,5 @@ pub enum DataKey {
TrustedAddress(String),
Gateway,
GasService,
ChainName,
}
33 changes: 31 additions & 2 deletions contracts/interchain-token-service/tests/test.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ use interchain_token_service::error::ContractError;
use axelar_soroban_std::{assert_contract_err, assert_invoke_auth_err, assert_last_emitted_event};
use soroban_sdk::testutils::{MockAuth, MockAuthInvoke};

use soroban_sdk::BytesN;
use soroban_sdk::{testutils::Address as _, Address, Env, String, Symbol};

fn setup_gateway<'a>(env: &Env) -> AxelarGatewayClient<'a> {
Expand All @@ -28,9 +29,15 @@ fn setup_env<'a>() -> (Env, InterchainTokenServiceClient<'a>) {
let owner = Address::generate(&env);
let gateway_client = setup_gateway(&env);
let gas_service_client = setup_gas_service(&env);
let chain_name = String::from_str(&env, "chain_name");
let contract_id = env.register(
InterchainTokenService,
(&owner, gateway_client.address, gas_service_client.address),
(
&owner,
gateway_client.address,
gas_service_client.address,
chain_name,
),
);
let client = InterchainTokenServiceClient::new(&env, &contract_id);

Expand All @@ -43,9 +50,15 @@ fn register_interchain_token_service() {
let owner = Address::generate(&env);
let gateway_client = setup_gateway(&env);
let gas_service_client = setup_gas_service(&env);
let chain_name = String::from_str(&env, "chain_name");
let contract_id = env.register(
InterchainTokenService,
(&owner, gateway_client.address, gas_service_client.address),
(
&owner,
gateway_client.address,
gas_service_client.address,
chain_name,
),
);
let client = InterchainTokenServiceClient::new(&env, &contract_id);

Expand Down Expand Up @@ -175,3 +188,19 @@ fn transfer_ownership() {

assert_eq!(client.owner(), new_owner);
}

#[test]
fn interchain_token_deploy_salt() {
let (env, client) = setup_env();

let deployer: Address = Address::from_str(
&env,
"CAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAHK3M",
);

let salt = BytesN::<32>::from_array(&env, &[1; 32]);

let deploy_salt = client.interchain_token_deploy_salt(&deployer, &salt);

goldie::assert!(hex::encode(deploy_salt.to_array()));
}
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
c9041493478f368bec8b935a05d2a9e9f14d666a3e7cc2bc444cbfc2b06d1f9d
5 changes: 0 additions & 5 deletions contracts/interchain-token/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,11 +4,6 @@ pub mod error;

mod interface;

// Allows using std (and its macros) in test modules
#[cfg(test)]
#[macro_use]
extern crate std;

cfg_if::cfg_if! {
if #[cfg(all(feature = "library", not(feature = "testutils")))] {
pub use interface::{InterchainTokenClient, InterchainTokenInterface};
Expand Down
3 changes: 2 additions & 1 deletion contracts/interchain-token/tests/test.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,8 @@ extern crate std;
use axelar_soroban_std::{
assert_invoke_auth_err, assert_invoke_auth_ok, assert_last_emitted_event,
};
use interchain_token::{contract::InterchainToken, InterchainTokenClient};

use interchain_token::contract::{InterchainToken, InterchainTokenClient};
use soroban_sdk::testutils::{MockAuth, MockAuthInvoke};
use soroban_sdk::{
testutils::{Address as _, BytesN as _},
Expand Down

0 comments on commit 017d421

Please sign in to comment.