Allow for custom transaction properties
This commit is contained in:
parent
440ca6360b
commit
a7d1944406
|
@ -47,10 +47,14 @@ template raiseContractError(message: string) =
|
||||||
|
|
||||||
proc createTransaction(contract: Contract,
|
proc createTransaction(contract: Contract,
|
||||||
function: string,
|
function: string,
|
||||||
parameters: tuple): Transaction =
|
parameters: tuple,
|
||||||
|
overrides = Transaction.default): Transaction =
|
||||||
let selector = selector(function, typeof parameters).toArray
|
let selector = selector(function, typeof parameters).toArray
|
||||||
let data = @selector & AbiEncoder.encode(parameters)
|
let data = @selector & AbiEncoder.encode(parameters)
|
||||||
Transaction(to: contract.address, data: data)
|
var transaction = overrides
|
||||||
|
transaction.to = contract.address
|
||||||
|
transaction.data = data
|
||||||
|
return transaction
|
||||||
|
|
||||||
proc decodeResponse(T: type, multiple: static bool, bytes: seq[byte]): T =
|
proc decodeResponse(T: type, multiple: static bool, bytes: seq[byte]): T =
|
||||||
when multiple:
|
when multiple:
|
||||||
|
@ -77,11 +81,13 @@ proc call(contract: Contract,
|
||||||
let response = await contract.provider.call(transaction, blockTag)
|
let response = await contract.provider.call(transaction, blockTag)
|
||||||
return decodeResponse(ReturnType, returnMultiple, response)
|
return decodeResponse(ReturnType, returnMultiple, response)
|
||||||
|
|
||||||
proc send(contract: Contract, function: string, parameters: tuple):
|
proc send(contract: Contract,
|
||||||
|
function: string,
|
||||||
|
parameters: tuple,
|
||||||
|
overrides = Transaction.default):
|
||||||
Future[?TransactionResponse] {.async.} =
|
Future[?TransactionResponse] {.async.} =
|
||||||
|
|
||||||
if signer =? contract.signer:
|
if signer =? contract.signer:
|
||||||
let transaction = createTransaction(contract, function, parameters)
|
let transaction = createTransaction(contract, function, parameters, overrides)
|
||||||
let populated = await signer.populateTransaction(transaction)
|
let populated = await signer.populateTransaction(transaction)
|
||||||
let txResp = await signer.sendTransaction(populated)
|
let txResp = await signer.sendTransaction(populated)
|
||||||
return txResp.some
|
return txResp.some
|
||||||
|
@ -111,6 +117,15 @@ func isMultipleReturn(returnType: NimNode): bool =
|
||||||
(returnType.kind == nnkTupleConstr) or
|
(returnType.kind == nnkTupleConstr) or
|
||||||
(returnType.kind == nnkTupleTy)
|
(returnType.kind == nnkTupleTy)
|
||||||
|
|
||||||
|
func addOverrides(procedure: var NimNode) =
|
||||||
|
procedure[3].add(
|
||||||
|
newIdentDefs(
|
||||||
|
ident("overrides"),
|
||||||
|
newEmptyNode(),
|
||||||
|
quote do: Transaction.default
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
func addContractCall(procedure: var NimNode) =
|
func addContractCall(procedure: var NimNode) =
|
||||||
let contract = procedure[3][1][0]
|
let contract = procedure[3][1][0]
|
||||||
let function = $basename(procedure[0])
|
let function = $basename(procedure[0])
|
||||||
|
@ -118,6 +133,8 @@ func addContractCall(procedure: var NimNode) =
|
||||||
let returnType = procedure[3][0]
|
let returnType = procedure[3][0]
|
||||||
let returnMultiple = returnType.isMultipleReturn.newLit
|
let returnMultiple = returnType.isMultipleReturn.newLit
|
||||||
|
|
||||||
|
procedure.addOverrides()
|
||||||
|
|
||||||
func call: NimNode =
|
func call: NimNode =
|
||||||
if returnType.kind == nnkEmpty:
|
if returnType.kind == nnkEmpty:
|
||||||
quote:
|
quote:
|
||||||
|
@ -130,12 +147,12 @@ func addContractCall(procedure: var NimNode) =
|
||||||
func send: NimNode =
|
func send: NimNode =
|
||||||
if returnType.kind == nnkEmpty:
|
if returnType.kind == nnkEmpty:
|
||||||
quote:
|
quote:
|
||||||
discard await send(`contract`, `function`, `parameters`)
|
discard await send(`contract`, `function`, `parameters`, overrides)
|
||||||
else:
|
else:
|
||||||
quote:
|
quote:
|
||||||
when typeof(result) isnot Confirmable:
|
when typeof(result) isnot Confirmable:
|
||||||
{.error: "unexpected return type, missing {.view.} or {.pure.} ?".}
|
{.error: "unexpected return type, missing {.view.} or {.pure.} ?".}
|
||||||
return await send(`contract`, `function`, `parameters`)
|
return await send(`contract`, `function`, `parameters`, overrides)
|
||||||
|
|
||||||
procedure[6] =
|
procedure[6] =
|
||||||
if procedure.isConstant:
|
if procedure.isConstant:
|
||||||
|
|
|
@ -0,0 +1,20 @@
|
||||||
|
import pkg/ethers
|
||||||
|
|
||||||
|
type MockSigner* = ref object of Signer
|
||||||
|
provider: Provider
|
||||||
|
address*: Address
|
||||||
|
transactions*: seq[Transaction]
|
||||||
|
|
||||||
|
func new*(_: type MockSigner, provider: Provider): MockSigner =
|
||||||
|
MockSigner(provider: provider)
|
||||||
|
|
||||||
|
method provider*(signer: MockSigner): Provider =
|
||||||
|
signer.provider
|
||||||
|
|
||||||
|
method getAddress*(signer: MockSigner): Future[Address] {.async.} =
|
||||||
|
return signer.address
|
||||||
|
|
||||||
|
method sendTransaction*(signer: MockSigner,
|
||||||
|
transaction: Transaction):
|
||||||
|
Future[TransactionResponse] {.async.} =
|
||||||
|
signer.transactions.add(transaction)
|
|
@ -5,6 +5,7 @@ import pkg/stint
|
||||||
import pkg/ethers
|
import pkg/ethers
|
||||||
import ./hardhat
|
import ./hardhat
|
||||||
import ./miner
|
import ./miner
|
||||||
|
import ./mocks
|
||||||
|
|
||||||
type
|
type
|
||||||
|
|
||||||
|
@ -112,6 +113,19 @@ suite "Contracts":
|
||||||
check (await token.connect(provider).balanceOf(accounts[1])) == 25.u256
|
check (await token.connect(provider).balanceOf(accounts[1])) == 25.u256
|
||||||
check (await token.connect(provider).balanceOf(accounts[2])) == 25.u256
|
check (await token.connect(provider).balanceOf(accounts[2])) == 25.u256
|
||||||
|
|
||||||
|
test "takes custom values for nonce, gasprice and gaslimit":
|
||||||
|
let overrides = Transaction(
|
||||||
|
nonce: some 100.u256,
|
||||||
|
gasPrice: some 200.u256,
|
||||||
|
gasLimit: some 300.u256
|
||||||
|
)
|
||||||
|
let signer = MockSigner.new(provider)
|
||||||
|
discard await token.connect(signer).mint(accounts[0], 42.u256, overrides)
|
||||||
|
check signer.transactions.len == 1
|
||||||
|
check signer.transactions[0].nonce == overrides.nonce
|
||||||
|
check signer.transactions[0].gasPrice == overrides.gasPrice
|
||||||
|
check signer.transactions[0].gasLimit == overrides.gasLimit
|
||||||
|
|
||||||
test "receives events when subscribed":
|
test "receives events when subscribed":
|
||||||
var transfers: seq[Transfer]
|
var transfers: seq[Transfer]
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue