user logout in the vault changed to queuing mechanism, and add function of batch sending WUSD
This commit is contained in:
219
scripts/upgrade/upgradeYTAssetVault.ts
Normal file
219
scripts/upgrade/upgradeYTAssetVault.ts
Normal file
@@ -0,0 +1,219 @@
|
||||
import { ethers, upgrades } from "hardhat";
|
||||
import * as fs from "fs";
|
||||
import * as path from "path";
|
||||
|
||||
/**
|
||||
* 升级 YTAssetVault 合约
|
||||
*
|
||||
* 升级步骤:
|
||||
* 1. 部署新的 YTAssetVault 实现合约
|
||||
* 2. 通过 Factory 更新 vaultImplementation 地址
|
||||
* 3. 可选:批量升级现有的 Vault 代理合约
|
||||
*
|
||||
* 注意:
|
||||
* - 升级后,新创建的 vault 将使用新实现
|
||||
* - 已存在的 vault 需要手动升级才能使用新功能
|
||||
*/
|
||||
async function main() {
|
||||
const [deployer] = await ethers.getSigners();
|
||||
console.log("\n==========================================");
|
||||
console.log("🔄 升级 YTAssetVault 系统");
|
||||
console.log("==========================================");
|
||||
console.log("升级账户:", deployer.address);
|
||||
console.log("账户余额:", ethers.formatEther(await ethers.provider.getBalance(deployer.address)), "ETH\n");
|
||||
|
||||
// ========== 读取部署信息 ==========
|
||||
const deploymentsPath = path.join(__dirname, "../../deployments-vault-system.json");
|
||||
if (!fs.existsSync(deploymentsPath)) {
|
||||
throw new Error("未找到部署信息文件 deployments-vault-system.json,请先运行部署脚本");
|
||||
}
|
||||
|
||||
const deployments = JSON.parse(fs.readFileSync(deploymentsPath, "utf-8"));
|
||||
|
||||
if (!deployments.contracts?.YTAssetVault?.implementation) {
|
||||
throw new Error("未找到 YTAssetVault 部署信息");
|
||||
}
|
||||
|
||||
console.log("📋 当前部署的合约:");
|
||||
console.log(" YTAssetVault Implementation (旧):", deployments.contracts.YTAssetVault.implementation);
|
||||
console.log(" YTAssetFactory Proxy: ", deployments.contracts.YTAssetFactory.proxy);
|
||||
console.log(" YTAssetFactory Implementation: ", deployments.contracts.YTAssetFactory.implementation);
|
||||
console.log(" 已创建的 Vaults 数量: ", deployments.vaults?.length || 0);
|
||||
console.log("");
|
||||
|
||||
// ========== Phase 1: 部署新的 YTAssetVault 实现 ==========
|
||||
console.log("🔄 Phase 1: 部署新的 YTAssetVault 实现合约");
|
||||
console.log(" 编译新的 YTAssetVault 合约...");
|
||||
|
||||
const YTAssetVaultV2 = await ethers.getContractFactory("YTAssetVault");
|
||||
|
||||
console.log(" 部署新实现合约...");
|
||||
const newVaultImpl = await YTAssetVaultV2.deploy();
|
||||
await newVaultImpl.waitForDeployment();
|
||||
|
||||
const newVaultImplAddress = await newVaultImpl.getAddress();
|
||||
console.log(" ✅ 新 YTAssetVault Implementation:", newVaultImplAddress);
|
||||
console.log("");
|
||||
|
||||
// ========== Phase 2: 通过 Factory 更新实现地址 ==========
|
||||
console.log("🔄 Phase 2: 通过 Factory 更新 vaultImplementation");
|
||||
|
||||
const factory = await ethers.getContractAt(
|
||||
"YTAssetFactory",
|
||||
deployments.contracts.YTAssetFactory.proxy
|
||||
);
|
||||
|
||||
console.log(" 当前 Factory 的 vaultImplementation:", await factory.vaultImplementation());
|
||||
console.log(" 准备更新为新实现地址...");
|
||||
|
||||
const updateTx = await factory.setVaultImplementation(newVaultImplAddress);
|
||||
await updateTx.wait();
|
||||
|
||||
console.log(" ✅ Factory vaultImplementation 已更新!");
|
||||
console.log(" 新地址:", await factory.vaultImplementation());
|
||||
console.log("");
|
||||
|
||||
// ========== Phase 3: 升级现有的 Vault 代理(可选) ==========
|
||||
console.log("🔄 Phase 3: 升级现有的 Vault 代理合约");
|
||||
|
||||
const existingVaults = deployments.vaults || [];
|
||||
|
||||
if (existingVaults.length === 0) {
|
||||
console.log(" ⚠️ 没有已部署的 Vault,跳过此步骤");
|
||||
} else {
|
||||
console.log(` 发现 ${existingVaults.length} 个已部署的 Vault\n`);
|
||||
|
||||
// 询问是否升级现有 Vault(在实际使用中可以配置)
|
||||
const UPGRADE_EXISTING_VAULTS = true; // 设置为 true 自动升级所有 vault
|
||||
const VAULTS_TO_UPGRADE: number[] = [0, 1, 2]; // 可以指定要升级的 vault 索引,如 [0, 1]
|
||||
|
||||
if (UPGRADE_EXISTING_VAULTS) {
|
||||
console.log(" 📝 准备升级现有的 Vault 代理合约...\n");
|
||||
|
||||
const vaultsToProcess = VAULTS_TO_UPGRADE.length > 0
|
||||
? VAULTS_TO_UPGRADE
|
||||
: existingVaults.map((_: any, idx: number) => idx);
|
||||
|
||||
for (const idx of vaultsToProcess) {
|
||||
const vaultInfo = existingVaults[idx];
|
||||
if (!vaultInfo) {
|
||||
console.log(` ⚠️ 索引 ${idx} 无效,跳过`);
|
||||
continue;
|
||||
}
|
||||
|
||||
console.log(` [${idx + 1}/${vaultsToProcess.length}] 升级 ${vaultInfo.symbol} (${vaultInfo.address})`);
|
||||
|
||||
try {
|
||||
// 通过 Factory 调用 upgradeVault
|
||||
const upgradeTx = await factory.upgradeVault(
|
||||
vaultInfo.address,
|
||||
newVaultImplAddress
|
||||
);
|
||||
await upgradeTx.wait();
|
||||
|
||||
// 验证升级
|
||||
const vault = await ethers.getContractAt("YTAssetVault", vaultInfo.address);
|
||||
const currentImpl = await upgrades.erc1967.getImplementationAddress(vaultInfo.address);
|
||||
|
||||
if (currentImpl.toLowerCase() === newVaultImplAddress.toLowerCase()) {
|
||||
console.log(` ✅ 升级成功!新实现: ${currentImpl}`);
|
||||
|
||||
// 验证新功能(检查是否有排队提现机制)
|
||||
try {
|
||||
const pendingCount = await vault.pendingRequestsCount();
|
||||
console.log(` ✅ 新功能验证通过(pendingRequestsCount: ${pendingCount})`);
|
||||
} catch (e) {
|
||||
console.log(` ⚠️ 新功能验证失败,可能升级未完全生效`);
|
||||
}
|
||||
|
||||
// 更新部署信息中的实现地址
|
||||
vaultInfo.implementationAddress = currentImpl;
|
||||
vaultInfo.lastUpgraded = new Date().toISOString();
|
||||
} else {
|
||||
console.log(` ⚠️ 升级可能未成功,当前实现: ${currentImpl}`);
|
||||
}
|
||||
} catch (error: any) {
|
||||
console.log(` ❌ 升级失败: ${error.message}`);
|
||||
}
|
||||
console.log("");
|
||||
}
|
||||
} else {
|
||||
console.log(" ℹ️ 配置为不自动升级现有 Vault");
|
||||
console.log(" 💡 提示:可以稍后通过 Factory.upgradeVault() 手动升级\n");
|
||||
}
|
||||
}
|
||||
|
||||
// ========== 保存更新的部署信息 ==========
|
||||
// 保存旧的实现地址作为历史记录
|
||||
if (!deployments.upgradeHistory) {
|
||||
deployments.upgradeHistory = [];
|
||||
}
|
||||
|
||||
deployments.upgradeHistory.push({
|
||||
timestamp: new Date().toISOString(),
|
||||
oldImplementation: deployments.contracts.YTAssetVault.implementation,
|
||||
newImplementation: newVaultImplAddress,
|
||||
upgrader: deployer.address
|
||||
});
|
||||
|
||||
// 更新当前实现地址
|
||||
deployments.contracts.YTAssetVault.implementation = newVaultImplAddress;
|
||||
deployments.lastUpdate = new Date().toISOString();
|
||||
|
||||
fs.writeFileSync(deploymentsPath, JSON.stringify(deployments, null, 2));
|
||||
console.log("💾 升级信息已保存到:", deploymentsPath);
|
||||
|
||||
// ========== 升级总结 ==========
|
||||
console.log("\n🎉 升级总结:");
|
||||
console.log("=====================================");
|
||||
console.log("旧 YTAssetVault Implementation:");
|
||||
console.log(" ", deployments.upgradeHistory[deployments.upgradeHistory.length - 1].oldImplementation);
|
||||
console.log("");
|
||||
console.log("新 YTAssetVault Implementation:");
|
||||
console.log(" ", newVaultImplAddress);
|
||||
console.log("");
|
||||
console.log("Factory Proxy (不变):");
|
||||
console.log(" ", deployments.contracts.YTAssetFactory.proxy);
|
||||
console.log("");
|
||||
console.log("已升级的 Vaults:");
|
||||
if (existingVaults.length > 0) {
|
||||
existingVaults.forEach((v: any, idx: number) => {
|
||||
if (v.lastUpgraded) {
|
||||
console.log(` ✅ [${idx}] ${v.symbol}: ${v.address}`);
|
||||
} else {
|
||||
console.log(` ⏸️ [${idx}] ${v.symbol}: ${v.address} (未升级)`);
|
||||
}
|
||||
});
|
||||
} else {
|
||||
console.log(" (无)");
|
||||
}
|
||||
console.log("=====================================\n");
|
||||
|
||||
console.log("✅ 升级完成!");
|
||||
console.log("");
|
||||
console.log("📌 重要提示:");
|
||||
console.log(" 1. Factory 已更新为新实现,新创建的 vault 将使用新版本");
|
||||
console.log(" 2. 已升级的 vault 代理地址不变,状态数据已保留");
|
||||
console.log(" 3. 新增功能:");
|
||||
console.log(" • 两阶段提现机制(排队领取)");
|
||||
console.log(" • WithdrawRequest 请求记录");
|
||||
console.log(" • processBatchWithdrawals 批量处理");
|
||||
console.log(" • 多个查询函数(请求详情、队列进度等)");
|
||||
console.log(" 4. 如有未升级的 vault,可通过以下方式升级:");
|
||||
console.log(" factory.upgradeVault(vaultAddress, newImplementation)");
|
||||
console.log("");
|
||||
console.log("📝 下一步:");
|
||||
console.log(" 1. 在测试环境验证新功能");
|
||||
console.log(" 2. 测试 withdrawYT 的排队机制");
|
||||
console.log(" 3. 测试 processBatchWithdrawals 的批量处理");
|
||||
console.log(" 4. 确认所有查询函数工作正常");
|
||||
console.log(" 5. 主网升级前务必充分测试\n");
|
||||
}
|
||||
|
||||
main()
|
||||
.then(() => process.exit(0))
|
||||
.catch((error) => {
|
||||
console.error(error);
|
||||
process.exit(1);
|
||||
});
|
||||
|
||||
182
scripts/upgrade/verifyVaultUpgrade.ts
Normal file
182
scripts/upgrade/verifyVaultUpgrade.ts
Normal file
@@ -0,0 +1,182 @@
|
||||
import { ethers, upgrades } from "hardhat";
|
||||
import * as fs from "fs";
|
||||
import * as path from "path";
|
||||
|
||||
/**
|
||||
* 验证 YTAssetVault 升级结果
|
||||
*
|
||||
* 功能:
|
||||
* 1. 检查 Factory 的实现地址是否已更新
|
||||
* 2. 验证现有 Vault 的实现地址
|
||||
* 3. 测试新功能是否可用
|
||||
*/
|
||||
async function main() {
|
||||
console.log("\n==========================================");
|
||||
console.log("🔍 验证 YTAssetVault 升级结果");
|
||||
console.log("==========================================\n");
|
||||
|
||||
// ========== 读取部署信息 ==========
|
||||
const deploymentsPath = path.join(__dirname, "../../deployments-vault-system.json");
|
||||
if (!fs.existsSync(deploymentsPath)) {
|
||||
throw new Error("未找到部署信息文件");
|
||||
}
|
||||
|
||||
const deployments = JSON.parse(fs.readFileSync(deploymentsPath, "utf-8"));
|
||||
const factory = await ethers.getContractAt(
|
||||
"YTAssetFactory",
|
||||
deployments.contracts.YTAssetFactory.proxy
|
||||
);
|
||||
|
||||
// ========== 验证 Factory ==========
|
||||
console.log("📋 验证 Factory 配置");
|
||||
console.log("=====================================");
|
||||
|
||||
const currentImplInFactory = await factory.vaultImplementation();
|
||||
const expectedImpl = deployments.contracts.YTAssetVault.implementation;
|
||||
|
||||
console.log("Factory Proxy: ", deployments.contracts.YTAssetFactory.proxy);
|
||||
console.log("当前 vaultImplementation:", currentImplInFactory);
|
||||
console.log("配置文件中的实现: ", expectedImpl);
|
||||
|
||||
if (currentImplInFactory.toLowerCase() === expectedImpl.toLowerCase()) {
|
||||
console.log("✅ Factory 配置正确!\n");
|
||||
} else {
|
||||
console.log("❌ Factory 配置不匹配!\n");
|
||||
}
|
||||
|
||||
// ========== 验证已部署的 Vaults ==========
|
||||
const vaults = deployments.vaults || [];
|
||||
|
||||
if (vaults.length === 0) {
|
||||
console.log("ℹ️ 没有已部署的 Vault\n");
|
||||
return;
|
||||
}
|
||||
|
||||
console.log("📋 验证已部署的 Vaults");
|
||||
console.log("=====================================");
|
||||
console.log(`发现 ${vaults.length} 个 Vault\n`);
|
||||
|
||||
const results: any[] = [];
|
||||
|
||||
for (let i = 0; i < vaults.length; i++) {
|
||||
const vaultInfo = vaults[i];
|
||||
console.log(`[${i + 1}/${vaults.length}] 检查 ${vaultInfo.symbol} (${vaultInfo.address})`);
|
||||
|
||||
try {
|
||||
// 获取实现地址
|
||||
const implAddress = await upgrades.erc1967.getImplementationAddress(vaultInfo.address);
|
||||
const isUpgraded = implAddress.toLowerCase() === expectedImpl.toLowerCase();
|
||||
|
||||
console.log(` 实现地址: ${implAddress}`);
|
||||
console.log(` 状态: ${isUpgraded ? '✅ 已升级' : '⏸️ 未升级'}`);
|
||||
|
||||
// 如果已升级,测试新功能
|
||||
if (isUpgraded) {
|
||||
const vault = await ethers.getContractAt("YTAssetVault", vaultInfo.address);
|
||||
|
||||
try {
|
||||
// 测试新增的状态变量
|
||||
const pendingCount = await vault.pendingRequestsCount();
|
||||
const requestIdCounter = await vault.requestIdCounter();
|
||||
const processedUpToIndex = await vault.processedUpToIndex();
|
||||
|
||||
console.log(` 新功能验证:`);
|
||||
console.log(` - pendingRequestsCount: ${pendingCount}`);
|
||||
console.log(` - requestIdCounter: ${requestIdCounter}`);
|
||||
console.log(` - processedUpToIndex: ${processedUpToIndex}`);
|
||||
|
||||
// 测试新增的查询函数
|
||||
const queueProgress = await vault.getQueueProgress();
|
||||
console.log(` - 队列进度: ${queueProgress[0]}/${queueProgress[1]} (待处理: ${queueProgress[2]})`);
|
||||
|
||||
console.log(` ✅ 新功能工作正常`);
|
||||
|
||||
results.push({
|
||||
index: i,
|
||||
symbol: vaultInfo.symbol,
|
||||
address: vaultInfo.address,
|
||||
upgraded: true,
|
||||
functional: true
|
||||
});
|
||||
} catch (error: any) {
|
||||
console.log(` ⚠️ 新功能测试失败: ${error.message}`);
|
||||
results.push({
|
||||
index: i,
|
||||
symbol: vaultInfo.symbol,
|
||||
address: vaultInfo.address,
|
||||
upgraded: true,
|
||||
functional: false,
|
||||
error: error.message
|
||||
});
|
||||
}
|
||||
} else {
|
||||
results.push({
|
||||
index: i,
|
||||
symbol: vaultInfo.symbol,
|
||||
address: vaultInfo.address,
|
||||
upgraded: false,
|
||||
functional: false
|
||||
});
|
||||
}
|
||||
} catch (error: any) {
|
||||
console.log(` ❌ 检查失败: ${error.message}`);
|
||||
results.push({
|
||||
index: i,
|
||||
symbol: vaultInfo.symbol,
|
||||
address: vaultInfo.address,
|
||||
upgraded: false,
|
||||
functional: false,
|
||||
error: error.message
|
||||
});
|
||||
}
|
||||
console.log("");
|
||||
}
|
||||
|
||||
// ========== 验证总结 ==========
|
||||
console.log("📊 验证总结");
|
||||
console.log("=====================================");
|
||||
|
||||
const upgraded = results.filter(r => r.upgraded);
|
||||
const functional = results.filter(r => r.functional);
|
||||
const needsUpgrade = results.filter(r => !r.upgraded);
|
||||
|
||||
console.log(`总 Vaults 数量: ${results.length}`);
|
||||
console.log(`已升级: ${upgraded.length} ✅`);
|
||||
console.log(`功能正常: ${functional.length} ✅`);
|
||||
console.log(`待升级: ${needsUpgrade.length} ${needsUpgrade.length > 0 ? '⏸️' : ''}`);
|
||||
console.log("");
|
||||
|
||||
if (needsUpgrade.length > 0) {
|
||||
console.log("⏸️ 待升级的 Vaults:");
|
||||
needsUpgrade.forEach(v => {
|
||||
console.log(` [${v.index}] ${v.symbol}: ${v.address}`);
|
||||
});
|
||||
console.log("");
|
||||
console.log("💡 升级命令:");
|
||||
console.log(` factory.upgradeVault("vaultAddress", "${expectedImpl}")`);
|
||||
console.log("");
|
||||
}
|
||||
|
||||
// ========== 升级历史 ==========
|
||||
if (deployments.upgradeHistory && deployments.upgradeHistory.length > 0) {
|
||||
console.log("📜 升级历史");
|
||||
console.log("=====================================");
|
||||
deployments.upgradeHistory.forEach((h: any, idx: number) => {
|
||||
console.log(`[${idx + 1}] ${h.timestamp}`);
|
||||
console.log(` 升级者: ${h.upgrader}`);
|
||||
console.log(` 旧实现: ${h.oldImplementation}`);
|
||||
console.log(` 新实现: ${h.newImplementation}`);
|
||||
});
|
||||
console.log("");
|
||||
}
|
||||
|
||||
console.log("✅ 验证完成!\n");
|
||||
}
|
||||
|
||||
main()
|
||||
.then(() => process.exit(0))
|
||||
.catch((error) => {
|
||||
console.error(error);
|
||||
process.exit(1);
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user