Avalanche 地址管理
Avalanche 使用分层确定性(HD)钱包来管理地址和密钥。本指南将介绍如何创建、管理和使用 Avalanche 地址。
地址格式
Avalanche 使用 Bech32 编码的地址格式:
- X-Chain 地址:
X-
前缀,例如:X-fuji1cfvdpdqyzpp8pq0g6trmjsrn9pt8nutsfm7a40
- P-Chain 地址:
P-
前缀,例如:P-fuji1cfvdpdqyzpp8pq0g6trmjsrn9pt8nutsfm7a40
- C-Chain 地址:
0x
前缀(兼容以太坊),例如:0x742d35Cc6634C0532925a3b8D4C9db96C4b4d8b6
生成助记词
1. 创建新的助记词
const { Mnemonic } = require('avalanche');
// 获取助记词实例
const mnemonic = Mnemonic.getInstance();
// 生成 24 个单词的助记词 (256 位强度)
const words = mnemonic.generateMnemonic(256);
console.log('助记词:', words);
// 生成 12 个单词的助记词 (128 位强度)
const words12 = mnemonic.generateMnemonic(128);
console.log('12 词助记词:', words12);
2. 验证助记词
// 检查助记词是否有效
const isValid = mnemonic.validateMnemonic(words);
console.log('助记词有效:', isValid);
// 获取助记词强度
const strength = mnemonic.getMnemonicStrength(words);
console.log('助记词强度:', strength);
从助记词生成密钥
1. 生成种子
// 从助记词生成种子
const seed = mnemonic.mnemonicToSeedSync(words);
console.log('种子长度:', seed.length);
// 可选:添加密码短语
const seedWithPassphrase = mnemonic.mnemonicToSeedSync(words, 'my_password');
2. 创建 HD 钱包
const { HDNode } = require('avalanche');
// 从种子创建 HD 钱包
const hdnode = new HDNode(seed);
// 获取主私钥
const masterPrivateKey = hdnode.privateKeyCB58;
console.log('主私钥:', masterPrivateKey);
派生地址
1. BIP44 路径
Avalanche 使用 BIP44 标准,路径为:m/44'/9000'/0'/0/{index}
44'
: BIP44 标准9000'
: Avalanche 的币种标识符0'
: 账户索引0
: 链类型(0=外部链,1=内部链){index}
: 地址索引
// 派生第一个外部地址
const child0 = hdnode.derive("m/44'/9000'/0'/0/0");
console.log('地址 0 私钥:', child0.privateKeyCB58);
console.log('地址 0 公钥:', child0.publicKey.toString('hex'));
// 派生第二个外部地址
const child1 = hdnode.derive("m/44'/9000'/0'/0/1");
console.log('地址 1 私钥:', child1.privateKeyCB58);
// 派生内部地址(用于找零)
const internal0 = hdnode.derive("m/44'/9000'/0'/1/0");
console.log('内部地址 0 私钥:', internal0.privateKeyCB58);
2. 批量派生地址
function deriveAddresses(hdnode, startIndex, count) {
const addresses = [];
for (let i = startIndex; i < startIndex + count; i++) {
const child = hdnode.derive(`m/44'/9000'/0'/0/${i}`);
addresses.push({
index: i,
privateKey: child.privateKeyCB58,
publicKey: child.publicKey.toString('hex'),
path: `m/44'/9000'/0'/0/${i}`
});
}
return addresses;
}
// 派生前 5 个地址
const addressList = deriveAddresses(hdnode, 0, 5);
addressList.forEach(addr => {
console.log(`地址 ${addr.index}:`, addr.privateKey);
});
导入私钥
1. 导入到密钥链
const { Avalanche } = require('avalanche');
// 连接到网络
const avalanche = new Avalanche('api.avax-test.network', 443, 'https', 5);
const xchain = avalanche.XChain();
const keychain = xchain.keyChain();
// 导入私钥
const keyPair = keychain.importKey(privateKeyCB58);
console.log('导入的地址:', keyPair.getAddressString());
// 获取所有导入的地址
const addresses = keychain.getAddressStrings();
console.log('所有地址:', addresses);
2. 从不同格式导入
// 从十六进制私钥导入
const hexPrivateKey = Buffer.from('your_hex_private_key', 'hex');
const keyPairFromHex = keychain.importKey(hexPrivateKey);
// 从 WIF 格式导入(如果支持)
// const keyPairFromWIF = keychain.importKey(wifPrivateKey);
地址验证
1. 验证地址格式
function validateAvalancheAddress(address) {
// X-Chain 地址验证
if (address.startsWith('X-')) {
const regex = /^X-[a-zA-Z0-9]{39}$/;
return regex.test(address);
}
// P-Chain 地址验证
if (address.startsWith('P-')) {
const regex = /^P-[a-zA-Z0-9]{39}$/;
return regex.test(address);
}
// C-Chain 地址验证(以太坊格式)
if (address.startsWith('0x')) {
const regex = /^0x[a-fA-F0-9]{40}$/;
return regex.test(address);
}
return false;
}
// 测试地址
const testAddresses = [
'X-fuji1cfvdpdqyzpp8pq0g6trmjsrn9pt8nutsfm7a40',
'P-fuji1cfvdpdqyzpp8pq0g6trmjsrn9pt8nutsfm7a40',
'0x742d35Cc6634C0532925a3b8D4C9db96C4b4d8b6',
'invalid-address'
];
testAddresses.forEach(addr => {
console.log(`${addr}: ${validateAvalancheAddress(addr) ? '有效' : '无效'}`);
});
2. 地址类型检测
function getAddressType(address) {
if (address.startsWith('X-')) return 'X-Chain';
if (address.startsWith('P-')) return 'P-Chain';
if (address.startsWith('0x')) return 'C-Chain';
return 'Unknown';
}
// 检测地址类型
const address = 'X-fuji1cfvdpdqyzpp8pq0g6trmjsrn9pt8nutsfm7a40';
console.log('地址类型:', getAddressType(address));
地址转换
1. 在不同链之间转换
const { utils } = require('avalanche');
const { Serialization } = utils;
async function convertAddress(address, targetChain) {
const serialization = Serialization.getInstance();
try {
// 解析地址
const addressBuffer = xchain.parseAddress(address);
// 转换为目标链格式
let convertedAddress;
switch (targetChain) {
case 'X':
convertedAddress = serialization.bufferToType(
addressBuffer,
'bech32',
'X',
xchain.getChainID()
);
break;
case 'P':
convertedAddress = serialization.bufferToType(
addressBuffer,
'bech32',
'P',
pchain.getChainID()
);
break;
default:
throw new Error('不支持的链类型');
}
return convertedAddress;
} catch (error) {
console.error('地址转换失败:', error);
throw error;
}
}
安全最佳实践
1. 私钥管理
// 安全存储私钥
class SecureKeyManager {
constructor() {
this.encryptedKeys = new Map();
}
// 加密私钥
encryptPrivateKey(privateKey, password) {
// 使用强加密算法加密私钥
const encrypted = this.encrypt(privateKey, password);
return encrypted;
}
// 解密私钥
decryptPrivateKey(encryptedKey, password) {
try {
const decrypted = this.decrypt(encryptedKey, password);
return decrypted;
} catch (error) {
throw new Error('密码错误或私钥损坏');
}
}
// 存储加密的私钥
storeKey(keyId, encryptedKey) {
this.encryptedKeys.set(keyId, encryptedKey);
}
// 获取私钥
getKey(keyId, password) {
const encryptedKey = this.encryptedKeys.get(keyId);
if (!encryptedKey) {
throw new Error('私钥不存在');
}
return this.decryptPrivateKey(encryptedKey, password);
}
}
2. 地址轮换
// 实现地址轮换策略
class AddressRotation {
constructor(hdnode, maxAddresses = 10) {
this.hdnode = hdnode;
this.maxAddresses = maxAddresses;
this.currentIndex = 0;
}
// 获取下一个地址
getNextAddress() {
if (this.currentIndex >= this.maxAddresses) {
this.currentIndex = 0; // 重新开始
}
const child = this.hdnode.derive(`m/44'/9000'/0'/0/${this.currentIndex}`);
this.currentIndex++;
return {
index: this.currentIndex - 1,
address: child.getAddressString(),
privateKey: child.privateKeyCB58
};
}
// 获取当前使用的地址
getCurrentAddress() {
return this.getNextAddress();
}
}
完整示例
const { Mnemonic, HDNode, Avalanche } = require('avalanche');
async function createAvalancheWallet() {
try {
// 1. 生成助记词
const mnemonic = Mnemonic.getInstance();
const words = mnemonic.generateMnemonic(256);
console.log('生成的助记词:', words);
// 2. 生成种子
const seed = mnemonic.mnemonicToSeedSync(words);
// 3. 创建 HD 钱包
const hdnode = new HDNode(seed);
// 4. 派生地址
const addresses = [];
for (let i = 0; i < 5; i++) {
const child = hdnode.derive(`m/44'/9000'/0'/0/${i}`);
addresses.push({
index: i,
privateKey: child.privateKeyCB58,
publicKey: child.publicKey.toString('hex'),
address: child.getAddressString()
});
}
// 5. 连接到网络并导入密钥
const avalanche = new Avalanche('api.avax-test.network', 443, 'https', 5);
const xchain = avalanche.XChain();
const keychain = xchain.keyChain();
// 导入第一个地址
const keyPair = keychain.importKey(addresses[0].privateKey);
console.log('导入的地址:', keyPair.getAddressString());
return {
mnemonic: words,
addresses: addresses,
keychain: keychain
};
} catch (error) {
console.error('创建钱包失败:', error);
throw error;
}
}
// 使用示例
createAvalancheWallet()
.then(wallet => {
console.log('钱包创建成功');
console.log('地址数量:', wallet.addresses.length);
})
.catch(error => {
console.error('钱包创建失败:', error);
});