diff options
Diffstat (limited to 'test/scripts/e2e_subs/app-inner-calls.py')
-rwxr-xr-x | test/scripts/e2e_subs/app-inner-calls.py | 149 |
1 files changed, 149 insertions, 0 deletions
diff --git a/test/scripts/e2e_subs/app-inner-calls.py b/test/scripts/e2e_subs/app-inner-calls.py new file mode 100755 index 000000000..a027747b2 --- /dev/null +++ b/test/scripts/e2e_subs/app-inner-calls.py @@ -0,0 +1,149 @@ +#!/usr/bin/env python + +import os +import sys +from goal import Goal +import algosdk.logic as logic + +from datetime import datetime + +stamp = datetime.now().strftime("%Y%m%d_%H%M%S") +print(f"{os.path.basename(sys.argv[0])} start {stamp}") + +goal = Goal(sys.argv[1], autosend=True) + +joe = goal.new_account() + +txinfo, err = goal.pay(goal.account, joe, amt=500_000) +assert not err, err + +# Turn off rewards for precise balance checking +txinfo, err = goal.keyreg(joe, nonpart=True) +assert not err, err +joeb = goal.balance(joe) + +# When invoked, this app funds the app that was created in the txn +# before it and invokes its start(asset) method. Of course, this app must +# be prefunded to do so. And in real life, would want to check its +# sender as access control +fund_previous = """ +#pragma version 6 + txn ApplicationID + bz end + + itxn_begin + int pay + itxn_field TypeEnum + + txn GroupIndex + int 1 + - + gtxns CreatedApplicationID + dup + store 0 + app_params_get AppAddress + assert + itxn_field Receiver + + int 1000000 + itxn_field Amount + + itxn_next + + int appl + itxn_field TypeEnum + + load 0 + itxn_field ApplicationID + + txn GroupIndex + int 2 + - + gtxns CreatedAssetID + itxn_field Assets + + method "start(asset)" + itxn_field ApplicationArgs + + byte 0x00 + itxn_field ApplicationArgs + itxn_submit + + +end: + int 1 +""" + +txinfo, err = goal.app_create(joe, goal.assemble(fund_previous)) +assert not err, err +funder = txinfo['application-index'] +assert funder + +# Fund the funder +txinfo, err = goal.pay(goal.account, goal.app_address(funder), amt=4_000_000) +assert not err, err + +# Construct a group that creates an ASA and an app, then "starts" the +# new app by funding and invoking "start(asset)" on it. Inside the new +# app's start() method, there will be yet another inner transaction: +# it opts into the supplied asset. + +goal.autosend = False +create_asa = goal.asset_create(joe, total=10_000, unit_name="oz", asset_name="Gold") +app_teal = """ +#pragma version 6 + txn ApplicationID + bz end + txn ApplicationArgs 0 + method "start(asset)" + == + bz next0 + + itxn_begin + + int axfer + itxn_field TypeEnum + + txn ApplicationArgs 1 + btoi + txnas Assets + itxn_field XferAsset + + global CurrentApplicationAddress + itxn_field AssetReceiver + + itxn_submit + +next0: + +end: + int 1 +""" +create_app = goal.app_create(joe, goal.assemble(app_teal)) +start_app = goal.app_call(joe, funder) + +[asa_info, app_info, start_info], err = goal.send_group([create_asa, create_app, start_app]) +assert not err, err + +goal.autosend = True + +import json + +asa_id = asa_info['asset-index'] +app_id = app_info['application-index'] +assert asa_id+1 == app_id +app_account = logic.get_application_address(app_id) + +# Check balance on app account is right (1m - 1 optin fee) +assert 1_000_000-1000 == goal.balance(app_account), goal.balance(app_account) +assert 0 == goal.balance(app_account, asa_id) +# Check min-balance on app account is right (base + 1 asa) +assert 200_000 == goal.min_balance(app_account), goal.min_balance(app_account) + +# Ensure creator can send asa to app +txinfo, err = goal.axfer(joe, app_account, 10, asa_id) +assert not err, err +assert 10 == goal.balance(app_account, asa_id) + + +print(f"{os.path.basename(sys.argv[0])} OK {stamp}") |