solana@web3.js / 程序传输
solana@web3.js / program transfer
我正在尝试用 Solana 编写一个简单的程序,在用户批准后运行并将给定数量的 SOL 转移到程序的所有者帐户中。
从 JS 方面,我基于 Solana 存储库中的 HelloWorld 示例
...
const secretKeyString = await fs.readFile(filePath, {encoding: 'utf8'});
const secretKey = Uint8Array.from(JSON.parse(secretKeyString))
const keypair = Keypair.fromSecretKey(secretKey)
const instruction = new TransactionInstruction({
keys: [
{pubkey: publicKey, isSigner: false, isWritable: true}, // from wallet
{pubkey: keypair.publicKey, isSigner: false, isWritable: true} // from json file, program owner
],
programId,
data: Buffer.alloc(0)
});
const transaction = new Transaction().add(instruction);
signature = await sendTransaction(transaction, connection);
//toast('Transaction Sent');
在程序方面,我简单地使用了来自 Solana 存储库的 C 示例中的示例(未编辑)- 因此假设一切都很好
/**
* @brief A program demonstrating the transfer of lamports
*/
#include <solana_sdk.h>
extern uint64_t transfer(SolParameters *params) {
// As part of the program specification the first account is the source
// account and the second is the destination account
if (params->ka_num != 2) {
return ERROR_NOT_ENOUGH_ACCOUNT_KEYS;
}
SolAccountInfo *source_info = ¶ms->ka[0];
SolAccountInfo *destination_info = ¶ms->ka[1];
// Withdraw five lamports from the source
*source_info->lamports -= 100000000;
// Deposit five lamports into the destination
*destination_info->lamports += 100000000;
return SUCCESS;
}
extern uint64_t entrypoint(const uint8_t *input) {
SolAccountInfo accounts[2];
SolParameters params = (SolParameters){.ka = accounts};
if (!sol_deserialize(input, ¶ms, SOL_ARRAY_SIZE(accounts))) {
return ERROR_INVALID_ARGUMENT;
}
return transfer(¶ms);
}
然而,这一直失败并出现错误 ´-32003 交易创建失败。`
系统级别 SOL transfer
有一个约束,即 from
公钥必须是 系统拥有的帐户.这意味着程序或 PDA 拥有的帐户将失败,因为它们属于您的程序。 https://solanacookbook.com/references/accounts.html#transfer
仅当 from
公钥是 程序拥有的帐户 时,您的代码显示的 lamports 的传输才会发生。 https://solanacookbook.com/references/programs.html#transferring-lamports
我正在尝试用 Solana 编写一个简单的程序,在用户批准后运行并将给定数量的 SOL 转移到程序的所有者帐户中。
从 JS 方面,我基于 Solana 存储库中的 HelloWorld 示例
...
const secretKeyString = await fs.readFile(filePath, {encoding: 'utf8'});
const secretKey = Uint8Array.from(JSON.parse(secretKeyString))
const keypair = Keypair.fromSecretKey(secretKey)
const instruction = new TransactionInstruction({
keys: [
{pubkey: publicKey, isSigner: false, isWritable: true}, // from wallet
{pubkey: keypair.publicKey, isSigner: false, isWritable: true} // from json file, program owner
],
programId,
data: Buffer.alloc(0)
});
const transaction = new Transaction().add(instruction);
signature = await sendTransaction(transaction, connection);
//toast('Transaction Sent');
在程序方面,我简单地使用了来自 Solana 存储库的 C 示例中的示例(未编辑)- 因此假设一切都很好
/**
* @brief A program demonstrating the transfer of lamports
*/
#include <solana_sdk.h>
extern uint64_t transfer(SolParameters *params) {
// As part of the program specification the first account is the source
// account and the second is the destination account
if (params->ka_num != 2) {
return ERROR_NOT_ENOUGH_ACCOUNT_KEYS;
}
SolAccountInfo *source_info = ¶ms->ka[0];
SolAccountInfo *destination_info = ¶ms->ka[1];
// Withdraw five lamports from the source
*source_info->lamports -= 100000000;
// Deposit five lamports into the destination
*destination_info->lamports += 100000000;
return SUCCESS;
}
extern uint64_t entrypoint(const uint8_t *input) {
SolAccountInfo accounts[2];
SolParameters params = (SolParameters){.ka = accounts};
if (!sol_deserialize(input, ¶ms, SOL_ARRAY_SIZE(accounts))) {
return ERROR_INVALID_ARGUMENT;
}
return transfer(¶ms);
}
然而,这一直失败并出现错误 ´-32003 交易创建失败。`
系统级别 SOL transfer
有一个约束,即 from
公钥必须是 系统拥有的帐户.这意味着程序或 PDA 拥有的帐户将失败,因为它们属于您的程序。 https://solanacookbook.com/references/accounts.html#transfer
仅当 from
公钥是 程序拥有的帐户 时,您的代码显示的 lamports 的传输才会发生。 https://solanacookbook.com/references/programs.html#transferring-lamports