You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
NEP264, or function calls allowing splitting unused gas among async function calls near/NEPs#264 is being implemented here near/nearcore#6285.
The current API looks something like
#[ext_contract(ext)]
pub trait ExtCrossContract {
fn some_method(a: u8) -> String;
}
...
let contract_account_id: AccountId = todo!();
ext::some_method(/* parameters ***/, contract_account_id, 0 /*** deposit amount ***/, 5_000_000_000_000 /*** static amount of gas to attach */)
Where the limitations are that: 1. It's confusing which order deposit and gas are in 2. Not intuitive what the extra parameters are and where the function parameters end 3. Need to specify a static amount of gas 4. Need to define a trait with ext_contract where the macro will actually not use the trait at all (very confusing when there can be multiple traits in code with the same name) 5. The ext_contract API is not tied to the actual methods in any way, changes in one can silently cause bugs
and the initial proposition, noted in the NEP and in an exploratory PR for implementing this within the SDK, was to change the API to something like:
Where this is a builder pattern but uses the same ext_contract API. From experimenting in the PR linked above, the issue is that this result type of this must be an abstraction above Promise which causes some unideal patterns when migrating because an additional into_promise() method is required to convert it to this type. Also, it's a bit unideal that the account_id is still mixed with the method parameters, which can still be confusing. Finally, the issue of this external API not being tied to the callable one still causes issues.
So my proposal, and what I will experiment with, is having an ext method being added to any near_bindgen struct which will generate roughly the following:
MyContract::ext(contract_account_id)
// Optional config
.with_amount(1 /* default deposit of 0 */)
.with_static_gas(5_000_000_000_000 /* default of 0 */)
.with_unused_gas_weight(2 /* default 1 */)
// Then call any method to schedule the function call
.some_method(/* parameters */)
This solves basically all of the issues mentioned above, but the tradeoff is that the config attributes have to be defined before the method is called, which might not be intuitive for everyone, but it makes logical sense.
Another side benefit of this is that it does not rely on Promise being scheduled on Drop so frees up that API to change in the future.
The text was updated successfully, but these errors were encountered:
NEP264, or function calls allowing splitting unused gas among async function calls near/NEPs#264 is being implemented here near/nearcore#6285.
The current API looks something like
#[ext_contract(ext)] pub trait ExtCrossContract { fn some_method(a: u8) -> String; } ... let contract_account_id: AccountId = todo!(); ext::some_method(/* parameters ***/, contract_account_id, 0 /*** deposit amount ***/, 5_000_000_000_000 /*** static amount of gas to attach */)
Where the limitations are that: 1. It's confusing which order deposit and gas are in 2. Not intuitive what the extra parameters are and where the function parameters end 3. Need to specify a static amount of gas 4. Need to define a trait with
ext_contract
where the macro will actually not use the trait at all (very confusing when there can be multiple traits in code with the same name) 5. Theext_contract
API is not tied to the actual methods in any way, changes in one can silently cause bugsand the initial proposition, noted in the NEP and in an exploratory PR for implementing this within the SDK, was to change the API to something like:
Where this is a builder pattern but uses the same
ext_contract
API. From experimenting in the PR linked above, the issue is that this result type of this must be an abstraction abovePromise
which causes some unideal patterns when migrating because an additionalinto_promise()
method is required to convert it to this type. Also, it's a bit unideal that theaccount_id
is still mixed with the method parameters, which can still be confusing. Finally, the issue of this external API not being tied to the callable one still causes issues.So my proposal, and what I will experiment with, is having an
ext
method being added to anynear_bindgen
struct which will generate roughly the following:#[must_use] pub struct MyContractExt { .. } impl MyContractExt { pub fn with_amount(self) -> Self { .. } pub fn with_static_gas(self) -> Self { .. } pub fn with_unused_gas_weight(self) -> Self { .. } } impl MyContract { pub fn ext(account_id: AccountId) -> MyContractExt { ... } }
and will generate, for every public method within
#<span class="error">[near_bindgen]</span>
:where the API to use will look roughly like:
This solves basically all of the issues mentioned above, but the tradeoff is that the config attributes have to be defined before the method is called, which might not be intuitive for everyone, but it makes logical sense.
Another side benefit of this is that it does not rely on
Promise
being scheduled onDrop
so frees up that API to change in the future.The text was updated successfully, but these errors were encountered: