跳至主要内容

Smart Contract Execution

TxTypeSmartContractExecution executes a smart contract with the given data. TxTypeSmartContractExecution is accepted only if "to" is a smart contract account.

Fee Delegation

Import the @kaiachain/viem-ext packages to add kaia features on web3

Initializes a public client for read-only interactions with the Kaia blockchain.

Set up sender and fee payer wallets using createWalletClient, configured with the Kairos chain, an HTTP transport, and the sender’s private key converted to an account.

Set the contract address you want to execute into the to field and set ABI.

Encode the function name and parameter with the encodeFunctionData function

Create a transaction request for execute a smart contract using prepareTransactionRequest, specifying the sender’s account, recipient address, value to transfer (0 KLAY in this example) and transaction type (TxType.FeeDelegatedSmartContractDeploy)

Signing the transaction with the wallet client’s signTransaction method.

The sender submits the transaction to the Kaia blockchain using klay_sendRawTransaction, and the result (typically a transaction hash) is logged. The sender pays the transaction fees.

Prepares a fee-delegated transaction (FeeDelegatedSmartContractExecution) to call the same setNumber function on the contract. The setup is similar to the non-fee-delegated transaction, but the fee payer signs the transaction to cover the fees.

The sender signs the transaction first, the fee payer adds their signature, and the transaction is submitted to the Kaia blockchain.

Uses the public client to read the value of the number variable from the contract by calling the number function (a view function that doesn’t modify state).

FeeDelegatedSmartContractExecution.js

import {
http, encodeFunctionData, createWalletClient,
createPublicClient, kairos, TxType, privateKeyToAccount
} from "@kaiachain/viem-ext";
const publicClient = createPublicClient({
chain: kairos,
transport: http(),
});
const senderWallet = createWalletClient({
chain: kairos,
transport: http(),
account: privateKeyToAccount(
"0x0e4ca6d38096ad99324de0dde108587e5d7c600165ae4cd6c2462c597458c2b8"
),
})
const feePayerWallet = createWalletClient({
chain: kairos,
transport: http(),
account: privateKeyToAccount(
"0x9435261ed483b6efa3886d6ad9f64c12078a0e28d8d80715c773e16fc000cff4"
),
});
// Example usage
(async () => {
const contractAddr = "0x95Be48607498109030592C08aDC9577c7C2dD505";
const abi = [{ "inputs": [{ "internalType": "uint256", "name": "initNumber", "type": "uint256" }], "stateMutability": "nonpayable", "type": "constructor" }, { "anonymous": false, "inputs": [{ "indexed": false, "internalType": "uint256", "name": "number", "type": "uint256" }], "name": "SetNumber", "type": "event" }, { "inputs": [], "name": "increment", "outputs": [], "stateMutability": "nonpayable", "type": "function" }, { "inputs": [], "name": "number", "outputs": [{ "internalType": "uint256", "name": "", "type": "uint256" }], "stateMutability": "view", "type": "function" }, { "inputs": [{ "internalType": "uint256", "name": "newNumber", "type": "uint256" }], "name": "setNumber", "outputs": [], "stateMutability": "nonpayable", "type": "function" }];
const data = encodeFunctionData({
abi,
args: [123n],
functionName: "setNumber",
});
// non fee payer
const tx = await senderWallet.prepareTransactionRequest({
type: TxType.SmartContractExecution,
account: senderWallet.account,
to: contractAddr,
value: 0,
data,
});
console.log("preparedTx", tx);
const signedTx = await senderWallet.signTransaction(tx);
const sentTx = await senderWallet.request({
method: "klay_sendRawTransaction",
params: [signedTx],
});
console.log("contract interaction tx", sentTx);
// fee payer
const tx2 = await senderWallet.prepareTransactionRequest({
type: TxType.FeeDelegatedSmartContractExecution,
account: senderWallet.account,
to: contractAddr,
value: 0,
data,
});
const signedTx2 = await senderWallet.signTransaction(tx2);
const feePayerSignedTx = await feePayerWallet.signTransactionAsFeePayer(
signedTx2
);
const sentFeePayerTx = await feePayerWallet.request({
method: "klay_sendRawTransaction",
params: [feePayerSignedTx],
});
console.log("fee payer contract execution tx", sentFeePayerTx);
const result = await publicClient.readContract({
address: contractAddr,
abi,
functionName: 'number'
})
console.log('Current contract value', result);
})();

output

❯ js FeeDelegatedSmartContractExecution.js
preparedTx {
type: 48,
account: {
address: '0xA2a8854b1802D8Cd5De631E690817c253d6a9153',
nonceManager: undefined,
sign: [AsyncFunction: sign],
signAuthorization: [AsyncFunction: signAuthorization],
signMessage: [AsyncFunction: signMessage],
signTransaction: [AsyncFunction: signTransaction],
signTypedData: [AsyncFunction: signTypedData],
source: 'privateKey',
type: 'local',
publicKey: '0x04dc9dccbd788c00fa98f7f4082f2f714e799bc0c29d63f04d48b54fe6250453cdaf06ca34ae8714cf3dae06bacdb78c7c2d4054bd38961d40853cd5f15955da79'
},
to: '0x95Be48607498109030592C08aDC9577c7C2dD505',
value: 0,
data: '0x3fb5c1cb000000000000000000000000000000000000000000000000000000000000007b',
from: '0xA2a8854b1802D8Cd5De631E690817c253d6a9153',
nonce: 2396,
chainId: 1001,
gas: 25093n,
gasPrice: '0x66720b300',
gasLimit: 62732
}
contract interaction tx 0xf92b2450cfe8bb10cdb02f01c99a391be835d94435fd042d22128233e85c8592
fee payer contract execution tx 0x910b967d4bdaa439efab64fa8d7a092d075989a477ef723d66601e694f9c5698
Current contract value 123n

让这个页面变得更好