假设我们使用Ganache或Infura的RPC URL

admin1 2026-03-19 17:39

Python与以太坊:搭建你的第一个去中心化应用(DApp)后端**


以太坊作为全球领先的智能合约平台,为去中心化应用(DApps)的开发提供了强大的基础设施,而Python,以其简洁的语法、丰富的库生态和易用性,成为了与以太坊交互和搭建DApp后端的理想选择,本文将带你了解如何使用Python与以太坊进行交互,并搭建一个简单的DApp后端环境。

为什么选择Python与以太坊交互

在众多编程语言中,Python在以太坊生态中占据了一席之地,主要原因包括:

  1. 简洁易学:Python的语法清晰,接近自然语言,降低了开发门槛,使得开发者可以更专注于业务逻辑而非复杂的语言细节。
  2. 丰富的库支持:存在多个成熟的Python库(如Web3.py、Web3.py的衍生库或特定框架)用于与以太坊节点交互、部署智能合约、调用合约方法等。
  3. 强大的社区:Python拥有庞大的开发者社区,遇到问题时容易找到解决方案和帮助。
  4. 快速开发:Python的动态类型和丰富的第三方库使得原型开发和迭代速度非常快。

搭建Python以太坊开发环境

要使用Python与以太坊交互,我们需要搭建一个包含Python环境、以太坊节点(或连接到远程节点)以及必要库的开发环境。

安装Python

如果你的系统中尚未安装Python,请从Python官网下载并安装最新稳定版本(推荐3.8及以上),安装时请确保勾选“Add Python to PATH”选项。

安装Web3.py库

Web3.py是以太坊官方推荐的Python库,用于与以太坊网络进行交互,打开终端或命令提示符,执行以下命令安装:

pip install web3

如果需要特定版本或有其他依赖,可以通过pip install web3==版本号来安装。

选择以太坊节点连接方式

Python脚本需要连接到一个以太坊节点才能读取区块链数据、发送交易等,主要有两种方式:

  • 本地运行以太坊节点

    • Geth:Go语言实现的以太坊客户端,你可以从Geth官网下载并安装,安装后,可以通过命令行启动一个全节点或快照节点,并开启RPC服务(--http --http.addr 0.0.0.0 --http.port 8545 --http.api eth,net,web3,personal),注意,同步全节点需要大量时间和磁盘空间。
    • Parity:Rust语言实现的以太坊客户端,现已Open Source并更名为OpenEthereum,同样可以下载安装并启动RPC服务。
    • Ganache:一个个人以太坊区块链,用于开发,它非常轻量级,可以瞬间创建多个账户,并预设大量以太币,非常适合开发和测试,你可以从Ganache官网下载桌面版,或使用其命令行版本。
  • **连接到远程节点服务(推荐初学者):

    • 对于开发者来说,运行本地全节点资源消耗较大,连接到远程节点服务是更便捷的选择,许多服务商提供免费的以太坊节点RPC URL,
    • 注册这些服务后,你可以获得一个唯一的HTTP或WebSocket RPC URL,在你的Python代码中使用这个URL连接到以太坊网络。

使用Python与以太坊交互基础

安装好环境后,我们就可以开始使用Python进行一些基本的以太坊操作了。

连接到以太坊节点

from web3 import Web3
# Ganache默认RPC URL通常是 "HTTP://127.0.0.1:7545"
# Infura提供的URL类似 "https://mainnet.infura.io/v3/YOUR_PROJECT_ID"
infura_url = "https://mainnet.infura.io/v3/YOUR_PROJECT_ID" # 替换成你自己的Infura ID
ganache_url = "HTTP://127.0.0.1:7545"
# 连接到Ganache本地节点(示例)
w3 = Web3(Web3.HTTPProvider(ganache_url))
# 检查连接是否成功
if w3.is_connected():
    print(f"成功连接到以太坊节点!链ID: {w3.eth.chain_id}")
else:
    print("连接失败!")
# 连接到Infura主网(示例)
# w3 = Web3(Web3.HTTPProvider(infura_url))
# if w3.is_connected():
#     print(f"成功连接到Infura主网!链ID: {w3.eth.chain_id}")
# else:
#     print("连接失败!")

获取账户信息

# 获取节点上的第一个账户(通常是Ganache创建的第一个测试账户)
account = w3.eth.accounts[0]
print(f"默认账户地址: {account}")
# 获取账户余额
balance = w3.eth.get_balance(account)
# 余额通常是以wei为单位,转换为ether
balance_in_ether = w3.from_wei(balance, 'ether')
print(f"账户余额: {balance_in_ether} ETH")

发送交易(需要私钥)

发送交易需要发送方的私钥。请务必妥善保管私钥,切勿泄露!

from web3 import Account
# 假设我们有一个账户的私钥(仅用于示例,实际中应安全存储)
private_key = "0x你的私钥" # 替换成你的私钥,注意"0x"前缀
# 从私钥获取账户对象
sender_account = Account.from_key(private_key)
sender_address = sender_account.address
print(f"发送方地址: {sender_address}")
# 获取nonce(每个交易的序列号)
nonce = w3.eth.get_transaction_count(sender_address)
# 构建交易
# 假设我们要转账到另一个地址(这里用第一个账户作为示例接收方)
receiver_address = w3.eth.accounts[1]
value_in_wei = w3.to_wei(0.01, 'ether') # 转账0.01 ETH
gas_price = w3.eth.gas_price  # 获取当前建议的gas价格
gas_limit = 21000  # 转账ETH的典型gas限制
transaction = {
    'nonce': nonce,
    'to': receiver_address,
    'value': value_in_wei,
    'gas': gas_limit,
    'gasPrice': gas_price,
    'chainId': w3.eth.chain_id  # 确保交易在正确的链上执行
}
# 签名交易
signed_txn = w3.eth.account.sign_transaction(transaction, private_key)
# 发送交易
tx_hash = w3.eth.send_raw_transaction(signed_txn.rawTransaction)
print(f"交易发送中,交易哈希: {tx_hash.hex()}")
# 等待交易被打包
receipt = w3.eth.wait_for_transaction_receipt(tx_hash)
print(f"交易收据: {receipt}")

与智能合约交互

智能合约是以太坊的核心,要使用Python与智能合约交互,你需要:

  1. 智能合约的ABI(Application Binary Interface):这是合约与外界交互的接口,通常以JSON格式提供。
  2. 智能合约的地址:部署到以太坊网络后的合约地址。
  3. 合约实例:使用Web3.py和ABI、地址创建合约实例。
# 假设我们有一个简单的存储合约(Storage.sol)部署在本地测试网
# SPDX-License-Identifier: MIT
# pragma solidity ^0.8.0;
# contract Storage {
#     uint256 public storedData;
#
#     function set(uint256 x) public {
#         storedData = x;
#     }
#
#     function get() public view returns (uint256) {
#         return storedData;
#     }
# }
# 假设这个合约已经部署,地址为 0x5FbDB2315678afecb367f032d93F642f64180aa3 (Truffle默认部署地址之一)
# ABI是简化的,实际使用时需要完整的ABI
contract_address = "0x5FbDB2315678afecb367f032d93F642f64180aa3"
# 简化的ABI,包含get和set函数的selector
abi = [
    {
        "inputs": [],
        "name": "get",
        "outputs": [{"internalType": "uint256", "name": "", "type": "uint256"}],
        "stateMutability": "view",
        "

本文转载自互联网,具体来源未知,或在文章中已说明来源,若有权利人发现,请联系我们更正。本站尊重原创,转载文章仅为传递更多信息之目的,并不意味着赞同其观点或证实其内容的真实性。如其他媒体、网站或个人从本网站转载使用,请保留本站注明的文章来源,并自负版权等法律责任。如有关于文章内容的疑问或投诉,请及时联系我们。我们转载此文的目的在于传递更多信息,同时也希望找到原作者,感谢各位读者的支持!
最近发表
随机文章
随机文章