本文目录导读:

我来帮你理清 PHP 在前端 Web3 应用中的角色和实现方式。
核心理解
PHP 主要作为后端服务层,前端 Web3 交互仍由 JavaScript 处理,PHP 负责后端逻辑、API 服务、与区块链节点的间接通信。
架构方案
纯后端 API 模式
前端 (JS/Web3.js) <--> PHP API <--> 区块链节点
// PHP 后端示例 - 区块链数据查询
<?php
class Web3Service {
public function getBalance($address) {
// 通过 RPC 调用节点
$data = [
'jsonrpc' => '2.0',
'method' => 'eth_getBalance',
'params' => [$address, 'latest'],
'id' => 1
];
$ch = curl_init('https://mainnet.infura.io/v3/YOUR_PROJECT_ID');
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($data));
curl_setopt($ch, CURLOPT_HTTPHEADER, ['Content-Type: application/json']);
return curl_exec($ch);
}
}
前后端混合模式
前端 (HTML + JS)
<!DOCTYPE html>
<html>
<head>
<script src="https://cdn.jsdelivr.net/npm/web3@1.10.0/dist/web3.min.js"></script>
</head>
<body>
<button onclick="connectWallet()">连接钱包</button>
<button onclick="callPhpApi()">调用后端</button>
<script>
async function connectWallet() {
if (window.ethereum) {
window.web3 = new Web3(window.ethereum);
await ethereum.request({ method: 'eth_requestAccounts' });
}
}
async function callPhpApi() {
const accounts = await web3.eth.getAccounts();
// 调用 PHP 后端 API
const response = await fetch('/api/web3-action.php', {
method: 'POST',
headers: {'Content-Type': 'application/json'},
body: JSON.stringify({
userAddress: accounts[0],
action: 'verify_signature'
})
});
const data = await response.json();
console.log(data);
}
</script>
</body>
</html>
后端 (PHP)
<?php
// api/web3-action.php
header('Content-Type: application/json');
$input = json_decode(file_get_contents('php://input'), true);
$userAddress = $input['userAddress'];
// 验证签名或处理区块链相关操作
$response = [
'success' => true,
'data' => [
'message' => '用户 ' . $userAddress . ' 验证成功',
'timestamp' => time()
]
];
echo json_encode($response);
使用 Web3 PHP 库
安装依赖:
composer require web3p/web3.php
<?php
require_once 'vendor/autoload.php';
use Web3\Web3;
use Web3\Providers\HttpProvider;
use Web3\RequestManagers\HttpRequestManager;
class BlockchainService {
private $web3;
public function __construct() {
$this->web3 = new Web3(new HttpProvider(
new HttpRequestManager('https://mainnet.infura.io/v3/YOUR_PROJECT_ID', 30)
));
}
public function getBlockNumber() {
$this->web3->eth->blockNumber(function($err, $blockNumber) {
if ($err !== null) {
echo 'Error: ' . $err->getMessage();
return;
}
return $blockNumber->toString();
});
}
public function sendTransaction($from, $to, $value) {
// 发送交易(需要私钥)
$this->web3->eth->sendTransaction([
'from' => $from,
'to' => $to,
'value' => '0x' . dechex($value)
], function($err, $transaction) {
if ($err !== null) {
return ['error' => $err->getMessage()];
}
return ['txHash' => $transaction];
});
}
}
常用实践场景
MetaMask 签名验证
// PHP 验证签名
<?php
function verifySignature($message, $signature, $address) {
// 使用 secp256k1 算法验证
$hash = hash('sha256', $message);
$recovered = \Elliptic\EC::recoverPubKey('secp256k1', $hash, $signature);
return $recovered->getAddress() === $address;
}
智能合约交互
<?php
// 调用合约方法
$contract = new Contract($web3->provider, $abi);
$contract->at($contractAddress);
$contract->call('balanceOf', $userAddress, function($err, $result) {
// 处理结果
});
实用工具推荐
| 工具 | 用途 |
|---|---|
| web3.php | PHP 的 Web3 客户端库 |
| Infura/Alchemy | 区块链节点服务 |
| Etherscan API | 链上数据查询 |
| Laravel Web3 | Laravel 集成包 |
最佳实践
- 私钥安全:永远不要把私钥暴露给前端
- 签名验证:在后端验证所有来自前端的签名
- Gas 管理:PHP 后端处理交易的 gas 估算
- 缓存策略:频繁查询使用 Redis 缓存
项目示例结构
project/
├── frontend/
│ ├── index.html # 前端页面
│ ├── app.js # Web3 交互脚本
│ └── style.css
├── api/
│ ├── verify.php # 签名验证
│ ├── transaction.php # 交易处理
│ └── query.php # 数据查询
├── vendor/
│ └── web3p/
└── config.php # 配置信息
关键点:PHP 处理后端逻辑和安全性,前端负责钱包连接和交互体验,两者配合实现完整的 Web3 应用。