Last active
June 3, 2025 14:30
-
-
Save Jackarain/644a7b6e7a786d10f54dcf4f23ddad7a to your computer and use it in GitHub Desktop.
btc/eth/tron 地址转换
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* | |
* 需要安装以下依赖: | |
* yarn add ethers bitcoinjs-lib ecpair tiny-secp256k1 bs58 | |
* yarn add @types/bitcoinjs-lib @types/ecpair @types/tiny-secp256k1 @types/bs58 | |
* yarn add ts-node typescript | |
*/ | |
import { ethers } from 'ethers'; | |
import { ECPairFactory } from 'ecpair'; | |
import bitcoin from 'bitcoinjs-lib'; | |
import * as tinysecp from 'tiny-secp256k1'; | |
import bs58 from 'bs58'; | |
// 确保 tinysecp 被正确注册 | |
const ECPair = ECPairFactory(tinysecp); | |
// 生成以太坊公钥和地址 | |
function getEthereumAddress(pKey: string): void { | |
try { | |
const wallet: ethers.Wallet = new ethers.Wallet(pKey); | |
console.log('以太坊地址:', wallet.address); | |
} catch (error) { | |
console.error('以太坊地址生成失败:', (error as Error).message); | |
} | |
} | |
// 生成比特币地址(BTC) | |
function getBitcoinAddress(pKey: string): void { | |
try { | |
const keyPair = ECPair.fromPrivateKey(Buffer.from(pKey, 'hex')); | |
bitcoin.initEccLib(tinysecp); | |
const pubkey: Buffer = Buffer.isBuffer(keyPair.publicKey) | |
? keyPair.publicKey | |
: Buffer.from(keyPair.publicKey); | |
// 生成 P2PKH 地址 | |
const p2pkh = bitcoin.payments.p2pkh({ pubkey }); | |
console.log('P2PKH 地址:', p2pkh.address); | |
// 生成 P2WPKH 地址 | |
const p2wpkh = bitcoin.payments.p2wpkh({ pubkey }); | |
console.log('P2WPKH 地址:', p2wpkh.address); | |
// 生成 P2TR 地址(隔离见证) | |
const internalPubkey: Buffer = pubkey.subarray(1, 33); | |
const p2tr = bitcoin.payments.p2tr({ internalPubkey }); | |
console.log('P2TR 地址:', p2tr.address); | |
} catch (error) { | |
console.error('比特币地址生成失败:', (error as Error).message); | |
} | |
} | |
// 生成波场(TRON)地址 | |
function getTronAddress(pKey: string): void { | |
try { | |
const signingKey = new ethers.SigningKey(Buffer.from(pKey, 'hex')); | |
const publicKey: string = signingKey.publicKey; // 非压缩公钥(含04前缀) | |
const publicKeyBuffer: Buffer = Buffer.from(publicKey.slice(2), 'hex'); | |
// 使用顶层 keccak256 方法 | |
const hash: string = ethers.keccak256(publicKeyBuffer.subarray(1)); | |
const addressHex: string = hash.slice(-40); | |
const addressBuffer: Buffer = Buffer.from(addressHex, 'hex'); | |
const prefix: Buffer = Buffer.from([0x41]); | |
const rawAddress: Buffer = Buffer.concat([prefix, addressBuffer]); | |
const sha256Once: Buffer = bitcoin.crypto.sha256(rawAddress); | |
const sha256Twice: Buffer = bitcoin.crypto.sha256(sha256Once); | |
const checksum: Buffer = sha256Twice.subarray(0, 4); | |
const finalBuffer: Buffer = Buffer.concat([rawAddress, checksum]); | |
const tronAddress: string = bs58.encode(finalBuffer); | |
console.log('波场地址:', tronAddress); | |
} catch (error) { | |
console.error('波场地址生成失败:', (error as Error).message); | |
} | |
} | |
// 主函数 | |
function main(pKey : string) { | |
// 移除私钥开头的 '0x'(如果有),生成一个干净的私钥字符串 | |
const cleanPrivateKey: string = pKey.startsWith('0x') ? pKey.slice(2) : pKey; | |
// 验证私钥格式(必须是64位16进制) | |
if (!/^[0-9a-fA-F]{64}$/.test(cleanPrivateKey)) { | |
console.error('无效的私钥格式!私钥必须是64位16进制字符串。'); | |
return; | |
} | |
// 获取比特币地址 | |
getBitcoinAddress(cleanPrivateKey); | |
// 获取以太坊地址 | |
getEthereumAddress(cleanPrivateKey); | |
// 获取波场地址 | |
getTronAddress(cleanPrivateKey); | |
} | |
// 从命令行获取私钥参数 [6,7,8](@ref) | |
const args: string[] = process.argv.slice(2); | |
if (args.length === 0) { | |
console.error('错误:请提供私钥作为命令行参数'); | |
console.error('示例:yarn start e3ee395e5aeee67299e93bef917e8462e458da6543a3b52e041bc754b5132dbc'); | |
process.exit(1); | |
} | |
// 执行 | |
main(args[0]); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment