From 7e8c8e507ea40c7d141ed76a3788c3d0b0ca9df9 Mon Sep 17 00:00:00 2001 From: Phuc Ta Date: Thu, 14 Sep 2023 00:04:14 +0700 Subject: [PATCH] chore(examples): more examples for offchain vaults create/subscribe/redeem --- ...48_WithdrawValidatorCommission_Rewards.py} | 0 .../1_CreateOffChainSpotVault.py | 103 ++++++++++++++++ .../offchain_vaults/2_SubscribeSpotVault.py | 108 ++++++++++++++++ .../offchain_vaults/3_RedeemSpotVault.py | 109 +++++++++++++++++ .../4_CreateOffChainDerivativeVault.py | 115 ++++++++++++++++++ .../5_SubscribeDerivativeVault.py | 110 +++++++++++++++++ .../6_RedeemDerivativeVault.py | 113 +++++++++++++++++ pyinjective/async_client.py | 1 + pyinjective/composer.py | 19 +++ 9 files changed, 678 insertions(+) rename examples/chain_client/{48_WithdrawValidatorCommission_Rewards => 48_WithdrawValidatorCommission_Rewards.py} (100%) create mode 100644 examples/chain_client/offchain_vaults/1_CreateOffChainSpotVault.py create mode 100644 examples/chain_client/offchain_vaults/2_SubscribeSpotVault.py create mode 100644 examples/chain_client/offchain_vaults/3_RedeemSpotVault.py create mode 100644 examples/chain_client/offchain_vaults/4_CreateOffChainDerivativeVault.py create mode 100644 examples/chain_client/offchain_vaults/5_SubscribeDerivativeVault.py create mode 100644 examples/chain_client/offchain_vaults/6_RedeemDerivativeVault.py diff --git a/examples/chain_client/48_WithdrawValidatorCommission_Rewards b/examples/chain_client/48_WithdrawValidatorCommission_Rewards.py similarity index 100% rename from examples/chain_client/48_WithdrawValidatorCommission_Rewards rename to examples/chain_client/48_WithdrawValidatorCommission_Rewards.py diff --git a/examples/chain_client/offchain_vaults/1_CreateOffChainSpotVault.py b/examples/chain_client/offchain_vaults/1_CreateOffChainSpotVault.py new file mode 100644 index 00000000..6cfe8915 --- /dev/null +++ b/examples/chain_client/offchain_vaults/1_CreateOffChainSpotVault.py @@ -0,0 +1,103 @@ +import asyncio +import time + +from pyinjective.async_client import AsyncClient +from pyinjective.transaction import Transaction +from pyinjective.core.network import Network +from pyinjective.wallet import PrivateKey + +def address_from_response(resp): + for ev in resp.tx_response.events: + if ev.type != "cosmwasm.wasm.v1.EventContractInstantiated": + continue + for attr in ev.attributes: + if attr.key == "contract_address": + return attr.value.lstrip('"').rstrip('"') + return "" + + +async def main() -> None: + # # select network: local, testnet, mainnet + network = Network.testnet(node='sentry') + + # # initialize grpc client + # # set custom cookie location (optional) - defaults to current dir + client = AsyncClient(network) + composer = await client.composer() + await client.sync_timeout_height() + + # load account + priv_key = PrivateKey.from_hex("f9db9bf330e23cb7839039e944adef6e9df447b90b503d5b4464c90bea9022f3") + pub_key = priv_key.to_public_key() + address = pub_key.to_address() + await client.get_account(address.to_acc_bech32()) + + # prepare tx msg + # NOTE: COIN MUST BE SORTED IN ALPHABETICAL ORDER BY DENOMS + funds = [ + composer.Coin(amount=10000000000000000000, denom='inj'), + ] + + offchain_vault_code_id = 2711 + msg = composer.MsgInstantiateContract( + sender=address.to_acc_bech32(), + admin=address.to_acc_bech32(), + code_id=offchain_vault_code_id, + label='offchain vault example', + message=bytes('{"admin":"%s","vault_type":{"Spot":{"oracle_type":9,"base_oracle_symbol":"0x2d9315a88f3019f8efa88dfe9c0f0843712da0bac814461e27733f6b83eb51b3","quote_oracle_symbol":"0x1fc18861232290221461220bd4e2acd1dcdfbc89c84092c93c18bdc7756c1588","base_decimals":18,"quote_decimals":6}},"market_id":"0x0611780ba69656949525013d947713300f56c37b6175e02f26bffa495c3208fe","oracle_stale_time":3600,"notional_value_cap":"5000000000000"}' % address.to_acc_bech32(), 'utf8'), + funds=funds, + ) + + # build sim tx + tx = ( + Transaction() + .with_messages(msg) + .with_sequence(client.get_sequence()) + .with_account_num(client.get_number()) + .with_chain_id(network.chain_id) + ) + sim_sign_doc = tx.get_sign_doc(pub_key) + sim_sig = priv_key.sign(sim_sign_doc.SerializeToString()) + sim_tx_raw_bytes = tx.get_tx_data(sim_sig, pub_key) + + # simulate tx + (sim_res, success) = await client.simulate_tx(sim_tx_raw_bytes) + if not success: + print(sim_res) + return + + # build tx + gas_price = 500000000 + gas_limit = sim_res.gas_info.gas_used + 20000 # add 20k for gas, fee computation + gas_fee = '{:.18f}'.format((gas_price * gas_limit) / pow(10, 18)).rstrip('0') + fee = [composer.Coin( + amount=gas_price * gas_limit, + denom=network.fee_denom, + )] + tx = tx.with_gas(gas_limit).with_fee(fee).with_memo('').with_timeout_height(client.timeout_height) + sign_doc = tx.get_sign_doc(pub_key) + sig = priv_key.sign(sign_doc.SerializeToString()) + tx_raw_bytes = tx.get_tx_data(sig, pub_key) + + # broadcast tx: send_tx_async_mode, send_tx_sync_mode, send_tx_block_mode + res = await client.send_tx_sync_mode(tx_raw_bytes) + hash = res.txhash + print('instantiate tx hash:', hash) + + retry_count = 5 + resp = None + for _ in range(retry_count): + try: + resp = await client.get_tx(hash) + break + except: + pass + time.sleep(0.2) + + if resp == None: + print('tx is not succeeded') + return + print('spot vault contract address:', address_from_response(resp)) + +if __name__ == "__main__": + asyncio.get_event_loop().run_until_complete(main()) \ No newline at end of file diff --git a/examples/chain_client/offchain_vaults/2_SubscribeSpotVault.py b/examples/chain_client/offchain_vaults/2_SubscribeSpotVault.py new file mode 100644 index 00000000..3fb1cc57 --- /dev/null +++ b/examples/chain_client/offchain_vaults/2_SubscribeSpotVault.py @@ -0,0 +1,108 @@ +import asyncio +import time + +from pyinjective.async_client import AsyncClient +from pyinjective.transaction import Transaction +from pyinjective.core.network import Network +from pyinjective.wallet import PrivateKey + +def mint_amount_from_response(resp): + for ev in resp.tx_response.events: + if ev.type != "wasm-lp_balance_changed": + continue + for attr in ev.attributes: + if attr.key == "mint_amount": + return attr.value + return "" + + +async def main() -> None: + # # select network: local, testnet, mainnet + network = Network.testnet(node='sentry') + + # # initialize grpc client + # # set custom cookie location (optional) - defaults to current dir + client = AsyncClient(network) + composer = await client.composer() + await client.sync_timeout_height() + + # load account + priv_key = PrivateKey.from_hex("f9db9bf330e23cb7839039e944adef6e9df447b90b503d5b4464c90bea9022f3") + pub_key = priv_key.to_public_key() + address = pub_key.to_address() + await client.get_account(address.to_acc_bech32()) + subaccount_id = address.get_subaccount_id(0) + + contract_address = "inj1ckmdhdz7r8glfurckgtg0rt7x9uvner4ygqhlv" + msg = composer.MsgPrivilegedExecuteContract( + sender=address.to_acc_bech32(), + contract=contract_address, + msg=""" + { + "origin":"%s", + "name":"Subscribe", + "args":{ + "Subscribe":{ + "args":{ + "subscriber_subaccount_id":"%s" + } + } + } + } + """ % (address.to_acc_bech32(), subaccount_id), + funds='10000000000000000000inj,80000000peggy0x87aB3B4C8661e07D6372361211B96ed4Dc36B1B5', + ) + + # build sim tx + tx = ( + Transaction() + .with_messages(msg) + .with_sequence(client.get_sequence()) + .with_account_num(client.get_number()) + .with_chain_id(network.chain_id) + ) + sim_sign_doc = tx.get_sign_doc(pub_key) + sim_sig = priv_key.sign(sim_sign_doc.SerializeToString()) + sim_tx_raw_bytes = tx.get_tx_data(sim_sig, pub_key) + + # simulate tx + (sim_res, success) = await client.simulate_tx(sim_tx_raw_bytes) + if not success: + print(sim_res) + return + + # build tx + gas_price = 500000000 + gas_limit = sim_res.gas_info.gas_used + 20000 # add 20k for gas, fee computation + # gas_fee = '{:.18f}'.format((gas_price * gas_limit) / pow(10, 18)).rstrip('0') + fee = [composer.Coin( + amount=gas_price * gas_limit, + denom=network.fee_denom, + )] + tx = tx.with_gas(gas_limit).with_fee(fee).with_memo('').with_timeout_height(client.timeout_height) + sign_doc = tx.get_sign_doc(pub_key) + sig = priv_key.sign(sign_doc.SerializeToString()) + tx_raw_bytes = tx.get_tx_data(sig, pub_key) + + # broadcast tx: send_tx_async_mode, send_tx_sync_mode, send_tx_block_mode + res = await client.send_tx_sync_mode(tx_raw_bytes) + hash = res.txhash + print('instantiate tx hash:', hash) + + retry_count = 5 + resp = None + for _ in range(retry_count): + try: + resp = await client.get_tx(hash) + break + except: + pass + time.sleep(0.2) + + if resp == None: + print('tx is not succeeded') + return + print('spot vault LP mint amount:', mint_amount_from_response(resp) + 'factory/%s/lp' % contract_address) + +if __name__ == "__main__": + asyncio.get_event_loop().run_until_complete(main()) \ No newline at end of file diff --git a/examples/chain_client/offchain_vaults/3_RedeemSpotVault.py b/examples/chain_client/offchain_vaults/3_RedeemSpotVault.py new file mode 100644 index 00000000..6798ba4d --- /dev/null +++ b/examples/chain_client/offchain_vaults/3_RedeemSpotVault.py @@ -0,0 +1,109 @@ +import asyncio +import time + +from pyinjective.async_client import AsyncClient +from pyinjective.transaction import Transaction +from pyinjective.core.network import Network +from pyinjective.wallet import PrivateKey + +def mint_amount_from_response(resp): + for ev in resp.tx_response.events: + if ev.type != "wasm-lp_balance_changed": + continue + for attr in ev.attributes: + if attr.key == "mint_amount": + return attr.value + return "" + + +async def main() -> None: + # # select network: local, testnet, mainnet + network = Network.testnet(node='sentry') + + # # initialize grpc client + # # set custom cookie location (optional) - defaults to current dir + client = AsyncClient(network) + composer = await client.composer() + await client.sync_timeout_height() + + # load account + priv_key = PrivateKey.from_hex("f9db9bf330e23cb7839039e944adef6e9df447b90b503d5b4464c90bea9022f3") + pub_key = priv_key.to_public_key() + address = pub_key.to_address() + await client.get_account(address.to_acc_bech32()) + subaccount_id = address.get_subaccount_id(0) + + contract_address = "inj1ckmdhdz7r8glfurckgtg0rt7x9uvner4ygqhlv" + msg = composer.MsgPrivilegedExecuteContract( + sender=address.to_acc_bech32(), + contract=contract_address, + msg=""" + { + "args": { + "Redeem": { + "args":{ + "redeemer_subaccount_id":"%s", + "redemption_type": {"SpotRedemptionType":"FixedBaseAndQuote"} + } + } + }, + "name":"VaultRedeem", + "origin":"%s" + } + """ % (subaccount_id, address.to_acc_bech32()), + funds='2400000000000000000factory/%s/lp' % contract_address, + ) + + # build sim tx + tx = ( + Transaction() + .with_messages(msg) + .with_sequence(client.get_sequence()) + .with_account_num(client.get_number()) + .with_chain_id(network.chain_id) + ) + sim_sign_doc = tx.get_sign_doc(pub_key) + sim_sig = priv_key.sign(sim_sign_doc.SerializeToString()) + sim_tx_raw_bytes = tx.get_tx_data(sim_sig, pub_key) + + # simulate tx + (sim_res, success) = await client.simulate_tx(sim_tx_raw_bytes) + if not success: + print(sim_res) + return + + # build tx + gas_price = 500000000 + gas_limit = sim_res.gas_info.gas_used + 20000 # add 20k for gas, fee computation + # gas_fee = '{:.18f}'.format((gas_price * gas_limit) / pow(10, 18)).rstrip('0') + fee = [composer.Coin( + amount=gas_price * gas_limit, + denom=network.fee_denom, + )] + tx = tx.with_gas(gas_limit).with_fee(fee).with_memo('').with_timeout_height(client.timeout_height) + sign_doc = tx.get_sign_doc(pub_key) + sig = priv_key.sign(sign_doc.SerializeToString()) + tx_raw_bytes = tx.get_tx_data(sig, pub_key) + + # broadcast tx: send_tx_async_mode, send_tx_sync_mode, send_tx_block_mode + res = await client.send_tx_sync_mode(tx_raw_bytes) + hash = res.txhash + print('instantiate tx hash:', hash) + + retry_count = 5 + resp = None + for _ in range(retry_count): + try: + resp = await client.get_tx(hash) + break + except: + pass + time.sleep(0.4) + + if resp == None: + print('tx is not succeeded') + return + print('spot vault LP redeemed') + +if __name__ == "__main__": + asyncio.get_event_loop().run_until_complete(main()) \ No newline at end of file diff --git a/examples/chain_client/offchain_vaults/4_CreateOffChainDerivativeVault.py b/examples/chain_client/offchain_vaults/4_CreateOffChainDerivativeVault.py new file mode 100644 index 00000000..be665f31 --- /dev/null +++ b/examples/chain_client/offchain_vaults/4_CreateOffChainDerivativeVault.py @@ -0,0 +1,115 @@ +import asyncio +import time + +from pyinjective.async_client import AsyncClient +from pyinjective.transaction import Transaction +from pyinjective.core.network import Network +from pyinjective.wallet import PrivateKey + +def address_from_response(resp): + for ev in resp.tx_response.events: + if ev.type != "cosmwasm.wasm.v1.EventContractInstantiated": + continue + for attr in ev.attributes: + if attr.key == "contract_address": + return attr.value.lstrip('"').rstrip('"') + return "" + + +async def main() -> None: + # # select network: local, testnet, mainnet + network = Network.testnet(node='sentry') + + # # initialize grpc client + # # set custom cookie location (optional) - defaults to current dir + client = AsyncClient(network) + composer = await client.composer() + await client.sync_timeout_height() + + # load account + priv_key = PrivateKey.from_hex("f9db9bf330e23cb7839039e944adef6e9df447b90b503d5b4464c90bea9022f3") + pub_key = priv_key.to_public_key() + address = pub_key.to_address() + await client.get_account(address.to_acc_bech32()) + + # prepare tx msg + # NOTE: COIN MUST BE SORTED IN ALPHABETICAL ORDER BY DENOMS + funds = [ + composer.Coin(amount=10000000000000000000, denom='inj'), + ] + + offchain_vault_code_id = 2711 + msg = composer.MsgInstantiateContract( + sender=address.to_acc_bech32(), + admin=address.to_acc_bech32(), + code_id=offchain_vault_code_id, + label='offchain vault example', + message=bytes(""" + { + "admin":"%s", + "vault_type":{ + "Derivative":{ + "position_pnl_penalty":"0.05", + "allowed_derivative_redemption_types":3 + } + }, + "market_id":"0x17ef48032cb24375ba7c2e39f384e56433bcab20cbee9a7357e4cba2eb00abe6", + "oracle_stale_time":3600,"notional_value_cap":"5000000000000" + } + """ % address.to_acc_bech32(), 'utf8'), + funds=funds, + ) + + # build sim tx + tx = ( + Transaction() + .with_messages(msg) + .with_sequence(client.get_sequence()) + .with_account_num(client.get_number()) + .with_chain_id(network.chain_id) + ) + sim_sign_doc = tx.get_sign_doc(pub_key) + sim_sig = priv_key.sign(sim_sign_doc.SerializeToString()) + sim_tx_raw_bytes = tx.get_tx_data(sim_sig, pub_key) + + # simulate tx + (sim_res, success) = await client.simulate_tx(sim_tx_raw_bytes) + if not success: + print(sim_res) + return + + # build tx + gas_price = 500000000 + gas_limit = sim_res.gas_info.gas_used + 20000 # add 20k for gas, fee computation + gas_fee = '{:.18f}'.format((gas_price * gas_limit) / pow(10, 18)).rstrip('0') + fee = [composer.Coin( + amount=gas_price * gas_limit, + denom=network.fee_denom, + )] + tx = tx.with_gas(gas_limit).with_fee(fee).with_memo('').with_timeout_height(client.timeout_height) + sign_doc = tx.get_sign_doc(pub_key) + sig = priv_key.sign(sign_doc.SerializeToString()) + tx_raw_bytes = tx.get_tx_data(sig, pub_key) + + # broadcast tx: send_tx_async_mode, send_tx_sync_mode, send_tx_block_mode + res = await client.send_tx_sync_mode(tx_raw_bytes) + hash = res.txhash + print('instantiate tx hash:', hash) + + retry_count = 5 + resp = None + for _ in range(retry_count): + try: + resp = await client.get_tx(hash) + break + except: + pass + time.sleep(0.2) + + if resp == None: + print('tx is not succeeded') + return + print('spot vault contract address:', address_from_response(resp)) + +if __name__ == "__main__": + asyncio.get_event_loop().run_until_complete(main()) \ No newline at end of file diff --git a/examples/chain_client/offchain_vaults/5_SubscribeDerivativeVault.py b/examples/chain_client/offchain_vaults/5_SubscribeDerivativeVault.py new file mode 100644 index 00000000..aafc329d --- /dev/null +++ b/examples/chain_client/offchain_vaults/5_SubscribeDerivativeVault.py @@ -0,0 +1,110 @@ +import asyncio +import time + +from pyinjective.async_client import AsyncClient +from pyinjective.transaction import Transaction +from pyinjective.core.network import Network +from pyinjective.wallet import PrivateKey + +def mint_amount_from_response(resp): + for ev in resp.tx_response.events: + if ev.type != "wasm-lp_balance_changed": + continue + for attr in ev.attributes: + if attr.key == "mint_amount": + return attr.value + return "" + + +async def main() -> None: + # # select network: local, testnet, mainnet + network = Network.testnet(node='sentry') + + # # initialize grpc client + # # set custom cookie location (optional) - defaults to current dir + client = AsyncClient(network) + composer = await client.composer() + await client.sync_timeout_height() + + # load account + priv_key = PrivateKey.from_hex("f9db9bf330e23cb7839039e944adef6e9df447b90b503d5b4464c90bea9022f3") + pub_key = priv_key.to_public_key() + address = pub_key.to_address() + await client.get_account(address.to_acc_bech32()) + subaccount_id = address.get_subaccount_id(0) + + # this contract is derivative offchain vault for INJ/USDT PERP on testnet + contract_address = "inj1v4s3v3nmsx6szyxqgcnqdfseucu4ccm65sh0xr" + msg = composer.MsgPrivilegedExecuteContract( + sender=address.to_acc_bech32(), + contract=contract_address, + msg=""" + { + "origin":"%s", + "name":"Subscribe", + "args":{ + "Subscribe":{ + "args":{ + "subscriber_subaccount_id":"%s", + "slippage":{"max_penalty":"0.05"} + } + } + } + } + """ % (address.to_acc_bech32(), subaccount_id), + funds='10000000peggy0x87aB3B4C8661e07D6372361211B96ed4Dc36B1B5', + ) + + # build sim tx + tx = ( + Transaction() + .with_messages(msg) + .with_sequence(client.get_sequence()) + .with_account_num(client.get_number()) + .with_chain_id(network.chain_id) + ) + sim_sign_doc = tx.get_sign_doc(pub_key) + sim_sig = priv_key.sign(sim_sign_doc.SerializeToString()) + sim_tx_raw_bytes = tx.get_tx_data(sim_sig, pub_key) + + # simulate tx + (sim_res, success) = await client.simulate_tx(sim_tx_raw_bytes) + if not success: + print(sim_res) + return + + # build tx + gas_price = 500000000 + gas_limit = sim_res.gas_info.gas_used + 20000 # add 20k for gas, fee computation + # gas_fee = '{:.18f}'.format((gas_price * gas_limit) / pow(10, 18)).rstrip('0') + fee = [composer.Coin( + amount=gas_price * gas_limit, + denom=network.fee_denom, + )] + tx = tx.with_gas(gas_limit).with_fee(fee).with_memo('').with_timeout_height(client.timeout_height) + sign_doc = tx.get_sign_doc(pub_key) + sig = priv_key.sign(sign_doc.SerializeToString()) + tx_raw_bytes = tx.get_tx_data(sig, pub_key) + + # broadcast tx: send_tx_async_mode, send_tx_sync_mode, send_tx_block_mode + res = await client.send_tx_sync_mode(tx_raw_bytes) + hash = res.txhash + print('instantiate tx hash:', hash) + + retry_count = 5 + resp = None + for _ in range(retry_count): + try: + resp = await client.get_tx(hash) + break + except: + pass + time.sleep(0.2) + + if resp == None: + print('tx is not succeeded') + return + print('spot vault LP mint amount:', mint_amount_from_response(resp) + 'factory/%s/lp' % contract_address) + +if __name__ == "__main__": + asyncio.get_event_loop().run_until_complete(main()) \ No newline at end of file diff --git a/examples/chain_client/offchain_vaults/6_RedeemDerivativeVault.py b/examples/chain_client/offchain_vaults/6_RedeemDerivativeVault.py new file mode 100644 index 00000000..d3881fa1 --- /dev/null +++ b/examples/chain_client/offchain_vaults/6_RedeemDerivativeVault.py @@ -0,0 +1,113 @@ +import asyncio +import time + +from pyinjective.async_client import AsyncClient +from pyinjective.transaction import Transaction +from pyinjective.core.network import Network +from pyinjective.wallet import PrivateKey + +def mint_amount_from_response(resp): + for ev in resp.tx_response.events: + if ev.type != "wasm-lp_balance_changed": + continue + for attr in ev.attributes: + if attr.key == "mint_amount": + return attr.value + return "" + + +async def main() -> None: + # # select network: local, testnet, mainnet + network = Network.testnet(node='sentry') + + # # initialize grpc client + # # set custom cookie location (optional) - defaults to current dir + client = AsyncClient(network) + composer = await client.composer() + await client.sync_timeout_height() + + # load account + priv_key = PrivateKey.from_hex("f9db9bf330e23cb7839039e944adef6e9df447b90b503d5b4464c90bea9022f3") + pub_key = priv_key.to_public_key() + address = pub_key.to_address() + await client.get_account(address.to_acc_bech32()) + subaccount_id = address.get_subaccount_id(0) + + # this contract is derivative offchain vault for INJ/USDT PERP on testnet + contract_address = "inj1v4s3v3nmsx6szyxqgcnqdfseucu4ccm65sh0xr" + msg = composer.MsgPrivilegedExecuteContract( + sender=address.to_acc_bech32(), + contract=contract_address, + msg=""" + { + "args":{ + "Redeem":{ + "args":{ + "redeemer_subaccount_id":"%s", + "redemption_type":{ + "DerivativeRedemptionType":"PositionAndQuote" + }, + "slippage":{"max_penalty":"0.1"} + } + } + }, + "name":"VaultRedeem", + "origin":"%s" + } + """ % (subaccount_id, address.to_acc_bech32()), + funds='1000000000000000factory/%s/lp' % contract_address, + ) + + # build sim tx + tx = ( + Transaction() + .with_messages(msg) + .with_sequence(client.get_sequence()) + .with_account_num(client.get_number()) + .with_chain_id(network.chain_id) + ) + sim_sign_doc = tx.get_sign_doc(pub_key) + sim_sig = priv_key.sign(sim_sign_doc.SerializeToString()) + sim_tx_raw_bytes = tx.get_tx_data(sim_sig, pub_key) + + # simulate tx + (sim_res, success) = await client.simulate_tx(sim_tx_raw_bytes) + if not success: + print(sim_res) + return + + # build tx + gas_price = 500000000 + gas_limit = sim_res.gas_info.gas_used + 20000 # add 20k for gas, fee computation + # gas_fee = '{:.18f}'.format((gas_price * gas_limit) / pow(10, 18)).rstrip('0') + fee = [composer.Coin( + amount=gas_price * gas_limit, + denom=network.fee_denom, + )] + tx = tx.with_gas(gas_limit).with_fee(fee).with_memo('').with_timeout_height(client.timeout_height) + sign_doc = tx.get_sign_doc(pub_key) + sig = priv_key.sign(sign_doc.SerializeToString()) + tx_raw_bytes = tx.get_tx_data(sig, pub_key) + + # broadcast tx: send_tx_async_mode, send_tx_sync_mode, send_tx_block_mode + res = await client.send_tx_sync_mode(tx_raw_bytes) + hash = res.txhash + print('instantiate tx hash:', hash) + + retry_count = 5 + resp = None + for _ in range(retry_count): + try: + resp = await client.get_tx(hash) + break + except: + pass + time.sleep(0.4) + + if resp == None: + print('tx is not succeeded') + return + print('derivative vault LP redeemed') + +if __name__ == "__main__": + asyncio.get_event_loop().run_until_complete(main()) \ No newline at end of file diff --git a/pyinjective/async_client.py b/pyinjective/async_client.py index 3374f6c1..f62554d7 100644 --- a/pyinjective/async_client.py +++ b/pyinjective/async_client.py @@ -234,6 +234,7 @@ async def get_account(self, address: str) -> Optional[account_pb2.EthAccount]: self.number = int(account.base_account.account_number) self.sequence = int(account.base_account.sequence) except Exception as e: + print('exception:', e) LoggerProvider().logger_for_class(logging_class=self.__class__).debug( f"error while fetching sequence and number {e}") return None diff --git a/pyinjective/composer.py b/pyinjective/composer.py index 41140aea..1df630ed 100644 --- a/pyinjective/composer.py +++ b/pyinjective/composer.py @@ -293,6 +293,24 @@ def MsgExecuteContract(self, sender: str, contract: str, msg: str, **kwargs): msg=bytes(msg, "utf-8"), funds=kwargs.get('funds') # funds is a list of cosmos_dot_base_dot_v1beta1_dot_coin__pb2.Coin. The coins in the list must be sorted in alphabetical order by denoms. ) + + def MsgPrivilegedExecuteContract(self, sender: str, contract: str, msg: str, **kwargs): + return injective_exchange_tx_pb.MsgPrivilegedExecuteContract( + sender=sender, + contract_address=contract, + data=msg, + funds=kwargs.get('funds') # funds is a list of cosmos_dot_base_dot_v1beta1_dot_coin__pb2.Coin. The coins in the list must be sorted in alphabetical order by denoms. + ) + + def MsgInstantiateContract(self, sender, admin: str, code_id: int, label: str, message: bytes, **kwargs): + return wasm_tx_pb.MsgInstantiateContract( + sender=sender, + admin=admin, + code_id=code_id, + label=label, + msg=message, + funds=kwargs.get('funds'), + ) def MsgDeposit(self, sender: str, subaccount_id: str, amount: float, denom: str): token = self.tokens[denom] @@ -938,6 +956,7 @@ def MsgResponses(response, simulation=False): "/cosmos.authz.v1beta1.MsgRevokeResponse": cosmos_authz_tx_pb.MsgRevokeResponse, "/injective.oracle.v1beta1.MsgRelayPriceFeedPriceResponse": injective_oracle_tx_pb.MsgRelayPriceFeedPriceResponse, "/injective.oracle.v1beta1.MsgRelayProviderPricesResponse": injective_oracle_tx_pb.MsgRelayProviderPrices, + "/cosmwasm.wasm.v1.MsgInstantiateContractResponse": wasm_tx_pb.MsgInstantiateContractResponse, } msgs = []