0
# Method Execution
1
2
Contract method calls for both read-only operations and state-changing transactions with full TypeScript type safety based on contract ABI.
3
4
## Capabilities
5
6
### Method Object Types
7
8
Different method object interfaces depending on the contract method's state mutability.
9
10
```typescript { .api }
11
/**
12
* Interface for non-payable contract methods (view, pure, nonpayable)
13
*/
14
interface NonPayableMethodObject<Inputs = unknown[], Outputs = unknown[]> {
15
/** The arguments passed to this method */
16
arguments: Inputs;
17
18
/**
19
* Call a method and execute its smart contract method in the EVM without sending any transaction
20
* Note: calling cannot alter the smart contract state
21
* @param options - The options used for calling
22
* @returns Promise that resolves to the method return values
23
*/
24
call(options?: NonPayableCallOptions): Promise<Outputs>;
25
26
/**
27
* Estimate the gas required for this method
28
* @param options - The options used for gas estimation
29
* @returns Promise that resolves to estimated gas amount
30
*/
31
estimateGas(options?: NonPayableCallOptions): Promise<number>;
32
33
/**
34
* Create an access list for this method call
35
* @param options - The options used for access list creation
36
* @returns Promise that resolves to access list result
37
*/
38
createAccessList(options?: NonPayableCallOptions): Promise<AccessListResult>;
39
40
/**
41
* Encode the ABI for this method including function signature and parameters
42
* @returns The encoded ABI byte code to send via a transaction or call
43
*/
44
encodeABI(): string;
45
46
/**
47
* Decode raw result of method call into readable values
48
* @param data - The data to decode
49
* @returns The decoded data
50
*/
51
decodeData(data: HexString): Inputs;
52
53
/**
54
* Populate transaction object for this method call
55
* @param options - Transaction options
56
* @param contractOptions - Contract default options
57
* @returns Transaction call object
58
*/
59
populateTransaction(options?: NonPayableCallOptions, contractOptions?: ContractOptions): TransactionCall;
60
}
61
62
/**
63
* Interface for payable contract methods
64
*/
65
interface PayableMethodObject<Inputs = unknown[], Outputs = unknown[]>
66
extends NonPayableMethodObject<Inputs, Outputs> {
67
68
/**
69
* Send a transaction to execute this method and change contract state
70
* @param options - The options used for sending the transaction
71
* @returns PromiEvent that resolves to transaction receipt with events
72
*/
73
send(options?: PayableCallOptions): Web3PromiEvent<TransactionReceipt, SendTransactionEvents>;
74
}
75
```
76
77
### Method Access
78
79
Access contract methods through the dynamically generated `methods` property.
80
81
```typescript { .api }
82
class Contract<Abi extends ContractAbi> {
83
/** Dynamically generated methods based on contract ABI */
84
readonly methods: ContractMethodsInterface<Abi>;
85
}
86
87
type ContractMethodsInterface<Abi extends ContractAbi> = {
88
[MethodAbi in FilterAbis<Abi, AbiFunctionFragment & { type: 'function' }> as MethodAbi['name']]: ContractBoundMethod<MethodAbi>;
89
} & {
90
/** Allow access by method signature for overloaded methods */
91
[key: string]: ContractBoundMethod<any>;
92
};
93
94
type ContractBoundMethod<Abi extends AbiFunctionFragment> = (
95
...args: ContractMethodInputParameters<Abi['inputs']>
96
) => Abi['stateMutability'] extends 'payable' | 'pure'
97
? PayableMethodObject<ContractMethodInputParameters<Abi['inputs']>, ContractMethodOutputParameters<Abi['outputs']>>
98
: NonPayableMethodObject<ContractMethodInputParameters<Abi['inputs']>, ContractMethodOutputParameters<Abi['outputs']>>;
99
```
100
101
### Call Options
102
103
Options for method calls and transactions.
104
105
```typescript { .api }
106
// From web3-types
107
interface NonPayableCallOptions {
108
from?: Address;
109
gas?: Numbers;
110
gasPrice?: Numbers;
111
maxFeePerGas?: Numbers;
112
maxPriorityFeePerGas?: Numbers;
113
nonce?: Numbers;
114
block?: BlockNumberOrTag;
115
}
116
117
interface PayableCallOptions extends NonPayableCallOptions {
118
value?: Numbers;
119
}
120
121
type NonPayableTxOptions = NonPayableCallOptions;
122
type PayableTxOptions = PayableCallOptions;
123
```
124
125
## Usage Examples
126
127
### Read-Only Method Calls
128
129
```typescript
130
import { Contract } from "web3-eth-contract";
131
132
const abi = [
133
{
134
inputs: [],
135
name: "getValue",
136
outputs: [{ name: "", type: "uint256" }],
137
stateMutability: "view",
138
type: "function"
139
},
140
{
141
inputs: [{ name: "account", type: "address" }],
142
name: "balanceOf",
143
outputs: [{ name: "", type: "uint256" }],
144
stateMutability: "view",
145
type: "function"
146
}
147
] as const;
148
149
const contract = new Contract(abi, contractAddress);
150
151
// Simple call without options
152
const value = await contract.methods.getValue().call();
153
console.log("Current value:", value);
154
155
// Call with specific options
156
const balance = await contract.methods.balanceOf("0x1234...").call({
157
from: "0xabcd...",
158
block: "latest"
159
});
160
console.log("Balance:", balance);
161
162
// Multi-return method
163
const abi2 = [{
164
inputs: [],
165
name: "getInfo",
166
outputs: [
167
{ name: "name", type: "string" },
168
{ name: "value", type: "uint256" }
169
],
170
stateMutability: "view",
171
type: "function"
172
}] as const;
173
174
const contract2 = new Contract(abi2, contractAddress);
175
const result = await contract2.methods.getInfo().call();
176
// result.name and result.value are properly typed
177
console.log("Name:", result.name, "Value:", result.value);
178
// Also accessible by index: result[0], result[1]
179
```
180
181
### State-Changing Transactions
182
183
```typescript
184
const abi = [
185
{
186
inputs: [{ name: "newValue", type: "uint256" }],
187
name: "setValue",
188
outputs: [],
189
stateMutability: "nonpayable",
190
type: "function"
191
},
192
{
193
inputs: [
194
{ name: "to", type: "address" },
195
{ name: "amount", type: "uint256" }
196
],
197
name: "transfer",
198
outputs: [{ name: "", type: "bool" }],
199
stateMutability: "nonpayable",
200
type: "function"
201
}
202
] as const;
203
204
const contract = new Contract(abi, contractAddress);
205
206
// Simple transaction
207
const receipt = await contract.methods.setValue(42).send({
208
from: "0x1234567890123456789012345678901234567890",
209
gas: 100000,
210
gasPrice: "20000000000"
211
});
212
213
console.log("Transaction hash:", receipt.transactionHash);
214
console.log("Gas used:", receipt.gasUsed);
215
216
// Transaction with event monitoring
217
const promiEvent = contract.methods.transfer("0xabcd...", 1000).send({
218
from: "0x1234...",
219
gas: 50000
220
});
221
222
promiEvent
223
.on('transactionHash', (hash) => {
224
console.log("Transaction sent:", hash);
225
})
226
.on('receipt', (receipt) => {
227
console.log("Transaction confirmed:", receipt);
228
})
229
.on('error', (error) => {
230
console.error("Transaction failed:", error);
231
});
232
233
const receipt = await promiEvent;
234
```
235
236
### Payable Methods
237
238
```typescript
239
const abi = [{
240
inputs: [],
241
name: "deposit",
242
outputs: [],
243
stateMutability: "payable",
244
type: "function"
245
}] as const;
246
247
const contract = new Contract(abi, contractAddress);
248
249
// Send ether with the transaction
250
const receipt = await contract.methods.deposit().send({
251
from: "0x1234...",
252
value: web3.utils.toWei("1", "ether"), // Send 1 ETH
253
gas: 100000
254
});
255
```
256
257
### Gas Estimation
258
259
```typescript
260
// Estimate gas before sending transaction
261
const gasEstimate = await contract.methods.setValue(42).estimateGas({
262
from: "0x1234567890123456789012345678901234567890"
263
});
264
265
console.log("Estimated gas:", gasEstimate);
266
267
// Use estimated gas with buffer
268
const receipt = await contract.methods.setValue(42).send({
269
from: "0x1234567890123456789012345678901234567890",
270
gas: Math.floor(gasEstimate * 1.2) // Add 20% buffer
271
});
272
```
273
274
### Access List Creation
275
276
```typescript
277
// Create access list for EIP-2930 transactions
278
const accessList = await contract.methods.setValue(42).createAccessList({
279
from: "0x1234567890123456789012345678901234567890"
280
});
281
282
console.log("Access list:", accessList.accessList);
283
console.log("Gas used:", accessList.gasUsed);
284
285
// Use access list in transaction
286
const receipt = await contract.methods.setValue(42).send({
287
from: "0x1234567890123456789012345678901234567890",
288
accessList: accessList.accessList,
289
type: 1 // EIP-2930 transaction type
290
});
291
```
292
293
### Overloaded Methods
294
295
```typescript
296
// For overloaded methods, access by signature
297
const abi = [
298
{
299
inputs: [{ name: "value", type: "uint256" }],
300
name: "set",
301
outputs: [],
302
stateMutability: "nonpayable",
303
type: "function"
304
},
305
{
306
inputs: [
307
{ name: "key", type: "string" },
308
{ name: "value", type: "uint256" }
309
],
310
name: "set",
311
outputs: [],
312
stateMutability: "nonpayable",
313
type: "function"
314
}
315
] as const;
316
317
const contract = new Contract(abi, contractAddress);
318
319
// Access by method signature for overloaded methods
320
await contract.methods["set(uint256)"](42).send({ from: account });
321
await contract.methods["set(string,uint256)"]("key", 42).send({ from: account });
322
323
// Or by index if there are naming conflicts
324
await contract.methods.set(42).send({ from: account }); // First definition
325
```
326
327
## Return Types
328
329
```typescript { .api }
330
// Transaction receipt type
331
interface TransactionReceipt {
332
transactionHash: string;
333
transactionIndex: number;
334
blockHash: string;
335
blockNumber: number;
336
from: string;
337
to: string;
338
gasUsed: number;
339
cumulativeGasUsed: number;
340
logs: EventLog[];
341
status: boolean;
342
// ... other receipt fields
343
}
344
345
// PromiEvent for transaction sending
346
type ContractMethodSend = Web3PromiEvent<
347
FormatType<TransactionReceipt, DataFormat>,
348
SendTransactionEvents<DataFormat>
349
>;
350
351
// Access list result
352
interface AccessListResult {
353
accessList: AccessList;
354
gasUsed: string;
355
}
356
```